@cosyte/x12 0.0.9 → 0.0.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +336 -4
- package/dist/index.cjs +360 -171
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +241 -7
- package/dist/index.d.ts +241 -7
- package/dist/index.mjs +357 -172
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -140,7 +140,10 @@ var WARNING_CODES = {
|
|
|
140
140
|
X12_837_UNKNOWN_VARIANT: "X12_837_UNKNOWN_VARIANT",
|
|
141
141
|
X12_UNKNOWN_CLAIM_STATUS_CATEGORY: "X12_UNKNOWN_CLAIM_STATUS_CATEGORY",
|
|
142
142
|
X12_UNKNOWN_CLAIM_STATUS: "X12_UNKNOWN_CLAIM_STATUS",
|
|
143
|
-
X12_834_UNKNOWN_MAINTENANCE_TYPE: "X12_834_UNKNOWN_MAINTENANCE_TYPE"
|
|
143
|
+
X12_834_UNKNOWN_MAINTENANCE_TYPE: "X12_834_UNKNOWN_MAINTENANCE_TYPE",
|
|
144
|
+
X12_UNPARSEABLE_DECIMAL: "X12_UNPARSEABLE_DECIMAL",
|
|
145
|
+
X12_837_SERVICE_LINE_NOT_DECODED: "X12_837_SERVICE_LINE_NOT_DECODED",
|
|
146
|
+
X12_837_SERVICE_LINE_DROPPED: "X12_837_SERVICE_LINE_DROPPED"
|
|
144
147
|
};
|
|
145
148
|
var CONTROL_NUMBER_PAIRS = {
|
|
146
149
|
/** ISA-13 against IEA-02. */
|
|
@@ -213,7 +216,10 @@ var WARNING_MESSAGES = {
|
|
|
213
216
|
X12_837_UNKNOWN_VARIANT: `837 variant could not be resolved: ST-03's implementation convention reference is not one of "005010X222A2" / "005010X223A3" / "005010X224A2", and no SVx service-line segment was present to fall back on. The verbatim reference is preserved on the model.`,
|
|
214
217
|
X12_UNKNOWN_CLAIM_STATUS_CATEGORY: "Unknown claim status category (CSCC): the STC composite's first component is outside the bundled snapshot. The verbatim code is preserved on the status; only its description is unavailable.",
|
|
215
218
|
X12_UNKNOWN_CLAIM_STATUS: "Unknown claim status code (CSC): the STC composite's second component is outside the bundled snapshot. The verbatim code is preserved on the status; only its description is unavailable.",
|
|
216
|
-
X12_834_UNKNOWN_MAINTENANCE_TYPE: "Unknown 834 maintenance type: the INS-03/HD-01 code is outside the bundled snapshot. The verbatim code is preserved on the enrollment and the action is NEVER inferred."
|
|
219
|
+
X12_834_UNKNOWN_MAINTENANCE_TYPE: "Unknown 834 maintenance type: the INS-03/HD-01 code is outside the bundled snapshot. The verbatim code is preserved on the enrollment and the action is NEVER inferred.",
|
|
220
|
+
X12_UNPARSEABLE_DECIMAL: "Unparseable decimal: the element at `position.elementIndex` held bytes this library could not decode as a decimal, so NO value was decoded from it. Whatever occupies that slot on the model, including 0 and undefined, is a stand-in and is NOT a value the sender supplied. The verbatim bytes are preserved on the segment; read them there before acting on the amount, quantity or percent.",
|
|
221
|
+
X12_837_SERVICE_LINE_NOT_DECODED: "837 service line with no decoded service segment: the Loop 2400 line opened at `position.segmentIndex` is followed by no SV1 / SV2 / SV3 matching the variant this submission resolved to, so NOTHING carried by the service segment was read. The line's `charge` and `units` hold 0 as a stand-in and are NOT values the sender supplied; its procedure code, modifiers, unit of measure and place of service are equally undecoded. Two common causes: the line carries no SVx at all, or it carries one for a different 837 variant than ST-03 (or the caller's `type` option) named. Which side is wrong is NOT decided here, because a caller-supplied `type` can disagree with a perfectly conformant document. The verbatim segments are preserved on the transaction set; read them there before acting on the charge or the quantity.",
|
|
222
|
+
X12_837_SERVICE_LINE_DROPPED: "837 service line dropped from the typed model: the LX at `position.segmentIndex` opened no Loop 2400, so no line appears on any claim's `serviceLines` for it and the SV1 / SV2 / SV3 that followed - its charge, units, procedure code and modifiers - was read into nothing. Compare `X12_837_SERVICE_LINE_NOT_DECODED`, where the line IS on the model and only its service segment went unread. Two causes: no Loop 2300 (CLM) is open at this LX, so there is no claim to attach a line to; or the submission's variant is not one of P / I / D, so no variant-specific line shape could be built. Read `submission.variant` and `submission.claims` to tell them apart; do NOT expect `X12_837_UNKNOWN_VARIANT` alongside this code, because a caller-supplied `type` outside P / I / D reaches the second cause without it. Nothing is fabricated to stand in for the missing line and no claim is synthesized. What becomes of a DTP / AMT / NTE / REF that follows the dropped LX depends on the route and this message does not say; see KNOWN-LIMITATIONS.md. The verbatim segments are preserved on the transaction set; read them there before concluding the claim had no service lines."
|
|
217
223
|
};
|
|
218
224
|
var ALL_WARNING_MESSAGES = new Set(
|
|
219
225
|
Object.values(WARNING_MESSAGES)
|
|
@@ -374,6 +380,20 @@ function unknown837Variant(position) {
|
|
|
374
380
|
position
|
|
375
381
|
};
|
|
376
382
|
}
|
|
383
|
+
function serviceLineNotDecoded(position) {
|
|
384
|
+
return {
|
|
385
|
+
code: WARNING_CODES.X12_837_SERVICE_LINE_NOT_DECODED,
|
|
386
|
+
message: WARNING_MESSAGES.X12_837_SERVICE_LINE_NOT_DECODED,
|
|
387
|
+
position
|
|
388
|
+
};
|
|
389
|
+
}
|
|
390
|
+
function serviceLineDropped(position) {
|
|
391
|
+
return {
|
|
392
|
+
code: WARNING_CODES.X12_837_SERVICE_LINE_DROPPED,
|
|
393
|
+
message: WARNING_MESSAGES.X12_837_SERVICE_LINE_DROPPED,
|
|
394
|
+
position
|
|
395
|
+
};
|
|
396
|
+
}
|
|
377
397
|
function unknownClaimStatusCategory(position) {
|
|
378
398
|
return {
|
|
379
399
|
code: WARNING_CODES.X12_UNKNOWN_CLAIM_STATUS_CATEGORY,
|
|
@@ -395,6 +415,13 @@ function unknownMaintenanceType(position) {
|
|
|
395
415
|
position
|
|
396
416
|
};
|
|
397
417
|
}
|
|
418
|
+
function unparseableDecimal(position) {
|
|
419
|
+
return {
|
|
420
|
+
code: WARNING_CODES.X12_UNPARSEABLE_DECIMAL,
|
|
421
|
+
message: WARNING_MESSAGES.X12_UNPARSEABLE_DECIMAL,
|
|
422
|
+
position
|
|
423
|
+
};
|
|
424
|
+
}
|
|
398
425
|
|
|
399
426
|
// src/parser/release.ts
|
|
400
427
|
var RELEASE_CHAR = "?";
|
|
@@ -908,13 +935,26 @@ function componentOptional(seg, n, p, delimiters) {
|
|
|
908
935
|
const v = getSegmentValue(seg, `${String(n).padStart(2, "0")}-${String(p)}`, delimiters);
|
|
909
936
|
return v === void 0 || v === "" ? void 0 : v;
|
|
910
937
|
}
|
|
911
|
-
function
|
|
938
|
+
function readElementDecimal(seg, n, delimiters) {
|
|
912
939
|
const raw = elementOptional(seg, n, delimiters);
|
|
913
|
-
if (raw === void 0) return void 0;
|
|
914
|
-
|
|
940
|
+
if (raw === void 0) return { value: void 0, status: "absent" };
|
|
941
|
+
const value = X12Decimal.fromString(raw);
|
|
942
|
+
if (value === void 0) return { value: void 0, status: "unparseable" };
|
|
943
|
+
return { value, status: "decoded" };
|
|
915
944
|
}
|
|
916
|
-
function
|
|
917
|
-
|
|
945
|
+
function elementDecimal(seg, n, delimiters, sink) {
|
|
946
|
+
const read = readElementDecimal(seg, n, delimiters);
|
|
947
|
+
if (read.status === "unparseable" && sink !== void 0) {
|
|
948
|
+
sink.warnings.push(unparseableDecimal({ ...sink.position, elementIndex: n }));
|
|
949
|
+
}
|
|
950
|
+
return read.value;
|
|
951
|
+
}
|
|
952
|
+
function elementDecimalOrZero(seg, n, delimiters, sink) {
|
|
953
|
+
const read = readElementDecimal(seg, n, delimiters);
|
|
954
|
+
if (read.status === "unparseable" && sink !== void 0) {
|
|
955
|
+
sink.warnings.push(unparseableDecimal({ ...sink.position, elementIndex: n }));
|
|
956
|
+
}
|
|
957
|
+
return read.value ?? X12Decimal.ZERO;
|
|
918
958
|
}
|
|
919
959
|
function collectElementValues(seg, start, end, delimiters) {
|
|
920
960
|
const out = [];
|
|
@@ -1420,6 +1460,7 @@ function defineLoopSpec(input) {
|
|
|
1420
1460
|
// src/code-lists/meta.ts
|
|
1421
1461
|
function makeLookup(snapshot) {
|
|
1422
1462
|
return (code) => {
|
|
1463
|
+
if (!Object.hasOwn(snapshot.codes, code)) return void 0;
|
|
1423
1464
|
const description = snapshot.codes[code];
|
|
1424
1465
|
if (description === void 0) return void 0;
|
|
1425
1466
|
return Object.freeze({ code, description });
|
|
@@ -1668,7 +1709,7 @@ var CLAIM_ADJUSTMENT_GROUP_CODES = {
|
|
|
1668
1709
|
PI: "PI"
|
|
1669
1710
|
};
|
|
1670
1711
|
function isClaimAdjustmentGroupCode(value) {
|
|
1671
|
-
return value
|
|
1712
|
+
return Object.hasOwn(CLAIM_ADJUSTMENT_GROUP_CODES, value);
|
|
1672
1713
|
}
|
|
1673
1714
|
|
|
1674
1715
|
// src/code-lists/rarc.ts
|
|
@@ -1808,6 +1849,7 @@ var HI_QUALIFIERS = {
|
|
|
1808
1849
|
}
|
|
1809
1850
|
};
|
|
1810
1851
|
function resolveHiQualifier(qualifier) {
|
|
1852
|
+
if (!Object.hasOwn(HI_QUALIFIERS, qualifier)) return void 0;
|
|
1811
1853
|
return HI_QUALIFIERS[qualifier];
|
|
1812
1854
|
}
|
|
1813
1855
|
function isDiagnosisQualifier(qualifier) {
|
|
@@ -1917,9 +1959,10 @@ function get835(delimiters, tx) {
|
|
|
1917
1959
|
const seg = body[i];
|
|
1918
1960
|
if (seg === void 0) continue;
|
|
1919
1961
|
const position = { segmentIndex: i + 1, transactionIndex: 0 };
|
|
1962
|
+
const sink = { warnings, position };
|
|
1920
1963
|
switch (seg.id) {
|
|
1921
1964
|
case "BPR": {
|
|
1922
|
-
payment = decodeBpr(seg, delimiters);
|
|
1965
|
+
payment = decodeBpr(seg, delimiters, sink);
|
|
1923
1966
|
bprSegmentIndex = position.segmentIndex;
|
|
1924
1967
|
break;
|
|
1925
1968
|
}
|
|
@@ -1994,7 +2037,7 @@ function get835(delimiters, tx) {
|
|
|
1994
2037
|
case "CLP": {
|
|
1995
2038
|
flushClaim();
|
|
1996
2039
|
lastParty = void 0;
|
|
1997
|
-
currentClaim = openClaim(seg, delimiters, position.segmentIndex);
|
|
2040
|
+
currentClaim = openClaim(seg, delimiters, position.segmentIndex, sink);
|
|
1998
2041
|
break;
|
|
1999
2042
|
}
|
|
2000
2043
|
case "CAS": {
|
|
@@ -2046,7 +2089,7 @@ function get835(delimiters, tx) {
|
|
|
2046
2089
|
break;
|
|
2047
2090
|
}
|
|
2048
2091
|
case "AMT": {
|
|
2049
|
-
const amount = decodeAmt(seg, delimiters);
|
|
2092
|
+
const amount = decodeAmt(seg, delimiters, sink);
|
|
2050
2093
|
if (amount === void 0) break;
|
|
2051
2094
|
if (currentServiceLine !== void 0) currentServiceLine.amounts.push(amount);
|
|
2052
2095
|
else if (currentClaim !== void 0) currentClaim.amounts.push(amount);
|
|
@@ -2065,12 +2108,12 @@ function get835(delimiters, tx) {
|
|
|
2065
2108
|
}
|
|
2066
2109
|
case "SVC": {
|
|
2067
2110
|
flushServiceLine();
|
|
2068
|
-
currentServiceLine = openServiceLine(seg, delimiters);
|
|
2111
|
+
currentServiceLine = openServiceLine(seg, delimiters, sink);
|
|
2069
2112
|
break;
|
|
2070
2113
|
}
|
|
2071
2114
|
case "PLB": {
|
|
2072
2115
|
flushClaim();
|
|
2073
|
-
for (const p of decodePlb(seg, delimiters)) providerAdjustments.push(p);
|
|
2116
|
+
for (const p of decodePlb(seg, delimiters, sink)) providerAdjustments.push(p);
|
|
2074
2117
|
break;
|
|
2075
2118
|
}
|
|
2076
2119
|
}
|
|
@@ -2101,10 +2144,10 @@ function get835(delimiters, tx) {
|
|
|
2101
2144
|
warnings: Object.freeze(warnings.slice())
|
|
2102
2145
|
});
|
|
2103
2146
|
}
|
|
2104
|
-
function decodeBpr(seg, delimiters) {
|
|
2147
|
+
function decodeBpr(seg, delimiters, sink) {
|
|
2105
2148
|
return Object.freeze({
|
|
2106
2149
|
transactionHandlingCode: elementValue(seg, 1, delimiters),
|
|
2107
|
-
totalActualPayment: elementDecimalOrZero(seg, 2, delimiters),
|
|
2150
|
+
totalActualPayment: elementDecimalOrZero(seg, 2, delimiters, sink),
|
|
2108
2151
|
creditDebitFlag: elementValue(seg, 3, delimiters),
|
|
2109
2152
|
method: elementValue(seg, 4, delimiters),
|
|
2110
2153
|
paymentFormatCode: elementOptional(seg, 5, delimiters),
|
|
@@ -2163,8 +2206,8 @@ function decodePer(seg, delimiters) {
|
|
|
2163
2206
|
communications: Object.freeze(comms)
|
|
2164
2207
|
});
|
|
2165
2208
|
}
|
|
2166
|
-
function decodeAmt(seg, delimiters) {
|
|
2167
|
-
const amount = elementDecimal(seg, 2, delimiters);
|
|
2209
|
+
function decodeAmt(seg, delimiters, sink) {
|
|
2210
|
+
const amount = elementDecimal(seg, 2, delimiters, sink);
|
|
2168
2211
|
if (amount === void 0) return void 0;
|
|
2169
2212
|
return Object.freeze({
|
|
2170
2213
|
qualifier: elementValue(seg, 1, delimiters),
|
|
@@ -2200,13 +2243,14 @@ function collectMoaRemarks(seg, delimiters) {
|
|
|
2200
2243
|
return out;
|
|
2201
2244
|
}
|
|
2202
2245
|
function decodeCasAdjustments(seg, delimiters, warnings, position) {
|
|
2246
|
+
const sink = { warnings, position };
|
|
2203
2247
|
const groupCode = elementValue(seg, 1, delimiters);
|
|
2204
2248
|
const out = [];
|
|
2205
2249
|
for (let triple = 0; triple < 6; triple += 1) {
|
|
2206
2250
|
const base = 2 + triple * 3;
|
|
2207
2251
|
const reasonCode = elementOptional(seg, base, delimiters);
|
|
2208
|
-
const amount = elementDecimal(seg, base + 1, delimiters);
|
|
2209
|
-
const quantity = elementDecimal(seg, base + 2, delimiters);
|
|
2252
|
+
const amount = elementDecimal(seg, base + 1, delimiters, sink);
|
|
2253
|
+
const quantity = elementDecimal(seg, base + 2, delimiters, sink);
|
|
2210
2254
|
if (reasonCode === void 0 && amount === void 0) continue;
|
|
2211
2255
|
const code = reasonCode ?? "";
|
|
2212
2256
|
const entry = code === "" ? void 0 : lookupCarc(code);
|
|
@@ -2250,7 +2294,7 @@ function decodeNm1(seg, delimiters) {
|
|
|
2250
2294
|
})
|
|
2251
2295
|
};
|
|
2252
2296
|
}
|
|
2253
|
-
function openClaim(seg, delimiters, clpSegmentIndex) {
|
|
2297
|
+
function openClaim(seg, delimiters, clpSegmentIndex, sink) {
|
|
2254
2298
|
const claimStatusCode = elementValue(seg, 2, delimiters);
|
|
2255
2299
|
const claimStatusDescription = lookupClpStatus(claimStatusCode)?.description;
|
|
2256
2300
|
const facilityTypeCode = componentOptional(seg, 8, 1, delimiters) ?? elementOptional(seg, 8, delimiters);
|
|
@@ -2260,9 +2304,9 @@ function openClaim(seg, delimiters, clpSegmentIndex) {
|
|
|
2260
2304
|
patientControlNumber: elementValue(seg, 1, delimiters),
|
|
2261
2305
|
claimStatusCode,
|
|
2262
2306
|
claimStatusDescription,
|
|
2263
|
-
totalChargeAmount: elementDecimalOrZero(seg, 3, delimiters),
|
|
2264
|
-
totalPaymentAmount: elementDecimalOrZero(seg, 4, delimiters),
|
|
2265
|
-
patientResponsibilityAmount: elementDecimalOrZero(seg, 5, delimiters),
|
|
2307
|
+
totalChargeAmount: elementDecimalOrZero(seg, 3, delimiters, sink),
|
|
2308
|
+
totalPaymentAmount: elementDecimalOrZero(seg, 4, delimiters, sink),
|
|
2309
|
+
patientResponsibilityAmount: elementDecimalOrZero(seg, 5, delimiters, sink),
|
|
2266
2310
|
claimFilingIndicatorCode: elementOptional(seg, 6, delimiters),
|
|
2267
2311
|
payerClaimControlNumber: elementOptional(seg, 7, delimiters),
|
|
2268
2312
|
facilityTypeCode,
|
|
@@ -2281,7 +2325,7 @@ function openClaim(seg, delimiters, clpSegmentIndex) {
|
|
|
2281
2325
|
serviceLines: []
|
|
2282
2326
|
};
|
|
2283
2327
|
}
|
|
2284
|
-
function openServiceLine(seg, delimiters) {
|
|
2328
|
+
function openServiceLine(seg, delimiters, sink) {
|
|
2285
2329
|
const productServiceIdQualifier = componentOptional(seg, 1, 1, delimiters) ?? "";
|
|
2286
2330
|
const productServiceId = componentOptional(seg, 1, 2, delimiters) ?? "";
|
|
2287
2331
|
const modifiers = [];
|
|
@@ -2289,18 +2333,20 @@ function openServiceLine(seg, delimiters) {
|
|
|
2289
2333
|
const m = componentOptional(seg, 1, comp, delimiters);
|
|
2290
2334
|
if (m !== void 0) modifiers.push(m);
|
|
2291
2335
|
}
|
|
2292
|
-
const revenueCode = elementOptional(seg,
|
|
2293
|
-
const paidUnitsOfService = elementDecimal(seg,
|
|
2336
|
+
const revenueCode = elementOptional(seg, 4, delimiters);
|
|
2337
|
+
const paidUnitsOfService = elementDecimal(seg, 5, delimiters, sink);
|
|
2338
|
+
const originalUnitsOfService = elementDecimal(seg, 7, delimiters, sink);
|
|
2294
2339
|
const originalServiceIdQualifier = componentOptional(seg, 6, 1, delimiters);
|
|
2295
2340
|
const originalServiceId = componentOptional(seg, 6, 2, delimiters);
|
|
2296
2341
|
return {
|
|
2297
2342
|
productServiceIdQualifier,
|
|
2298
2343
|
productServiceId,
|
|
2299
2344
|
modifiers,
|
|
2300
|
-
chargeAmount: elementDecimalOrZero(seg, 2, delimiters),
|
|
2301
|
-
paymentAmount: elementDecimalOrZero(seg, 3, delimiters),
|
|
2345
|
+
chargeAmount: elementDecimalOrZero(seg, 2, delimiters, sink),
|
|
2346
|
+
paymentAmount: elementDecimalOrZero(seg, 3, delimiters, sink),
|
|
2302
2347
|
revenueCode,
|
|
2303
2348
|
paidUnitsOfService,
|
|
2349
|
+
originalUnitsOfService,
|
|
2304
2350
|
originalServiceId,
|
|
2305
2351
|
originalServiceIdQualifier,
|
|
2306
2352
|
serviceDateStart: void 0,
|
|
@@ -2326,13 +2372,13 @@ function attachServiceLineDtm(line, seg, delimiters) {
|
|
|
2326
2372
|
if (qualifier === "472" || qualifier === "150") line.serviceDateStart = date;
|
|
2327
2373
|
if (qualifier === "472" || qualifier === "151") line.serviceDateEnd = date;
|
|
2328
2374
|
}
|
|
2329
|
-
function decodePlb(seg, delimiters) {
|
|
2375
|
+
function decodePlb(seg, delimiters, sink) {
|
|
2330
2376
|
const providerId = elementValue(seg, 1, delimiters);
|
|
2331
2377
|
const fiscalPeriodDate = elementValue(seg, 2, delimiters);
|
|
2332
2378
|
const out = [];
|
|
2333
2379
|
for (let pair = 0; pair < 6; pair += 1) {
|
|
2334
2380
|
const composite = 3 + pair * 2;
|
|
2335
|
-
const amount = elementDecimal(seg, composite + 1, delimiters);
|
|
2381
|
+
const amount = elementDecimal(seg, composite + 1, delimiters, sink);
|
|
2336
2382
|
const reasonCode = componentOptional(seg, composite, 1, delimiters);
|
|
2337
2383
|
const subCode = componentOptional(seg, composite, 2, delimiters);
|
|
2338
2384
|
if (amount === void 0 && reasonCode === void 0) continue;
|
|
@@ -2396,6 +2442,7 @@ function freezeServiceLine(acc) {
|
|
|
2396
2442
|
paymentAmount: acc.paymentAmount,
|
|
2397
2443
|
revenueCode: acc.revenueCode,
|
|
2398
2444
|
paidUnitsOfService: acc.paidUnitsOfService,
|
|
2445
|
+
originalUnitsOfService: acc.originalUnitsOfService,
|
|
2399
2446
|
originalServiceId: acc.originalServiceId,
|
|
2400
2447
|
originalServiceIdQualifier: acc.originalServiceIdQualifier,
|
|
2401
2448
|
serviceDateStart: acc.serviceDateStart,
|
|
@@ -2511,6 +2558,49 @@ function isRealArray(value) {
|
|
|
2511
2558
|
return Array.isArray(value);
|
|
2512
2559
|
}
|
|
2513
2560
|
|
|
2561
|
+
// src/builder/caller-decimal.ts
|
|
2562
|
+
function describeCallerDecimal(value) {
|
|
2563
|
+
if (value === null) return "null";
|
|
2564
|
+
if (value === void 0) return "undefined";
|
|
2565
|
+
const type = typeof value;
|
|
2566
|
+
if (type === "object") return Array.isArray(value) ? "an array" : "an object";
|
|
2567
|
+
if (type === "function") return "a function";
|
|
2568
|
+
return `a ${type} (${renderCallerValue(value)})`;
|
|
2569
|
+
}
|
|
2570
|
+
function requireCallerDecimal(value, at, refuse) {
|
|
2571
|
+
if (value instanceof X12Decimal) return value;
|
|
2572
|
+
refuse(
|
|
2573
|
+
`${at}: every numeric element value must be an X12Decimal, but received ${describeCallerDecimal(value)}. Values are never coerced - a JavaScript number has no X12 lexical form (0.1 + 0.2 renders as "0.30000000000000004", 1e21 as "1e+21", NaN as "NaN"), and rounding one here would guess a scale the caller never stated. Build it with X12Decimal.fromString() at the call site.`
|
|
2574
|
+
);
|
|
2575
|
+
}
|
|
2576
|
+
|
|
2577
|
+
// src/builder/caller-segment.ts
|
|
2578
|
+
function describeSegmentValue(value) {
|
|
2579
|
+
if (value === null) return "null";
|
|
2580
|
+
if (value === void 0) return "undefined";
|
|
2581
|
+
const type = typeof value;
|
|
2582
|
+
if (type === "object") return Array.isArray(value) ? "an array" : "an object";
|
|
2583
|
+
if (type === "function") return "a function";
|
|
2584
|
+
return `a ${type} (${renderCallerValue(value)})`;
|
|
2585
|
+
}
|
|
2586
|
+
function locateSlot(parts, index) {
|
|
2587
|
+
const id = parts[0];
|
|
2588
|
+
const position = String(index).padStart(2, "0");
|
|
2589
|
+
if (typeof id !== "string" || id.length === 0) return `element ${String(index)}`;
|
|
2590
|
+
return `${renderCallerValue(id)}-${position}`;
|
|
2591
|
+
}
|
|
2592
|
+
function requireCallerSegment(parts, at, refuse) {
|
|
2593
|
+
let index = 0;
|
|
2594
|
+
for (const part of parts) {
|
|
2595
|
+
if (typeof part !== "string") {
|
|
2596
|
+
refuse(
|
|
2597
|
+
`${at}: ${locateSlot(parts, index)} must be a string, but received ${describeSegmentValue(part)}. Values are never coerced - a JavaScript number cannot carry a leading-zero identifier, so converting here could emit a different value than the caller sent. Convert at the call site.`
|
|
2598
|
+
);
|
|
2599
|
+
}
|
|
2600
|
+
index += 1;
|
|
2601
|
+
}
|
|
2602
|
+
}
|
|
2603
|
+
|
|
2514
2604
|
// src/builder/caller-string.ts
|
|
2515
2605
|
function describeCallerValue(value) {
|
|
2516
2606
|
if (value === null) return "null";
|
|
@@ -2534,6 +2624,9 @@ function makeCallerEscaper(delimiters, at, refuse) {
|
|
|
2534
2624
|
function refuseSpec(message) {
|
|
2535
2625
|
throw new Remit835BuildError(REMIT_835_BUILD_ERROR_CODES.X12_835_BUILD_INVALID_SPEC, message);
|
|
2536
2626
|
}
|
|
2627
|
+
function escDec(value, esc) {
|
|
2628
|
+
return esc(requireCallerDecimal(value, "build835", refuseSpec).toString());
|
|
2629
|
+
}
|
|
2537
2630
|
var X221A1_VERSION_RELEASE = "005010X221A1";
|
|
2538
2631
|
var X12_835_FUNCTIONAL_ID = "HP";
|
|
2539
2632
|
var X12_AGENCY_CODE = "X";
|
|
@@ -2557,6 +2650,7 @@ function build835(spec) {
|
|
|
2557
2650
|
};
|
|
2558
2651
|
const esc = makeCallerEscaper(delimiters, "build835", refuseSpec);
|
|
2559
2652
|
const seg = (parts) => {
|
|
2653
|
+
requireCallerSegment(parts, "build835", refuseSpec);
|
|
2560
2654
|
let end = parts.length;
|
|
2561
2655
|
while (end > 1 && parts[end - 1] === "") end -= 1;
|
|
2562
2656
|
return parts.slice(0, end).join(elementSeparator) + segmentTerminator;
|
|
@@ -2618,9 +2712,9 @@ function build835(spec) {
|
|
|
2618
2712
|
// GS-02
|
|
2619
2713
|
esc(applicationReceiverCode),
|
|
2620
2714
|
// GS-03
|
|
2621
|
-
groupDate,
|
|
2715
|
+
esc(groupDate),
|
|
2622
2716
|
// GS-04 - CCYYMMDD
|
|
2623
|
-
groupTime,
|
|
2717
|
+
esc(groupTime),
|
|
2624
2718
|
// GS-05 - HHMM
|
|
2625
2719
|
esc(envelope.groupControlNumber),
|
|
2626
2720
|
// GS-06
|
|
@@ -2636,7 +2730,7 @@ function build835(spec) {
|
|
|
2636
2730
|
seg([
|
|
2637
2731
|
"BPR",
|
|
2638
2732
|
esc(spec.payment.transactionHandlingCode),
|
|
2639
|
-
|
|
2733
|
+
escDec(spec.payment.totalActualPayment, esc),
|
|
2640
2734
|
esc(spec.payment.creditDebitFlag),
|
|
2641
2735
|
esc(spec.payment.method),
|
|
2642
2736
|
esc(spec.payment.paymentFormatCode ?? ""),
|
|
@@ -2771,6 +2865,7 @@ function materializeServiceLine(spec) {
|
|
|
2771
2865
|
paymentAmount: spec.paymentAmount,
|
|
2772
2866
|
revenueCode: spec.revenueCode,
|
|
2773
2867
|
paidUnitsOfService: spec.paidUnitsOfService,
|
|
2868
|
+
originalUnitsOfService: spec.originalUnitsOfService,
|
|
2774
2869
|
originalServiceId: spec.originalServiceId,
|
|
2775
2870
|
originalServiceIdQualifier: spec.originalServiceIdQualifier,
|
|
2776
2871
|
serviceDateStart: spec.serviceDateStart,
|
|
@@ -2866,9 +2961,9 @@ function emitClaim(claim, body, seg, esc, comp) {
|
|
|
2866
2961
|
"CLP",
|
|
2867
2962
|
esc(claim.patientControlNumber),
|
|
2868
2963
|
esc(claim.claimStatusCode),
|
|
2869
|
-
|
|
2870
|
-
|
|
2871
|
-
|
|
2964
|
+
escDec(claim.totalChargeAmount, esc),
|
|
2965
|
+
escDec(claim.totalPaymentAmount, esc),
|
|
2966
|
+
escDec(claim.patientResponsibilityAmount, esc),
|
|
2872
2967
|
esc(claim.claimFilingIndicatorCode ?? ""),
|
|
2873
2968
|
esc(claim.payerClaimControlNumber ?? ""),
|
|
2874
2969
|
comp([claim.facilityTypeCode ?? "", "", claim.claimFrequencyCode ?? ""])
|
|
@@ -2890,7 +2985,7 @@ function emitClaim(claim, body, seg, esc, comp) {
|
|
|
2890
2985
|
}
|
|
2891
2986
|
for (const ref of claim.references ?? []) body.push(emitRef(ref, seg, esc));
|
|
2892
2987
|
for (const amt of claim.amounts ?? []) {
|
|
2893
|
-
body.push(seg(["AMT", esc(amt.qualifier),
|
|
2988
|
+
body.push(seg(["AMT", esc(amt.qualifier), escDec(amt.amount, esc)]));
|
|
2894
2989
|
}
|
|
2895
2990
|
for (const remark of claim.remarks ?? []) {
|
|
2896
2991
|
body.push(seg(["LQ", esc(remark.system), esc(remark.code)]));
|
|
@@ -2910,20 +3005,24 @@ function emitServiceLine(line, body, seg, esc, comp) {
|
|
|
2910
3005
|
seg([
|
|
2911
3006
|
"SVC",
|
|
2912
3007
|
svc01,
|
|
2913
|
-
|
|
2914
|
-
|
|
2915
|
-
|
|
2916
|
-
// SVC-
|
|
3008
|
+
escDec(line.chargeAmount, esc),
|
|
3009
|
+
escDec(line.paymentAmount, esc),
|
|
3010
|
+
// SVC-04 is the NUBC revenue code (element 234, Product/Service ID) and
|
|
3011
|
+
// SVC-05 is the Units of Service PAID Count (element 380, Quantity).
|
|
3012
|
+
// SVC-07 is the ORIGINAL (submitted) units, a different quantity from
|
|
3013
|
+
// SVC-05 - so the two never share a field. See the SVC note in
|
|
3014
|
+
// KNOWN-LIMITATIONS.md for the sources.
|
|
2917
3015
|
esc(line.revenueCode ?? ""),
|
|
3016
|
+
line.paidUnitsOfService === void 0 ? "" : escDec(line.paidUnitsOfService, esc),
|
|
2918
3017
|
svc06,
|
|
2919
|
-
line.
|
|
3018
|
+
line.originalUnitsOfService === void 0 ? "" : escDec(line.originalUnitsOfService, esc)
|
|
2920
3019
|
])
|
|
2921
3020
|
);
|
|
2922
3021
|
emitServiceLineDtm(line, body, seg, esc);
|
|
2923
3022
|
emitCasGroup(line.adjustments, "build835: serviceLine.adjustments", body, seg, esc);
|
|
2924
3023
|
for (const ref of line.references ?? []) body.push(emitRef(ref, seg, esc));
|
|
2925
3024
|
for (const amt of line.amounts ?? []) {
|
|
2926
|
-
body.push(seg(["AMT", esc(amt.qualifier),
|
|
3025
|
+
body.push(seg(["AMT", esc(amt.qualifier), escDec(amt.amount, esc)]));
|
|
2927
3026
|
}
|
|
2928
3027
|
for (const remark of line.remarks ?? []) {
|
|
2929
3028
|
body.push(seg(["LQ", esc(remark.system), esc(remark.code)]));
|
|
@@ -2955,8 +3054,8 @@ function emitCasGroup(raw, at, body, seg, esc) {
|
|
|
2955
3054
|
if (adj === void 0 || adj.groupCode !== groupCode) break;
|
|
2956
3055
|
parts.push(
|
|
2957
3056
|
esc(adj.reasonCode),
|
|
2958
|
-
|
|
2959
|
-
adj.quantity === void 0 ? "" :
|
|
3057
|
+
escDec(adj.amount, esc),
|
|
3058
|
+
adj.quantity === void 0 ? "" : escDec(adj.quantity, esc)
|
|
2960
3059
|
);
|
|
2961
3060
|
triples += 1;
|
|
2962
3061
|
i += 1;
|
|
@@ -3014,7 +3113,7 @@ function emitProviderAdjustments(raw, at, body, seg, esc, comp) {
|
|
|
3014
3113
|
if (adj === void 0 || adj.providerId !== providerId || adj.fiscalPeriodDate !== fiscalPeriodDate) {
|
|
3015
3114
|
break;
|
|
3016
3115
|
}
|
|
3017
|
-
parts.push(comp([adj.reasonCode, adj.subCode ?? ""]),
|
|
3116
|
+
parts.push(comp([adj.reasonCode, adj.subCode ?? ""]), escDec(adj.amount, esc));
|
|
3018
3117
|
pairs += 1;
|
|
3019
3118
|
i += 1;
|
|
3020
3119
|
}
|
|
@@ -3112,13 +3211,22 @@ var REMIT_835_LOOP_1000B = defineLoopSpec({
|
|
|
3112
3211
|
]
|
|
3113
3212
|
});
|
|
3114
3213
|
|
|
3214
|
+
// src/parser/lookup.ts
|
|
3215
|
+
function wireLookup(entries) {
|
|
3216
|
+
const table = /* @__PURE__ */ Object.create(null);
|
|
3217
|
+
for (const [key, value] of Object.entries(entries)) {
|
|
3218
|
+
table[key] = value;
|
|
3219
|
+
}
|
|
3220
|
+
return Object.freeze(table);
|
|
3221
|
+
}
|
|
3222
|
+
|
|
3115
3223
|
// src/transactions/claim/get-837.ts
|
|
3116
|
-
var VARIANT_BY_ICR =
|
|
3224
|
+
var VARIANT_BY_ICR = wireLookup({
|
|
3117
3225
|
"005010X222A2": "P",
|
|
3118
3226
|
"005010X223A3": "I",
|
|
3119
3227
|
"005010X224A2": "D"
|
|
3120
3228
|
});
|
|
3121
|
-
var VARIANT_BY_SV_SEGMENT =
|
|
3229
|
+
var VARIANT_BY_SV_SEGMENT = wireLookup({
|
|
3122
3230
|
SV1: "P",
|
|
3123
3231
|
SV2: "I",
|
|
3124
3232
|
SV3: "D"
|
|
@@ -3139,7 +3247,7 @@ var NM1_QUALIFIERS = Object.freeze({
|
|
|
3139
3247
|
PAYER: "PR",
|
|
3140
3248
|
PATIENT: "QC"
|
|
3141
3249
|
});
|
|
3142
|
-
var EXPECTED_PARENT_LEVEL =
|
|
3250
|
+
var EXPECTED_PARENT_LEVEL = wireLookup({
|
|
3143
3251
|
[HL_LEVEL_CODES.INFORMATION_SOURCE]: void 0,
|
|
3144
3252
|
[HL_LEVEL_CODES.SUBSCRIBER]: HL_LEVEL_CODES.INFORMATION_SOURCE,
|
|
3145
3253
|
[HL_LEVEL_CODES.DEPENDENT]: HL_LEVEL_CODES.SUBSCRIBER
|
|
@@ -3194,6 +3302,9 @@ function get837Claims(delimiters, tx, opts) {
|
|
|
3194
3302
|
const flushServiceLine = () => {
|
|
3195
3303
|
flushAdjudication();
|
|
3196
3304
|
if (currentServiceLine !== void 0 && currentClaim !== void 0) {
|
|
3305
|
+
if (!currentServiceLine.serviceSegmentDecoded) {
|
|
3306
|
+
warnings.push(serviceLineNotDecoded(currentServiceLine.position));
|
|
3307
|
+
}
|
|
3197
3308
|
currentClaim.serviceLines.push(freezeServiceLine2(currentServiceLine));
|
|
3198
3309
|
}
|
|
3199
3310
|
currentServiceLine = void 0;
|
|
@@ -3267,6 +3378,7 @@ function get837Claims(delimiters, tx, opts) {
|
|
|
3267
3378
|
const seg = body[i];
|
|
3268
3379
|
if (seg === void 0) continue;
|
|
3269
3380
|
const position = { segmentIndex: i + 1, transactionIndex: 0 };
|
|
3381
|
+
const sink = { warnings, position };
|
|
3270
3382
|
switch (seg.id) {
|
|
3271
3383
|
case "HL": {
|
|
3272
3384
|
flushClaim();
|
|
@@ -3414,16 +3526,21 @@ function get837Claims(delimiters, tx, opts) {
|
|
|
3414
3526
|
warnings.push(missingRequiredLoop(position, REQUIRED_LOOPS.PAYER_NAME_2010BB));
|
|
3415
3527
|
}
|
|
3416
3528
|
}
|
|
3417
|
-
currentClaim = openClaim2(
|
|
3418
|
-
|
|
3419
|
-
|
|
3420
|
-
|
|
3421
|
-
|
|
3422
|
-
|
|
3423
|
-
|
|
3424
|
-
|
|
3425
|
-
|
|
3426
|
-
|
|
3529
|
+
currentClaim = openClaim2(
|
|
3530
|
+
seg,
|
|
3531
|
+
delimiters,
|
|
3532
|
+
{
|
|
3533
|
+
variant,
|
|
3534
|
+
hierarchy: currentPatientHl ?? currentSubscriberHl,
|
|
3535
|
+
billingProvider,
|
|
3536
|
+
payToAddress,
|
|
3537
|
+
payToPlan,
|
|
3538
|
+
subscriber: currentSubscriberMember,
|
|
3539
|
+
payer: currentPayer,
|
|
3540
|
+
patient: currentPatientMember
|
|
3541
|
+
},
|
|
3542
|
+
sink
|
|
3543
|
+
);
|
|
3427
3544
|
activeEntity = void 0;
|
|
3428
3545
|
context = { kind: "loop2300" };
|
|
3429
3546
|
break;
|
|
@@ -3462,7 +3579,7 @@ function get837Claims(delimiters, tx, opts) {
|
|
|
3462
3579
|
break;
|
|
3463
3580
|
}
|
|
3464
3581
|
case "AMT": {
|
|
3465
|
-
const amount = decodeAmt2(seg, delimiters);
|
|
3582
|
+
const amount = decodeAmt2(seg, delimiters, sink);
|
|
3466
3583
|
if (amount === void 0) break;
|
|
3467
3584
|
if (currentAdjudication !== void 0) break;
|
|
3468
3585
|
if (currentServiceLine !== void 0) currentServiceLine.amounts.push(amount);
|
|
@@ -3471,22 +3588,26 @@ function get837Claims(delimiters, tx, opts) {
|
|
|
3471
3588
|
}
|
|
3472
3589
|
case "LX": {
|
|
3473
3590
|
flushServiceLine();
|
|
3474
|
-
if (currentClaim === void 0)
|
|
3475
|
-
|
|
3591
|
+
if (currentClaim === void 0) {
|
|
3592
|
+
warnings.push(serviceLineDropped(position));
|
|
3593
|
+
break;
|
|
3594
|
+
}
|
|
3595
|
+
currentServiceLine = openServiceLine2(seg, delimiters, currentClaim.variant, position);
|
|
3596
|
+
if (currentServiceLine === void 0) warnings.push(serviceLineDropped(position));
|
|
3476
3597
|
activeEntity = void 0;
|
|
3477
3598
|
context = { kind: "loop2400" };
|
|
3478
3599
|
break;
|
|
3479
3600
|
}
|
|
3480
3601
|
case "SV1": {
|
|
3481
|
-
if (currentServiceLine !== void 0) decodeSv1(currentServiceLine, seg, delimiters);
|
|
3602
|
+
if (currentServiceLine !== void 0) decodeSv1(currentServiceLine, seg, delimiters, sink);
|
|
3482
3603
|
break;
|
|
3483
3604
|
}
|
|
3484
3605
|
case "SV2": {
|
|
3485
|
-
if (currentServiceLine !== void 0) decodeSv2(currentServiceLine, seg, delimiters);
|
|
3606
|
+
if (currentServiceLine !== void 0) decodeSv2(currentServiceLine, seg, delimiters, sink);
|
|
3486
3607
|
break;
|
|
3487
3608
|
}
|
|
3488
3609
|
case "SV3": {
|
|
3489
|
-
if (currentServiceLine !== void 0) decodeSv3(currentServiceLine, seg, delimiters);
|
|
3610
|
+
if (currentServiceLine !== void 0) decodeSv3(currentServiceLine, seg, delimiters, sink);
|
|
3490
3611
|
break;
|
|
3491
3612
|
}
|
|
3492
3613
|
case "TOO": {
|
|
@@ -3512,7 +3633,7 @@ function get837Claims(delimiters, tx, opts) {
|
|
|
3512
3633
|
}
|
|
3513
3634
|
currentServiceLine.drug = {
|
|
3514
3635
|
...currentServiceLine.drug,
|
|
3515
|
-
quantity: elementDecimal(seg, 4, delimiters),
|
|
3636
|
+
quantity: elementDecimal(seg, 4, delimiters, sink),
|
|
3516
3637
|
unitOfMeasure: componentOptional(seg, 5, 1, delimiters)
|
|
3517
3638
|
};
|
|
3518
3639
|
break;
|
|
@@ -3520,7 +3641,7 @@ function get837Claims(delimiters, tx, opts) {
|
|
|
3520
3641
|
case "SVD": {
|
|
3521
3642
|
flushAdjudication();
|
|
3522
3643
|
if (currentServiceLine === void 0) break;
|
|
3523
|
-
currentAdjudication = openAdjudication(seg, delimiters);
|
|
3644
|
+
currentAdjudication = openAdjudication(seg, delimiters, sink);
|
|
3524
3645
|
break;
|
|
3525
3646
|
}
|
|
3526
3647
|
case "CAS": {
|
|
@@ -3698,19 +3819,20 @@ function decodeNte(seg, delimiters) {
|
|
|
3698
3819
|
description: note
|
|
3699
3820
|
});
|
|
3700
3821
|
}
|
|
3701
|
-
function decodeAmt2(seg, delimiters) {
|
|
3702
|
-
const amount = elementDecimal(seg, 2, delimiters);
|
|
3822
|
+
function decodeAmt2(seg, delimiters, sink) {
|
|
3823
|
+
const amount = elementDecimal(seg, 2, delimiters, sink);
|
|
3703
3824
|
if (amount === void 0) return void 0;
|
|
3704
3825
|
return Object.freeze({ qualifier: elementValue(seg, 1, delimiters), amount });
|
|
3705
3826
|
}
|
|
3706
3827
|
function decodeCas(seg, delimiters, warnings, position) {
|
|
3828
|
+
const sink = { warnings, position };
|
|
3707
3829
|
const groupCode = elementValue(seg, 1, delimiters);
|
|
3708
3830
|
const out = [];
|
|
3709
3831
|
for (let triple = 0; triple < 6; triple += 1) {
|
|
3710
3832
|
const base = 2 + triple * 3;
|
|
3711
3833
|
const reasonCode = elementOptional(seg, base, delimiters);
|
|
3712
|
-
const amount = elementDecimal(seg, base + 1, delimiters);
|
|
3713
|
-
const quantity = elementDecimal(seg, base + 2, delimiters);
|
|
3834
|
+
const amount = elementDecimal(seg, base + 1, delimiters, sink);
|
|
3835
|
+
const quantity = elementDecimal(seg, base + 2, delimiters, sink);
|
|
3714
3836
|
if (reasonCode === void 0 && amount === void 0) continue;
|
|
3715
3837
|
const code = reasonCode ?? "";
|
|
3716
3838
|
const entry = code === "" ? void 0 : lookupCarc(code);
|
|
@@ -3745,7 +3867,7 @@ var EMPTY_SUBSCRIBER_INFO = Object.freeze({
|
|
|
3745
3867
|
groupName: void 0,
|
|
3746
3868
|
claimFilingIndicator: void 0
|
|
3747
3869
|
});
|
|
3748
|
-
function openClaim2(seg, delimiters, ctx) {
|
|
3870
|
+
function openClaim2(seg, delimiters, ctx, sink) {
|
|
3749
3871
|
const {
|
|
3750
3872
|
variant,
|
|
3751
3873
|
hierarchy,
|
|
@@ -3766,7 +3888,7 @@ function openClaim2(seg, delimiters, ctx) {
|
|
|
3766
3888
|
payer,
|
|
3767
3889
|
patient,
|
|
3768
3890
|
claimId: elementValue(seg, 1, delimiters),
|
|
3769
|
-
totalCharge: elementDecimalOrZero(seg, 2, delimiters),
|
|
3891
|
+
totalCharge: elementDecimalOrZero(seg, 2, delimiters, sink),
|
|
3770
3892
|
placeOfServiceCode: componentOptional(seg, 5, 1, delimiters),
|
|
3771
3893
|
facilityCodeQualifier: componentOptional(seg, 5, 2, delimiters),
|
|
3772
3894
|
claimFrequencyCode: componentOptional(seg, 5, 3, delimiters),
|
|
@@ -3786,10 +3908,12 @@ function openClaim2(seg, delimiters, ctx) {
|
|
|
3786
3908
|
serviceLines: []
|
|
3787
3909
|
};
|
|
3788
3910
|
}
|
|
3789
|
-
function openServiceLine2(seg, delimiters, variant) {
|
|
3911
|
+
function openServiceLine2(seg, delimiters, variant, position) {
|
|
3790
3912
|
const lineNumber = elementValue(seg, 1, delimiters);
|
|
3791
3913
|
const base = {
|
|
3792
3914
|
lineNumber,
|
|
3915
|
+
position,
|
|
3916
|
+
serviceSegmentDecoded: false,
|
|
3793
3917
|
charge: X12Decimal.ZERO,
|
|
3794
3918
|
units: X12Decimal.ZERO,
|
|
3795
3919
|
unitOfMeasure: void 0,
|
|
@@ -3841,8 +3965,9 @@ function openServiceLine2(seg, delimiters, variant) {
|
|
|
3841
3965
|
}
|
|
3842
3966
|
return void 0;
|
|
3843
3967
|
}
|
|
3844
|
-
function decodeSv1(acc, seg, delimiters) {
|
|
3968
|
+
function decodeSv1(acc, seg, delimiters, sink) {
|
|
3845
3969
|
if (acc.variant !== "P") return;
|
|
3970
|
+
acc.serviceSegmentDecoded = true;
|
|
3846
3971
|
acc.procedureQualifier = componentOptional(seg, 1, 1, delimiters) ?? "";
|
|
3847
3972
|
acc.procedureCode = componentOptional(seg, 1, 2, delimiters) ?? "";
|
|
3848
3973
|
const mods = [];
|
|
@@ -3851,9 +3976,9 @@ function decodeSv1(acc, seg, delimiters) {
|
|
|
3851
3976
|
if (m !== void 0) mods.push(m);
|
|
3852
3977
|
}
|
|
3853
3978
|
acc.modifiers = mods;
|
|
3854
|
-
acc.charge = elementDecimalOrZero(seg, 2, delimiters);
|
|
3979
|
+
acc.charge = elementDecimalOrZero(seg, 2, delimiters, sink);
|
|
3855
3980
|
acc.unitOfMeasure = elementOptional(seg, 3, delimiters);
|
|
3856
|
-
acc.units = elementDecimalOrZero(seg, 4, delimiters);
|
|
3981
|
+
acc.units = elementDecimalOrZero(seg, 4, delimiters, sink);
|
|
3857
3982
|
acc.placeOfServiceCode = elementOptional(seg, 5, delimiters);
|
|
3858
3983
|
const pointers = [];
|
|
3859
3984
|
for (let p = 1; p <= 4; p += 1) {
|
|
@@ -3865,8 +3990,9 @@ function decodeSv1(acc, seg, delimiters) {
|
|
|
3865
3990
|
acc.epsdtIndicator = elementOptional(seg, 11, delimiters);
|
|
3866
3991
|
acc.familyPlanningIndicator = elementOptional(seg, 12, delimiters);
|
|
3867
3992
|
}
|
|
3868
|
-
function decodeSv2(acc, seg, delimiters) {
|
|
3993
|
+
function decodeSv2(acc, seg, delimiters, sink) {
|
|
3869
3994
|
if (acc.variant !== "I") return;
|
|
3995
|
+
acc.serviceSegmentDecoded = true;
|
|
3870
3996
|
acc.revenueCode = elementValue(seg, 1, delimiters);
|
|
3871
3997
|
acc.procedureQualifier = componentOptional(seg, 2, 1, delimiters);
|
|
3872
3998
|
acc.procedureCode = componentOptional(seg, 2, 2, delimiters);
|
|
@@ -3876,14 +4002,15 @@ function decodeSv2(acc, seg, delimiters) {
|
|
|
3876
4002
|
if (m !== void 0) mods.push(m);
|
|
3877
4003
|
}
|
|
3878
4004
|
acc.modifiers = mods;
|
|
3879
|
-
acc.charge = elementDecimalOrZero(seg, 3, delimiters);
|
|
4005
|
+
acc.charge = elementDecimalOrZero(seg, 3, delimiters, sink);
|
|
3880
4006
|
acc.unitOfMeasure = elementOptional(seg, 4, delimiters);
|
|
3881
|
-
acc.units = elementDecimalOrZero(seg, 5, delimiters);
|
|
3882
|
-
acc.serviceLineRate = elementDecimal(seg, 6, delimiters);
|
|
3883
|
-
acc.nonCoveredCharge = elementDecimal(seg, 7, delimiters);
|
|
4007
|
+
acc.units = elementDecimalOrZero(seg, 5, delimiters, sink);
|
|
4008
|
+
acc.serviceLineRate = elementDecimal(seg, 6, delimiters, sink);
|
|
4009
|
+
acc.nonCoveredCharge = elementDecimal(seg, 7, delimiters, sink);
|
|
3884
4010
|
}
|
|
3885
|
-
function decodeSv3(acc, seg, delimiters) {
|
|
4011
|
+
function decodeSv3(acc, seg, delimiters, sink) {
|
|
3886
4012
|
if (acc.variant !== "D") return;
|
|
4013
|
+
acc.serviceSegmentDecoded = true;
|
|
3887
4014
|
acc.procedureQualifier = componentOptional(seg, 1, 1, delimiters) ?? "";
|
|
3888
4015
|
acc.procedureCode = componentOptional(seg, 1, 2, delimiters) ?? "";
|
|
3889
4016
|
const mods = [];
|
|
@@ -3892,7 +4019,7 @@ function decodeSv3(acc, seg, delimiters) {
|
|
|
3892
4019
|
if (m !== void 0) mods.push(m);
|
|
3893
4020
|
}
|
|
3894
4021
|
acc.modifiers = mods;
|
|
3895
|
-
acc.charge = elementDecimalOrZero(seg, 2, delimiters);
|
|
4022
|
+
acc.charge = elementDecimalOrZero(seg, 2, delimiters, sink);
|
|
3896
4023
|
acc.placeOfServiceCode = elementOptional(seg, 3, delimiters);
|
|
3897
4024
|
const cavities = [];
|
|
3898
4025
|
for (let p = 1; p <= 5; p += 1) {
|
|
@@ -3901,15 +4028,15 @@ function decodeSv3(acc, seg, delimiters) {
|
|
|
3901
4028
|
}
|
|
3902
4029
|
acc.oralCavityArea = cavities;
|
|
3903
4030
|
acc.prosthesisCrownInlayCode = elementOptional(seg, 5, delimiters);
|
|
3904
|
-
acc.units = elementDecimalOrZero(seg, 6, delimiters);
|
|
4031
|
+
acc.units = elementDecimalOrZero(seg, 6, delimiters, sink);
|
|
3905
4032
|
}
|
|
3906
|
-
function openAdjudication(seg, delimiters) {
|
|
4033
|
+
function openAdjudication(seg, delimiters, sink) {
|
|
3907
4034
|
return {
|
|
3908
4035
|
otherPayerId: elementValue(seg, 1, delimiters),
|
|
3909
|
-
amountPaid: elementDecimalOrZero(seg, 2, delimiters),
|
|
4036
|
+
amountPaid: elementDecimalOrZero(seg, 2, delimiters, sink),
|
|
3910
4037
|
procedureQualifier: componentOptional(seg, 3, 1, delimiters),
|
|
3911
4038
|
procedureCode: componentOptional(seg, 3, 2, delimiters),
|
|
3912
|
-
paidUnits: elementDecimal(seg, 5, delimiters),
|
|
4039
|
+
paidUnits: elementDecimal(seg, 5, delimiters, sink),
|
|
3913
4040
|
adjustments: [],
|
|
3914
4041
|
dateAdjudicated: void 0
|
|
3915
4042
|
};
|
|
@@ -4201,6 +4328,12 @@ function refuseHierarchy(message) {
|
|
|
4201
4328
|
function refuseSpec2(message) {
|
|
4202
4329
|
throw new Claim837BuildError(CLAIM_837_BUILD_ERROR_CODES.X12_837_BUILD_INVALID_SPEC, message);
|
|
4203
4330
|
}
|
|
4331
|
+
function decStr(value) {
|
|
4332
|
+
return requireCallerDecimal(value, "build837", refuseSpec2).toString();
|
|
4333
|
+
}
|
|
4334
|
+
function escDec2(value, esc) {
|
|
4335
|
+
return esc(decStr(value));
|
|
4336
|
+
}
|
|
4204
4337
|
var VERSION_BY_VARIANT = {
|
|
4205
4338
|
P: "005010X222A2",
|
|
4206
4339
|
I: "005010X223A3",
|
|
@@ -4234,6 +4367,7 @@ function buildClaim837(variant, spec) {
|
|
|
4234
4367
|
};
|
|
4235
4368
|
const esc = makeCallerEscaper(delimiters, "build837", refuseSpec2);
|
|
4236
4369
|
const seg = (parts) => {
|
|
4370
|
+
requireCallerSegment(parts, "build837", refuseSpec2);
|
|
4237
4371
|
let end = parts.length;
|
|
4238
4372
|
while (end > 1 && parts[end - 1] === "") end -= 1;
|
|
4239
4373
|
return parts.slice(0, end).join(elementSeparator) + segmentTerminator;
|
|
@@ -4277,8 +4411,8 @@ function buildClaim837(variant, spec) {
|
|
|
4277
4411
|
X12_837_FUNCTIONAL_ID,
|
|
4278
4412
|
esc(applicationSenderCode),
|
|
4279
4413
|
esc(applicationReceiverCode),
|
|
4280
|
-
groupDate,
|
|
4281
|
-
groupTime,
|
|
4414
|
+
esc(groupDate),
|
|
4415
|
+
esc(groupTime),
|
|
4282
4416
|
esc(envelope.groupControlNumber),
|
|
4283
4417
|
X12_AGENCY_CODE2,
|
|
4284
4418
|
versionRelease
|
|
@@ -4493,7 +4627,7 @@ function emitClaim2(variant, claim, body, ctx) {
|
|
|
4493
4627
|
ctx.seg([
|
|
4494
4628
|
"CLM",
|
|
4495
4629
|
ctx.esc(claim.claimId),
|
|
4496
|
-
|
|
4630
|
+
escDec2(claim.totalCharge, ctx.esc),
|
|
4497
4631
|
"",
|
|
4498
4632
|
"",
|
|
4499
4633
|
ctx.comp([
|
|
@@ -4541,8 +4675,8 @@ function emitOtherSubscriber(other, body, ctx) {
|
|
|
4541
4675
|
if (other.otherPayer !== void 0) emitEntity(other.otherPayer, body, ctx);
|
|
4542
4676
|
}
|
|
4543
4677
|
function emitServiceLine2(variant, line, lineNumber, body, ctx) {
|
|
4544
|
-
body.push(ctx.seg(["LX", line.lineNumber ?? String(lineNumber)]));
|
|
4545
|
-
const units = line.units === void 0 ? "0" : line.units
|
|
4678
|
+
body.push(ctx.seg(["LX", ctx.esc(line.lineNumber ?? String(lineNumber))]));
|
|
4679
|
+
const units = line.units === void 0 ? "0" : decStr(line.units);
|
|
4546
4680
|
if (line.variant === "P") {
|
|
4547
4681
|
const proc = ctx.comp([line.procedureQualifier, line.procedureCode, ...line.modifiers ?? []]);
|
|
4548
4682
|
const pointers = ctx.comp(line.diagnosisPointers ?? []);
|
|
@@ -4550,7 +4684,7 @@ function emitServiceLine2(variant, line, lineNumber, body, ctx) {
|
|
|
4550
4684
|
ctx.seg([
|
|
4551
4685
|
"SV1",
|
|
4552
4686
|
proc,
|
|
4553
|
-
|
|
4687
|
+
escDec2(line.charge, ctx.esc),
|
|
4554
4688
|
ctx.esc(line.unitOfMeasure ?? ""),
|
|
4555
4689
|
ctx.esc(units),
|
|
4556
4690
|
ctx.esc(line.placeOfServiceCode ?? ""),
|
|
@@ -4574,11 +4708,11 @@ function emitServiceLine2(variant, line, lineNumber, body, ctx) {
|
|
|
4574
4708
|
"SV2",
|
|
4575
4709
|
ctx.esc(line.revenueCode),
|
|
4576
4710
|
proc,
|
|
4577
|
-
|
|
4711
|
+
escDec2(line.charge, ctx.esc),
|
|
4578
4712
|
ctx.esc(line.unitOfMeasure ?? ""),
|
|
4579
4713
|
ctx.esc(units),
|
|
4580
|
-
line.serviceLineRate === void 0 ? "" :
|
|
4581
|
-
line.nonCoveredCharge === void 0 ? "" :
|
|
4714
|
+
line.serviceLineRate === void 0 ? "" : escDec2(line.serviceLineRate, ctx.esc),
|
|
4715
|
+
line.nonCoveredCharge === void 0 ? "" : escDec2(line.nonCoveredCharge, ctx.esc)
|
|
4582
4716
|
])
|
|
4583
4717
|
);
|
|
4584
4718
|
} else {
|
|
@@ -4588,7 +4722,7 @@ function emitServiceLine2(variant, line, lineNumber, body, ctx) {
|
|
|
4588
4722
|
ctx.seg([
|
|
4589
4723
|
"SV3",
|
|
4590
4724
|
proc,
|
|
4591
|
-
|
|
4725
|
+
escDec2(line.charge, ctx.esc),
|
|
4592
4726
|
ctx.esc(line.placeOfServiceCode ?? ""),
|
|
4593
4727
|
cavity,
|
|
4594
4728
|
ctx.esc(line.prosthesisCrownInlayCode ?? ""),
|
|
@@ -4607,7 +4741,7 @@ function emitServiceLine2(variant, line, lineNumber, body, ctx) {
|
|
|
4607
4741
|
"",
|
|
4608
4742
|
"",
|
|
4609
4743
|
"",
|
|
4610
|
-
drug.quantity === void 0 ? "" :
|
|
4744
|
+
drug.quantity === void 0 ? "" : escDec2(drug.quantity, ctx.esc),
|
|
4611
4745
|
ctx.esc(drug.unitOfMeasure ?? "")
|
|
4612
4746
|
])
|
|
4613
4747
|
);
|
|
@@ -4637,10 +4771,10 @@ function emitAdjudication(adj, body, ctx) {
|
|
|
4637
4771
|
ctx.seg([
|
|
4638
4772
|
"SVD",
|
|
4639
4773
|
ctx.esc(adj.otherPayerId),
|
|
4640
|
-
|
|
4774
|
+
escDec2(adj.amountPaid, ctx.esc),
|
|
4641
4775
|
proc,
|
|
4642
4776
|
"",
|
|
4643
|
-
adj.paidUnits === void 0 ? "" :
|
|
4777
|
+
adj.paidUnits === void 0 ? "" : escDec2(adj.paidUnits, ctx.esc)
|
|
4644
4778
|
])
|
|
4645
4779
|
);
|
|
4646
4780
|
emitCasGroup2(adj.adjustments, "build837: adjudication.adjustments", body, ctx);
|
|
@@ -4665,8 +4799,8 @@ function emitCasGroup2(raw, at, body, ctx) {
|
|
|
4665
4799
|
if (adj === void 0 || adj.groupCode !== groupCode) break;
|
|
4666
4800
|
parts.push(
|
|
4667
4801
|
ctx.esc(adj.reasonCode),
|
|
4668
|
-
|
|
4669
|
-
adj.quantity === void 0 ? "" :
|
|
4802
|
+
escDec2(adj.amount, ctx.esc),
|
|
4803
|
+
adj.quantity === void 0 ? "" : escDec2(adj.quantity, ctx.esc)
|
|
4670
4804
|
);
|
|
4671
4805
|
triples += 1;
|
|
4672
4806
|
i += 1;
|
|
@@ -4737,7 +4871,7 @@ function emitNote(note, body, ctx) {
|
|
|
4737
4871
|
body.push(ctx.seg(["NTE", ctx.esc(note.noteReferenceCode), ctx.esc(note.description)]));
|
|
4738
4872
|
}
|
|
4739
4873
|
function emitAmount(amt, body, ctx) {
|
|
4740
|
-
body.push(ctx.seg(["AMT", ctx.esc(amt.qualifier),
|
|
4874
|
+
body.push(ctx.seg(["AMT", ctx.esc(amt.qualifier), escDec2(amt.amount, ctx.esc)]));
|
|
4741
4875
|
}
|
|
4742
4876
|
function emitHi(hi, body, ctx) {
|
|
4743
4877
|
const composite = ctx.comp([
|
|
@@ -4745,8 +4879,10 @@ function emitHi(hi, body, ctx) {
|
|
|
4745
4879
|
hi.code,
|
|
4746
4880
|
hi.dateQualifier ?? "",
|
|
4747
4881
|
hi.date ?? "",
|
|
4748
|
-
|
|
4749
|
-
|
|
4882
|
+
// `decStr`, not `escDec`: `ctx.comp` maps `esc` over every component, so
|
|
4883
|
+
// escaping here would double-release an active delimiter.
|
|
4884
|
+
hi.monetaryAmount === void 0 ? "" : decStr(hi.monetaryAmount),
|
|
4885
|
+
hi.quantity === void 0 ? "" : decStr(hi.quantity),
|
|
4750
4886
|
hi.versionId ?? "",
|
|
4751
4887
|
"",
|
|
4752
4888
|
hi.poaIndicator ?? ""
|
|
@@ -5058,6 +5194,7 @@ function get271Eligibility(delimiters, tx) {
|
|
|
5058
5194
|
const seg = body[i];
|
|
5059
5195
|
if (seg === void 0) continue;
|
|
5060
5196
|
const position = { segmentIndex: i + 1, transactionIndex: 0 };
|
|
5197
|
+
const sink = { warnings, position };
|
|
5061
5198
|
switch (seg.id) {
|
|
5062
5199
|
case "HL": {
|
|
5063
5200
|
const hl = decodeHl2(seg, delimiters);
|
|
@@ -5161,7 +5298,7 @@ function get271Eligibility(delimiters, tx) {
|
|
|
5161
5298
|
case "EB": {
|
|
5162
5299
|
flushBenefit();
|
|
5163
5300
|
if (currentSubscriber === void 0 && currentDependent === void 0) break;
|
|
5164
|
-
currentBenefit = openBenefit(seg, delimiters);
|
|
5301
|
+
currentBenefit = openBenefit(seg, delimiters, sink);
|
|
5165
5302
|
break;
|
|
5166
5303
|
}
|
|
5167
5304
|
case "MSG": {
|
|
@@ -5258,7 +5395,7 @@ function decodeDtp2(seg, delimiters) {
|
|
|
5258
5395
|
value
|
|
5259
5396
|
});
|
|
5260
5397
|
}
|
|
5261
|
-
function openBenefit(seg, delimiters) {
|
|
5398
|
+
function openBenefit(seg, delimiters, sink) {
|
|
5262
5399
|
const serviceTypeCodes = [];
|
|
5263
5400
|
for (const code of getAllSegmentValues(seg, "03", delimiters)) {
|
|
5264
5401
|
if (code === "") continue;
|
|
@@ -5273,10 +5410,10 @@ function openBenefit(seg, delimiters) {
|
|
|
5273
5410
|
insuranceTypeCode: elementOptional(seg, 4, delimiters),
|
|
5274
5411
|
planCoverageDescription: elementOptional(seg, 5, delimiters),
|
|
5275
5412
|
timePeriodQualifier: elementOptional(seg, 6, delimiters),
|
|
5276
|
-
monetaryAmount: elementDecimal(seg, 7, delimiters),
|
|
5277
|
-
percent: elementDecimal(seg, 8, delimiters),
|
|
5413
|
+
monetaryAmount: elementDecimal(seg, 7, delimiters, sink),
|
|
5414
|
+
percent: elementDecimal(seg, 8, delimiters, sink),
|
|
5278
5415
|
quantityQualifier: elementOptional(seg, 9, delimiters),
|
|
5279
|
-
quantity: elementDecimal(seg, 10, delimiters),
|
|
5416
|
+
quantity: elementDecimal(seg, 10, delimiters, sink),
|
|
5280
5417
|
authorizationRequired: elementOptional(seg, 11, delimiters),
|
|
5281
5418
|
inPlanNetwork: elementOptional(seg, 12, delimiters),
|
|
5282
5419
|
references: [],
|
|
@@ -5379,6 +5516,9 @@ function refuseSpec3(message) {
|
|
|
5379
5516
|
message
|
|
5380
5517
|
);
|
|
5381
5518
|
}
|
|
5519
|
+
function escDec3(value, esc) {
|
|
5520
|
+
return esc(requireCallerDecimal(value, "build271", refuseSpec3).toString());
|
|
5521
|
+
}
|
|
5382
5522
|
var X279A1_VERSION_RELEASE = "005010X279A1";
|
|
5383
5523
|
var X12_271_FUNCTIONAL_ID = "HB";
|
|
5384
5524
|
var X12_AGENCY_CODE3 = "X";
|
|
@@ -5398,6 +5538,7 @@ function build271(spec) {
|
|
|
5398
5538
|
};
|
|
5399
5539
|
const esc = makeCallerEscaper(delimiters, "build271", refuseSpec3);
|
|
5400
5540
|
const seg = (parts) => {
|
|
5541
|
+
requireCallerSegment(parts, "build271", refuseSpec3);
|
|
5401
5542
|
let end = parts.length;
|
|
5402
5543
|
while (end > 1 && parts[end - 1] === "") end -= 1;
|
|
5403
5544
|
return parts.slice(0, end).join(elementSeparator) + segmentTerminator;
|
|
@@ -5435,8 +5576,8 @@ function build271(spec) {
|
|
|
5435
5576
|
X12_271_FUNCTIONAL_ID,
|
|
5436
5577
|
esc(applicationSenderCode),
|
|
5437
5578
|
esc(applicationReceiverCode),
|
|
5438
|
-
groupDate,
|
|
5439
|
-
groupTime,
|
|
5579
|
+
esc(groupDate),
|
|
5580
|
+
esc(groupTime),
|
|
5440
5581
|
esc(envelope.groupControlNumber),
|
|
5441
5582
|
X12_AGENCY_CODE3,
|
|
5442
5583
|
X279A1_VERSION_RELEASE
|
|
@@ -5606,10 +5747,10 @@ function emitBenefit(benefit, body, ctx) {
|
|
|
5606
5747
|
ctx.esc(benefit.insuranceTypeCode ?? ""),
|
|
5607
5748
|
ctx.esc(benefit.planCoverageDescription ?? ""),
|
|
5608
5749
|
ctx.esc(benefit.timePeriodQualifier ?? ""),
|
|
5609
|
-
benefit.monetaryAmount === void 0 ? "" :
|
|
5610
|
-
benefit.percent === void 0 ? "" :
|
|
5750
|
+
benefit.monetaryAmount === void 0 ? "" : escDec3(benefit.monetaryAmount, ctx.esc),
|
|
5751
|
+
benefit.percent === void 0 ? "" : escDec3(benefit.percent, ctx.esc),
|
|
5611
5752
|
ctx.esc(benefit.quantityQualifier ?? ""),
|
|
5612
|
-
benefit.quantity === void 0 ? "" :
|
|
5753
|
+
benefit.quantity === void 0 ? "" : escDec3(benefit.quantity, ctx.esc),
|
|
5613
5754
|
ctx.esc(benefit.authorizationRequired ?? ""),
|
|
5614
5755
|
ctx.esc(benefit.inPlanNetwork ?? "")
|
|
5615
5756
|
])
|
|
@@ -5816,6 +5957,7 @@ function walk277(delimiters, tx) {
|
|
|
5816
5957
|
const seg = body[i];
|
|
5817
5958
|
if (seg === void 0) continue;
|
|
5818
5959
|
const position = { segmentIndex: i + 1, transactionIndex: 0 };
|
|
5960
|
+
const sink = { warnings, position };
|
|
5819
5961
|
switch (seg.id) {
|
|
5820
5962
|
case "HL": {
|
|
5821
5963
|
flushClaim();
|
|
@@ -5893,7 +6035,7 @@ function walk277(delimiters, tx) {
|
|
|
5893
6035
|
case "SVC": {
|
|
5894
6036
|
flushServiceLine();
|
|
5895
6037
|
if (currentClaim === void 0) currentClaim = openClaim3();
|
|
5896
|
-
currentServiceLine = openServiceLine3(seg, delimiters);
|
|
6038
|
+
currentServiceLine = openServiceLine3(seg, delimiters, sink);
|
|
5897
6039
|
break;
|
|
5898
6040
|
}
|
|
5899
6041
|
case "REF": {
|
|
@@ -5967,6 +6109,7 @@ function decodeDtp3(seg, delimiters) {
|
|
|
5967
6109
|
});
|
|
5968
6110
|
}
|
|
5969
6111
|
function decodeStc(seg, delimiters, warnings, position) {
|
|
6112
|
+
const sink = { warnings, position };
|
|
5970
6113
|
const statuses = [];
|
|
5971
6114
|
for (const elementIndex of [1, 10, 11]) {
|
|
5972
6115
|
const code = decodeStatusComposite(seg, elementIndex, delimiters, warnings, position);
|
|
@@ -5975,8 +6118,8 @@ function decodeStc(seg, delimiters, warnings, position) {
|
|
|
5975
6118
|
return Object.freeze({
|
|
5976
6119
|
statusEffectiveDate: elementOptional(seg, 2, delimiters),
|
|
5977
6120
|
actionCode: elementOptional(seg, 3, delimiters),
|
|
5978
|
-
totalChargeAmount: elementDecimal(seg, 4, delimiters),
|
|
5979
|
-
paymentAmount: elementDecimal(seg, 5, delimiters),
|
|
6121
|
+
totalChargeAmount: elementDecimal(seg, 4, delimiters, sink),
|
|
6122
|
+
paymentAmount: elementDecimal(seg, 5, delimiters, sink),
|
|
5980
6123
|
adjudicationDate: elementOptional(seg, 6, delimiters),
|
|
5981
6124
|
message: elementOptional(seg, 12, delimiters),
|
|
5982
6125
|
statuses: Object.freeze(statuses)
|
|
@@ -6003,7 +6146,7 @@ function decodeStatusComposite(seg, n, delimiters, warnings, position) {
|
|
|
6003
6146
|
entityCode
|
|
6004
6147
|
});
|
|
6005
6148
|
}
|
|
6006
|
-
function openServiceLine3(seg, delimiters) {
|
|
6149
|
+
function openServiceLine3(seg, delimiters, sink) {
|
|
6007
6150
|
const modifiers = [];
|
|
6008
6151
|
for (let comp = 3; comp <= 6; comp += 1) {
|
|
6009
6152
|
const m = componentOptional(seg, 1, comp, delimiters);
|
|
@@ -6013,9 +6156,13 @@ function openServiceLine3(seg, delimiters) {
|
|
|
6013
6156
|
serviceIdQualifier: componentOptional(seg, 1, 1, delimiters),
|
|
6014
6157
|
procedureCode: componentOptional(seg, 1, 2, delimiters),
|
|
6015
6158
|
modifiers,
|
|
6016
|
-
lineChargeAmount: elementDecimal(seg, 2, delimiters),
|
|
6017
|
-
linePaymentAmount: elementDecimal(seg, 3, delimiters),
|
|
6159
|
+
lineChargeAmount: elementDecimal(seg, 2, delimiters, sink),
|
|
6160
|
+
linePaymentAmount: elementDecimal(seg, 3, delimiters, sink),
|
|
6018
6161
|
revenueCode: elementOptional(seg, 4, delimiters),
|
|
6162
|
+
// SVC-07. SVC-05 (Quantity) and SVC-06 (a second composite) are NOT USED
|
|
6163
|
+
// in both X212 and X214, so they are deliberately left unread rather than
|
|
6164
|
+
// decoded "for symmetry" with the 835, whose SVC-05 IS the paid count.
|
|
6165
|
+
unitsOfService: elementDecimal(seg, 7, delimiters, sink),
|
|
6019
6166
|
statuses: [],
|
|
6020
6167
|
references: [],
|
|
6021
6168
|
dates: []
|
|
@@ -6029,6 +6176,7 @@ function freezeServiceLine3(acc) {
|
|
|
6029
6176
|
lineChargeAmount: acc.lineChargeAmount,
|
|
6030
6177
|
linePaymentAmount: acc.linePaymentAmount,
|
|
6031
6178
|
revenueCode: acc.revenueCode,
|
|
6179
|
+
unitsOfService: acc.unitsOfService,
|
|
6032
6180
|
statuses: Object.freeze(acc.statuses.slice()),
|
|
6033
6181
|
references: Object.freeze(acc.references.slice()),
|
|
6034
6182
|
dates: Object.freeze(acc.dates.slice())
|
|
@@ -6077,6 +6225,9 @@ function refuseSpec4(message) {
|
|
|
6077
6225
|
message
|
|
6078
6226
|
);
|
|
6079
6227
|
}
|
|
6228
|
+
function escDec4(value, esc) {
|
|
6229
|
+
return esc(requireCallerDecimal(value, "build277", refuseSpec4).toString());
|
|
6230
|
+
}
|
|
6080
6231
|
var X12_277_FUNCTIONAL_ID = "HN";
|
|
6081
6232
|
var X12_AGENCY_CODE4 = "X";
|
|
6082
6233
|
var HL_LEVEL3 = {
|
|
@@ -6094,7 +6245,7 @@ function build277CA(spec) {
|
|
|
6094
6245
|
}
|
|
6095
6246
|
function buildClaimStatus(version, spec) {
|
|
6096
6247
|
const { envelope } = spec;
|
|
6097
|
-
enforceStructuralSpec4(spec);
|
|
6248
|
+
enforceStructuralSpec4(version, spec);
|
|
6098
6249
|
const elementSeparator = envelope.elementSeparator ?? "*";
|
|
6099
6250
|
const repetitionSeparator = envelope.repetitionSeparator ?? "^";
|
|
6100
6251
|
const componentSeparator = envelope.componentSeparator ?? ":";
|
|
@@ -6107,6 +6258,7 @@ function buildClaimStatus(version, spec) {
|
|
|
6107
6258
|
};
|
|
6108
6259
|
const esc = makeCallerEscaper(delimiters, "build277", refuseSpec4);
|
|
6109
6260
|
const seg = (parts) => {
|
|
6261
|
+
requireCallerSegment(parts, "build277", refuseSpec4);
|
|
6110
6262
|
let end = parts.length;
|
|
6111
6263
|
while (end > 1 && parts[end - 1] === "") end -= 1;
|
|
6112
6264
|
return parts.slice(0, end).join(elementSeparator) + segmentTerminator;
|
|
@@ -6150,8 +6302,8 @@ function buildClaimStatus(version, spec) {
|
|
|
6150
6302
|
X12_277_FUNCTIONAL_ID,
|
|
6151
6303
|
esc(applicationSenderCode),
|
|
6152
6304
|
esc(applicationReceiverCode),
|
|
6153
|
-
groupDate,
|
|
6154
|
-
groupTime,
|
|
6305
|
+
esc(groupDate),
|
|
6306
|
+
esc(groupTime),
|
|
6155
6307
|
esc(envelope.groupControlNumber),
|
|
6156
6308
|
X12_AGENCY_CODE4,
|
|
6157
6309
|
version
|
|
@@ -6170,7 +6322,7 @@ function buildClaimStatus(version, spec) {
|
|
|
6170
6322
|
const raw = isa + gs + st + body.join("") + se + ge + iea;
|
|
6171
6323
|
return parseX12(raw);
|
|
6172
6324
|
}
|
|
6173
|
-
function enforceStructuralSpec4(spec) {
|
|
6325
|
+
function enforceStructuralSpec4(version, spec) {
|
|
6174
6326
|
const sources = requireCallerArray(
|
|
6175
6327
|
spec.informationSources,
|
|
6176
6328
|
"build277: spec.informationSources",
|
|
@@ -6228,13 +6380,13 @@ function enforceStructuralSpec4(spec) {
|
|
|
6228
6380
|
for (let u = 0; u < subscribers.length; u += 1) {
|
|
6229
6381
|
const subscriber = subscribers[u];
|
|
6230
6382
|
if (subscriber === void 0) continue;
|
|
6231
|
-
enforceSubscriber(subscriber, `${locator}.subscriber[${String(u)}]`);
|
|
6383
|
+
enforceSubscriber(version, subscriber, `${locator}.subscriber[${String(u)}]`);
|
|
6232
6384
|
}
|
|
6233
6385
|
}
|
|
6234
6386
|
}
|
|
6235
6387
|
}
|
|
6236
6388
|
}
|
|
6237
|
-
function enforceSubscriber(subscriber, locator) {
|
|
6389
|
+
function enforceSubscriber(version, subscriber, locator) {
|
|
6238
6390
|
const claims = requireCallerArray(
|
|
6239
6391
|
subscriber.claims,
|
|
6240
6392
|
`build277: subscriber at ${locator}: claims`,
|
|
@@ -6253,7 +6405,8 @@ function enforceSubscriber(subscriber, locator) {
|
|
|
6253
6405
|
}
|
|
6254
6406
|
for (let c = 0; c < claims.length; c += 1) {
|
|
6255
6407
|
const claim = claims[c];
|
|
6256
|
-
if (claim !== void 0)
|
|
6408
|
+
if (claim !== void 0)
|
|
6409
|
+
enforceClaim2(version, claim, `${locator}.claim[${String(c)}]`, c === 0);
|
|
6257
6410
|
}
|
|
6258
6411
|
for (let d = 0; d < dependents.length; d += 1) {
|
|
6259
6412
|
const dependent = dependents[d];
|
|
@@ -6272,11 +6425,12 @@ function enforceSubscriber(subscriber, locator) {
|
|
|
6272
6425
|
}
|
|
6273
6426
|
for (let c = 0; c < depClaims.length; c += 1) {
|
|
6274
6427
|
const claim = depClaims[c];
|
|
6275
|
-
if (claim !== void 0)
|
|
6428
|
+
if (claim !== void 0)
|
|
6429
|
+
enforceClaim2(version, claim, `${depLocator}.claim[${String(c)}]`, c === 0);
|
|
6276
6430
|
}
|
|
6277
6431
|
}
|
|
6278
6432
|
}
|
|
6279
|
-
function enforceClaim2(claim, locator, isFirst) {
|
|
6433
|
+
function enforceClaim2(version, claim, locator, isFirst) {
|
|
6280
6434
|
const statuses = requireCallerArray(
|
|
6281
6435
|
claim.statuses,
|
|
6282
6436
|
`build277: claim at ${locator}: statuses`,
|
|
@@ -6305,6 +6459,12 @@ function enforceClaim2(claim, locator, isFirst) {
|
|
|
6305
6459
|
for (let l = 0; l < serviceLines.length; l += 1) {
|
|
6306
6460
|
const line = serviceLines[l];
|
|
6307
6461
|
if (line === void 0) continue;
|
|
6462
|
+
if (version === "005010X212" && line.unitsOfService === void 0) {
|
|
6463
|
+
throw new ClaimStatus277BuildError(
|
|
6464
|
+
CLAIM_STATUS_277_BUILD_ERROR_CODES.X12_277_BUILD_INVALID_SPEC,
|
|
6465
|
+
`build277: service line at ${locator}.line[${String(l)}] has no unitsOfService, and SVC-07 is a required element in 005010X212. Supply the submitted count; it is never defaulted. In 005010X214 it is situational, so build277CA accepts the same line.`
|
|
6466
|
+
);
|
|
6467
|
+
}
|
|
6308
6468
|
const lineStatuses = requireCallerArray(
|
|
6309
6469
|
line.statuses,
|
|
6310
6470
|
`build277: claim at ${locator}.line[${String(l)}]: statuses`,
|
|
@@ -6398,9 +6558,12 @@ function emitServiceLine3(line, body, ctx) {
|
|
|
6398
6558
|
ctx.seg([
|
|
6399
6559
|
"SVC",
|
|
6400
6560
|
svc01,
|
|
6401
|
-
line.lineChargeAmount === void 0 ? "" :
|
|
6402
|
-
line.linePaymentAmount === void 0 ? "" :
|
|
6403
|
-
ctx.esc(line.revenueCode ?? "")
|
|
6561
|
+
line.lineChargeAmount === void 0 ? "" : escDec4(line.lineChargeAmount, ctx.esc),
|
|
6562
|
+
line.linePaymentAmount === void 0 ? "" : escDec4(line.linePaymentAmount, ctx.esc),
|
|
6563
|
+
ctx.esc(line.revenueCode ?? ""),
|
|
6564
|
+
"",
|
|
6565
|
+
"",
|
|
6566
|
+
line.unitsOfService === void 0 ? "" : escDec4(line.unitsOfService, ctx.esc)
|
|
6404
6567
|
])
|
|
6405
6568
|
);
|
|
6406
6569
|
for (const status of line.statuses ?? []) emitStatus(status, body, ctx);
|
|
@@ -6419,8 +6582,8 @@ function emitStatus(status, body, ctx) {
|
|
|
6419
6582
|
composite(0),
|
|
6420
6583
|
ctx.esc(status.statusEffectiveDate ?? ""),
|
|
6421
6584
|
ctx.esc(status.actionCode ?? ""),
|
|
6422
|
-
status.totalChargeAmount === void 0 ? "" :
|
|
6423
|
-
status.paymentAmount === void 0 ? "" :
|
|
6585
|
+
status.totalChargeAmount === void 0 ? "" : escDec4(status.totalChargeAmount, ctx.esc),
|
|
6586
|
+
status.paymentAmount === void 0 ? "" : escDec4(status.paymentAmount, ctx.esc),
|
|
6424
6587
|
ctx.esc(status.adjudicationDate ?? ""),
|
|
6425
6588
|
"",
|
|
6426
6589
|
"",
|
|
@@ -6590,9 +6753,11 @@ function get820Payments(delimiters, tx) {
|
|
|
6590
6753
|
for (let i = 0; i < body.length; i += 1) {
|
|
6591
6754
|
const seg = body[i];
|
|
6592
6755
|
if (seg === void 0) continue;
|
|
6756
|
+
const position = { segmentIndex: i + 1, transactionIndex: 0 };
|
|
6757
|
+
const sink = { warnings, position };
|
|
6593
6758
|
switch (seg.id) {
|
|
6594
6759
|
case "BPR": {
|
|
6595
|
-
payment = decodeBpr2(seg, delimiters);
|
|
6760
|
+
payment = decodeBpr2(seg, delimiters, sink);
|
|
6596
6761
|
break;
|
|
6597
6762
|
}
|
|
6598
6763
|
case "TRN": {
|
|
@@ -6659,13 +6824,13 @@ function get820Payments(delimiters, tx) {
|
|
|
6659
6824
|
}
|
|
6660
6825
|
case "RMR": {
|
|
6661
6826
|
if (current === void 0) break;
|
|
6662
|
-
const item = decodeRmr(seg, delimiters);
|
|
6827
|
+
const item = decodeRmr(seg, delimiters, sink);
|
|
6663
6828
|
if (item !== void 0) current.openItems.push(item);
|
|
6664
6829
|
break;
|
|
6665
6830
|
}
|
|
6666
6831
|
case "ADX": {
|
|
6667
6832
|
if (current === void 0) break;
|
|
6668
|
-
const adjustment = decodeAdx(seg, delimiters);
|
|
6833
|
+
const adjustment = decodeAdx(seg, delimiters, sink);
|
|
6669
6834
|
if (adjustment !== void 0) current.adjustments.push(adjustment);
|
|
6670
6835
|
break;
|
|
6671
6836
|
}
|
|
@@ -6717,10 +6882,10 @@ function freezeRemittance(acc) {
|
|
|
6717
6882
|
adjustments: Object.freeze(acc.adjustments.slice())
|
|
6718
6883
|
});
|
|
6719
6884
|
}
|
|
6720
|
-
function decodeBpr2(seg, delimiters) {
|
|
6885
|
+
function decodeBpr2(seg, delimiters, sink) {
|
|
6721
6886
|
return Object.freeze({
|
|
6722
6887
|
transactionHandlingCode: elementValue(seg, 1, delimiters),
|
|
6723
|
-
totalPremiumAmount: elementDecimalOrZero(seg, 2, delimiters),
|
|
6888
|
+
totalPremiumAmount: elementDecimalOrZero(seg, 2, delimiters, sink),
|
|
6724
6889
|
creditDebitFlag: elementValue(seg, 3, delimiters),
|
|
6725
6890
|
method: elementValue(seg, 4, delimiters),
|
|
6726
6891
|
paymentFormatCode: elementOptional(seg, 5, delimiters),
|
|
@@ -6788,7 +6953,7 @@ function decodeNm13(seg, delimiters) {
|
|
|
6788
6953
|
idCode: elementOptional(seg, 9, delimiters)
|
|
6789
6954
|
});
|
|
6790
6955
|
}
|
|
6791
|
-
function decodeRmr(seg, delimiters) {
|
|
6956
|
+
function decodeRmr(seg, delimiters, sink) {
|
|
6792
6957
|
const qualifier = elementValue(seg, 1, delimiters);
|
|
6793
6958
|
const referenceId = elementValue(seg, 2, delimiters);
|
|
6794
6959
|
if (qualifier === "" && referenceId === "") return void 0;
|
|
@@ -6796,12 +6961,12 @@ function decodeRmr(seg, delimiters) {
|
|
|
6796
6961
|
qualifier,
|
|
6797
6962
|
referenceId,
|
|
6798
6963
|
paymentActionCode: elementOptional(seg, 3, delimiters),
|
|
6799
|
-
amountPaid: elementDecimalOrZero(seg, 4, delimiters),
|
|
6800
|
-
amountDue: elementDecimal(seg, 5, delimiters)
|
|
6964
|
+
amountPaid: elementDecimalOrZero(seg, 4, delimiters, sink),
|
|
6965
|
+
amountDue: elementDecimal(seg, 5, delimiters, sink)
|
|
6801
6966
|
});
|
|
6802
6967
|
}
|
|
6803
|
-
function decodeAdx(seg, delimiters) {
|
|
6804
|
-
const amount = elementDecimal(seg, 1, delimiters);
|
|
6968
|
+
function decodeAdx(seg, delimiters, sink) {
|
|
6969
|
+
const amount = elementDecimal(seg, 1, delimiters, sink);
|
|
6805
6970
|
if (amount === void 0) return void 0;
|
|
6806
6971
|
return Object.freeze({
|
|
6807
6972
|
amount,
|
|
@@ -6862,6 +7027,9 @@ var Premium820BuildError = class extends Error {
|
|
|
6862
7027
|
function refuseSpec5(message) {
|
|
6863
7028
|
throw new Premium820BuildError(PREMIUM_820_BUILD_ERROR_CODES.X12_820_BUILD_INVALID_SPEC, message);
|
|
6864
7029
|
}
|
|
7030
|
+
function escDec5(value, esc) {
|
|
7031
|
+
return esc(requireCallerDecimal(value, "build820", refuseSpec5).toString());
|
|
7032
|
+
}
|
|
6865
7033
|
var X218_VERSION_RELEASE = "005010X218";
|
|
6866
7034
|
var X12_820_FUNCTIONAL_ID = "RA";
|
|
6867
7035
|
var X12_AGENCY_CODE5 = "X";
|
|
@@ -6880,6 +7048,7 @@ function build820(spec) {
|
|
|
6880
7048
|
};
|
|
6881
7049
|
const esc = makeCallerEscaper(delimiters, "build820", refuseSpec5);
|
|
6882
7050
|
const seg = (parts) => {
|
|
7051
|
+
requireCallerSegment(parts, "build820", refuseSpec5);
|
|
6883
7052
|
let end = parts.length;
|
|
6884
7053
|
while (end > 1 && parts[end - 1] === "") end -= 1;
|
|
6885
7054
|
return parts.slice(0, end).join(elementSeparator) + segmentTerminator;
|
|
@@ -6935,9 +7104,9 @@ function build820(spec) {
|
|
|
6935
7104
|
// GS-02
|
|
6936
7105
|
esc(applicationReceiverCode),
|
|
6937
7106
|
// GS-03
|
|
6938
|
-
groupDate,
|
|
7107
|
+
esc(groupDate),
|
|
6939
7108
|
// GS-04 - CCYYMMDD
|
|
6940
|
-
groupTime,
|
|
7109
|
+
esc(groupTime),
|
|
6941
7110
|
// GS-05 - HHMM
|
|
6942
7111
|
esc(envelope.groupControlNumber),
|
|
6943
7112
|
// GS-06
|
|
@@ -6953,7 +7122,7 @@ function build820(spec) {
|
|
|
6953
7122
|
seg([
|
|
6954
7123
|
"BPR",
|
|
6955
7124
|
esc(spec.payment.transactionHandlingCode),
|
|
6956
|
-
|
|
7125
|
+
escDec5(spec.payment.totalPremiumAmount, esc),
|
|
6957
7126
|
esc(spec.payment.creditDebitFlag),
|
|
6958
7127
|
esc(spec.payment.method),
|
|
6959
7128
|
esc(spec.payment.paymentFormatCode ?? ""),
|
|
@@ -7110,7 +7279,7 @@ function emitRemittance(remittance, body, seg, esc) {
|
|
|
7110
7279
|
body.push(
|
|
7111
7280
|
seg([
|
|
7112
7281
|
"ADX",
|
|
7113
|
-
|
|
7282
|
+
escDec5(adjustment.amount, esc),
|
|
7114
7283
|
esc(adjustment.reasonCode),
|
|
7115
7284
|
esc(adjustment.referenceQualifier ?? ""),
|
|
7116
7285
|
esc(adjustment.referenceId ?? "")
|
|
@@ -7140,8 +7309,8 @@ function emitOpenItem(item, seg, esc) {
|
|
|
7140
7309
|
esc(item.qualifier),
|
|
7141
7310
|
esc(item.referenceId),
|
|
7142
7311
|
esc(item.paymentActionCode ?? ""),
|
|
7143
|
-
|
|
7144
|
-
item.amountDue === void 0 ? "" :
|
|
7312
|
+
escDec5(item.amountPaid, esc),
|
|
7313
|
+
item.amountDue === void 0 ? "" : escDec5(item.amountDue, esc)
|
|
7145
7314
|
]);
|
|
7146
7315
|
}
|
|
7147
7316
|
function emitRef5(ref, seg, esc) {
|
|
@@ -7372,7 +7541,8 @@ async function* get834Enrollments(delimiters, tx) {
|
|
|
7372
7541
|
}
|
|
7373
7542
|
case "AMT": {
|
|
7374
7543
|
if (currentCoverage === void 0) break;
|
|
7375
|
-
const
|
|
7544
|
+
const sink = { warnings: current.warnings, position };
|
|
7545
|
+
const amount = decodeAmt3(seg, delimiters, sink);
|
|
7376
7546
|
if (amount !== void 0) currentCoverage.amounts.push(amount);
|
|
7377
7547
|
break;
|
|
7378
7548
|
}
|
|
@@ -7498,8 +7668,8 @@ function decodeDtp4(seg, delimiters) {
|
|
|
7498
7668
|
value
|
|
7499
7669
|
});
|
|
7500
7670
|
}
|
|
7501
|
-
function decodeAmt3(seg, delimiters) {
|
|
7502
|
-
const amount = elementDecimal(seg, 2, delimiters);
|
|
7671
|
+
function decodeAmt3(seg, delimiters, sink) {
|
|
7672
|
+
const amount = elementDecimal(seg, 2, delimiters, sink);
|
|
7503
7673
|
if (amount === void 0) return void 0;
|
|
7504
7674
|
return Object.freeze({
|
|
7505
7675
|
qualifier: elementValue(seg, 1, delimiters),
|
|
@@ -7561,6 +7731,9 @@ function refuseSpec6(message) {
|
|
|
7561
7731
|
message
|
|
7562
7732
|
);
|
|
7563
7733
|
}
|
|
7734
|
+
function escDec6(value, esc) {
|
|
7735
|
+
return esc(requireCallerDecimal(value, "build834", refuseSpec6).toString());
|
|
7736
|
+
}
|
|
7564
7737
|
var X220A1_VERSION_RELEASE = "005010X220A1";
|
|
7565
7738
|
var X12_834_FUNCTIONAL_ID = "BE";
|
|
7566
7739
|
var X12_AGENCY_CODE6 = "X";
|
|
@@ -7581,6 +7754,7 @@ function build834(spec) {
|
|
|
7581
7754
|
};
|
|
7582
7755
|
const esc = makeCallerEscaper(delimiters, "build834", refuseSpec6);
|
|
7583
7756
|
const seg = (parts) => {
|
|
7757
|
+
requireCallerSegment(parts, "build834", refuseSpec6);
|
|
7584
7758
|
let end = parts.length;
|
|
7585
7759
|
while (end > 1 && parts[end - 1] === "") end -= 1;
|
|
7586
7760
|
return parts.slice(0, end).join(elementSeparator) + segmentTerminator;
|
|
@@ -7636,9 +7810,9 @@ function build834(spec) {
|
|
|
7636
7810
|
// GS-02
|
|
7637
7811
|
esc(applicationReceiverCode),
|
|
7638
7812
|
// GS-03
|
|
7639
|
-
groupDate,
|
|
7813
|
+
esc(groupDate),
|
|
7640
7814
|
// GS-04 - CCYYMMDD
|
|
7641
|
-
groupTime,
|
|
7815
|
+
esc(groupTime),
|
|
7642
7816
|
// GS-05 - HHMM
|
|
7643
7817
|
esc(envelope.groupControlNumber),
|
|
7644
7818
|
// GS-06
|
|
@@ -7819,7 +7993,7 @@ function emitCoverage(coverage, body, seg, esc) {
|
|
|
7819
7993
|
);
|
|
7820
7994
|
for (const date of coverage.dates ?? []) body.push(emitDate4(date, seg, esc));
|
|
7821
7995
|
for (const amount of coverage.amounts ?? []) {
|
|
7822
|
-
body.push(seg(["AMT", esc(amount.qualifier),
|
|
7996
|
+
body.push(seg(["AMT", esc(amount.qualifier), escDec6(amount.amount, esc)]));
|
|
7823
7997
|
}
|
|
7824
7998
|
}
|
|
7825
7999
|
function emitRef6(ref, seg, esc) {
|
|
@@ -8248,6 +8422,7 @@ function buildServicesReview(version, direction, spec) {
|
|
|
8248
8422
|
};
|
|
8249
8423
|
const esc = makeCallerEscaper(delimiters, "build278", refuseSpec7);
|
|
8250
8424
|
const seg = (parts) => {
|
|
8425
|
+
requireCallerSegment(parts, "build278", refuseSpec7);
|
|
8251
8426
|
let end = parts.length;
|
|
8252
8427
|
while (end > 1 && parts[end - 1] === "") end -= 1;
|
|
8253
8428
|
return parts.slice(0, end).join(elementSeparator) + segmentTerminator;
|
|
@@ -8291,8 +8466,8 @@ function buildServicesReview(version, direction, spec) {
|
|
|
8291
8466
|
X12_278_FUNCTIONAL_ID,
|
|
8292
8467
|
esc(applicationSenderCode),
|
|
8293
8468
|
esc(applicationReceiverCode),
|
|
8294
|
-
groupDate,
|
|
8295
|
-
groupTime,
|
|
8469
|
+
esc(groupDate),
|
|
8470
|
+
esc(groupTime),
|
|
8296
8471
|
esc(envelope.groupControlNumber),
|
|
8297
8472
|
X12_AGENCY_CODE7,
|
|
8298
8473
|
version
|
|
@@ -8421,7 +8596,7 @@ function emitReview(review, parentHlId, direction, body, ctx, counter) {
|
|
|
8421
8596
|
const nested = review.reviews ?? [];
|
|
8422
8597
|
const hasChild = nested.length > 0 ? "1" : "0";
|
|
8423
8598
|
const levelCode = review.levelCode ?? DEFAULT_REVIEW_LEVEL;
|
|
8424
|
-
body.push(ctx.seg(["HL", hlId, parentHlId, levelCode, hasChild]));
|
|
8599
|
+
body.push(ctx.seg(["HL", hlId, parentHlId, ctx.esc(levelCode), hasChild]));
|
|
8425
8600
|
for (const trace of review.traces ?? []) {
|
|
8426
8601
|
body.push(
|
|
8427
8602
|
ctx.seg([
|
|
@@ -9068,13 +9243,13 @@ function build999(spec) {
|
|
|
9068
9243
|
// GS-02
|
|
9069
9244
|
esc(envelope.receiverId),
|
|
9070
9245
|
// GS-03
|
|
9071
|
-
groupDate,
|
|
9246
|
+
esc(groupDate),
|
|
9072
9247
|
// GS-04 - CCYYMMDD
|
|
9073
|
-
groupTime,
|
|
9248
|
+
esc(groupTime),
|
|
9074
9249
|
// GS-05 - HHMM
|
|
9075
|
-
envelope.groupControlNumber,
|
|
9250
|
+
esc(envelope.groupControlNumber),
|
|
9076
9251
|
// GS-06
|
|
9077
|
-
groupResponsibleAgency,
|
|
9252
|
+
esc(groupResponsibleAgency),
|
|
9078
9253
|
// GS-07
|
|
9079
9254
|
X231A1_VERSION_RELEASE
|
|
9080
9255
|
// GS-08 - the 999 TR3
|
|
@@ -9084,7 +9259,7 @@ function build999(spec) {
|
|
|
9084
9259
|
);
|
|
9085
9260
|
const stControlNumber = envelope.transactionSetControlNumber;
|
|
9086
9261
|
const st = joinSeg(
|
|
9087
|
-
["ST", "999", stControlNumber, X231A1_VERSION_RELEASE],
|
|
9262
|
+
["ST", "999", esc(stControlNumber), X231A1_VERSION_RELEASE],
|
|
9088
9263
|
elementSeparator,
|
|
9089
9264
|
segmentTerminator
|
|
9090
9265
|
);
|
|
@@ -9117,8 +9292,16 @@ function build999(spec) {
|
|
|
9117
9292
|
const ak9 = buildAk9(functionalGroup, esc, elementSeparator, segmentTerminator);
|
|
9118
9293
|
const bodySegments = [st, ak1, ...responseSegments, ak9];
|
|
9119
9294
|
const seCount = bodySegments.length + 1;
|
|
9120
|
-
const se = joinSeg(
|
|
9121
|
-
|
|
9295
|
+
const se = joinSeg(
|
|
9296
|
+
["SE", String(seCount), esc(stControlNumber)],
|
|
9297
|
+
elementSeparator,
|
|
9298
|
+
segmentTerminator
|
|
9299
|
+
);
|
|
9300
|
+
const ge = joinSeg(
|
|
9301
|
+
["GE", "1", esc(envelope.groupControlNumber)],
|
|
9302
|
+
elementSeparator,
|
|
9303
|
+
segmentTerminator
|
|
9304
|
+
);
|
|
9122
9305
|
const iea = joinSeg(["IEA", "1", interchangeControlNumber], elementSeparator, segmentTerminator);
|
|
9123
9306
|
const raw = isa + gs + bodySegments.join("") + se + ge + iea;
|
|
9124
9307
|
return parseX12(raw);
|
|
@@ -9240,7 +9423,7 @@ function buildIk4(elemError, esc, componentSeparator, elementSeparator, segmentT
|
|
|
9240
9423
|
return joinSeg(parts, elementSeparator, segmentTerminator);
|
|
9241
9424
|
}
|
|
9242
9425
|
function buildIk5(response, esc, elementSeparator, segmentTerminator) {
|
|
9243
|
-
const parts = ["IK5", response.disposition];
|
|
9426
|
+
const parts = ["IK5", esc(response.disposition)];
|
|
9244
9427
|
const codes = response.syntaxErrorCodes ?? [];
|
|
9245
9428
|
if (codes.length > 5) {
|
|
9246
9429
|
throw new AckBuildError(
|
|
@@ -9254,7 +9437,7 @@ function buildIk5(response, esc, elementSeparator, segmentTerminator) {
|
|
|
9254
9437
|
function buildAk9(group, esc, elementSeparator, segmentTerminator) {
|
|
9255
9438
|
const parts = [
|
|
9256
9439
|
"AK9",
|
|
9257
|
-
group.disposition,
|
|
9440
|
+
esc(group.disposition),
|
|
9258
9441
|
String(group.numberOfTransactionSets),
|
|
9259
9442
|
String(group.numberOfReceivedTransactionSets),
|
|
9260
9443
|
String(group.numberOfAcceptedTransactionSets)
|
|
@@ -9270,6 +9453,7 @@ function buildAk9(group, esc, elementSeparator, segmentTerminator) {
|
|
|
9270
9453
|
return joinSeg(parts, elementSeparator, segmentTerminator);
|
|
9271
9454
|
}
|
|
9272
9455
|
function joinSeg(parts, elementSeparator, segmentTerminator) {
|
|
9456
|
+
requireCallerSegment(parts, "build999", refuseSpec8);
|
|
9273
9457
|
return parts.join(elementSeparator) + segmentTerminator;
|
|
9274
9458
|
}
|
|
9275
9459
|
function pad8(value, width) {
|
|
@@ -9624,6 +9808,7 @@ function buildTransaction(tx, esc, elementSeparator, segmentTerminator) {
|
|
|
9624
9808
|
return st + bodySegments + se;
|
|
9625
9809
|
}
|
|
9626
9810
|
function joinSeg2(parts, elementSeparator, segmentTerminator) {
|
|
9811
|
+
requireCallerSegment(parts, "buildInterchange", refuseSpec9);
|
|
9627
9812
|
return parts.join(elementSeparator) + segmentTerminator;
|
|
9628
9813
|
}
|
|
9629
9814
|
function pad9(value, width) {
|
|
@@ -9932,7 +10117,7 @@ var profiles = Object.freeze({
|
|
|
9932
10117
|
});
|
|
9933
10118
|
|
|
9934
10119
|
// src/index.ts
|
|
9935
|
-
var VERSION = "0.0.
|
|
10120
|
+
var VERSION = "0.0.10";
|
|
9936
10121
|
|
|
9937
10122
|
exports.ACK_BUILD_ERROR_CODES = ACK_BUILD_ERROR_CODES;
|
|
9938
10123
|
exports.ALL_WARNING_MESSAGES = ALL_WARNING_MESSAGES;
|
|
@@ -10107,11 +10292,14 @@ exports.parseX12 = parseX12;
|
|
|
10107
10292
|
exports.partitionWarnings = partitionWarnings;
|
|
10108
10293
|
exports.pre005010 = pre005010;
|
|
10109
10294
|
exports.profiles = profiles;
|
|
10295
|
+
exports.readElementDecimal = readElementDecimal;
|
|
10110
10296
|
exports.remitBalanceMismatch = remitBalanceMismatch;
|
|
10111
10297
|
exports.renderCallerValue = renderCallerValue;
|
|
10112
10298
|
exports.resolveHiQualifier = resolveHiQualifier;
|
|
10113
10299
|
exports.segmentCountMismatch = segmentCountMismatch;
|
|
10114
10300
|
exports.serializeX12 = serializeX12;
|
|
10301
|
+
exports.serviceLineDropped = serviceLineDropped;
|
|
10302
|
+
exports.serviceLineNotDecoded = serviceLineNotDecoded;
|
|
10115
10303
|
exports.setDefaultProfile = setDefaultProfile;
|
|
10116
10304
|
exports.trailingGarbage = trailingGarbage;
|
|
10117
10305
|
exports.transactionCountMismatch = transactionCountMismatch;
|
|
@@ -10124,5 +10312,6 @@ exports.unknownClaimStatusCategory = unknownClaimStatusCategory;
|
|
|
10124
10312
|
exports.unknownHiQualifier = unknownHiQualifier;
|
|
10125
10313
|
exports.unknownMaintenanceType = unknownMaintenanceType;
|
|
10126
10314
|
exports.unknownRarc = unknownRarc;
|
|
10315
|
+
exports.unparseableDecimal = unparseableDecimal;
|
|
10127
10316
|
//# sourceMappingURL=index.cjs.map
|
|
10128
10317
|
//# sourceMappingURL=index.cjs.map
|