jupiter-dynamic-forms 1.20.1 → 1.20.3
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/dist/core/concept-tree.d.ts.map +1 -1
- package/dist/core/dynamic-form.d.ts +42 -0
- package/dist/core/dynamic-form.d.ts.map +1 -1
- package/dist/core/form-field.d.ts.map +1 -1
- package/dist/core/form-section.d.ts +50 -1
- package/dist/core/form-section.d.ts.map +1 -1
- package/dist/core/formula-validation-dialog.d.ts +30 -0
- package/dist/core/formula-validation-dialog.d.ts.map +1 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +351 -75
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +1784 -306
- package/dist/index.mjs.map +1 -1
- package/dist/schema/types.d.ts +26 -0
- package/dist/schema/types.d.ts.map +1 -1
- package/dist/schema/xbrl-types.d.ts +67 -0
- package/dist/schema/xbrl-types.d.ts.map +1 -1
- package/dist/utils/formula-constants.d.ts +7 -0
- package/dist/utils/formula-constants.d.ts.map +1 -0
- package/dist/utils/formula-expression-evaluator.d.ts +64 -0
- package/dist/utils/formula-expression-evaluator.d.ts.map +1 -0
- package/dist/utils/formula-precondition-evaluator.d.ts +33 -0
- package/dist/utils/formula-precondition-evaluator.d.ts.map +1 -0
- package/dist/utils/formula-resolution-context.d.ts +45 -0
- package/dist/utils/formula-resolution-context.d.ts.map +1 -0
- package/dist/utils/formula-variable-resolver.d.ts +30 -0
- package/dist/utils/formula-variable-resolver.d.ts.map +1 -0
- package/dist/utils/total-group-resolver.d.ts +68 -0
- package/dist/utils/total-group-resolver.d.ts.map +1 -0
- package/dist/utils/total-label.d.ts +9 -0
- package/dist/utils/total-label.d.ts.map +1 -0
- package/package.json +1 -1
package/dist/index.mjs
CHANGED
|
@@ -1817,6 +1817,15 @@ const calculationWarning$1 = {
|
|
|
1817
1817
|
added: "Added",
|
|
1818
1818
|
subtracted: "Subtracted (opposite balance)"
|
|
1819
1819
|
};
|
|
1820
|
+
const formulaValidation$1 = {
|
|
1821
|
+
dialogTitle: "Formula check results",
|
|
1822
|
+
allPassed: "All formula checks passed",
|
|
1823
|
+
summaryCount: "{{failed}} of {{total}} checks failed",
|
|
1824
|
+
summaryCountBreakdown: "{{warnings}} warnings, {{errors}} errors",
|
|
1825
|
+
severityWarning: "Warning",
|
|
1826
|
+
severityError: "Error",
|
|
1827
|
+
close: "Close"
|
|
1828
|
+
};
|
|
1820
1829
|
const enTranslations = {
|
|
1821
1830
|
conceptInfo: conceptInfo$1,
|
|
1822
1831
|
form: form$1,
|
|
@@ -1828,7 +1837,8 @@ const enTranslations = {
|
|
|
1828
1837
|
validation: validation$1,
|
|
1829
1838
|
xbrlValidation: xbrlValidation$1,
|
|
1830
1839
|
error: error$1,
|
|
1831
|
-
calculationWarning: calculationWarning$1
|
|
1840
|
+
calculationWarning: calculationWarning$1,
|
|
1841
|
+
formulaValidation: formulaValidation$1
|
|
1832
1842
|
};
|
|
1833
1843
|
const conceptInfo = {
|
|
1834
1844
|
title: "Conceptinformatie",
|
|
@@ -2012,6 +2022,15 @@ const calculationWarning = {
|
|
|
2012
2022
|
added: "Opgeteld",
|
|
2013
2023
|
subtracted: "Afgetrokken (tegengestelde balans)"
|
|
2014
2024
|
};
|
|
2025
|
+
const formulaValidation = {
|
|
2026
|
+
dialogTitle: "Resultaten formulecontrole",
|
|
2027
|
+
allPassed: "Alle formulecontroles geslaagd",
|
|
2028
|
+
summaryCount: "{{failed}} van {{total}} controles mislukt",
|
|
2029
|
+
summaryCountBreakdown: "{{warnings}} waarschuwingen, {{errors}} fouten",
|
|
2030
|
+
severityWarning: "Waarschuwing",
|
|
2031
|
+
severityError: "Fout",
|
|
2032
|
+
close: "Sluiten"
|
|
2033
|
+
};
|
|
2015
2034
|
const nlTranslations = {
|
|
2016
2035
|
conceptInfo,
|
|
2017
2036
|
form,
|
|
@@ -2023,7 +2042,8 @@ const nlTranslations = {
|
|
|
2023
2042
|
validation,
|
|
2024
2043
|
xbrlValidation,
|
|
2025
2044
|
error,
|
|
2026
|
-
calculationWarning
|
|
2045
|
+
calculationWarning,
|
|
2046
|
+
formulaValidation
|
|
2027
2047
|
};
|
|
2028
2048
|
const translations = {
|
|
2029
2049
|
en: enTranslations,
|
|
@@ -2102,6 +2122,9 @@ class I18n {
|
|
|
2102
2122
|
}
|
|
2103
2123
|
}
|
|
2104
2124
|
I18n.currentLanguage = "en";
|
|
2125
|
+
function isTotalLabel$1(preferredLabel) {
|
|
2126
|
+
return !!(preferredLabel == null ? void 0 : preferredLabel.toLowerCase().includes("totallabel"));
|
|
2127
|
+
}
|
|
2105
2128
|
class DraftStorageService {
|
|
2106
2129
|
constructor(useSessionStorage = false) {
|
|
2107
2130
|
this.DRAFT_DATA_KEY = "jupiter-form-draft-data";
|
|
@@ -2261,7 +2284,7 @@ class DraftStorageService {
|
|
|
2261
2284
|
/**
|
|
2262
2285
|
* Create metadata snapshot from current form state
|
|
2263
2286
|
*/
|
|
2264
|
-
createMetadataSnapshot(periodStartDate, periodEndDate, language, selectedRoleIds, allSections, typedMemberData, periodPreferences, periodData, unitData, reportingLanguage = "en", repeatCounts, decimalsData, roleCompletedStates, hiddenColumns) {
|
|
2287
|
+
createMetadataSnapshot(periodStartDate, periodEndDate, language, selectedRoleIds, allSections, typedMemberData, periodPreferences, periodData, unitData, reportingLanguage = "en", repeatCounts, decimalsData, roleCompletedStates, hiddenColumns, totalManuallyEditedData) {
|
|
2265
2288
|
return {
|
|
2266
2289
|
periodStartDate,
|
|
2267
2290
|
periodEndDate,
|
|
@@ -2278,6 +2301,7 @@ class DraftStorageService {
|
|
|
2278
2301
|
repeatCounts,
|
|
2279
2302
|
roleCompletedStates,
|
|
2280
2303
|
hiddenColumns,
|
|
2304
|
+
totalManuallyEditedData,
|
|
2281
2305
|
schemaVersion: this.STORAGE_VERSION
|
|
2282
2306
|
};
|
|
2283
2307
|
}
|
|
@@ -2300,6 +2324,801 @@ class DraftStorageService {
|
|
|
2300
2324
|
return { compatible, warnings };
|
|
2301
2325
|
}
|
|
2302
2326
|
}
|
|
2327
|
+
const CALCULATION_TOLERANCE = 0.01;
|
|
2328
|
+
class FormulaExpressionError extends Error {
|
|
2329
|
+
constructor(message, test, reason = "unsupported-syntax") {
|
|
2330
|
+
super(message);
|
|
2331
|
+
this.test = test;
|
|
2332
|
+
this.reason = reason;
|
|
2333
|
+
this.name = "FormulaExpressionError";
|
|
2334
|
+
}
|
|
2335
|
+
}
|
|
2336
|
+
const TOKEN_PATTERN = /\s*(?:(\$[A-Za-z_][\w-]*)|(-?\d+(?:\.\d+)?)|([A-Za-z][\w:-]*)|('[^']*')|(\()|(\))|(\+)|(-)|(=))/y;
|
|
2337
|
+
function tokenize(test) {
|
|
2338
|
+
const tokens = [];
|
|
2339
|
+
TOKEN_PATTERN.lastIndex = 0;
|
|
2340
|
+
let index = 0;
|
|
2341
|
+
while (index < test.length) {
|
|
2342
|
+
TOKEN_PATTERN.lastIndex = index;
|
|
2343
|
+
const match = TOKEN_PATTERN.exec(test);
|
|
2344
|
+
if (!match || match.index !== index) {
|
|
2345
|
+
if (/^\s*$/.test(test.slice(index)))
|
|
2346
|
+
break;
|
|
2347
|
+
throw new FormulaExpressionError(`Unrecognized token at position ${index}: "${test.slice(index, index + 10)}..."`, test, "unsupported-syntax");
|
|
2348
|
+
}
|
|
2349
|
+
const [full, variable, number, ident, string, lparen, rparen, plus, minus, equals] = match;
|
|
2350
|
+
if (variable)
|
|
2351
|
+
tokens.push({ type: "VARIABLE", value: variable.slice(1) });
|
|
2352
|
+
else if (number)
|
|
2353
|
+
tokens.push({ type: "NUMBER", value: number });
|
|
2354
|
+
else if (ident)
|
|
2355
|
+
tokens.push({ type: "IDENT", value: ident });
|
|
2356
|
+
else if (string)
|
|
2357
|
+
tokens.push({ type: "STRING", value: string.slice(1, -1) });
|
|
2358
|
+
else if (lparen)
|
|
2359
|
+
tokens.push({ type: "LPAREN", value: lparen });
|
|
2360
|
+
else if (rparen)
|
|
2361
|
+
tokens.push({ type: "RPAREN", value: rparen });
|
|
2362
|
+
else if (plus)
|
|
2363
|
+
tokens.push({ type: "PLUS", value: plus });
|
|
2364
|
+
else if (minus)
|
|
2365
|
+
tokens.push({ type: "MINUS", value: minus });
|
|
2366
|
+
else if (equals)
|
|
2367
|
+
tokens.push({ type: "EQUALS", value: equals });
|
|
2368
|
+
index += full.length;
|
|
2369
|
+
}
|
|
2370
|
+
tokens.push({ type: "EOF", value: "" });
|
|
2371
|
+
return tokens;
|
|
2372
|
+
}
|
|
2373
|
+
class Parser {
|
|
2374
|
+
constructor(tokens, test) {
|
|
2375
|
+
this.tokens = tokens;
|
|
2376
|
+
this.test = test;
|
|
2377
|
+
this.pos = 0;
|
|
2378
|
+
}
|
|
2379
|
+
peek() {
|
|
2380
|
+
return this.tokens[this.pos];
|
|
2381
|
+
}
|
|
2382
|
+
next() {
|
|
2383
|
+
return this.tokens[this.pos++];
|
|
2384
|
+
}
|
|
2385
|
+
expect(type) {
|
|
2386
|
+
const token = this.next();
|
|
2387
|
+
if (token.type !== type) {
|
|
2388
|
+
throw new FormulaExpressionError(
|
|
2389
|
+
`Expected ${type} but got ${token.type} ("${token.value}")`,
|
|
2390
|
+
this.test,
|
|
2391
|
+
"parse-error"
|
|
2392
|
+
);
|
|
2393
|
+
}
|
|
2394
|
+
return token;
|
|
2395
|
+
}
|
|
2396
|
+
parseBoolExpr() {
|
|
2397
|
+
const node = this.parseOrExpr();
|
|
2398
|
+
if (this.peek().type !== "EOF") {
|
|
2399
|
+
throw new FormulaExpressionError(
|
|
2400
|
+
`Unexpected trailing token "${this.peek().value}"`,
|
|
2401
|
+
this.test,
|
|
2402
|
+
"unsupported-syntax"
|
|
2403
|
+
);
|
|
2404
|
+
}
|
|
2405
|
+
return node;
|
|
2406
|
+
}
|
|
2407
|
+
parseOrExpr() {
|
|
2408
|
+
const terms = [this.parseAndExpr()];
|
|
2409
|
+
while (this.peek().type === "IDENT" && this.peek().value === "or") {
|
|
2410
|
+
this.next();
|
|
2411
|
+
terms.push(this.parseAndExpr());
|
|
2412
|
+
}
|
|
2413
|
+
return terms.length === 1 ? terms[0] : { kind: "or", terms };
|
|
2414
|
+
}
|
|
2415
|
+
parseAndExpr() {
|
|
2416
|
+
const terms = [this.parseBoolTerm()];
|
|
2417
|
+
while (this.peek().type === "IDENT" && this.peek().value === "and") {
|
|
2418
|
+
this.next();
|
|
2419
|
+
terms.push(this.parseBoolTerm());
|
|
2420
|
+
}
|
|
2421
|
+
return terms.length === 1 ? terms[0] : { kind: "and", terms };
|
|
2422
|
+
}
|
|
2423
|
+
parseBoolTerm() {
|
|
2424
|
+
const token = this.peek();
|
|
2425
|
+
if (token.type === "IDENT" && token.value === "not") {
|
|
2426
|
+
this.next();
|
|
2427
|
+
this.expect("LPAREN");
|
|
2428
|
+
const arg = this.parseOrExpr();
|
|
2429
|
+
this.expect("RPAREN");
|
|
2430
|
+
return { kind: "not", arg };
|
|
2431
|
+
}
|
|
2432
|
+
if (token.type === "IDENT" && token.value === "empty") {
|
|
2433
|
+
this.next();
|
|
2434
|
+
this.expect("LPAREN");
|
|
2435
|
+
const variable = this.expect("VARIABLE").value;
|
|
2436
|
+
this.expect("RPAREN");
|
|
2437
|
+
return { kind: "empty", variable };
|
|
2438
|
+
}
|
|
2439
|
+
if (token.type === "IDENT" && token.value === "xff:has-fallback-value") {
|
|
2440
|
+
this.next();
|
|
2441
|
+
this.expect("LPAREN");
|
|
2442
|
+
const inner = this.next();
|
|
2443
|
+
if (inner.type !== "IDENT" || inner.value !== "xs:QName") {
|
|
2444
|
+
throw new FormulaExpressionError(
|
|
2445
|
+
`Expected xs:QName(...) inside xff:has-fallback-value(...), got "${inner.value}"`,
|
|
2446
|
+
this.test,
|
|
2447
|
+
"unsupported-syntax"
|
|
2448
|
+
);
|
|
2449
|
+
}
|
|
2450
|
+
this.expect("LPAREN");
|
|
2451
|
+
const variableName = this.expect("STRING").value;
|
|
2452
|
+
this.expect("RPAREN");
|
|
2453
|
+
this.expect("RPAREN");
|
|
2454
|
+
return { kind: "hasFallbackValue", variableName };
|
|
2455
|
+
}
|
|
2456
|
+
const left = this.parseValueExpr();
|
|
2457
|
+
const opToken = this.peek();
|
|
2458
|
+
if (opToken.type === "EQUALS") {
|
|
2459
|
+
this.next();
|
|
2460
|
+
return { kind: "comparison", op: "=", left, right: this.parseValueExpr() };
|
|
2461
|
+
}
|
|
2462
|
+
if (opToken.type === "IDENT" && opToken.value === "eq") {
|
|
2463
|
+
this.next();
|
|
2464
|
+
return { kind: "comparison", op: "eq", left, right: this.parseValueExpr() };
|
|
2465
|
+
}
|
|
2466
|
+
throw new FormulaExpressionError(
|
|
2467
|
+
`Expected a comparison operator ("=" or "eq") after value expression, got "${opToken.value}"`,
|
|
2468
|
+
this.test,
|
|
2469
|
+
"unsupported-syntax"
|
|
2470
|
+
);
|
|
2471
|
+
}
|
|
2472
|
+
parseValueExpr() {
|
|
2473
|
+
const terms = [];
|
|
2474
|
+
let sign = 1;
|
|
2475
|
+
if (this.peek().type === "PLUS") {
|
|
2476
|
+
this.next();
|
|
2477
|
+
} else if (this.peek().type === "MINUS") {
|
|
2478
|
+
this.next();
|
|
2479
|
+
sign = -1;
|
|
2480
|
+
}
|
|
2481
|
+
terms.push({ sign, term: this.parseValueTerm() });
|
|
2482
|
+
while (this.peek().type === "PLUS" || this.peek().type === "MINUS") {
|
|
2483
|
+
const opSign = this.next().type === "PLUS" ? 1 : -1;
|
|
2484
|
+
terms.push({ sign: opSign, term: this.parseValueTerm() });
|
|
2485
|
+
}
|
|
2486
|
+
return terms.length === 1 && terms[0].sign === 1 ? terms[0].term : { kind: "additive", terms };
|
|
2487
|
+
}
|
|
2488
|
+
parseValueTerm() {
|
|
2489
|
+
const token = this.peek();
|
|
2490
|
+
if (token.type === "NUMBER") {
|
|
2491
|
+
this.next();
|
|
2492
|
+
return { kind: "number", value: Number(token.value) };
|
|
2493
|
+
}
|
|
2494
|
+
if (token.type === "VARIABLE") {
|
|
2495
|
+
this.next();
|
|
2496
|
+
return { kind: "variable", name: token.value };
|
|
2497
|
+
}
|
|
2498
|
+
if (token.type === "IDENT" && token.value === "sum") {
|
|
2499
|
+
this.next();
|
|
2500
|
+
this.expect("LPAREN");
|
|
2501
|
+
const variable = this.expect("VARIABLE").value;
|
|
2502
|
+
this.expect("RPAREN");
|
|
2503
|
+
return { kind: "sum", variable };
|
|
2504
|
+
}
|
|
2505
|
+
if (token.type === "LPAREN") {
|
|
2506
|
+
this.next();
|
|
2507
|
+
const inner = this.parseValueExpr();
|
|
2508
|
+
this.expect("RPAREN");
|
|
2509
|
+
return inner;
|
|
2510
|
+
}
|
|
2511
|
+
throw new FormulaExpressionError(
|
|
2512
|
+
`Expected a number, variable, sum(...), or parenthesized expression, got "${token.value}"`,
|
|
2513
|
+
this.test,
|
|
2514
|
+
"unsupported-syntax"
|
|
2515
|
+
);
|
|
2516
|
+
}
|
|
2517
|
+
}
|
|
2518
|
+
function lookup(bindings, name) {
|
|
2519
|
+
return bindings.get(name);
|
|
2520
|
+
}
|
|
2521
|
+
function evalSum(variable, bindings) {
|
|
2522
|
+
const binding = lookup(bindings, variable);
|
|
2523
|
+
if (binding === void 0)
|
|
2524
|
+
return 0;
|
|
2525
|
+
if (Array.isArray(binding))
|
|
2526
|
+
return binding.reduce((total, value) => total + value, 0);
|
|
2527
|
+
return binding;
|
|
2528
|
+
}
|
|
2529
|
+
function evalValue(node, bindings, test) {
|
|
2530
|
+
switch (node.kind) {
|
|
2531
|
+
case "number":
|
|
2532
|
+
return node.value;
|
|
2533
|
+
case "sum":
|
|
2534
|
+
return evalSum(node.variable, bindings);
|
|
2535
|
+
case "variable": {
|
|
2536
|
+
const binding = lookup(bindings, node.name);
|
|
2537
|
+
if (binding === void 0) {
|
|
2538
|
+
throw new FormulaExpressionError(
|
|
2539
|
+
`Variable "$${node.name}" has no bound fact and cannot be evaluated directly (only sum()/empty() tolerate an unbound variable)`,
|
|
2540
|
+
test,
|
|
2541
|
+
"unbound-variable"
|
|
2542
|
+
);
|
|
2543
|
+
}
|
|
2544
|
+
if (Array.isArray(binding)) {
|
|
2545
|
+
throw new FormulaExpressionError(
|
|
2546
|
+
`Variable "$${node.name}" is a sequence and must be wrapped in sum(...) to be used in arithmetic`,
|
|
2547
|
+
test,
|
|
2548
|
+
"unsupported-syntax"
|
|
2549
|
+
);
|
|
2550
|
+
}
|
|
2551
|
+
return binding;
|
|
2552
|
+
}
|
|
2553
|
+
case "additive":
|
|
2554
|
+
return node.terms.reduce((total, { sign, term }) => total + sign * evalValue(term, bindings, test), 0);
|
|
2555
|
+
}
|
|
2556
|
+
}
|
|
2557
|
+
function evalBool(node, bindings, test, fallbackUsage) {
|
|
2558
|
+
switch (node.kind) {
|
|
2559
|
+
case "or":
|
|
2560
|
+
return node.terms.some((term) => evalBool(term, bindings, test, fallbackUsage));
|
|
2561
|
+
case "and":
|
|
2562
|
+
return node.terms.every((term) => evalBool(term, bindings, test, fallbackUsage));
|
|
2563
|
+
case "not":
|
|
2564
|
+
return !evalBool(node.arg, bindings, test, fallbackUsage);
|
|
2565
|
+
case "empty": {
|
|
2566
|
+
const binding = lookup(bindings, node.variable);
|
|
2567
|
+
return binding === void 0 || Array.isArray(binding) && binding.length === 0;
|
|
2568
|
+
}
|
|
2569
|
+
case "hasFallbackValue": {
|
|
2570
|
+
const usedFallback = fallbackUsage.get(node.variableName);
|
|
2571
|
+
if (usedFallback === void 0) {
|
|
2572
|
+
throw new FormulaExpressionError(
|
|
2573
|
+
`xff:has-fallback-value(xs:QName('${node.variableName}')) could not be evaluated — no fallback-usage tracked for this variable (either not one of this assertion's FACT_VARIABLEs, or it matched zero facts with no fallbackValue declared)`,
|
|
2574
|
+
test,
|
|
2575
|
+
"unbound-variable"
|
|
2576
|
+
);
|
|
2577
|
+
}
|
|
2578
|
+
return usedFallback;
|
|
2579
|
+
}
|
|
2580
|
+
case "comparison": {
|
|
2581
|
+
const left = evalValue(node.left, bindings, test);
|
|
2582
|
+
const right = evalValue(node.right, bindings, test);
|
|
2583
|
+
return Math.abs(left - right) < CALCULATION_TOLERANCE;
|
|
2584
|
+
}
|
|
2585
|
+
}
|
|
2586
|
+
}
|
|
2587
|
+
function evaluateFormulaTest(test, bindings, fallbackUsage = /* @__PURE__ */ new Map()) {
|
|
2588
|
+
const tokens = tokenize(test);
|
|
2589
|
+
const ast = new Parser(tokens, test).parseBoolExpr();
|
|
2590
|
+
return evalBool(ast, bindings, test, fallbackUsage);
|
|
2591
|
+
}
|
|
2592
|
+
const EXISTENCE_TEST_PATTERN = /^\.\s*(eq|ne|gt|lt|ge|le)\s+(-?\d+(?:\.\d+)?)$/;
|
|
2593
|
+
function compareExistence(op, count, threshold) {
|
|
2594
|
+
switch (op) {
|
|
2595
|
+
case "eq":
|
|
2596
|
+
return count === threshold;
|
|
2597
|
+
case "ne":
|
|
2598
|
+
return count !== threshold;
|
|
2599
|
+
case "gt":
|
|
2600
|
+
return count > threshold;
|
|
2601
|
+
case "lt":
|
|
2602
|
+
return count < threshold;
|
|
2603
|
+
case "ge":
|
|
2604
|
+
return count >= threshold;
|
|
2605
|
+
case "le":
|
|
2606
|
+
return count <= threshold;
|
|
2607
|
+
}
|
|
2608
|
+
}
|
|
2609
|
+
function evaluateExistenceTest(test, matchedFactCount) {
|
|
2610
|
+
const trimmed = (test ?? "").trim();
|
|
2611
|
+
if (trimmed === "") {
|
|
2612
|
+
return matchedFactCount > 0;
|
|
2613
|
+
}
|
|
2614
|
+
const clauses = trimmed.split(/\bor\b/);
|
|
2615
|
+
return clauses.some((clause) => {
|
|
2616
|
+
const match = EXISTENCE_TEST_PATTERN.exec(clause.trim());
|
|
2617
|
+
if (!match) {
|
|
2618
|
+
throw new FormulaExpressionError(`Unsupported existence-assertion test shape: "${clause.trim()}"`, trimmed, "unsupported-syntax");
|
|
2619
|
+
}
|
|
2620
|
+
const [, op, thresholdText] = match;
|
|
2621
|
+
return compareExistence(op, matchedFactCount, Number(thresholdText));
|
|
2622
|
+
});
|
|
2623
|
+
}
|
|
2624
|
+
function isTotalLabel(preferredLabel) {
|
|
2625
|
+
return !!(preferredLabel == null ? void 0 : preferredLabel.toLowerCase().includes("totallabel"));
|
|
2626
|
+
}
|
|
2627
|
+
function isNegatedTotalLabel(preferredLabel) {
|
|
2628
|
+
return !!(preferredLabel == null ? void 0 : preferredLabel.toLowerCase().includes("negatedtotallabel"));
|
|
2629
|
+
}
|
|
2630
|
+
function resolveValueNode(node, accessors, depth = 0) {
|
|
2631
|
+
if (!accessors.isAbstract(node))
|
|
2632
|
+
return node;
|
|
2633
|
+
if (depth > 5)
|
|
2634
|
+
return null;
|
|
2635
|
+
const children = accessors.getChildren(node);
|
|
2636
|
+
const nestedTotal = children.find((child) => isTotalLabel(accessors.getPreferredLabel(child)));
|
|
2637
|
+
if (!nestedTotal)
|
|
2638
|
+
return null;
|
|
2639
|
+
return resolveValueNode(nestedTotal, accessors, depth + 1);
|
|
2640
|
+
}
|
|
2641
|
+
function resolveTotalGroupMembers(nodes, i2, lastTotalIdx, rawSiblings, accessors) {
|
|
2642
|
+
if (lastTotalIdx < 0)
|
|
2643
|
+
return rawSiblings;
|
|
2644
|
+
const node = nodes[i2];
|
|
2645
|
+
if (isNegatedTotalLabel(accessors.getPreferredLabel(node))) {
|
|
2646
|
+
return rawSiblings.length > 0 ? rawSiblings : [nodes[lastTotalIdx]];
|
|
2647
|
+
}
|
|
2648
|
+
if (rawSiblings.length > 0) {
|
|
2649
|
+
return [nodes[lastTotalIdx], ...rawSiblings];
|
|
2650
|
+
}
|
|
2651
|
+
if (isNegatedTotalLabel(accessors.getPreferredLabel(nodes[lastTotalIdx]))) {
|
|
2652
|
+
let grandTotalIdx = -1;
|
|
2653
|
+
for (let k = lastTotalIdx - 1; k >= 0; k--) {
|
|
2654
|
+
if (isTotalLabel(accessors.getPreferredLabel(nodes[k]))) {
|
|
2655
|
+
grandTotalIdx = k;
|
|
2656
|
+
break;
|
|
2657
|
+
}
|
|
2658
|
+
}
|
|
2659
|
+
return grandTotalIdx >= 0 ? [nodes[grandTotalIdx], nodes[lastTotalIdx]] : [nodes[lastTotalIdx]];
|
|
2660
|
+
}
|
|
2661
|
+
return [nodes[lastTotalIdx]];
|
|
2662
|
+
}
|
|
2663
|
+
function buildTotalGroupChildrenIndex(roots, accessors) {
|
|
2664
|
+
const index = /* @__PURE__ */ new Map();
|
|
2665
|
+
function registerGroup(totalNode, members) {
|
|
2666
|
+
const resolvedIds = [];
|
|
2667
|
+
for (const member of members) {
|
|
2668
|
+
const resolved = resolveValueNode(member, accessors);
|
|
2669
|
+
if (resolved)
|
|
2670
|
+
resolvedIds.push(accessors.getId(resolved));
|
|
2671
|
+
}
|
|
2672
|
+
if (resolvedIds.length === 0)
|
|
2673
|
+
return;
|
|
2674
|
+
index.set(accessors.getId(totalNode), resolvedIds);
|
|
2675
|
+
}
|
|
2676
|
+
function traverse(nodes) {
|
|
2677
|
+
for (let i2 = 0; i2 < nodes.length; i2++) {
|
|
2678
|
+
const node = nodes[i2];
|
|
2679
|
+
if (isTotalLabel(accessors.getPreferredLabel(node))) {
|
|
2680
|
+
const children2 = accessors.getChildren(node);
|
|
2681
|
+
if (children2.length === 0) {
|
|
2682
|
+
let lastTotalIdx = -1;
|
|
2683
|
+
for (let j = i2 - 1; j >= 0; j--) {
|
|
2684
|
+
if (isTotalLabel(accessors.getPreferredLabel(nodes[j]))) {
|
|
2685
|
+
lastTotalIdx = j;
|
|
2686
|
+
break;
|
|
2687
|
+
}
|
|
2688
|
+
}
|
|
2689
|
+
const rawSiblings = nodes.slice(lastTotalIdx + 1, i2);
|
|
2690
|
+
const members = resolveTotalGroupMembers(nodes, i2, lastTotalIdx, rawSiblings, accessors);
|
|
2691
|
+
if (members.length > 0)
|
|
2692
|
+
registerGroup(node, members);
|
|
2693
|
+
}
|
|
2694
|
+
}
|
|
2695
|
+
const children = accessors.getChildren(node);
|
|
2696
|
+
if (children.length > 0)
|
|
2697
|
+
traverse(children);
|
|
2698
|
+
}
|
|
2699
|
+
}
|
|
2700
|
+
traverse(roots);
|
|
2701
|
+
return index;
|
|
2702
|
+
}
|
|
2703
|
+
function isNonEmptyRawValue(rawValue) {
|
|
2704
|
+
return rawValue !== void 0 && rawValue !== null && rawValue !== "";
|
|
2705
|
+
}
|
|
2706
|
+
function collectAllCandidates(formData) {
|
|
2707
|
+
const candidates = [];
|
|
2708
|
+
for (const conceptId of Object.keys(formData)) {
|
|
2709
|
+
const columnValues = formData[conceptId] || {};
|
|
2710
|
+
for (const columnId of Object.keys(columnValues)) {
|
|
2711
|
+
if (isNonEmptyRawValue(columnValues[columnId])) {
|
|
2712
|
+
candidates.push({ conceptId, columnId });
|
|
2713
|
+
}
|
|
2714
|
+
}
|
|
2715
|
+
}
|
|
2716
|
+
return candidates;
|
|
2717
|
+
}
|
|
2718
|
+
function indexConceptTree(concept, conceptByQName, conceptById, childrenIndex) {
|
|
2719
|
+
const info = {
|
|
2720
|
+
conceptId: concept.id,
|
|
2721
|
+
qname: concept.conceptName,
|
|
2722
|
+
balance: concept.balance
|
|
2723
|
+
};
|
|
2724
|
+
if (!conceptById.has(concept.id))
|
|
2725
|
+
conceptById.set(concept.id, info);
|
|
2726
|
+
if (!conceptByQName.has(concept.conceptName))
|
|
2727
|
+
conceptByQName.set(concept.conceptName, info);
|
|
2728
|
+
const children = concept.children || [];
|
|
2729
|
+
childrenIndex.set(
|
|
2730
|
+
concept.id,
|
|
2731
|
+
children.map((child) => child.id)
|
|
2732
|
+
);
|
|
2733
|
+
children.forEach((child) => indexConceptTree(child, conceptByQName, conceptById, childrenIndex));
|
|
2734
|
+
}
|
|
2735
|
+
function indexMemberTree(member, memberQNameToId) {
|
|
2736
|
+
if (!memberQNameToId.has(member.conceptName))
|
|
2737
|
+
memberQNameToId.set(member.conceptName, member.id);
|
|
2738
|
+
(member.children || []).forEach((child) => indexMemberTree(child, memberQNameToId));
|
|
2739
|
+
}
|
|
2740
|
+
const PRESENTATION_TOTAL_GROUP_ACCESSORS = {
|
|
2741
|
+
getId: (concept) => concept.id,
|
|
2742
|
+
getPreferredLabel: (concept) => concept.preferredLabel,
|
|
2743
|
+
isAbstract: (concept) => concept.elementAbstract,
|
|
2744
|
+
getChildren: (concept) => concept.children || []
|
|
2745
|
+
};
|
|
2746
|
+
function buildFormulaResolutionContext(formData, columns, presentationRoles, hypercubeRoles, periodStartDate, periodEndDate) {
|
|
2747
|
+
const conceptByQName = /* @__PURE__ */ new Map();
|
|
2748
|
+
const conceptById = /* @__PURE__ */ new Map();
|
|
2749
|
+
const childrenByRole = /* @__PURE__ */ new Map();
|
|
2750
|
+
const totalGroupChildrenByRole = /* @__PURE__ */ new Map();
|
|
2751
|
+
presentationRoles.forEach((role) => {
|
|
2752
|
+
var _a;
|
|
2753
|
+
const concepts = ((_a = role.presentationLinkbase) == null ? void 0 : _a.concepts) || [];
|
|
2754
|
+
const childrenIndex = /* @__PURE__ */ new Map();
|
|
2755
|
+
concepts.forEach((concept) => indexConceptTree(concept, conceptByQName, conceptById, childrenIndex));
|
|
2756
|
+
childrenByRole.set(role.roleURI, childrenIndex);
|
|
2757
|
+
totalGroupChildrenByRole.set(role.roleURI, buildTotalGroupChildrenIndex(concepts, PRESENTATION_TOTAL_GROUP_ACCESSORS));
|
|
2758
|
+
});
|
|
2759
|
+
const dimensionQNameToId = /* @__PURE__ */ new Map();
|
|
2760
|
+
const memberQNameToId = /* @__PURE__ */ new Map();
|
|
2761
|
+
(hypercubeRoles || []).forEach((role) => {
|
|
2762
|
+
role.items.forEach((item) => {
|
|
2763
|
+
item.dimensions.forEach((dimension) => {
|
|
2764
|
+
if (!dimensionQNameToId.has(dimension.conceptName)) {
|
|
2765
|
+
dimensionQNameToId.set(dimension.conceptName, dimension.id);
|
|
2766
|
+
}
|
|
2767
|
+
(dimension.members || []).forEach((member) => indexMemberTree(member, memberQNameToId));
|
|
2768
|
+
});
|
|
2769
|
+
});
|
|
2770
|
+
});
|
|
2771
|
+
return {
|
|
2772
|
+
formData,
|
|
2773
|
+
columns,
|
|
2774
|
+
periodStartDate,
|
|
2775
|
+
periodEndDate,
|
|
2776
|
+
conceptByQName,
|
|
2777
|
+
conceptById,
|
|
2778
|
+
childrenByRole,
|
|
2779
|
+
totalGroupChildrenByRole,
|
|
2780
|
+
dimensionQNameToId,
|
|
2781
|
+
memberQNameToId,
|
|
2782
|
+
allCandidates: collectAllCandidates(formData)
|
|
2783
|
+
};
|
|
2784
|
+
}
|
|
2785
|
+
function collectDescendantConceptIds(childrenIndex, rootConceptId) {
|
|
2786
|
+
const result = [];
|
|
2787
|
+
const stack = [...childrenIndex.get(rootConceptId) || []];
|
|
2788
|
+
const seen = /* @__PURE__ */ new Set();
|
|
2789
|
+
while (stack.length > 0) {
|
|
2790
|
+
const conceptId = stack.pop();
|
|
2791
|
+
if (seen.has(conceptId))
|
|
2792
|
+
continue;
|
|
2793
|
+
seen.add(conceptId);
|
|
2794
|
+
result.push(conceptId);
|
|
2795
|
+
stack.push(...childrenIndex.get(conceptId) || []);
|
|
2796
|
+
}
|
|
2797
|
+
return result;
|
|
2798
|
+
}
|
|
2799
|
+
function candidateKey(candidate) {
|
|
2800
|
+
return `${candidate.conceptId}::${candidate.columnId}`;
|
|
2801
|
+
}
|
|
2802
|
+
function resolveMatchedCandidates(variable, ctx) {
|
|
2803
|
+
return intersectCandidates(variable.filters.map((filter2) => resolveFilter(filter2, ctx.allCandidates, ctx)));
|
|
2804
|
+
}
|
|
2805
|
+
function getColumn(ctx, columnId) {
|
|
2806
|
+
return ctx.columns.find((column2) => column2.id === columnId);
|
|
2807
|
+
}
|
|
2808
|
+
function columnMatchesExplicitDimension(column2, axisId, memberId) {
|
|
2809
|
+
if (!(column2 == null ? void 0 : column2.dimensionData))
|
|
2810
|
+
return false;
|
|
2811
|
+
const primaryMatch = column2.dimensionData.axisId === axisId && (memberId === void 0 || column2.dimensionData.memberId === memberId);
|
|
2812
|
+
if (primaryMatch)
|
|
2813
|
+
return true;
|
|
2814
|
+
return (column2.dimensionData.combinations || []).some(
|
|
2815
|
+
(combo) => combo.axisId === axisId && (memberId === void 0 || combo.memberId === memberId)
|
|
2816
|
+
);
|
|
2817
|
+
}
|
|
2818
|
+
function columnMatchesTypedDimension(column2, axisId) {
|
|
2819
|
+
if (!(column2 == null ? void 0 : column2.dimensionData))
|
|
2820
|
+
return false;
|
|
2821
|
+
if (column2.dimensionData.typedMemberId !== void 0 && column2.dimensionData.axisId === axisId)
|
|
2822
|
+
return true;
|
|
2823
|
+
return (column2.dimensionData.typedMembers || []).some((typedMember) => typedMember.axisId === axisId);
|
|
2824
|
+
}
|
|
2825
|
+
function paramTokenName(rawDate) {
|
|
2826
|
+
if (!rawDate)
|
|
2827
|
+
return void 0;
|
|
2828
|
+
return rawDate.startsWith("$") ? rawDate.slice(1) : rawDate;
|
|
2829
|
+
}
|
|
2830
|
+
function resolveParamDate(paramToken, ctx) {
|
|
2831
|
+
const isStart = paramToken.includes("StartDate");
|
|
2832
|
+
const isEnd = paramToken.includes("EndDate") || paramToken === "FinancialReportingPeriodCurrentEndDateParam";
|
|
2833
|
+
if (paramToken.startsWith("FinancialReportingPeriodCurrent")) {
|
|
2834
|
+
return isStart ? { start: ctx.periodStartDate } : isEnd ? { end: ctx.periodEndDate } : void 0;
|
|
2835
|
+
}
|
|
2836
|
+
if (paramToken.startsWith("FinancialReportingPeriodPrePrevious") || paramToken.startsWith("FinancialReportingPeriodPrevious")) {
|
|
2837
|
+
const previousYearColumn = findPreviousYearColumn(ctx);
|
|
2838
|
+
if (!previousYearColumn)
|
|
2839
|
+
return void 0;
|
|
2840
|
+
return isStart ? { start: previousYearColumn.periodStartDate } : isEnd ? { end: previousYearColumn.periodEndDate } : void 0;
|
|
2841
|
+
}
|
|
2842
|
+
return void 0;
|
|
2843
|
+
}
|
|
2844
|
+
function findPreviousYearColumn(ctx) {
|
|
2845
|
+
return ctx.columns.find((column2) => column2.periodEndDate !== void 0 && column2.periodEndDate < ctx.periodEndDate);
|
|
2846
|
+
}
|
|
2847
|
+
function columnEffectivePeriod(column2, ctx) {
|
|
2848
|
+
return {
|
|
2849
|
+
start: (column2 == null ? void 0 : column2.periodStartDate) ?? ctx.periodStartDate,
|
|
2850
|
+
end: (column2 == null ? void 0 : column2.periodEndDate) ?? ctx.periodEndDate
|
|
2851
|
+
};
|
|
2852
|
+
}
|
|
2853
|
+
function columnMatchesPeriod(column2, dateAttribute, ctx) {
|
|
2854
|
+
const paramToken = paramTokenName(dateAttribute);
|
|
2855
|
+
if (!paramToken)
|
|
2856
|
+
return false;
|
|
2857
|
+
const resolved = resolveParamDate(paramToken, ctx);
|
|
2858
|
+
if (!resolved)
|
|
2859
|
+
return false;
|
|
2860
|
+
const period = columnEffectivePeriod(column2, ctx);
|
|
2861
|
+
const targetDate = resolved.end ?? resolved.start;
|
|
2862
|
+
return period.end === targetDate;
|
|
2863
|
+
}
|
|
2864
|
+
function unionCandidates(lists) {
|
|
2865
|
+
const merged = /* @__PURE__ */ new Map();
|
|
2866
|
+
lists.forEach((list) => list.forEach((candidate) => merged.set(candidateKey(candidate), candidate)));
|
|
2867
|
+
return Array.from(merged.values());
|
|
2868
|
+
}
|
|
2869
|
+
function matchFilter(filter2, universe, ctx) {
|
|
2870
|
+
var _a;
|
|
2871
|
+
switch (filter2.type) {
|
|
2872
|
+
case "CONCEPT_NAME": {
|
|
2873
|
+
const qname = filter2.attributes["concept.qname"];
|
|
2874
|
+
const info = qname ? ctx.conceptByQName.get(qname) : void 0;
|
|
2875
|
+
if (!info)
|
|
2876
|
+
return [];
|
|
2877
|
+
return universe.filter((candidate) => candidate.conceptId === info.conceptId);
|
|
2878
|
+
}
|
|
2879
|
+
case "CONCEPT_BALANCE": {
|
|
2880
|
+
const balance = filter2.attributes["balance"];
|
|
2881
|
+
return universe.filter((candidate) => {
|
|
2882
|
+
var _a2;
|
|
2883
|
+
return ((_a2 = ctx.conceptById.get(candidate.conceptId)) == null ? void 0 : _a2.balance) === balance;
|
|
2884
|
+
});
|
|
2885
|
+
}
|
|
2886
|
+
case "CONCEPT_RELATION": {
|
|
2887
|
+
const anchorQName = filter2.attributes["qname"];
|
|
2888
|
+
const linkrole = filter2.attributes["linkrole"];
|
|
2889
|
+
const axis = filter2.attributes["axis"];
|
|
2890
|
+
const anchorInfo = anchorQName ? ctx.conceptByQName.get(anchorQName) : void 0;
|
|
2891
|
+
const childrenIndex = linkrole ? ctx.childrenByRole.get(linkrole) : void 0;
|
|
2892
|
+
if (!anchorInfo || !childrenIndex)
|
|
2893
|
+
return [];
|
|
2894
|
+
let relatedConceptIds;
|
|
2895
|
+
if (axis === "descendant") {
|
|
2896
|
+
relatedConceptIds = collectDescendantConceptIds(childrenIndex, anchorInfo.conceptId);
|
|
2897
|
+
} else {
|
|
2898
|
+
const nestedChildren = childrenIndex.get(anchorInfo.conceptId) || [];
|
|
2899
|
+
relatedConceptIds = nestedChildren.length > 0 ? nestedChildren : ((_a = ctx.totalGroupChildrenByRole.get(linkrole ?? "")) == null ? void 0 : _a.get(anchorInfo.conceptId)) || [];
|
|
2900
|
+
}
|
|
2901
|
+
const relatedSet = new Set(relatedConceptIds);
|
|
2902
|
+
return universe.filter((candidate) => relatedSet.has(candidate.conceptId));
|
|
2903
|
+
}
|
|
2904
|
+
case "EXPLICIT_DIMENSION": {
|
|
2905
|
+
const dimensionQName = filter2.attributes["dimension.qname"];
|
|
2906
|
+
const memberQName = filter2.attributes["member.qname"];
|
|
2907
|
+
const axisId = dimensionQName ? ctx.dimensionQNameToId.get(dimensionQName) : void 0;
|
|
2908
|
+
const memberId = memberQName ? ctx.memberQNameToId.get(memberQName) : void 0;
|
|
2909
|
+
if (!axisId)
|
|
2910
|
+
return [];
|
|
2911
|
+
return universe.filter((candidate) => columnMatchesExplicitDimension(getColumn(ctx, candidate.columnId), axisId, memberId));
|
|
2912
|
+
}
|
|
2913
|
+
case "TYPED_DIMENSION": {
|
|
2914
|
+
const dimensionQName = filter2.attributes["dimension.qname"];
|
|
2915
|
+
const axisId = dimensionQName ? ctx.dimensionQNameToId.get(dimensionQName) : void 0;
|
|
2916
|
+
if (!axisId)
|
|
2917
|
+
return [];
|
|
2918
|
+
return universe.filter((candidate) => columnMatchesTypedDimension(getColumn(ctx, candidate.columnId), axisId));
|
|
2919
|
+
}
|
|
2920
|
+
case "PERIOD_INSTANT":
|
|
2921
|
+
case "PERIOD_END": {
|
|
2922
|
+
const dateAttribute = filter2.attributes["date"];
|
|
2923
|
+
return universe.filter((candidate) => columnMatchesPeriod(getColumn(ctx, candidate.columnId), dateAttribute, ctx));
|
|
2924
|
+
}
|
|
2925
|
+
case "OR_FILTER":
|
|
2926
|
+
return unionCandidates(filter2.children.map((child) => resolveFilter(child, universe, ctx)));
|
|
2927
|
+
default:
|
|
2928
|
+
return [];
|
|
2929
|
+
}
|
|
2930
|
+
}
|
|
2931
|
+
function resolveFilter(filter2, universe, ctx) {
|
|
2932
|
+
const matched = matchFilter(filter2, universe, ctx);
|
|
2933
|
+
if (!filter2.complement)
|
|
2934
|
+
return matched;
|
|
2935
|
+
const matchedKeys = new Set(matched.map(candidateKey));
|
|
2936
|
+
return universe.filter((candidate) => !matchedKeys.has(candidateKey(candidate)));
|
|
2937
|
+
}
|
|
2938
|
+
function intersectCandidates(sets) {
|
|
2939
|
+
if (sets.length === 0)
|
|
2940
|
+
return [];
|
|
2941
|
+
return sets.reduce((acc, set) => {
|
|
2942
|
+
const setKeys = new Set(set.map(candidateKey));
|
|
2943
|
+
return acc.filter((candidate) => setKeys.has(candidateKey(candidate)));
|
|
2944
|
+
});
|
|
2945
|
+
}
|
|
2946
|
+
function resolveFormulaVariable(variable, ctx) {
|
|
2947
|
+
const matched = resolveMatchedCandidates(variable, ctx);
|
|
2948
|
+
const values = matched.map((candidate) => {
|
|
2949
|
+
var _a;
|
|
2950
|
+
return parseFloat((_a = ctx.formData[candidate.conceptId]) == null ? void 0 : _a[candidate.columnId]);
|
|
2951
|
+
}).filter((value) => !Number.isNaN(value));
|
|
2952
|
+
if (variable.bindAsSequence) {
|
|
2953
|
+
if (values.length === 0 && variable.fallbackValue === "()")
|
|
2954
|
+
return [];
|
|
2955
|
+
if (values.length === 0)
|
|
2956
|
+
return void 0;
|
|
2957
|
+
return values;
|
|
2958
|
+
}
|
|
2959
|
+
if (values.length === 0)
|
|
2960
|
+
return void 0;
|
|
2961
|
+
if (values.length > 1) {
|
|
2962
|
+
console.warn(
|
|
2963
|
+
`[formula-variable-resolver] Variable "${variable.name}" is scalar (bindAsSequence: false) but matched ${values.length} facts; using the first match by column order. This can legitimately happen when filters under-constrain the candidate set.`
|
|
2964
|
+
);
|
|
2965
|
+
}
|
|
2966
|
+
return values[0];
|
|
2967
|
+
}
|
|
2968
|
+
function resolveFormulaVariableMatchCount(variable, ctx) {
|
|
2969
|
+
return resolveMatchedCandidates(variable, ctx).length;
|
|
2970
|
+
}
|
|
2971
|
+
function resolveFormulaVariableUsedFallback(variable, ctx) {
|
|
2972
|
+
const matchCount = resolveFormulaVariableMatchCount(variable, ctx);
|
|
2973
|
+
if (matchCount > 0)
|
|
2974
|
+
return false;
|
|
2975
|
+
if (variable.fallbackValue !== void 0)
|
|
2976
|
+
return true;
|
|
2977
|
+
return void 0;
|
|
2978
|
+
}
|
|
2979
|
+
function buildAssertionBindings(assertion, ctx) {
|
|
2980
|
+
const bindings = /* @__PURE__ */ new Map();
|
|
2981
|
+
for (const variable of assertion.variables) {
|
|
2982
|
+
bindings.set(variable.name, resolveFormulaVariable(variable, ctx));
|
|
2983
|
+
}
|
|
2984
|
+
return bindings;
|
|
2985
|
+
}
|
|
2986
|
+
function buildAssertionFallbackUsage(assertion, ctx) {
|
|
2987
|
+
var _a;
|
|
2988
|
+
const usesHasFallbackValue = ((_a = assertion.test) == null ? void 0 : _a.includes("has-fallback-value")) || assertion.preconditions.some((precondition) => precondition.test.includes("has-fallback-value"));
|
|
2989
|
+
if (!usesHasFallbackValue)
|
|
2990
|
+
return /* @__PURE__ */ new Map();
|
|
2991
|
+
const fallbackUsage = /* @__PURE__ */ new Map();
|
|
2992
|
+
for (const variable of assertion.variables) {
|
|
2993
|
+
const usedFallback = resolveFormulaVariableUsedFallback(variable, ctx);
|
|
2994
|
+
if (usedFallback !== void 0)
|
|
2995
|
+
fallbackUsage.set(variable.name, usedFallback);
|
|
2996
|
+
}
|
|
2997
|
+
return fallbackUsage;
|
|
2998
|
+
}
|
|
2999
|
+
function evaluateAssertionPreconditions(preconditions, bindings, fallbackUsage = /* @__PURE__ */ new Map()) {
|
|
3000
|
+
if (preconditions.length === 0)
|
|
3001
|
+
return { satisfied: true };
|
|
3002
|
+
for (const precondition of preconditions) {
|
|
3003
|
+
let result;
|
|
3004
|
+
try {
|
|
3005
|
+
result = evaluateFormulaTest(precondition.test, bindings, fallbackUsage);
|
|
3006
|
+
} catch (error2) {
|
|
3007
|
+
if (error2 instanceof FormulaExpressionError) {
|
|
3008
|
+
return { satisfied: false, skipReason: "unresolvable" };
|
|
3009
|
+
}
|
|
3010
|
+
throw error2;
|
|
3011
|
+
}
|
|
3012
|
+
if (!result) {
|
|
3013
|
+
return { satisfied: false, skipReason: "precondition" };
|
|
3014
|
+
}
|
|
3015
|
+
}
|
|
3016
|
+
return { satisfied: true };
|
|
3017
|
+
}
|
|
3018
|
+
class FormulaValidationService {
|
|
3019
|
+
/**
|
|
3020
|
+
* Evaluates every assertion in `xbrlInput.formula[0].roles` (only the first entrypoint,
|
|
3021
|
+
* consistent with how xbrl-form-builder.ts uses presentation/hypercube data) against the
|
|
3022
|
+
* given resolution context. One bad assertion never aborts the other 783 — resolution/
|
|
3023
|
+
* evaluation errors are caught per-assertion and recorded as skipped, not thrown.
|
|
3024
|
+
*/
|
|
3025
|
+
evaluate(xbrlInput, ctx, language) {
|
|
3026
|
+
var _a;
|
|
3027
|
+
const formulaData = (_a = xbrlInput.formula) == null ? void 0 : _a[0];
|
|
3028
|
+
if (!formulaData)
|
|
3029
|
+
return [];
|
|
3030
|
+
const results = [];
|
|
3031
|
+
for (const role of formulaData.roles) {
|
|
3032
|
+
for (const assertion of role.assertions) {
|
|
3033
|
+
results.push(this._evaluateAssertion(assertion, role, ctx, language));
|
|
3034
|
+
}
|
|
3035
|
+
}
|
|
3036
|
+
return results;
|
|
3037
|
+
}
|
|
3038
|
+
summarize(results) {
|
|
3039
|
+
const summary = {
|
|
3040
|
+
totalAssertions: results.length,
|
|
3041
|
+
evaluated: 0,
|
|
3042
|
+
skipped: 0,
|
|
3043
|
+
passed: 0,
|
|
3044
|
+
failed: 0,
|
|
3045
|
+
failedWarnings: 0,
|
|
3046
|
+
failedErrors: 0
|
|
3047
|
+
};
|
|
3048
|
+
for (const result of results) {
|
|
3049
|
+
if (result.skipped) {
|
|
3050
|
+
summary.skipped += 1;
|
|
3051
|
+
continue;
|
|
3052
|
+
}
|
|
3053
|
+
summary.evaluated += 1;
|
|
3054
|
+
if (result.satisfied) {
|
|
3055
|
+
summary.passed += 1;
|
|
3056
|
+
} else {
|
|
3057
|
+
summary.failed += 1;
|
|
3058
|
+
if (result.severity === "ERROR")
|
|
3059
|
+
summary.failedErrors += 1;
|
|
3060
|
+
else
|
|
3061
|
+
summary.failedWarnings += 1;
|
|
3062
|
+
}
|
|
3063
|
+
}
|
|
3064
|
+
return summary;
|
|
3065
|
+
}
|
|
3066
|
+
_evaluateAssertion(assertion, role, ctx, language) {
|
|
3067
|
+
try {
|
|
3068
|
+
const bindings = buildAssertionBindings(assertion, ctx);
|
|
3069
|
+
const fallbackUsage = buildAssertionFallbackUsage(assertion, ctx);
|
|
3070
|
+
const precondition = evaluateAssertionPreconditions(assertion.preconditions, bindings, fallbackUsage);
|
|
3071
|
+
if (!precondition.satisfied) {
|
|
3072
|
+
return this._skippedResult(assertion, role, precondition.skipReason ?? "unresolvable");
|
|
3073
|
+
}
|
|
3074
|
+
if (assertion.type === "EXISTENCE_ASSERTION") {
|
|
3075
|
+
const matchedFactCount = resolveFormulaVariableMatchCount(assertion.variables[0], ctx);
|
|
3076
|
+
const satisfied2 = evaluateExistenceTest(assertion.test, matchedFactCount);
|
|
3077
|
+
return this._evaluatedResult(assertion, role, satisfied2, language, matchedFactCount);
|
|
3078
|
+
}
|
|
3079
|
+
const satisfied = evaluateFormulaTest(assertion.test, bindings, fallbackUsage);
|
|
3080
|
+
return this._evaluatedResult(assertion, role, satisfied, language);
|
|
3081
|
+
} catch (error2) {
|
|
3082
|
+
if (error2 instanceof FormulaExpressionError) {
|
|
3083
|
+
console.warn(`[FormulaValidationService] Assertion "${assertion.id}" could not be evaluated (${error2.reason}): ${error2.message}`);
|
|
3084
|
+
return this._skippedResult(assertion, role, "unresolvable");
|
|
3085
|
+
}
|
|
3086
|
+
throw error2;
|
|
3087
|
+
}
|
|
3088
|
+
}
|
|
3089
|
+
_skippedResult(assertion, role, skipReason) {
|
|
3090
|
+
return {
|
|
3091
|
+
assertionId: assertion.id,
|
|
3092
|
+
roleURI: role.roleURI,
|
|
3093
|
+
roleLabel: role.role,
|
|
3094
|
+
type: assertion.type,
|
|
3095
|
+
severity: assertion.severity,
|
|
3096
|
+
satisfied: false,
|
|
3097
|
+
skipped: true,
|
|
3098
|
+
skipReason
|
|
3099
|
+
};
|
|
3100
|
+
}
|
|
3101
|
+
_evaluatedResult(assertion, role, satisfied, language, matchedFactCount) {
|
|
3102
|
+
return {
|
|
3103
|
+
assertionId: assertion.id,
|
|
3104
|
+
roleURI: role.roleURI,
|
|
3105
|
+
roleLabel: role.role,
|
|
3106
|
+
type: assertion.type,
|
|
3107
|
+
severity: assertion.severity,
|
|
3108
|
+
satisfied,
|
|
3109
|
+
skipped: false,
|
|
3110
|
+
message: satisfied ? void 0 : this._pickMessage(assertion, language),
|
|
3111
|
+
matchedFactCount
|
|
3112
|
+
};
|
|
3113
|
+
}
|
|
3114
|
+
_pickMessage(assertion, language) {
|
|
3115
|
+
const messages = assertion.messages;
|
|
3116
|
+
if (messages.length === 0)
|
|
3117
|
+
return void 0;
|
|
3118
|
+
const message = messages.find((m) => m.xmlLang === language) ?? messages.find((m) => m.xmlLang === "en") ?? messages[0];
|
|
3119
|
+
return message.text;
|
|
3120
|
+
}
|
|
3121
|
+
}
|
|
2303
3122
|
class FactMatcher {
|
|
2304
3123
|
/**
|
|
2305
3124
|
* Find a matching fact for a given cell context
|
|
@@ -3153,15 +3972,15 @@ function determineInputTypeFromBaseChain(baseTypeChain, datatypes) {
|
|
|
3153
3972
|
placeholder: I18n.t("field.enterValue")
|
|
3154
3973
|
};
|
|
3155
3974
|
}
|
|
3156
|
-
var __defProp$
|
|
3157
|
-
var __getOwnPropDesc$
|
|
3158
|
-
var __decorateClass$
|
|
3159
|
-
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$
|
|
3975
|
+
var __defProp$7 = Object.defineProperty;
|
|
3976
|
+
var __getOwnPropDesc$7 = Object.getOwnPropertyDescriptor;
|
|
3977
|
+
var __decorateClass$7 = (decorators, target, key, kind) => {
|
|
3978
|
+
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$7(target, key) : target;
|
|
3160
3979
|
for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
|
|
3161
3980
|
if (decorator = decorators[i2])
|
|
3162
3981
|
result = (kind ? decorator(target, key, result) : decorator(result)) || result;
|
|
3163
3982
|
if (kind && result)
|
|
3164
|
-
__defProp$
|
|
3983
|
+
__defProp$7(target, key, result);
|
|
3165
3984
|
return result;
|
|
3166
3985
|
};
|
|
3167
3986
|
let JupiterFormField = class extends LitElement {
|
|
@@ -4178,6 +4997,7 @@ let JupiterFormField = class extends LitElement {
|
|
|
4178
4997
|
<button
|
|
4179
4998
|
class="period-icon-btn"
|
|
4180
4999
|
type="button"
|
|
5000
|
+
tabindex="-1"
|
|
4181
5001
|
@click="${this._handlePeriodIconClick}"
|
|
4182
5002
|
title="Edit period"
|
|
4183
5003
|
>
|
|
@@ -4674,99 +5494,99 @@ JupiterFormField.styles = css`
|
|
|
4674
5494
|
animation: concept-highlight-pulse 10s ease-out forwards;
|
|
4675
5495
|
}
|
|
4676
5496
|
`;
|
|
4677
|
-
__decorateClass$
|
|
5497
|
+
__decorateClass$7([
|
|
4678
5498
|
n2({ type: Object })
|
|
4679
5499
|
], JupiterFormField.prototype, "field", 2);
|
|
4680
|
-
__decorateClass$
|
|
5500
|
+
__decorateClass$7([
|
|
4681
5501
|
n2({ type: String })
|
|
4682
5502
|
], JupiterFormField.prototype, "conceptId", 2);
|
|
4683
|
-
__decorateClass$
|
|
5503
|
+
__decorateClass$7([
|
|
4684
5504
|
n2({ type: String })
|
|
4685
5505
|
], JupiterFormField.prototype, "conceptType", 2);
|
|
4686
|
-
__decorateClass$
|
|
5506
|
+
__decorateClass$7([
|
|
4687
5507
|
n2({ type: Array })
|
|
4688
5508
|
], JupiterFormField.prototype, "datatypes", 2);
|
|
4689
|
-
__decorateClass$
|
|
5509
|
+
__decorateClass$7([
|
|
4690
5510
|
n2({ type: Array })
|
|
4691
5511
|
], JupiterFormField.prototype, "defaultUnits", 2);
|
|
4692
|
-
__decorateClass$
|
|
5512
|
+
__decorateClass$7([
|
|
4693
5513
|
n2({ type: String })
|
|
4694
5514
|
], JupiterFormField.prototype, "columnId", 2);
|
|
4695
|
-
__decorateClass$
|
|
5515
|
+
__decorateClass$7([
|
|
4696
5516
|
n2()
|
|
4697
5517
|
], JupiterFormField.prototype, "value", 2);
|
|
4698
|
-
__decorateClass$
|
|
5518
|
+
__decorateClass$7([
|
|
4699
5519
|
n2({ type: Boolean })
|
|
4700
5520
|
], JupiterFormField.prototype, "disabled", 2);
|
|
4701
|
-
__decorateClass$
|
|
5521
|
+
__decorateClass$7([
|
|
4702
5522
|
n2({ type: String })
|
|
4703
5523
|
], JupiterFormField.prototype, "locale", 2);
|
|
4704
|
-
__decorateClass$
|
|
5524
|
+
__decorateClass$7([
|
|
4705
5525
|
n2({ type: Boolean })
|
|
4706
5526
|
], JupiterFormField.prototype, "hideLabel", 2);
|
|
4707
|
-
__decorateClass$
|
|
5527
|
+
__decorateClass$7([
|
|
4708
5528
|
n2({ type: String })
|
|
4709
5529
|
], JupiterFormField.prototype, "mode", 2);
|
|
4710
|
-
__decorateClass$
|
|
5530
|
+
__decorateClass$7([
|
|
4711
5531
|
n2({ type: Object })
|
|
4712
5532
|
], JupiterFormField.prototype, "masterData", 2);
|
|
4713
|
-
__decorateClass$
|
|
5533
|
+
__decorateClass$7([
|
|
4714
5534
|
n2({ type: Array })
|
|
4715
5535
|
], JupiterFormField.prototype, "facts", 2);
|
|
4716
|
-
__decorateClass$
|
|
5536
|
+
__decorateClass$7([
|
|
4717
5537
|
n2({ type: Object })
|
|
4718
5538
|
], JupiterFormField.prototype, "column", 2);
|
|
4719
|
-
__decorateClass$
|
|
5539
|
+
__decorateClass$7([
|
|
4720
5540
|
n2({ type: String })
|
|
4721
5541
|
], JupiterFormField.prototype, "periodStartDate", 2);
|
|
4722
|
-
__decorateClass$
|
|
5542
|
+
__decorateClass$7([
|
|
4723
5543
|
n2({ type: String })
|
|
4724
5544
|
], JupiterFormField.prototype, "periodEndDate", 2);
|
|
4725
|
-
__decorateClass$
|
|
5545
|
+
__decorateClass$7([
|
|
4726
5546
|
n2({ type: String })
|
|
4727
5547
|
], JupiterFormField.prototype, "periodInstantDate", 2);
|
|
4728
|
-
__decorateClass$
|
|
5548
|
+
__decorateClass$7([
|
|
4729
5549
|
n2({ type: String })
|
|
4730
5550
|
], JupiterFormField.prototype, "unit", 2);
|
|
4731
|
-
__decorateClass$
|
|
5551
|
+
__decorateClass$7([
|
|
4732
5552
|
n2({ type: String })
|
|
4733
5553
|
], JupiterFormField.prototype, "decimals", 2);
|
|
4734
|
-
__decorateClass$
|
|
5554
|
+
__decorateClass$7([
|
|
4735
5555
|
n2({ type: String })
|
|
4736
5556
|
], JupiterFormField.prototype, "globalDecimals", 2);
|
|
4737
|
-
__decorateClass$
|
|
5557
|
+
__decorateClass$7([
|
|
4738
5558
|
n2({ type: Object })
|
|
4739
5559
|
], JupiterFormField.prototype, "typedMemberValues", 2);
|
|
4740
|
-
__decorateClass$
|
|
5560
|
+
__decorateClass$7([
|
|
4741
5561
|
r()
|
|
4742
5562
|
], JupiterFormField.prototype, "_errors", 2);
|
|
4743
|
-
__decorateClass$
|
|
5563
|
+
__decorateClass$7([
|
|
4744
5564
|
r()
|
|
4745
5565
|
], JupiterFormField.prototype, "_xbrlErrors", 2);
|
|
4746
|
-
__decorateClass$
|
|
5566
|
+
__decorateClass$7([
|
|
4747
5567
|
r()
|
|
4748
5568
|
], JupiterFormField.prototype, "_touched", 2);
|
|
4749
|
-
__decorateClass$
|
|
5569
|
+
__decorateClass$7([
|
|
4750
5570
|
r()
|
|
4751
5571
|
], JupiterFormField.prototype, "_showPeriodPopup", 2);
|
|
4752
|
-
__decorateClass$
|
|
5572
|
+
__decorateClass$7([
|
|
4753
5573
|
r()
|
|
4754
5574
|
], JupiterFormField.prototype, "_availableUnits", 2);
|
|
4755
|
-
__decorateClass$
|
|
5575
|
+
__decorateClass$7([
|
|
4756
5576
|
r()
|
|
4757
5577
|
], JupiterFormField.prototype, "_numericDraftValue", 2);
|
|
4758
|
-
JupiterFormField = __decorateClass$
|
|
5578
|
+
JupiterFormField = __decorateClass$7([
|
|
4759
5579
|
t$1("jupiter-form-field")
|
|
4760
5580
|
], JupiterFormField);
|
|
4761
|
-
var __defProp$
|
|
4762
|
-
var __getOwnPropDesc$
|
|
4763
|
-
var __decorateClass$
|
|
4764
|
-
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$
|
|
5581
|
+
var __defProp$6 = Object.defineProperty;
|
|
5582
|
+
var __getOwnPropDesc$6 = Object.getOwnPropertyDescriptor;
|
|
5583
|
+
var __decorateClass$6 = (decorators, target, key, kind) => {
|
|
5584
|
+
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$6(target, key) : target;
|
|
4765
5585
|
for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
|
|
4766
5586
|
if (decorator = decorators[i2])
|
|
4767
5587
|
result = (kind ? decorator(target, key, result) : decorator(result)) || result;
|
|
4768
5588
|
if (kind && result)
|
|
4769
|
-
__defProp$
|
|
5589
|
+
__defProp$6(target, key, result);
|
|
4770
5590
|
return result;
|
|
4771
5591
|
};
|
|
4772
5592
|
let JupiterConceptTree = class extends LitElement {
|
|
@@ -5036,6 +5856,7 @@ let JupiterConceptTree = class extends LitElement {
|
|
|
5036
5856
|
const hasChildren = this.concept.children && this.concept.children.length > 0;
|
|
5037
5857
|
const level = this.concept.level || 0;
|
|
5038
5858
|
const isAbstract = this.concept.abstract || false;
|
|
5859
|
+
const isTotal = isTotalLabel$1(this.concept.preferredLabel);
|
|
5039
5860
|
return html`
|
|
5040
5861
|
<!-- Concept Name Cell (Left Column) -->
|
|
5041
5862
|
<td class="concept-name-cell ${isAbstract ? "abstract" : hasChildren ? "" : "leaf"} ${this.rowFocused ? "row-focused" : ""}">
|
|
@@ -5045,7 +5866,7 @@ let JupiterConceptTree = class extends LitElement {
|
|
|
5045
5866
|
@click="${this._toggleExpanded}">
|
|
5046
5867
|
${hasChildren ? "▶" : ""}
|
|
5047
5868
|
</div>
|
|
5048
|
-
<div class="concept-label"
|
|
5869
|
+
<div class="concept-label ${isTotal ? "total-concept-label" : ""}"
|
|
5049
5870
|
@click="${this._toggleExpanded}"
|
|
5050
5871
|
title="${this.concept.id}${this.concept.description ? " - " + this.concept.description : ""}">
|
|
5051
5872
|
${this.concept.label}
|
|
@@ -5053,14 +5874,14 @@ let JupiterConceptTree = class extends LitElement {
|
|
|
5053
5874
|
${this.concept.balance ? html`
|
|
5054
5875
|
<div class="concept-balance ${this.concept.balance}">${this.concept.balance}</div>
|
|
5055
5876
|
` : ""}
|
|
5056
|
-
<button class="concept-info-btn" type="button" title="${I18n.t("conceptInfo.title")}"
|
|
5877
|
+
<button class="concept-info-btn" type="button" tabindex="-1" title="${I18n.t("conceptInfo.title")}"
|
|
5057
5878
|
@click="${this._openInfoDialog}">ℹ</button>
|
|
5058
5879
|
${this.showAddButton ? html`
|
|
5059
|
-
<button class="repeat-btn" type="button" title="Add row"
|
|
5880
|
+
<button class="repeat-btn" type="button" tabindex="-1" title="Add row"
|
|
5060
5881
|
@click="${this._handleAddRepeat}">+</button>
|
|
5061
5882
|
` : ""}
|
|
5062
5883
|
${this.showRemoveButton ? html`
|
|
5063
|
-
<button class="repeat-btn remove" type="button" title="Remove row"
|
|
5884
|
+
<button class="repeat-btn remove" type="button" tabindex="-1" title="Remove row"
|
|
5064
5885
|
@click="${this._handleRemoveRepeat}">−</button>
|
|
5065
5886
|
` : ""}
|
|
5066
5887
|
</div>
|
|
@@ -5078,11 +5899,12 @@ let JupiterConceptTree = class extends LitElement {
|
|
|
5078
5899
|
const storedDecimals = (_d = (_c = this.decimalsData) == null ? void 0 : _c[this.concept.id]) == null ? void 0 : _d[column2.id];
|
|
5079
5900
|
const calcMismatch = this.mode !== "readonly" ? (_e = this.calculationMismatches) == null ? void 0 : _e.get(`${this.concept.id}__${column2.id}`) : void 0;
|
|
5080
5901
|
return html`
|
|
5081
|
-
<td class="field-cell ${!shouldShowField ? "empty" : ""} ${isAbstract ? "abstract-row" : ""} ${this.highlightType && column2.id === this.highlightColumnId ? "highlight-" + this.highlightType : ""} ${calcMismatch ? "calc-warning" : ""} ${this.rowFocused ? "row-focused" : ""}">
|
|
5902
|
+
<td class="field-cell ${!shouldShowField ? "empty" : ""} ${isAbstract ? "abstract-row" : ""} ${isTotal ? "total-row" : ""} ${this.highlightType && column2.id === this.highlightColumnId ? "highlight-" + this.highlightType : ""} ${calcMismatch ? "calc-warning" : ""} ${this.rowFocused ? "row-focused" : ""}">
|
|
5082
5903
|
${calcMismatch ? html`
|
|
5083
5904
|
<button
|
|
5084
5905
|
class="calc-warning-badge"
|
|
5085
5906
|
type="button"
|
|
5907
|
+
tabindex="-1"
|
|
5086
5908
|
title="${calcMismatch.message}"
|
|
5087
5909
|
@click="${(e2) => this._openCalculationWarningDialog(e2, calcMismatch)}"
|
|
5088
5910
|
>!</button>
|
|
@@ -5199,6 +6021,10 @@ JupiterConceptTree.styles = css`
|
|
|
5199
6021
|
min-width: 0; /* Allows flex item to shrink below content size */
|
|
5200
6022
|
}
|
|
5201
6023
|
|
|
6024
|
+
.concept-label.total-concept-label {
|
|
6025
|
+
font-weight: 700;
|
|
6026
|
+
}
|
|
6027
|
+
|
|
5202
6028
|
.concept-balance {
|
|
5203
6029
|
margin-left: 8px;
|
|
5204
6030
|
font-size: 11px;
|
|
@@ -5290,6 +6116,10 @@ JupiterConceptTree.styles = css`
|
|
|
5290
6116
|
color: #fff;
|
|
5291
6117
|
}
|
|
5292
6118
|
|
|
6119
|
+
.field-cell.total-row {
|
|
6120
|
+
background: var(--jupiter-total-cell-background, rgba(0, 0, 0, 0.045));
|
|
6121
|
+
}
|
|
6122
|
+
|
|
5293
6123
|
.field-cell.highlight-total {
|
|
5294
6124
|
background: rgba(25, 118, 210, 0.15);
|
|
5295
6125
|
}
|
|
@@ -5395,90 +6225,90 @@ JupiterConceptTree.styles = css`
|
|
|
5395
6225
|
}
|
|
5396
6226
|
|
|
5397
6227
|
`;
|
|
5398
|
-
__decorateClass$
|
|
6228
|
+
__decorateClass$6([
|
|
5399
6229
|
n2({ type: Object })
|
|
5400
6230
|
], JupiterConceptTree.prototype, "concept", 2);
|
|
5401
|
-
__decorateClass$
|
|
6231
|
+
__decorateClass$6([
|
|
5402
6232
|
n2({ type: Array })
|
|
5403
6233
|
], JupiterConceptTree.prototype, "columns", 2);
|
|
5404
|
-
__decorateClass$
|
|
6234
|
+
__decorateClass$6([
|
|
5405
6235
|
n2({ type: Object })
|
|
5406
6236
|
], JupiterConceptTree.prototype, "formData", 2);
|
|
5407
|
-
__decorateClass$
|
|
6237
|
+
__decorateClass$6([
|
|
5408
6238
|
n2({ type: Object })
|
|
5409
6239
|
], JupiterConceptTree.prototype, "periodData", 2);
|
|
5410
|
-
__decorateClass$
|
|
6240
|
+
__decorateClass$6([
|
|
5411
6241
|
n2({ type: Object })
|
|
5412
6242
|
], JupiterConceptTree.prototype, "unitData", 2);
|
|
5413
|
-
__decorateClass$
|
|
6243
|
+
__decorateClass$6([
|
|
5414
6244
|
n2({ type: Object })
|
|
5415
6245
|
], JupiterConceptTree.prototype, "decimalsData", 2);
|
|
5416
|
-
__decorateClass$
|
|
6246
|
+
__decorateClass$6([
|
|
5417
6247
|
n2({ type: String })
|
|
5418
6248
|
], JupiterConceptTree.prototype, "globalDecimals", 2);
|
|
5419
|
-
__decorateClass$
|
|
6249
|
+
__decorateClass$6([
|
|
5420
6250
|
n2({ type: Array })
|
|
5421
6251
|
], JupiterConceptTree.prototype, "defaultUnits", 2);
|
|
5422
|
-
__decorateClass$
|
|
6252
|
+
__decorateClass$6([
|
|
5423
6253
|
n2({ type: Boolean })
|
|
5424
6254
|
], JupiterConceptTree.prototype, "disabled", 2);
|
|
5425
|
-
__decorateClass$
|
|
6255
|
+
__decorateClass$6([
|
|
5426
6256
|
n2({ type: String })
|
|
5427
6257
|
], JupiterConceptTree.prototype, "locale", 2);
|
|
5428
|
-
__decorateClass$
|
|
6258
|
+
__decorateClass$6([
|
|
5429
6259
|
n2({ type: Set })
|
|
5430
6260
|
], JupiterConceptTree.prototype, "expandedConcepts", 2);
|
|
5431
|
-
__decorateClass$
|
|
6261
|
+
__decorateClass$6([
|
|
5432
6262
|
n2({ type: Array })
|
|
5433
6263
|
], JupiterConceptTree.prototype, "datatypes", 2);
|
|
5434
|
-
__decorateClass$
|
|
6264
|
+
__decorateClass$6([
|
|
5435
6265
|
n2({ type: String })
|
|
5436
6266
|
], JupiterConceptTree.prototype, "mode", 2);
|
|
5437
|
-
__decorateClass$
|
|
6267
|
+
__decorateClass$6([
|
|
5438
6268
|
n2({ type: Object })
|
|
5439
6269
|
], JupiterConceptTree.prototype, "masterData", 2);
|
|
5440
|
-
__decorateClass$
|
|
6270
|
+
__decorateClass$6([
|
|
5441
6271
|
n2({ type: Array })
|
|
5442
6272
|
], JupiterConceptTree.prototype, "facts", 2);
|
|
5443
|
-
__decorateClass$
|
|
6273
|
+
__decorateClass$6([
|
|
5444
6274
|
n2({ type: Object })
|
|
5445
6275
|
], JupiterConceptTree.prototype, "typedMemberData", 2);
|
|
5446
|
-
__decorateClass$
|
|
6276
|
+
__decorateClass$6([
|
|
5447
6277
|
n2({ type: Boolean })
|
|
5448
6278
|
], JupiterConceptTree.prototype, "showAddButton", 2);
|
|
5449
|
-
__decorateClass$
|
|
6279
|
+
__decorateClass$6([
|
|
5450
6280
|
n2({ type: Boolean })
|
|
5451
6281
|
], JupiterConceptTree.prototype, "showRemoveButton", 2);
|
|
5452
|
-
__decorateClass$
|
|
6282
|
+
__decorateClass$6([
|
|
5453
6283
|
n2({ type: String })
|
|
5454
6284
|
], JupiterConceptTree.prototype, "highlightType", 2);
|
|
5455
|
-
__decorateClass$
|
|
6285
|
+
__decorateClass$6([
|
|
5456
6286
|
n2({ type: String })
|
|
5457
6287
|
], JupiterConceptTree.prototype, "highlightColumnId", 2);
|
|
5458
|
-
__decorateClass$
|
|
6288
|
+
__decorateClass$6([
|
|
5459
6289
|
n2({ type: Object })
|
|
5460
6290
|
], JupiterConceptTree.prototype, "calculationMismatches", 2);
|
|
5461
|
-
__decorateClass$
|
|
6291
|
+
__decorateClass$6([
|
|
5462
6292
|
n2({ type: String })
|
|
5463
6293
|
], JupiterConceptTree.prototype, "language", 2);
|
|
5464
|
-
__decorateClass$
|
|
6294
|
+
__decorateClass$6([
|
|
5465
6295
|
n2({ type: Boolean })
|
|
5466
6296
|
], JupiterConceptTree.prototype, "rowFocused", 2);
|
|
5467
|
-
__decorateClass$
|
|
6297
|
+
__decorateClass$6([
|
|
5468
6298
|
r()
|
|
5469
6299
|
], JupiterConceptTree.prototype, "_expanded", 2);
|
|
5470
|
-
JupiterConceptTree = __decorateClass$
|
|
6300
|
+
JupiterConceptTree = __decorateClass$6([
|
|
5471
6301
|
t$1("jupiter-concept-tree")
|
|
5472
6302
|
], JupiterConceptTree);
|
|
5473
|
-
var __defProp$
|
|
5474
|
-
var __getOwnPropDesc$
|
|
5475
|
-
var __decorateClass$
|
|
5476
|
-
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$
|
|
6303
|
+
var __defProp$5 = Object.defineProperty;
|
|
6304
|
+
var __getOwnPropDesc$5 = Object.getOwnPropertyDescriptor;
|
|
6305
|
+
var __decorateClass$5 = (decorators, target, key, kind) => {
|
|
6306
|
+
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$5(target, key) : target;
|
|
5477
6307
|
for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
|
|
5478
6308
|
if (decorator = decorators[i2])
|
|
5479
6309
|
result = (kind ? decorator(target, key, result) : decorator(result)) || result;
|
|
5480
6310
|
if (kind && result)
|
|
5481
|
-
__defProp$
|
|
6311
|
+
__defProp$5(target, key, result);
|
|
5482
6312
|
return result;
|
|
5483
6313
|
};
|
|
5484
6314
|
let JupiterAddColumnDialog = class extends LitElement {
|
|
@@ -6087,48 +6917,48 @@ JupiterAddColumnDialog.styles = css`
|
|
|
6087
6917
|
line-height: 1.4;
|
|
6088
6918
|
}
|
|
6089
6919
|
`;
|
|
6090
|
-
__decorateClass$
|
|
6920
|
+
__decorateClass$5([
|
|
6091
6921
|
n2({ type: String })
|
|
6092
6922
|
], JupiterAddColumnDialog.prototype, "periodType", 2);
|
|
6093
|
-
__decorateClass$
|
|
6923
|
+
__decorateClass$5([
|
|
6094
6924
|
n2({ type: Boolean })
|
|
6095
6925
|
], JupiterAddColumnDialog.prototype, "open", 2);
|
|
6096
|
-
__decorateClass$
|
|
6926
|
+
__decorateClass$5([
|
|
6097
6927
|
n2({ type: Array })
|
|
6098
6928
|
], JupiterAddColumnDialog.prototype, "availableDimensions", 2);
|
|
6099
|
-
__decorateClass$
|
|
6929
|
+
__decorateClass$5([
|
|
6100
6930
|
n2({ type: String })
|
|
6101
6931
|
], JupiterAddColumnDialog.prototype, "periodStartDate", 2);
|
|
6102
|
-
__decorateClass$
|
|
6932
|
+
__decorateClass$5([
|
|
6103
6933
|
n2({ type: String })
|
|
6104
6934
|
], JupiterAddColumnDialog.prototype, "periodEndDate", 2);
|
|
6105
|
-
__decorateClass$
|
|
6935
|
+
__decorateClass$5([
|
|
6106
6936
|
r()
|
|
6107
6937
|
], JupiterAddColumnDialog.prototype, "_startDate", 2);
|
|
6108
|
-
__decorateClass$
|
|
6938
|
+
__decorateClass$5([
|
|
6109
6939
|
r()
|
|
6110
6940
|
], JupiterAddColumnDialog.prototype, "_endDate", 2);
|
|
6111
|
-
__decorateClass$
|
|
6941
|
+
__decorateClass$5([
|
|
6112
6942
|
r()
|
|
6113
6943
|
], JupiterAddColumnDialog.prototype, "_instantDate", 2);
|
|
6114
|
-
__decorateClass$
|
|
6944
|
+
__decorateClass$5([
|
|
6115
6945
|
r()
|
|
6116
6946
|
], JupiterAddColumnDialog.prototype, "_selectedType", 2);
|
|
6117
|
-
__decorateClass$
|
|
6947
|
+
__decorateClass$5([
|
|
6118
6948
|
r()
|
|
6119
6949
|
], JupiterAddColumnDialog.prototype, "_selectedDimensions", 2);
|
|
6120
|
-
JupiterAddColumnDialog = __decorateClass$
|
|
6950
|
+
JupiterAddColumnDialog = __decorateClass$5([
|
|
6121
6951
|
t$1("jupiter-add-column-dialog")
|
|
6122
6952
|
], JupiterAddColumnDialog);
|
|
6123
|
-
var __defProp$
|
|
6124
|
-
var __getOwnPropDesc$
|
|
6125
|
-
var __decorateClass$
|
|
6126
|
-
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$
|
|
6953
|
+
var __defProp$4 = Object.defineProperty;
|
|
6954
|
+
var __getOwnPropDesc$4 = Object.getOwnPropertyDescriptor;
|
|
6955
|
+
var __decorateClass$4 = (decorators, target, key, kind) => {
|
|
6956
|
+
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$4(target, key) : target;
|
|
6127
6957
|
for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
|
|
6128
6958
|
if (decorator = decorators[i2])
|
|
6129
6959
|
result = (kind ? decorator(target, key, result) : decorator(result)) || result;
|
|
6130
6960
|
if (kind && result)
|
|
6131
|
-
__defProp$
|
|
6961
|
+
__defProp$4(target, key, result);
|
|
6132
6962
|
return result;
|
|
6133
6963
|
};
|
|
6134
6964
|
let JupiterFormSection = class extends LitElement {
|
|
@@ -6154,6 +6984,8 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6154
6984
|
this.periodStartDate = "";
|
|
6155
6985
|
this.periodEndDate = "";
|
|
6156
6986
|
this.language = "en";
|
|
6987
|
+
this.calculationEnabled = false;
|
|
6988
|
+
this.totalManuallyEditedData = {};
|
|
6157
6989
|
this._expanded = true;
|
|
6158
6990
|
this._showAddColumnDialog = false;
|
|
6159
6991
|
this._sectionPeriodType = "duration";
|
|
@@ -6162,7 +6994,7 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6162
6994
|
this._boundFieldBlur = (e2) => {
|
|
6163
6995
|
this._clearHighlights();
|
|
6164
6996
|
this._focusedConceptId = null;
|
|
6165
|
-
if (this.mode === "readonly")
|
|
6997
|
+
if (this.mode === "readonly" || !this.calculationEnabled)
|
|
6166
6998
|
return;
|
|
6167
6999
|
const detail = e2.detail;
|
|
6168
7000
|
if ((detail == null ? void 0 : detail.conceptId) && (detail == null ? void 0 : detail.columnId)) {
|
|
@@ -6178,6 +7010,7 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6178
7010
|
this._memberParentMap = /* @__PURE__ */ new Map();
|
|
6179
7011
|
this._totalConceptMap = /* @__PURE__ */ new Map();
|
|
6180
7012
|
this._totalChildConceptsMap = /* @__PURE__ */ new Map();
|
|
7013
|
+
this._sessionManuallyEditedTotals = /* @__PURE__ */ new Set();
|
|
6181
7014
|
}
|
|
6182
7015
|
connectedCallback() {
|
|
6183
7016
|
super.connectedCallback();
|
|
@@ -6198,8 +7031,15 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6198
7031
|
if (changedProperties.has("isFirstSection") || changedProperties.has("section")) {
|
|
6199
7032
|
this._checkAndExpandFirstSection();
|
|
6200
7033
|
}
|
|
6201
|
-
if (changedProperties.has("section")
|
|
6202
|
-
this.
|
|
7034
|
+
if (changedProperties.has("section") || changedProperties.has("calculationEnabled")) {
|
|
7035
|
+
if (this.calculationEnabled && ((_a = this.section) == null ? void 0 : _a.concepts)) {
|
|
7036
|
+
this._buildTotalMaps(this.section.concepts);
|
|
7037
|
+
} else {
|
|
7038
|
+
this._clearCalculationState();
|
|
7039
|
+
}
|
|
7040
|
+
}
|
|
7041
|
+
if (changedProperties.has("totalManuallyEditedData")) {
|
|
7042
|
+
this._sessionManuallyEditedTotals.clear();
|
|
6203
7043
|
}
|
|
6204
7044
|
}
|
|
6205
7045
|
_checkAndExpandFirstSection() {
|
|
@@ -6350,6 +7190,15 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6350
7190
|
}
|
|
6351
7191
|
_handleFieldChange(event) {
|
|
6352
7192
|
event.stopPropagation();
|
|
7193
|
+
const { conceptId, columnId } = event.detail || {};
|
|
7194
|
+
if (conceptId && columnId && this._totalConceptMap.has(conceptId)) {
|
|
7195
|
+
this._sessionManuallyEditedTotals.add(`${conceptId}__${columnId}`);
|
|
7196
|
+
this.dispatchEvent(new CustomEvent("total-manually-edited", {
|
|
7197
|
+
detail: { conceptId, columnId },
|
|
7198
|
+
bubbles: true,
|
|
7199
|
+
composed: true
|
|
7200
|
+
}));
|
|
7201
|
+
}
|
|
6353
7202
|
this.dispatchEvent(new CustomEvent("field-change", {
|
|
6354
7203
|
detail: event.detail,
|
|
6355
7204
|
bubbles: true,
|
|
@@ -6378,6 +7227,13 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6378
7227
|
}
|
|
6379
7228
|
return result;
|
|
6380
7229
|
}
|
|
7230
|
+
_isTotalManuallyEdited(totalConceptId, columnId) {
|
|
7231
|
+
var _a, _b;
|
|
7232
|
+
const key = `${totalConceptId}__${columnId}`;
|
|
7233
|
+
if (this._sessionManuallyEditedTotals.has(key))
|
|
7234
|
+
return true;
|
|
7235
|
+
return ((_b = (_a = this.totalManuallyEditedData) == null ? void 0 : _a[totalConceptId]) == null ? void 0 : _b[columnId]) === true;
|
|
7236
|
+
}
|
|
6381
7237
|
/**
|
|
6382
7238
|
* Returns true when every column cell for a concept has no value.
|
|
6383
7239
|
* Used in readonly mode to hide fully-blank rows.
|
|
@@ -6435,6 +7291,21 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6435
7291
|
this._totalChildConceptsMap.clear();
|
|
6436
7292
|
this._traverseTotalGroups(concepts);
|
|
6437
7293
|
}
|
|
7294
|
+
/**
|
|
7295
|
+
* JDF-041: drops all calculation-warning state — used when the feature is disabled/toggled off.
|
|
7296
|
+
* Clears each existing mismatch through `_clearCalculationMismatch` (rather than resetting the
|
|
7297
|
+
* map directly) so the parent's validation summary, which tracks mismatches via the dispatched
|
|
7298
|
+
* `calculation-mismatch-changed` events, is told about each removal instead of being left stale.
|
|
7299
|
+
*/
|
|
7300
|
+
_clearCalculationState() {
|
|
7301
|
+
this._totalChildrenMap.clear();
|
|
7302
|
+
this._memberParentMap.clear();
|
|
7303
|
+
this._totalConceptMap.clear();
|
|
7304
|
+
this._totalChildConceptsMap.clear();
|
|
7305
|
+
for (const key of Array.from(this._calculationMismatches.keys())) {
|
|
7306
|
+
this._clearCalculationMismatch(key);
|
|
7307
|
+
}
|
|
7308
|
+
}
|
|
6438
7309
|
/**
|
|
6439
7310
|
* JDF-038: XBRL uses more than one preferredLabel role to mark a "total" row — the plain
|
|
6440
7311
|
* `.../role/totalLabel` and the sign-flipped `.../role/negatedTotalLabel` (used for subtotals of
|
|
@@ -6443,7 +7314,16 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6443
7314
|
* matching is the single source of truth for "is this row a total" everywhere in this file.
|
|
6444
7315
|
*/
|
|
6445
7316
|
static _isTotalLabel(preferredLabel) {
|
|
6446
|
-
return
|
|
7317
|
+
return isTotalLabel$1(preferredLabel);
|
|
7318
|
+
}
|
|
7319
|
+
/**
|
|
7320
|
+
* JDF-041: distinguishes a self-contained "deduction block" subtotal (negatedTotalLabel, e.g.
|
|
7321
|
+
* "Total of sum of expenses") from a plain cascading/running total. Only the latter is treated as
|
|
7322
|
+
* additively built on the total before it — a negatedTotalLabel row summarizes just the raw items
|
|
7323
|
+
* directly before it and must not also absorb an unrelated earlier total into its own check.
|
|
7324
|
+
*/
|
|
7325
|
+
static _isNegatedTotalLabel(preferredLabel) {
|
|
7326
|
+
return !!(preferredLabel == null ? void 0 : preferredLabel.toLowerCase().includes("negatedtotallabel"));
|
|
6447
7327
|
}
|
|
6448
7328
|
/**
|
|
6449
7329
|
* A member of a total's sibling/child group can itself be a presentation-only abstract wrapper
|
|
@@ -6475,6 +7355,47 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6475
7355
|
this._memberParentMap.set(memberId, totalConcept.id);
|
|
6476
7356
|
}
|
|
6477
7357
|
}
|
|
7358
|
+
/**
|
|
7359
|
+
* JDF-041: computes the JDF-030 sibling-fallback member set for a total at `concepts[i]`, given the
|
|
7360
|
+
* nearest preceding total's index (`lastTotalIdx`, -1 if none) and the raw siblings between them.
|
|
7361
|
+
*
|
|
7362
|
+
* - No preceding total → members are just the raw siblings (unchanged, e.g. the very first total
|
|
7363
|
+
* in the role).
|
|
7364
|
+
* - This total is itself a negatedTotalLabel (a self-contained deduction-block subtotal, e.g.
|
|
7365
|
+
* "Total of sum of expenses") → the preceding total stays a scan boundary only, never a member —
|
|
7366
|
+
* it summarizes just its own raw siblings, same as before JDF-041.
|
|
7367
|
+
* - Otherwise (a plain totalLabel, cascading/running total) with raw siblings before it → the
|
|
7368
|
+
* preceding total is included as a real member alongside them, since this total is built
|
|
7369
|
+
* additively on top of it.
|
|
7370
|
+
* - Otherwise (a plain totalLabel adjacent to the preceding total, zero raw siblings between them):
|
|
7371
|
+
* if that preceding total is itself a negatedTotalLabel subtotal, it doesn't carry the running
|
|
7372
|
+
* total from before it forward (per the rule above) — reach one more hop back to also include the
|
|
7373
|
+
* total the subtotal was deducted from (e.g. "Net operating result" needs both "Gross operating
|
|
7374
|
+
* result" and "Total of sum of expenses", not just the latter). Otherwise, the single preceding
|
|
7375
|
+
* total is the member, as it was for JDF-038's original adjacent-boundary case.
|
|
7376
|
+
*/
|
|
7377
|
+
_resolveTotalGroupMembers(concepts, i2, lastTotalIdx, siblings) {
|
|
7378
|
+
if (lastTotalIdx < 0)
|
|
7379
|
+
return siblings;
|
|
7380
|
+
const concept = concepts[i2];
|
|
7381
|
+
if (JupiterFormSection._isNegatedTotalLabel(concept.preferredLabel)) {
|
|
7382
|
+
return siblings.length > 0 ? siblings : [concepts[lastTotalIdx]];
|
|
7383
|
+
}
|
|
7384
|
+
if (siblings.length > 0) {
|
|
7385
|
+
return [concepts[lastTotalIdx], ...siblings];
|
|
7386
|
+
}
|
|
7387
|
+
if (JupiterFormSection._isNegatedTotalLabel(concepts[lastTotalIdx].preferredLabel)) {
|
|
7388
|
+
let grandTotalIdx = -1;
|
|
7389
|
+
for (let k = lastTotalIdx - 1; k >= 0; k--) {
|
|
7390
|
+
if (JupiterFormSection._isTotalLabel(concepts[k].preferredLabel)) {
|
|
7391
|
+
grandTotalIdx = k;
|
|
7392
|
+
break;
|
|
7393
|
+
}
|
|
7394
|
+
}
|
|
7395
|
+
return grandTotalIdx >= 0 ? [concepts[grandTotalIdx], concepts[lastTotalIdx]] : [concepts[lastTotalIdx]];
|
|
7396
|
+
}
|
|
7397
|
+
return [concepts[lastTotalIdx]];
|
|
7398
|
+
}
|
|
6478
7399
|
_traverseTotalGroups(concepts) {
|
|
6479
7400
|
var _a, _b;
|
|
6480
7401
|
for (let i2 = 0; i2 < concepts.length; i2++) {
|
|
@@ -6491,10 +7412,9 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6491
7412
|
}
|
|
6492
7413
|
}
|
|
6493
7414
|
const siblings = concepts.slice(lastTotalIdx + 1, i2);
|
|
6494
|
-
|
|
6495
|
-
|
|
6496
|
-
|
|
6497
|
-
this._registerTotalGroup(concept, [concepts[lastTotalIdx]]);
|
|
7415
|
+
const members = this._resolveTotalGroupMembers(concepts, i2, lastTotalIdx, siblings);
|
|
7416
|
+
if (members.length > 0) {
|
|
7417
|
+
this._registerTotalGroup(concept, members);
|
|
6498
7418
|
}
|
|
6499
7419
|
}
|
|
6500
7420
|
}
|
|
@@ -6515,10 +7435,29 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6515
7435
|
}
|
|
6516
7436
|
}
|
|
6517
7437
|
_evaluateTotal(totalConceptId, columnId) {
|
|
6518
|
-
var _a;
|
|
7438
|
+
var _a, _b;
|
|
6519
7439
|
const totalConcept = this._totalConceptMap.get(totalConceptId);
|
|
6520
|
-
const totalRaw = (_a = this.formData[totalConceptId]) == null ? void 0 : _a[columnId];
|
|
6521
7440
|
const key = `${totalConceptId}__${columnId}`;
|
|
7441
|
+
const children = this._totalChildConceptsMap.get(totalConceptId) || [];
|
|
7442
|
+
const { calculatedSum, hasAnyValue, breakdown } = this._buildCalculationBreakdown(
|
|
7443
|
+
children,
|
|
7444
|
+
this.formData,
|
|
7445
|
+
columnId,
|
|
7446
|
+
totalConcept.balance
|
|
7447
|
+
);
|
|
7448
|
+
if (!this._isTotalManuallyEdited(totalConceptId, columnId)) {
|
|
7449
|
+
if (hasAnyValue) {
|
|
7450
|
+
const currentRaw = (_a = this.formData[totalConceptId]) == null ? void 0 : _a[columnId];
|
|
7451
|
+
const currentValue = parseFloat(currentRaw);
|
|
7452
|
+
const isBlank = currentRaw === null || currentRaw === void 0 || currentRaw === "";
|
|
7453
|
+
if (isBlank || isNaN(currentValue) || !JupiterFormSection._checkTotal(currentValue, calculatedSum)) {
|
|
7454
|
+
this._dispatchCalculationTotalAutoPopulated(totalConceptId, columnId, calculatedSum);
|
|
7455
|
+
}
|
|
7456
|
+
}
|
|
7457
|
+
this._clearCalculationMismatch(key);
|
|
7458
|
+
return;
|
|
7459
|
+
}
|
|
7460
|
+
const totalRaw = (_b = this.formData[totalConceptId]) == null ? void 0 : _b[columnId];
|
|
6522
7461
|
if (totalRaw === null || totalRaw === void 0 || totalRaw === "") {
|
|
6523
7462
|
this._clearCalculationMismatch(key);
|
|
6524
7463
|
return;
|
|
@@ -6528,13 +7467,6 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6528
7467
|
this._clearCalculationMismatch(key);
|
|
6529
7468
|
return;
|
|
6530
7469
|
}
|
|
6531
|
-
const children = this._totalChildConceptsMap.get(totalConceptId) || [];
|
|
6532
|
-
const { calculatedSum, hasAnyValue, breakdown } = JupiterFormSection._buildCalculationBreakdown(
|
|
6533
|
-
children,
|
|
6534
|
-
this.formData,
|
|
6535
|
-
columnId,
|
|
6536
|
-
totalConcept.balance
|
|
6537
|
-
);
|
|
6538
7470
|
if (!hasAnyValue || JupiterFormSection._checkTotal(totalValue, calculatedSum)) {
|
|
6539
7471
|
this._clearCalculationMismatch(key);
|
|
6540
7472
|
return;
|
|
@@ -6557,6 +7489,13 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6557
7489
|
this._calculationMismatches = next;
|
|
6558
7490
|
this._dispatchCalculationMismatchChanged(key, detail);
|
|
6559
7491
|
}
|
|
7492
|
+
_dispatchCalculationTotalAutoPopulated(conceptId, columnId, value) {
|
|
7493
|
+
this.dispatchEvent(new CustomEvent("calculation-total-auto-populated", {
|
|
7494
|
+
detail: { conceptId, columnId, value, sectionId: this.section.id },
|
|
7495
|
+
bubbles: true,
|
|
7496
|
+
composed: true
|
|
7497
|
+
}));
|
|
7498
|
+
}
|
|
6560
7499
|
_clearCalculationMismatch(key) {
|
|
6561
7500
|
if (!this._calculationMismatches.has(key))
|
|
6562
7501
|
return;
|
|
@@ -6576,24 +7515,51 @@ let JupiterFormSection = class extends LitElement {
|
|
|
6576
7515
|
static _resolveWeight(totalBalance, childBalance) {
|
|
6577
7516
|
return !totalBalance || !childBalance || totalBalance === childBalance ? 1 : -1;
|
|
6578
7517
|
}
|
|
6579
|
-
|
|
7518
|
+
/**
|
|
7519
|
+
* JDF-041: a group member can itself be a registered cascading total with no entered value (e.g. a
|
|
7520
|
+
* customer who fills in "Operating income" directly without ever populating the "Net operating
|
|
7521
|
+
* result" running-subtotal row it's built on). Treating a blank member as a zero contribution
|
|
7522
|
+
* silently drops whatever it's actually built from and produces a false-positive mismatch. Instead,
|
|
7523
|
+
* look through a blank total member into its own registered members, recursively, so the check
|
|
7524
|
+
* reaches the real entered values wherever they are in the chain. `visited`/`depth` guard against
|
|
7525
|
+
* cycles and unbounded recursion (mirrors `_resolveValueConcept`'s depth cutoff).
|
|
7526
|
+
*/
|
|
7527
|
+
_resolveMemberContributions(member, weight, formData, columnId, visited, depth = 0) {
|
|
6580
7528
|
var _a;
|
|
7529
|
+
const val = parseFloat((_a = formData[member.id]) == null ? void 0 : _a[columnId]);
|
|
7530
|
+
if (!isNaN(val)) {
|
|
7531
|
+
return [{ conceptId: member.id, label: member.label, value: val, balance: member.balance, weight }];
|
|
7532
|
+
}
|
|
7533
|
+
if (depth >= 5 || visited.has(member.id))
|
|
7534
|
+
return [];
|
|
7535
|
+
const nestedMembers = this._totalChildConceptsMap.get(member.id);
|
|
7536
|
+
if (!nestedMembers)
|
|
7537
|
+
return [];
|
|
7538
|
+
const nextVisited = new Set(visited).add(member.id);
|
|
7539
|
+
const contributions = [];
|
|
7540
|
+
for (const nested of nestedMembers) {
|
|
7541
|
+
const nestedWeight = weight * JupiterFormSection._resolveWeight(member.balance, nested.balance);
|
|
7542
|
+
contributions.push(...this._resolveMemberContributions(nested, nestedWeight, formData, columnId, nextVisited, depth + 1));
|
|
7543
|
+
}
|
|
7544
|
+
return contributions;
|
|
7545
|
+
}
|
|
7546
|
+
_buildCalculationBreakdown(children, formData, columnId, totalBalance) {
|
|
6581
7547
|
let calculatedSum = 0;
|
|
6582
7548
|
let hasAnyValue = false;
|
|
6583
7549
|
const breakdown = [];
|
|
6584
7550
|
for (const child of children) {
|
|
6585
|
-
const val = parseFloat((_a = formData[child.id]) == null ? void 0 : _a[columnId]);
|
|
6586
|
-
if (isNaN(val))
|
|
6587
|
-
continue;
|
|
6588
|
-
hasAnyValue = true;
|
|
6589
7551
|
const weight = JupiterFormSection._resolveWeight(totalBalance, child.balance);
|
|
6590
|
-
|
|
6591
|
-
|
|
7552
|
+
const contributions = this._resolveMemberContributions(child, weight, formData, columnId, /* @__PURE__ */ new Set());
|
|
7553
|
+
for (const contribution of contributions) {
|
|
7554
|
+
calculatedSum += contribution.weight * contribution.value;
|
|
7555
|
+
hasAnyValue = true;
|
|
7556
|
+
breakdown.push(contribution);
|
|
7557
|
+
}
|
|
6592
7558
|
}
|
|
6593
7559
|
return { calculatedSum, hasAnyValue, breakdown };
|
|
6594
7560
|
}
|
|
6595
7561
|
static _checkTotal(totalValue, calculatedSum) {
|
|
6596
|
-
return Math.abs(calculatedSum - totalValue) <
|
|
7562
|
+
return Math.abs(calculatedSum - totalValue) < CALCULATION_TOLERANCE;
|
|
6597
7563
|
}
|
|
6598
7564
|
static _formatNumber(n3) {
|
|
6599
7565
|
return Number.isInteger(n3) ? String(n3) : n3.toFixed(2);
|
|
@@ -7179,120 +8145,126 @@ JupiterFormSection.styles = css`
|
|
|
7179
8145
|
font-style: italic;
|
|
7180
8146
|
}
|
|
7181
8147
|
`;
|
|
7182
|
-
__decorateClass$
|
|
8148
|
+
__decorateClass$4([
|
|
7183
8149
|
n2({ type: Object })
|
|
7184
8150
|
], JupiterFormSection.prototype, "section", 2);
|
|
7185
|
-
__decorateClass$
|
|
8151
|
+
__decorateClass$4([
|
|
7186
8152
|
n2({ type: Array })
|
|
7187
8153
|
], JupiterFormSection.prototype, "columns", 2);
|
|
7188
|
-
__decorateClass$
|
|
8154
|
+
__decorateClass$4([
|
|
7189
8155
|
n2({ type: Array })
|
|
7190
8156
|
], JupiterFormSection.prototype, "datatypes", 2);
|
|
7191
|
-
__decorateClass$
|
|
8157
|
+
__decorateClass$4([
|
|
7192
8158
|
n2({ type: Object })
|
|
7193
8159
|
], JupiterFormSection.prototype, "formData", 2);
|
|
7194
|
-
__decorateClass$
|
|
8160
|
+
__decorateClass$4([
|
|
7195
8161
|
n2({ type: Object })
|
|
7196
8162
|
], JupiterFormSection.prototype, "periodData", 2);
|
|
7197
|
-
__decorateClass$
|
|
8163
|
+
__decorateClass$4([
|
|
7198
8164
|
n2({ type: Object })
|
|
7199
8165
|
], JupiterFormSection.prototype, "unitData", 2);
|
|
7200
|
-
__decorateClass$
|
|
8166
|
+
__decorateClass$4([
|
|
7201
8167
|
n2({ type: Object })
|
|
7202
8168
|
], JupiterFormSection.prototype, "decimalsData", 2);
|
|
7203
|
-
__decorateClass$
|
|
8169
|
+
__decorateClass$4([
|
|
7204
8170
|
n2({ type: String })
|
|
7205
8171
|
], JupiterFormSection.prototype, "globalDecimals", 2);
|
|
7206
|
-
__decorateClass$
|
|
8172
|
+
__decorateClass$4([
|
|
7207
8173
|
n2({ type: Object })
|
|
7208
8174
|
], JupiterFormSection.prototype, "typedMemberData", 2);
|
|
7209
|
-
__decorateClass$
|
|
8175
|
+
__decorateClass$4([
|
|
7210
8176
|
n2({ type: Object })
|
|
7211
8177
|
], JupiterFormSection.prototype, "repeatCounts", 2);
|
|
7212
|
-
__decorateClass$
|
|
8178
|
+
__decorateClass$4([
|
|
7213
8179
|
n2({ type: Array })
|
|
7214
8180
|
], JupiterFormSection.prototype, "defaultUnits", 2);
|
|
7215
|
-
__decorateClass$
|
|
8181
|
+
__decorateClass$4([
|
|
7216
8182
|
n2({ type: Boolean })
|
|
7217
8183
|
], JupiterFormSection.prototype, "disabled", 2);
|
|
7218
|
-
__decorateClass$
|
|
8184
|
+
__decorateClass$4([
|
|
7219
8185
|
n2({ type: Boolean })
|
|
7220
8186
|
], JupiterFormSection.prototype, "collapsible", 2);
|
|
7221
|
-
__decorateClass$
|
|
8187
|
+
__decorateClass$4([
|
|
7222
8188
|
n2({ type: String })
|
|
7223
8189
|
], JupiterFormSection.prototype, "locale", 2);
|
|
7224
|
-
__decorateClass$
|
|
8190
|
+
__decorateClass$4([
|
|
7225
8191
|
n2({ type: Boolean })
|
|
7226
8192
|
], JupiterFormSection.prototype, "isFirstSection", 2);
|
|
7227
|
-
__decorateClass$
|
|
8193
|
+
__decorateClass$4([
|
|
7228
8194
|
n2({ type: Array })
|
|
7229
8195
|
], JupiterFormSection.prototype, "availableDimensions", 2);
|
|
7230
|
-
__decorateClass$
|
|
8196
|
+
__decorateClass$4([
|
|
7231
8197
|
n2({ type: Boolean })
|
|
7232
8198
|
], JupiterFormSection.prototype, "hideHeader", 2);
|
|
7233
|
-
__decorateClass$
|
|
8199
|
+
__decorateClass$4([
|
|
7234
8200
|
n2({ type: String })
|
|
7235
8201
|
], JupiterFormSection.prototype, "mode", 2);
|
|
7236
|
-
__decorateClass$
|
|
8202
|
+
__decorateClass$4([
|
|
7237
8203
|
n2({ type: Boolean })
|
|
7238
8204
|
], JupiterFormSection.prototype, "showFactsOnly", 2);
|
|
7239
|
-
__decorateClass$
|
|
8205
|
+
__decorateClass$4([
|
|
7240
8206
|
n2({ type: Object })
|
|
7241
8207
|
], JupiterFormSection.prototype, "conceptMatchIds", 2);
|
|
7242
|
-
__decorateClass$
|
|
8208
|
+
__decorateClass$4([
|
|
7243
8209
|
n2({ type: Object })
|
|
7244
8210
|
], JupiterFormSection.prototype, "masterData", 2);
|
|
7245
|
-
__decorateClass$
|
|
8211
|
+
__decorateClass$4([
|
|
7246
8212
|
n2({ type: String })
|
|
7247
8213
|
], JupiterFormSection.prototype, "periodStartDate", 2);
|
|
7248
|
-
__decorateClass$
|
|
8214
|
+
__decorateClass$4([
|
|
7249
8215
|
n2({ type: String })
|
|
7250
8216
|
], JupiterFormSection.prototype, "periodEndDate", 2);
|
|
7251
|
-
__decorateClass$
|
|
8217
|
+
__decorateClass$4([
|
|
7252
8218
|
n2({ type: String })
|
|
7253
8219
|
], JupiterFormSection.prototype, "language", 2);
|
|
7254
|
-
__decorateClass$
|
|
8220
|
+
__decorateClass$4([
|
|
8221
|
+
n2({ type: Boolean })
|
|
8222
|
+
], JupiterFormSection.prototype, "calculationEnabled", 2);
|
|
8223
|
+
__decorateClass$4([
|
|
8224
|
+
n2({ type: Object })
|
|
8225
|
+
], JupiterFormSection.prototype, "totalManuallyEditedData", 2);
|
|
8226
|
+
__decorateClass$4([
|
|
7255
8227
|
r()
|
|
7256
8228
|
], JupiterFormSection.prototype, "_expanded", 2);
|
|
7257
|
-
__decorateClass$
|
|
8229
|
+
__decorateClass$4([
|
|
7258
8230
|
r()
|
|
7259
8231
|
], JupiterFormSection.prototype, "_showAddColumnDialog", 2);
|
|
7260
|
-
__decorateClass$
|
|
8232
|
+
__decorateClass$4([
|
|
7261
8233
|
r()
|
|
7262
8234
|
], JupiterFormSection.prototype, "_sectionPeriodType", 2);
|
|
7263
|
-
__decorateClass$
|
|
8235
|
+
__decorateClass$4([
|
|
7264
8236
|
r()
|
|
7265
8237
|
], JupiterFormSection.prototype, "_openMenuColumnId", 2);
|
|
7266
|
-
__decorateClass$
|
|
8238
|
+
__decorateClass$4([
|
|
7267
8239
|
r()
|
|
7268
8240
|
], JupiterFormSection.prototype, "_insertAfterColumnId", 2);
|
|
7269
|
-
__decorateClass$
|
|
8241
|
+
__decorateClass$4([
|
|
7270
8242
|
r()
|
|
7271
8243
|
], JupiterFormSection.prototype, "_expandedConcepts", 2);
|
|
7272
|
-
__decorateClass$
|
|
8244
|
+
__decorateClass$4([
|
|
7273
8245
|
r()
|
|
7274
8246
|
], JupiterFormSection.prototype, "_allTreeExpanded", 2);
|
|
7275
|
-
__decorateClass$
|
|
8247
|
+
__decorateClass$4([
|
|
7276
8248
|
r()
|
|
7277
8249
|
], JupiterFormSection.prototype, "_highlightMap", 2);
|
|
7278
|
-
__decorateClass$
|
|
8250
|
+
__decorateClass$4([
|
|
7279
8251
|
r()
|
|
7280
8252
|
], JupiterFormSection.prototype, "_focusedConceptId", 2);
|
|
7281
|
-
__decorateClass$
|
|
8253
|
+
__decorateClass$4([
|
|
7282
8254
|
r()
|
|
7283
8255
|
], JupiterFormSection.prototype, "_calculationMismatches", 2);
|
|
7284
|
-
JupiterFormSection = __decorateClass$
|
|
8256
|
+
JupiterFormSection = __decorateClass$4([
|
|
7285
8257
|
t$1("jupiter-form-section")
|
|
7286
8258
|
], JupiterFormSection);
|
|
7287
|
-
var __defProp$
|
|
7288
|
-
var __getOwnPropDesc$
|
|
7289
|
-
var __decorateClass$
|
|
7290
|
-
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$
|
|
8259
|
+
var __defProp$3 = Object.defineProperty;
|
|
8260
|
+
var __getOwnPropDesc$3 = Object.getOwnPropertyDescriptor;
|
|
8261
|
+
var __decorateClass$3 = (decorators, target, key, kind) => {
|
|
8262
|
+
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$3(target, key) : target;
|
|
7291
8263
|
for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
|
|
7292
8264
|
if (decorator = decorators[i2])
|
|
7293
8265
|
result = (kind ? decorator(target, key, result) : decorator(result)) || result;
|
|
7294
8266
|
if (kind && result)
|
|
7295
|
-
__defProp$
|
|
8267
|
+
__defProp$3(target, key, result);
|
|
7296
8268
|
return result;
|
|
7297
8269
|
};
|
|
7298
8270
|
let JupiterAdvancedFilter = class extends LitElement {
|
|
@@ -7481,27 +8453,27 @@ JupiterAdvancedFilter.styles = css`
|
|
|
7481
8453
|
color: var(--primaryTextColor, var(--jupiter-text-primary, #333));
|
|
7482
8454
|
}
|
|
7483
8455
|
`;
|
|
7484
|
-
__decorateClass$
|
|
8456
|
+
__decorateClass$3([
|
|
7485
8457
|
n2({ type: Boolean })
|
|
7486
8458
|
], JupiterAdvancedFilter.prototype, "showFactsOnly", 2);
|
|
7487
|
-
__decorateClass$
|
|
8459
|
+
__decorateClass$3([
|
|
7488
8460
|
n2({ type: String })
|
|
7489
8461
|
], JupiterAdvancedFilter.prototype, "conceptSearchText", 2);
|
|
7490
|
-
__decorateClass$
|
|
8462
|
+
__decorateClass$3([
|
|
7491
8463
|
r()
|
|
7492
8464
|
], JupiterAdvancedFilter.prototype, "_localConceptSearchText", 2);
|
|
7493
|
-
JupiterAdvancedFilter = __decorateClass$
|
|
8465
|
+
JupiterAdvancedFilter = __decorateClass$3([
|
|
7494
8466
|
t$1("jupiter-advanced-filter")
|
|
7495
8467
|
], JupiterAdvancedFilter);
|
|
7496
|
-
var __defProp$
|
|
7497
|
-
var __getOwnPropDesc$
|
|
7498
|
-
var __decorateClass$
|
|
7499
|
-
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$
|
|
8468
|
+
var __defProp$2 = Object.defineProperty;
|
|
8469
|
+
var __getOwnPropDesc$2 = Object.getOwnPropertyDescriptor;
|
|
8470
|
+
var __decorateClass$2 = (decorators, target, key, kind) => {
|
|
8471
|
+
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$2(target, key) : target;
|
|
7500
8472
|
for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
|
|
7501
8473
|
if (decorator = decorators[i2])
|
|
7502
8474
|
result = (kind ? decorator(target, key, result) : decorator(result)) || result;
|
|
7503
8475
|
if (kind && result)
|
|
7504
|
-
__defProp$
|
|
8476
|
+
__defProp$2(target, key, result);
|
|
7505
8477
|
return result;
|
|
7506
8478
|
};
|
|
7507
8479
|
let _lastViewWasAdvancedFilter = false;
|
|
@@ -9092,188 +10064,519 @@ JupiterFilterRolesDialog.styles = css`
|
|
|
9092
10064
|
font-size: 14px;
|
|
9093
10065
|
}
|
|
9094
10066
|
|
|
9095
|
-
.picklist-search {
|
|
9096
|
-
padding: 12px;
|
|
9097
|
-
border-bottom: 1px solid var(--jupiter-border-color, #ddd);
|
|
10067
|
+
.picklist-search {
|
|
10068
|
+
padding: 12px;
|
|
10069
|
+
border-bottom: 1px solid var(--jupiter-border-color, #ddd);
|
|
10070
|
+
}
|
|
10071
|
+
|
|
10072
|
+
.picklist-list {
|
|
10073
|
+
flex: 1;
|
|
10074
|
+
overflow-y: auto;
|
|
10075
|
+
padding: 8px;
|
|
10076
|
+
}
|
|
10077
|
+
|
|
10078
|
+
.picklist-item {
|
|
10079
|
+
padding: 10px 12px;
|
|
10080
|
+
margin-bottom: 4px;
|
|
10081
|
+
border: 1px solid var(--jupiter-border-color, #ddd);
|
|
10082
|
+
border-radius: 4px;
|
|
10083
|
+
cursor: pointer;
|
|
10084
|
+
transition: all 0.2s ease;
|
|
10085
|
+
background: var(--jupiter-background, #fff);
|
|
10086
|
+
}
|
|
10087
|
+
|
|
10088
|
+
.picklist-item:hover {
|
|
10089
|
+
background: var(--jupiter-hover-background, #f5f5f5);
|
|
10090
|
+
border-color: var(--jupiter-primary-color, #1976d2);
|
|
10091
|
+
}
|
|
10092
|
+
|
|
10093
|
+
.picklist-item.selected {
|
|
10094
|
+
background: var(--jupiter-primary-color, #1976d2);
|
|
10095
|
+
color: white;
|
|
10096
|
+
border-color: var(--jupiter-primary-color, #1976d2);
|
|
10097
|
+
}
|
|
10098
|
+
|
|
10099
|
+
.picklist-item.dragging {
|
|
10100
|
+
opacity: 0.5;
|
|
10101
|
+
cursor: move;
|
|
10102
|
+
}
|
|
10103
|
+
|
|
10104
|
+
.picklist-item.drag-over {
|
|
10105
|
+
border-top: 3px solid var(--jupiter-primary-color, #1976d2);
|
|
10106
|
+
margin-top: 3px;
|
|
10107
|
+
}
|
|
10108
|
+
|
|
10109
|
+
.picklist-item[draggable="true"] {
|
|
10110
|
+
cursor: move;
|
|
10111
|
+
}
|
|
10112
|
+
|
|
10113
|
+
.picklist-item-label {
|
|
10114
|
+
font-weight: 500;
|
|
10115
|
+
font-size: 14px;
|
|
10116
|
+
margin-bottom: 4px;
|
|
10117
|
+
}
|
|
10118
|
+
|
|
10119
|
+
.picklist-item-value {
|
|
10120
|
+
font-size: 11px;
|
|
10121
|
+
opacity: 0.8;
|
|
10122
|
+
word-break: break-all;
|
|
10123
|
+
}
|
|
10124
|
+
|
|
10125
|
+
.picklist-controls {
|
|
10126
|
+
display: flex;
|
|
10127
|
+
flex-direction: column;
|
|
10128
|
+
justify-content: center;
|
|
10129
|
+
gap: 8px;
|
|
10130
|
+
padding: 0 8px;
|
|
10131
|
+
}
|
|
10132
|
+
|
|
10133
|
+
.picklist-button {
|
|
10134
|
+
background: var(--jupiter-primary-color, #1976d2);
|
|
10135
|
+
color: white;
|
|
10136
|
+
border: none;
|
|
10137
|
+
padding: 8px 16px;
|
|
10138
|
+
border-radius: 4px;
|
|
10139
|
+
cursor: pointer;
|
|
10140
|
+
font-size: 14px;
|
|
10141
|
+
transition: background-color 0.2s ease;
|
|
10142
|
+
}
|
|
10143
|
+
|
|
10144
|
+
.picklist-button:hover:not(:disabled) {
|
|
10145
|
+
background: var(--jupiter-primary-color-dark, #1565c0);
|
|
10146
|
+
}
|
|
10147
|
+
|
|
10148
|
+
.picklist-button:disabled {
|
|
10149
|
+
opacity: 0.4;
|
|
10150
|
+
cursor: not-allowed;
|
|
10151
|
+
}
|
|
10152
|
+
|
|
10153
|
+
.picklist-count {
|
|
10154
|
+
padding: 8px 12px;
|
|
10155
|
+
font-size: 12px;
|
|
10156
|
+
color: var(--jupiter-text-secondary, #666);
|
|
10157
|
+
background: var(--jupiter-background-light, #f8f9fa);
|
|
10158
|
+
border-top: 1px solid var(--jupiter-border-color, #ddd);
|
|
10159
|
+
text-align: center;
|
|
10160
|
+
}
|
|
10161
|
+
|
|
10162
|
+
.btn-text {
|
|
10163
|
+
background: none;
|
|
10164
|
+
border: none;
|
|
10165
|
+
color: var(--buttonBgColor, var(--jupiter-primary-color, #1976d2));
|
|
10166
|
+
padding: 10px 8px;
|
|
10167
|
+
font-size: 14px;
|
|
10168
|
+
font-weight: 500;
|
|
10169
|
+
font-family: inherit;
|
|
10170
|
+
cursor: pointer;
|
|
10171
|
+
margin-right: auto;
|
|
10172
|
+
border-radius: 4px;
|
|
10173
|
+
transition: background-color 0.2s ease;
|
|
10174
|
+
}
|
|
10175
|
+
|
|
10176
|
+
.btn-text:hover {
|
|
10177
|
+
background: var(--menuBgColorLighter, var(--jupiter-hover-background, #f5f5f5));
|
|
10178
|
+
}
|
|
10179
|
+
`;
|
|
10180
|
+
__decorateClass$2([
|
|
10181
|
+
n2({ type: Boolean, reflect: true })
|
|
10182
|
+
], JupiterFilterRolesDialog.prototype, "open", 2);
|
|
10183
|
+
__decorateClass$2([
|
|
10184
|
+
n2({ type: Array })
|
|
10185
|
+
], JupiterFilterRolesDialog.prototype, "availableRoles", 2);
|
|
10186
|
+
__decorateClass$2([
|
|
10187
|
+
n2({ type: Array })
|
|
10188
|
+
], JupiterFilterRolesDialog.prototype, "selectedRoleIds", 2);
|
|
10189
|
+
__decorateClass$2([
|
|
10190
|
+
n2({ type: Object })
|
|
10191
|
+
], JupiterFilterRolesDialog.prototype, "periodPreferences", 2);
|
|
10192
|
+
__decorateClass$2([
|
|
10193
|
+
n2({ type: String })
|
|
10194
|
+
], JupiterFilterRolesDialog.prototype, "mode", 2);
|
|
10195
|
+
__decorateClass$2([
|
|
10196
|
+
n2({ type: Object })
|
|
10197
|
+
], JupiterFilterRolesDialog.prototype, "hypercubeData", 2);
|
|
10198
|
+
__decorateClass$2([
|
|
10199
|
+
n2({ type: Boolean })
|
|
10200
|
+
], JupiterFilterRolesDialog.prototype, "showFactsOnly", 2);
|
|
10201
|
+
__decorateClass$2([
|
|
10202
|
+
n2({ type: String })
|
|
10203
|
+
], JupiterFilterRolesDialog.prototype, "conceptSearchText", 2);
|
|
10204
|
+
__decorateClass$2([
|
|
10205
|
+
r()
|
|
10206
|
+
], JupiterFilterRolesDialog.prototype, "_tempSelectedRoles", 2);
|
|
10207
|
+
__decorateClass$2([
|
|
10208
|
+
r()
|
|
10209
|
+
], JupiterFilterRolesDialog.prototype, "_searchQuery", 2);
|
|
10210
|
+
__decorateClass$2([
|
|
10211
|
+
r()
|
|
10212
|
+
], JupiterFilterRolesDialog.prototype, "_filteredRoles", 2);
|
|
10213
|
+
__decorateClass$2([
|
|
10214
|
+
r()
|
|
10215
|
+
], JupiterFilterRolesDialog.prototype, "_tempPeriodPreferences", 2);
|
|
10216
|
+
__decorateClass$2([
|
|
10217
|
+
r()
|
|
10218
|
+
], JupiterFilterRolesDialog.prototype, "_selectedAvailableRole", 2);
|
|
10219
|
+
__decorateClass$2([
|
|
10220
|
+
r()
|
|
10221
|
+
], JupiterFilterRolesDialog.prototype, "_selectedChosenRole", 2);
|
|
10222
|
+
__decorateClass$2([
|
|
10223
|
+
r()
|
|
10224
|
+
], JupiterFilterRolesDialog.prototype, "_chosenSearchQuery", 2);
|
|
10225
|
+
__decorateClass$2([
|
|
10226
|
+
r()
|
|
10227
|
+
], JupiterFilterRolesDialog.prototype, "_draggedRoleId", 2);
|
|
10228
|
+
__decorateClass$2([
|
|
10229
|
+
r()
|
|
10230
|
+
], JupiterFilterRolesDialog.prototype, "_dragOverRoleId", 2);
|
|
10231
|
+
__decorateClass$2([
|
|
10232
|
+
r()
|
|
10233
|
+
], JupiterFilterRolesDialog.prototype, "_chosenRoleOrder", 2);
|
|
10234
|
+
__decorateClass$2([
|
|
10235
|
+
r()
|
|
10236
|
+
], JupiterFilterRolesDialog.prototype, "_showAdvancedFilter", 2);
|
|
10237
|
+
__decorateClass$2([
|
|
10238
|
+
r()
|
|
10239
|
+
], JupiterFilterRolesDialog.prototype, "_showFactsOnly", 2);
|
|
10240
|
+
__decorateClass$2([
|
|
10241
|
+
r()
|
|
10242
|
+
], JupiterFilterRolesDialog.prototype, "_conceptSearchText", 2);
|
|
10243
|
+
__decorateClass$2([
|
|
10244
|
+
r()
|
|
10245
|
+
], JupiterFilterRolesDialog.prototype, "_collapsedRoles", 2);
|
|
10246
|
+
JupiterFilterRolesDialog = __decorateClass$2([
|
|
10247
|
+
t$1("jupiter-filter-roles-dialog")
|
|
10248
|
+
], JupiterFilterRolesDialog);
|
|
10249
|
+
var __defProp$1 = Object.defineProperty;
|
|
10250
|
+
var __getOwnPropDesc$1 = Object.getOwnPropertyDescriptor;
|
|
10251
|
+
var __decorateClass$1 = (decorators, target, key, kind) => {
|
|
10252
|
+
var result = kind > 1 ? void 0 : kind ? __getOwnPropDesc$1(target, key) : target;
|
|
10253
|
+
for (var i2 = decorators.length - 1, decorator; i2 >= 0; i2--)
|
|
10254
|
+
if (decorator = decorators[i2])
|
|
10255
|
+
result = (kind ? decorator(target, key, result) : decorator(result)) || result;
|
|
10256
|
+
if (kind && result)
|
|
10257
|
+
__defProp$1(target, key, result);
|
|
10258
|
+
return result;
|
|
10259
|
+
};
|
|
10260
|
+
let JupiterFormulaValidationDialog = class extends LitElement {
|
|
10261
|
+
constructor() {
|
|
10262
|
+
super(...arguments);
|
|
10263
|
+
this.results = [];
|
|
10264
|
+
this.open = false;
|
|
10265
|
+
this._collapsedGroups = /* @__PURE__ */ new Set();
|
|
10266
|
+
this._boundHandleKeydown = this._handleKeydown.bind(this);
|
|
10267
|
+
}
|
|
10268
|
+
connectedCallback() {
|
|
10269
|
+
super.connectedCallback();
|
|
10270
|
+
window.addEventListener("keydown", this._boundHandleKeydown);
|
|
10271
|
+
}
|
|
10272
|
+
disconnectedCallback() {
|
|
10273
|
+
window.removeEventListener("keydown", this._boundHandleKeydown);
|
|
10274
|
+
super.disconnectedCallback();
|
|
10275
|
+
}
|
|
10276
|
+
_handleKeydown(event) {
|
|
10277
|
+
if (this.open && event.key === "Escape") {
|
|
10278
|
+
this._handleClose();
|
|
10279
|
+
}
|
|
10280
|
+
}
|
|
10281
|
+
_handleClose() {
|
|
10282
|
+
this.open = false;
|
|
10283
|
+
this.dispatchEvent(new CustomEvent("dialog-cancel", { bubbles: true }));
|
|
10284
|
+
}
|
|
10285
|
+
_toggleGroup(roleLabel) {
|
|
10286
|
+
if (this._collapsedGroups.has(roleLabel)) {
|
|
10287
|
+
this._collapsedGroups.delete(roleLabel);
|
|
10288
|
+
} else {
|
|
10289
|
+
this._collapsedGroups.add(roleLabel);
|
|
10290
|
+
}
|
|
10291
|
+
this.requestUpdate();
|
|
10292
|
+
}
|
|
10293
|
+
_groupByRole(failures) {
|
|
10294
|
+
const grouped = failures.reduce((groups, result) => {
|
|
10295
|
+
var _a;
|
|
10296
|
+
(groups[_a = result.roleLabel] ?? (groups[_a] = [])).push(result);
|
|
10297
|
+
return groups;
|
|
10298
|
+
}, {});
|
|
10299
|
+
return Object.entries(grouped);
|
|
10300
|
+
}
|
|
10301
|
+
render() {
|
|
10302
|
+
if (!this.open)
|
|
10303
|
+
return html``;
|
|
10304
|
+
const failures = this.results.filter((result) => !result.skipped && !result.satisfied);
|
|
10305
|
+
const groups = this._groupByRole(failures);
|
|
10306
|
+
const summary = this.summary;
|
|
10307
|
+
return html`
|
|
10308
|
+
<div class="dialog" @click="${(e2) => e2.stopPropagation()}">
|
|
10309
|
+
<div class="dialog-header">
|
|
10310
|
+
<h2 class="dialog-title">${I18n.t("formulaValidation.dialogTitle")}</h2>
|
|
10311
|
+
${summary ? html`
|
|
10312
|
+
<p class="dialog-summary">
|
|
10313
|
+
${I18n.t("formulaValidation.summaryCount", { failed: summary.failed, total: summary.totalAssertions })}
|
|
10314
|
+
${summary.failed > 0 ? html`— ${I18n.t("formulaValidation.summaryCountBreakdown", { warnings: summary.failedWarnings, errors: summary.failedErrors })}` : ""}
|
|
10315
|
+
</p>
|
|
10316
|
+
` : ""}
|
|
10317
|
+
</div>
|
|
10318
|
+
|
|
10319
|
+
<div class="dialog-content">
|
|
10320
|
+
${failures.length === 0 ? html`
|
|
10321
|
+
<div class="all-passed">
|
|
10322
|
+
<div class="all-passed-icon">✓</div>
|
|
10323
|
+
<div class="all-passed-text">${I18n.t("formulaValidation.allPassed")}</div>
|
|
10324
|
+
</div>
|
|
10325
|
+
` : groups.map(([roleLabel, rows]) => {
|
|
10326
|
+
const collapsed = this._collapsedGroups.has(roleLabel);
|
|
10327
|
+
return html`
|
|
10328
|
+
<div class="role-group">
|
|
10329
|
+
<div class="role-group-header" @click="${() => this._toggleGroup(roleLabel)}">
|
|
10330
|
+
<span class="role-group-title">${roleLabel}</span>
|
|
10331
|
+
<span class="role-group-count">${rows.length}</span>
|
|
10332
|
+
<button class="role-group-toggle" type="button">${collapsed ? "▸" : "▾"}</button>
|
|
10333
|
+
</div>
|
|
10334
|
+
${collapsed ? "" : html`
|
|
10335
|
+
<div class="role-group-rows">
|
|
10336
|
+
${rows.map((result) => html`
|
|
10337
|
+
<div class="assertion-row">
|
|
10338
|
+
<span class="severity-badge ${result.severity === "ERROR" ? "error" : "warning"}">
|
|
10339
|
+
${result.severity === "ERROR" ? I18n.t("formulaValidation.severityError") : I18n.t("formulaValidation.severityWarning")}
|
|
10340
|
+
</span>
|
|
10341
|
+
<span class="assertion-message">${result.message}</span>
|
|
10342
|
+
</div>
|
|
10343
|
+
`)}
|
|
10344
|
+
</div>
|
|
10345
|
+
`}
|
|
10346
|
+
</div>
|
|
10347
|
+
`;
|
|
10348
|
+
})}
|
|
10349
|
+
</div>
|
|
10350
|
+
|
|
10351
|
+
<div class="dialog-actions">
|
|
10352
|
+
<button class="btn btn-primary" @click="${this._handleClose}">
|
|
10353
|
+
${I18n.t("formulaValidation.close")}
|
|
10354
|
+
</button>
|
|
10355
|
+
</div>
|
|
10356
|
+
</div>
|
|
10357
|
+
`;
|
|
10358
|
+
}
|
|
10359
|
+
};
|
|
10360
|
+
JupiterFormulaValidationDialog.styles = css`
|
|
10361
|
+
:host {
|
|
10362
|
+
position: fixed;
|
|
10363
|
+
top: 0;
|
|
10364
|
+
left: 0;
|
|
10365
|
+
width: 100%;
|
|
10366
|
+
height: 100%;
|
|
10367
|
+
background: rgba(0, 0, 0, 0.5);
|
|
10368
|
+
z-index: 1100;
|
|
10369
|
+
display: flex;
|
|
10370
|
+
align-items: center;
|
|
10371
|
+
justify-content: center;
|
|
10372
|
+
opacity: 0;
|
|
10373
|
+
visibility: hidden;
|
|
10374
|
+
transition: opacity 0.3s ease, visibility 0.3s ease;
|
|
10375
|
+
}
|
|
10376
|
+
|
|
10377
|
+
:host([open]) {
|
|
10378
|
+
opacity: 1;
|
|
10379
|
+
visibility: visible;
|
|
10380
|
+
}
|
|
10381
|
+
|
|
10382
|
+
.dialog {
|
|
10383
|
+
background: var(--bg-color-2, var(--jupiter-card-background, #fff));
|
|
10384
|
+
border-radius: 8px;
|
|
10385
|
+
padding: 24px;
|
|
10386
|
+
min-width: 420px;
|
|
10387
|
+
max-width: 640px;
|
|
10388
|
+
width: 90vw;
|
|
10389
|
+
max-height: 90vh;
|
|
10390
|
+
box-shadow: 0 10px 30px rgba(0, 0, 0, 0.3);
|
|
10391
|
+
transform: scale(0.9);
|
|
10392
|
+
transition: transform 0.3s ease;
|
|
10393
|
+
display: flex;
|
|
10394
|
+
flex-direction: column;
|
|
10395
|
+
}
|
|
10396
|
+
|
|
10397
|
+
:host([open]) .dialog {
|
|
10398
|
+
transform: scale(1);
|
|
10399
|
+
}
|
|
10400
|
+
|
|
10401
|
+
.dialog-header {
|
|
10402
|
+
margin-bottom: 16px;
|
|
10403
|
+
flex-shrink: 0;
|
|
10404
|
+
}
|
|
10405
|
+
|
|
10406
|
+
.dialog-title {
|
|
10407
|
+
font-size: 20px;
|
|
10408
|
+
font-weight: 600;
|
|
10409
|
+
color: var(--primaryTextColor, var(--jupiter-text-primary, #333));
|
|
10410
|
+
margin: 0 0 8px 0;
|
|
10411
|
+
}
|
|
10412
|
+
|
|
10413
|
+
.dialog-summary {
|
|
10414
|
+
font-size: 14px;
|
|
10415
|
+
color: var(--jupiter-text-secondary, #666);
|
|
10416
|
+
margin: 0;
|
|
10417
|
+
}
|
|
10418
|
+
|
|
10419
|
+
/* JDF-035 dialog-overflow fix: min-height: 0 is required on a flex-column scrollable child,
|
|
10420
|
+
otherwise the browser lets it grow past the dialog's max-height instead of scrolling. */
|
|
10421
|
+
.dialog-content {
|
|
10422
|
+
margin-bottom: 20px;
|
|
10423
|
+
flex: 1;
|
|
10424
|
+
overflow-y: auto;
|
|
10425
|
+
min-height: 0;
|
|
10426
|
+
}
|
|
10427
|
+
|
|
10428
|
+
.all-passed {
|
|
10429
|
+
display: flex;
|
|
10430
|
+
flex-direction: column;
|
|
10431
|
+
align-items: center;
|
|
10432
|
+
gap: 12px;
|
|
10433
|
+
padding: 32px 16px;
|
|
10434
|
+
color: var(--jupiter-text-primary, #333);
|
|
10435
|
+
}
|
|
10436
|
+
|
|
10437
|
+
.all-passed-icon {
|
|
10438
|
+
width: 40px;
|
|
10439
|
+
height: 40px;
|
|
10440
|
+
border-radius: 50%;
|
|
10441
|
+
background: var(--jupiter-success-color, #4caf50);
|
|
10442
|
+
color: #fff;
|
|
10443
|
+
display: flex;
|
|
10444
|
+
align-items: center;
|
|
10445
|
+
justify-content: center;
|
|
10446
|
+
font-size: 22px;
|
|
10447
|
+
font-weight: 700;
|
|
10448
|
+
}
|
|
10449
|
+
|
|
10450
|
+
.all-passed-text {
|
|
10451
|
+
font-size: 15px;
|
|
10452
|
+
font-weight: 500;
|
|
9098
10453
|
}
|
|
9099
10454
|
|
|
9100
|
-
.
|
|
9101
|
-
|
|
9102
|
-
|
|
9103
|
-
|
|
10455
|
+
.role-group {
|
|
10456
|
+
border: 1px solid var(--jupiter-border-color, #ddd);
|
|
10457
|
+
border-radius: 4px;
|
|
10458
|
+
margin-bottom: 12px;
|
|
10459
|
+
overflow: hidden;
|
|
9104
10460
|
}
|
|
9105
10461
|
|
|
9106
|
-
.
|
|
10462
|
+
.role-group-header {
|
|
10463
|
+
display: flex;
|
|
10464
|
+
align-items: center;
|
|
10465
|
+
justify-content: space-between;
|
|
10466
|
+
gap: 8px;
|
|
9107
10467
|
padding: 10px 12px;
|
|
9108
|
-
|
|
9109
|
-
border: 1px solid var(--jupiter-border-color, #ddd);
|
|
9110
|
-
border-radius: 4px;
|
|
10468
|
+
background: var(--jupiter-card-background, #fafafa);
|
|
9111
10469
|
cursor: pointer;
|
|
9112
|
-
|
|
9113
|
-
background: var(--jupiter-background, #fff);
|
|
10470
|
+
user-select: none;
|
|
9114
10471
|
}
|
|
9115
10472
|
|
|
9116
|
-
.
|
|
9117
|
-
|
|
9118
|
-
|
|
10473
|
+
.role-group-title {
|
|
10474
|
+
font-weight: 600;
|
|
10475
|
+
font-size: 14px;
|
|
10476
|
+
color: var(--primaryTextColor, var(--jupiter-text-primary, #333));
|
|
9119
10477
|
}
|
|
9120
10478
|
|
|
9121
|
-
.
|
|
9122
|
-
|
|
9123
|
-
color:
|
|
9124
|
-
border-color: var(--jupiter-primary-color, #1976d2);
|
|
10479
|
+
.role-group-count {
|
|
10480
|
+
font-size: 12px;
|
|
10481
|
+
color: var(--jupiter-text-secondary, #666);
|
|
9125
10482
|
}
|
|
9126
10483
|
|
|
9127
|
-
.
|
|
9128
|
-
|
|
9129
|
-
|
|
10484
|
+
.role-group-toggle {
|
|
10485
|
+
background: none;
|
|
10486
|
+
border: none;
|
|
10487
|
+
cursor: pointer;
|
|
10488
|
+
font-size: 12px;
|
|
10489
|
+
color: var(--jupiter-text-secondary, #666);
|
|
10490
|
+
padding: 0 4px;
|
|
9130
10491
|
}
|
|
9131
10492
|
|
|
9132
|
-
.
|
|
9133
|
-
|
|
9134
|
-
margin-top: 3px;
|
|
10493
|
+
.role-group-rows {
|
|
10494
|
+
padding: 4px 12px 8px 12px;
|
|
9135
10495
|
}
|
|
9136
10496
|
|
|
9137
|
-
.
|
|
9138
|
-
|
|
10497
|
+
.assertion-row {
|
|
10498
|
+
display: flex;
|
|
10499
|
+
align-items: flex-start;
|
|
10500
|
+
gap: 8px;
|
|
10501
|
+
padding: 8px 0;
|
|
10502
|
+
border-top: 1px solid var(--jupiter-border-color, #eee);
|
|
9139
10503
|
}
|
|
9140
10504
|
|
|
9141
|
-
.
|
|
9142
|
-
|
|
9143
|
-
font-size: 14px;
|
|
9144
|
-
margin-bottom: 4px;
|
|
10505
|
+
.assertion-row:first-child {
|
|
10506
|
+
border-top: none;
|
|
9145
10507
|
}
|
|
9146
10508
|
|
|
9147
|
-
.
|
|
10509
|
+
.severity-badge {
|
|
10510
|
+
flex-shrink: 0;
|
|
10511
|
+
display: inline-flex;
|
|
10512
|
+
align-items: center;
|
|
10513
|
+
gap: 4px;
|
|
10514
|
+
padding: 2px 8px;
|
|
10515
|
+
border-radius: 10px;
|
|
9148
10516
|
font-size: 11px;
|
|
9149
|
-
|
|
9150
|
-
|
|
9151
|
-
|
|
9152
|
-
|
|
9153
|
-
.picklist-controls {
|
|
9154
|
-
display: flex;
|
|
9155
|
-
flex-direction: column;
|
|
9156
|
-
justify-content: center;
|
|
9157
|
-
gap: 8px;
|
|
9158
|
-
padding: 0 8px;
|
|
10517
|
+
font-weight: 700;
|
|
10518
|
+
color: #fff;
|
|
10519
|
+
white-space: nowrap;
|
|
9159
10520
|
}
|
|
9160
10521
|
|
|
9161
|
-
.
|
|
9162
|
-
background: var(--jupiter-
|
|
9163
|
-
color: white;
|
|
9164
|
-
border: none;
|
|
9165
|
-
padding: 8px 16px;
|
|
9166
|
-
border-radius: 4px;
|
|
9167
|
-
cursor: pointer;
|
|
9168
|
-
font-size: 14px;
|
|
9169
|
-
transition: background-color 0.2s ease;
|
|
10522
|
+
.severity-badge.warning {
|
|
10523
|
+
background: var(--jupiter-warning-color, #ff9800);
|
|
9170
10524
|
}
|
|
9171
10525
|
|
|
9172
|
-
.
|
|
9173
|
-
background: var(--jupiter-
|
|
10526
|
+
.severity-badge.error {
|
|
10527
|
+
background: var(--jupiter-error-color, #d32f2f);
|
|
9174
10528
|
}
|
|
9175
10529
|
|
|
9176
|
-
.
|
|
9177
|
-
|
|
9178
|
-
|
|
10530
|
+
.assertion-message {
|
|
10531
|
+
font-size: 13px;
|
|
10532
|
+
color: var(--primaryTextColor, var(--jupiter-text-primary, #333));
|
|
10533
|
+
line-height: 1.4;
|
|
9179
10534
|
}
|
|
9180
10535
|
|
|
9181
|
-
.
|
|
9182
|
-
|
|
9183
|
-
|
|
9184
|
-
|
|
9185
|
-
|
|
10536
|
+
.dialog-actions {
|
|
10537
|
+
display: flex;
|
|
10538
|
+
gap: 12px;
|
|
10539
|
+
justify-content: flex-end;
|
|
10540
|
+
flex-shrink: 0;
|
|
9186
10541
|
border-top: 1px solid var(--jupiter-border-color, #ddd);
|
|
9187
|
-
|
|
10542
|
+
padding-top: 16px;
|
|
10543
|
+
margin-top: 16px;
|
|
9188
10544
|
}
|
|
9189
10545
|
|
|
9190
|
-
.btn
|
|
9191
|
-
|
|
10546
|
+
.btn {
|
|
10547
|
+
padding: 10px 20px;
|
|
9192
10548
|
border: none;
|
|
9193
|
-
|
|
9194
|
-
padding: 10px 8px;
|
|
10549
|
+
border-radius: 4px;
|
|
9195
10550
|
font-size: 14px;
|
|
9196
10551
|
font-weight: 500;
|
|
9197
|
-
font-family: inherit;
|
|
9198
10552
|
cursor: pointer;
|
|
9199
|
-
margin-right: auto;
|
|
9200
|
-
border-radius: 4px;
|
|
9201
10553
|
transition: background-color 0.2s ease;
|
|
9202
10554
|
}
|
|
9203
10555
|
|
|
9204
|
-
.btn-
|
|
9205
|
-
background: var(--
|
|
10556
|
+
.btn-primary {
|
|
10557
|
+
background: var(--buttonBgColor, var(--jupiter-primary-color, #1976d2));
|
|
10558
|
+
color: var(--buttonTextColor, white);
|
|
10559
|
+
}
|
|
10560
|
+
|
|
10561
|
+
.btn-primary:hover {
|
|
10562
|
+
opacity: 0.9;
|
|
9206
10563
|
}
|
|
9207
10564
|
`;
|
|
9208
|
-
__decorateClass$1([
|
|
9209
|
-
n2({ type: Boolean, reflect: true })
|
|
9210
|
-
], JupiterFilterRolesDialog.prototype, "open", 2);
|
|
9211
10565
|
__decorateClass$1([
|
|
9212
10566
|
n2({ type: Array })
|
|
9213
|
-
],
|
|
9214
|
-
__decorateClass$1([
|
|
9215
|
-
n2({ type: Array })
|
|
9216
|
-
], JupiterFilterRolesDialog.prototype, "selectedRoleIds", 2);
|
|
10567
|
+
], JupiterFormulaValidationDialog.prototype, "results", 2);
|
|
9217
10568
|
__decorateClass$1([
|
|
9218
10569
|
n2({ type: Object })
|
|
9219
|
-
],
|
|
9220
|
-
__decorateClass$1([
|
|
9221
|
-
n2({ type: String })
|
|
9222
|
-
], JupiterFilterRolesDialog.prototype, "mode", 2);
|
|
9223
|
-
__decorateClass$1([
|
|
9224
|
-
n2({ type: Object })
|
|
9225
|
-
], JupiterFilterRolesDialog.prototype, "hypercubeData", 2);
|
|
9226
|
-
__decorateClass$1([
|
|
9227
|
-
n2({ type: Boolean })
|
|
9228
|
-
], JupiterFilterRolesDialog.prototype, "showFactsOnly", 2);
|
|
9229
|
-
__decorateClass$1([
|
|
9230
|
-
n2({ type: String })
|
|
9231
|
-
], JupiterFilterRolesDialog.prototype, "conceptSearchText", 2);
|
|
9232
|
-
__decorateClass$1([
|
|
9233
|
-
r()
|
|
9234
|
-
], JupiterFilterRolesDialog.prototype, "_tempSelectedRoles", 2);
|
|
9235
|
-
__decorateClass$1([
|
|
9236
|
-
r()
|
|
9237
|
-
], JupiterFilterRolesDialog.prototype, "_searchQuery", 2);
|
|
9238
|
-
__decorateClass$1([
|
|
9239
|
-
r()
|
|
9240
|
-
], JupiterFilterRolesDialog.prototype, "_filteredRoles", 2);
|
|
9241
|
-
__decorateClass$1([
|
|
9242
|
-
r()
|
|
9243
|
-
], JupiterFilterRolesDialog.prototype, "_tempPeriodPreferences", 2);
|
|
9244
|
-
__decorateClass$1([
|
|
9245
|
-
r()
|
|
9246
|
-
], JupiterFilterRolesDialog.prototype, "_selectedAvailableRole", 2);
|
|
9247
|
-
__decorateClass$1([
|
|
9248
|
-
r()
|
|
9249
|
-
], JupiterFilterRolesDialog.prototype, "_selectedChosenRole", 2);
|
|
9250
|
-
__decorateClass$1([
|
|
9251
|
-
r()
|
|
9252
|
-
], JupiterFilterRolesDialog.prototype, "_chosenSearchQuery", 2);
|
|
9253
|
-
__decorateClass$1([
|
|
9254
|
-
r()
|
|
9255
|
-
], JupiterFilterRolesDialog.prototype, "_draggedRoleId", 2);
|
|
9256
|
-
__decorateClass$1([
|
|
9257
|
-
r()
|
|
9258
|
-
], JupiterFilterRolesDialog.prototype, "_dragOverRoleId", 2);
|
|
10570
|
+
], JupiterFormulaValidationDialog.prototype, "summary", 2);
|
|
9259
10571
|
__decorateClass$1([
|
|
9260
|
-
|
|
9261
|
-
],
|
|
9262
|
-
__decorateClass$1([
|
|
9263
|
-
r()
|
|
9264
|
-
], JupiterFilterRolesDialog.prototype, "_showAdvancedFilter", 2);
|
|
9265
|
-
__decorateClass$1([
|
|
9266
|
-
r()
|
|
9267
|
-
], JupiterFilterRolesDialog.prototype, "_showFactsOnly", 2);
|
|
9268
|
-
__decorateClass$1([
|
|
9269
|
-
r()
|
|
9270
|
-
], JupiterFilterRolesDialog.prototype, "_conceptSearchText", 2);
|
|
10572
|
+
n2({ type: Boolean, reflect: true })
|
|
10573
|
+
], JupiterFormulaValidationDialog.prototype, "open", 2);
|
|
9271
10574
|
__decorateClass$1([
|
|
9272
10575
|
r()
|
|
9273
|
-
],
|
|
9274
|
-
|
|
9275
|
-
t$1("jupiter-
|
|
9276
|
-
],
|
|
10576
|
+
], JupiterFormulaValidationDialog.prototype, "_collapsedGroups", 2);
|
|
10577
|
+
JupiterFormulaValidationDialog = __decorateClass$1([
|
|
10578
|
+
t$1("jupiter-formula-validation-dialog")
|
|
10579
|
+
], JupiterFormulaValidationDialog);
|
|
9277
10580
|
var __defProp = Object.defineProperty;
|
|
9278
10581
|
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
9279
10582
|
var __decorateClass = (decorators, target, key, kind) => {
|
|
@@ -9292,6 +10595,8 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
9292
10595
|
this.initialData = {};
|
|
9293
10596
|
this.disabled = false;
|
|
9294
10597
|
this.readonly = false;
|
|
10598
|
+
this.calculationEnabled = false;
|
|
10599
|
+
this.formulaEnabled = false;
|
|
9295
10600
|
this.periodStartDate = "2025-01-01";
|
|
9296
10601
|
this.periodEndDate = "2025-12-31";
|
|
9297
10602
|
this.language = "en";
|
|
@@ -9311,6 +10616,7 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
9311
10616
|
this._unitData = {};
|
|
9312
10617
|
this._preservedUnitData = {};
|
|
9313
10618
|
this._decimalsData = {};
|
|
10619
|
+
this._totalManuallyEditedData = {};
|
|
9314
10620
|
this._effectiveMasterData = void 0;
|
|
9315
10621
|
this._typedMemberData = {};
|
|
9316
10622
|
this._preservedTypedMemberData = {};
|
|
@@ -9343,6 +10649,9 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
9343
10649
|
this._contextMenuY = 0;
|
|
9344
10650
|
this._contextMenuRoleId = null;
|
|
9345
10651
|
this._validationStatus = "idle";
|
|
10652
|
+
this._formulaValidationResults = [];
|
|
10653
|
+
this._showFormulaValidationDialog = false;
|
|
10654
|
+
this._formulaValidationService = new FormulaValidationService();
|
|
9346
10655
|
this._skipDraftLoading = false;
|
|
9347
10656
|
this._skipPeriodPreferencesRestore = false;
|
|
9348
10657
|
this._autoSaveTimer = null;
|
|
@@ -9374,6 +10683,24 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
9374
10683
|
this.addEventListener("calculation-mismatch-changed", (e2) => {
|
|
9375
10684
|
this._handleCalculationMismatchChanged(e2);
|
|
9376
10685
|
});
|
|
10686
|
+
this.addEventListener("total-manually-edited", (e2) => {
|
|
10687
|
+
const { conceptId, columnId } = e2.detail;
|
|
10688
|
+
const updated = { ...this._totalManuallyEditedData };
|
|
10689
|
+
updated[conceptId] = { ...updated[conceptId], [columnId]: true };
|
|
10690
|
+
this._totalManuallyEditedData = updated;
|
|
10691
|
+
});
|
|
10692
|
+
this.addEventListener("calculation-total-auto-populated", (e2) => {
|
|
10693
|
+
const { conceptId, columnId, value } = e2.detail;
|
|
10694
|
+
const oldValue = this._writeFormDataValue(conceptId, columnId, value);
|
|
10695
|
+
this._touched.add(`${conceptId}-${columnId}`);
|
|
10696
|
+
this._dirty = true;
|
|
10697
|
+
this._validateForm();
|
|
10698
|
+
this.requestUpdate();
|
|
10699
|
+
this.dispatchEvent(new CustomEvent("field-change", {
|
|
10700
|
+
detail: { fieldId: conceptId, conceptId, columnId, value, oldValue, source: "auto-calculated" },
|
|
10701
|
+
bubbles: true
|
|
10702
|
+
}));
|
|
10703
|
+
});
|
|
9377
10704
|
document.addEventListener("click", () => {
|
|
9378
10705
|
if (this._showRoleContextMenu) {
|
|
9379
10706
|
this._showRoleContextMenu = false;
|
|
@@ -10048,6 +11375,12 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
10048
11375
|
const roleCount = this._getRoleIdsArray().length;
|
|
10049
11376
|
console.log(`🚫 Filter dialog cancelled. Current selection: ${roleCount}/${this._allSections.length}`);
|
|
10050
11377
|
}
|
|
11378
|
+
// JDF-050: closes the formula-validation results dialog opened by JDF-049's pre-flight.
|
|
11379
|
+
// Purely a visibility toggle — submit already proceeded on the click that opened it
|
|
11380
|
+
// (non-blocking, per the corrected JDF-043 Q4 decision), so there is nothing to resume here.
|
|
11381
|
+
_handleFormulaValidationDialogCancel() {
|
|
11382
|
+
this._showFormulaValidationDialog = false;
|
|
11383
|
+
}
|
|
10051
11384
|
_handleRoleFilterApply(event) {
|
|
10052
11385
|
var _a, _b;
|
|
10053
11386
|
const { selectedRoleIds, periodPreferences } = event.detail;
|
|
@@ -10075,7 +11408,8 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
10075
11408
|
this._repeatCounts,
|
|
10076
11409
|
this._decimalsData,
|
|
10077
11410
|
void 0,
|
|
10078
|
-
this._getHiddenColumnsForMetadata()
|
|
11411
|
+
this._getHiddenColumnsForMetadata(),
|
|
11412
|
+
this._totalManuallyEditedData
|
|
10079
11413
|
);
|
|
10080
11414
|
this._draftStorageService.saveDraft(currentFormData, currentMetadata);
|
|
10081
11415
|
console.log("✅ Current form data saved to draft storage with NEW preferences");
|
|
@@ -10184,9 +11518,13 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
10184
11518
|
this._calculationWarnings = next;
|
|
10185
11519
|
this._validateForm();
|
|
10186
11520
|
}
|
|
10187
|
-
|
|
10188
|
-
|
|
10189
|
-
|
|
11521
|
+
/**
|
|
11522
|
+
* JDF-058: single source of truth for writing a value into `_formData` with the immutable-update
|
|
11523
|
+
* pattern Lit reactivity needs — shared by a real user keystroke (`_handleFieldChange`) and the
|
|
11524
|
+
* auto-populate-totals `calculation-total-auto-populated` handler, so the update logic isn't
|
|
11525
|
+
* duplicated. Returns the value that was previously stored, for event `oldValue` fields.
|
|
11526
|
+
*/
|
|
11527
|
+
_writeFormDataValue(conceptId, columnId, value) {
|
|
10190
11528
|
const updatedFormData = { ...this._formData };
|
|
10191
11529
|
if (!updatedFormData[conceptId]) {
|
|
10192
11530
|
updatedFormData[conceptId] = {};
|
|
@@ -10194,6 +11532,12 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
10194
11532
|
const oldValue = updatedFormData[conceptId][columnId];
|
|
10195
11533
|
updatedFormData[conceptId] = { ...updatedFormData[conceptId], [columnId]: value };
|
|
10196
11534
|
this._formData = updatedFormData;
|
|
11535
|
+
return oldValue;
|
|
11536
|
+
}
|
|
11537
|
+
_handleFieldChange(event) {
|
|
11538
|
+
const { fieldId, conceptId, columnId, value } = event.detail;
|
|
11539
|
+
console.log(`📝 Field change: conceptId=${conceptId}, columnId=${columnId}, value=${value}, fieldId=${fieldId}`);
|
|
11540
|
+
const oldValue = this._writeFormDataValue(conceptId, columnId, value);
|
|
10197
11541
|
console.log(`💾 Updated formData[${conceptId}]:`, this._formData[conceptId]);
|
|
10198
11542
|
this._touched.add(`${conceptId}-${columnId}`);
|
|
10199
11543
|
this._dirty = true;
|
|
@@ -11175,6 +12519,7 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
11175
12519
|
return;
|
|
11176
12520
|
}
|
|
11177
12521
|
this._correctLegacyPeriodStartInstantDates();
|
|
12522
|
+
this._runFormulaValidationPreflight();
|
|
11178
12523
|
const submissionData = this._generateSubmissionData();
|
|
11179
12524
|
console.log("📊 Form Submission Data:", JSON.stringify(submissionData, null, 2));
|
|
11180
12525
|
console.log("📊 Submission Data Summary:");
|
|
@@ -11196,6 +12541,58 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
11196
12541
|
this._submitDisabled = false;
|
|
11197
12542
|
}, 1e3);
|
|
11198
12543
|
}
|
|
12544
|
+
/**
|
|
12545
|
+
* JDF-049: runs FormulaValidationService against the live form state and stores the results
|
|
12546
|
+
* for the results dialog (JDF-050). Graceful no-op — per JDF-048's gating and this ticket's
|
|
12547
|
+
* "no Validate-formulas affordance/effect when formula data is absent" requirement — when
|
|
12548
|
+
* `formulaEnabled` is off or `xbrlInput.formula` has no roles. Never blocks the caller; always
|
|
12549
|
+
* returns before any resolution work is attempted when gated off (JDF-048's "zero evaluation
|
|
12550
|
+
* cost when off" requirement).
|
|
12551
|
+
*/
|
|
12552
|
+
_runFormulaValidationPreflight() {
|
|
12553
|
+
var _a, _b, _c, _d, _e, _f, _g, _h, _i;
|
|
12554
|
+
if (!this.formulaEnabled)
|
|
12555
|
+
return;
|
|
12556
|
+
const formulaRoles = (_c = (_b = (_a = this.xbrlInput) == null ? void 0 : _a.formula) == null ? void 0 : _b[0]) == null ? void 0 : _c.roles;
|
|
12557
|
+
if (!formulaRoles || formulaRoles.length === 0)
|
|
12558
|
+
return;
|
|
12559
|
+
const ctx = buildFormulaResolutionContext(
|
|
12560
|
+
this._formData,
|
|
12561
|
+
this._mergeAllSectionColumns(),
|
|
12562
|
+
((_f = (_e = (_d = this.xbrlInput) == null ? void 0 : _d.presentation) == null ? void 0 : _e[0]) == null ? void 0 : _f.roles) || [],
|
|
12563
|
+
(_i = (_h = (_g = this.xbrlInput) == null ? void 0 : _g.hypercubes) == null ? void 0 : _h[0]) == null ? void 0 : _i.roles,
|
|
12564
|
+
this.periodStartDate,
|
|
12565
|
+
this.periodEndDate
|
|
12566
|
+
);
|
|
12567
|
+
const results = this._formulaValidationService.evaluate(this.xbrlInput, ctx, this.language);
|
|
12568
|
+
const summary = this._formulaValidationService.summarize(results);
|
|
12569
|
+
this._formulaValidationResults = results;
|
|
12570
|
+
this._formulaValidationSummary = summary;
|
|
12571
|
+
const hasFailures = results.some((result) => !result.skipped && !result.satisfied);
|
|
12572
|
+
if (hasFailures) {
|
|
12573
|
+
this._showFormulaValidationDialog = true;
|
|
12574
|
+
}
|
|
12575
|
+
this.dispatchEvent(new CustomEvent("formula-validation-complete", {
|
|
12576
|
+
detail: { results, summary },
|
|
12577
|
+
bubbles: true,
|
|
12578
|
+
composed: true
|
|
12579
|
+
}));
|
|
12580
|
+
}
|
|
12581
|
+
/**
|
|
12582
|
+
* Formula assertions can reference concepts/dimensions from any disclosure role, but
|
|
12583
|
+
* `FormColumn`s (especially dimension columns) are tracked per-section (`section.columns`),
|
|
12584
|
+
* with `this._columns` as the shared/default fallback (see the pattern at L1398/L2814/L5284).
|
|
12585
|
+
* `_formData` itself is already global (keyed by conceptId/columnId, no section nesting), so a
|
|
12586
|
+
* single merged, deduplicated-by-id column list is the correct match for it.
|
|
12587
|
+
*/
|
|
12588
|
+
_mergeAllSectionColumns() {
|
|
12589
|
+
const merged = /* @__PURE__ */ new Map();
|
|
12590
|
+
this._columns.forEach((column2) => merged.set(column2.id, column2));
|
|
12591
|
+
this._allSections.forEach((section2) => {
|
|
12592
|
+
(section2.columns || []).forEach((column2) => merged.set(column2.id, column2));
|
|
12593
|
+
});
|
|
12594
|
+
return Array.from(merged.values());
|
|
12595
|
+
}
|
|
11199
12596
|
_handleSaveDraft(source = "manual") {
|
|
11200
12597
|
console.log(`🔵 [Save Draft] Checking for errors...`);
|
|
11201
12598
|
console.log(`🔵 [Save Draft] _xbrlFormErrors.length: ${this._xbrlFormErrors.length}`);
|
|
@@ -11233,7 +12630,8 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
11233
12630
|
this._repeatCounts,
|
|
11234
12631
|
this._decimalsData,
|
|
11235
12632
|
roleCompletedStates,
|
|
11236
|
-
this._getHiddenColumnsForMetadata()
|
|
12633
|
+
this._getHiddenColumnsForMetadata(),
|
|
12634
|
+
this._totalManuallyEditedData
|
|
11237
12635
|
);
|
|
11238
12636
|
const draftPayloadSnapshot = JSON.stringify({
|
|
11239
12637
|
draftData,
|
|
@@ -11375,6 +12773,10 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
11375
12773
|
);
|
|
11376
12774
|
console.log("🔄 Restored hidden columns for", this._hiddenColumnIds.size, "sections");
|
|
11377
12775
|
}
|
|
12776
|
+
if (metadata.totalManuallyEditedData) {
|
|
12777
|
+
this._totalManuallyEditedData = metadata.totalManuallyEditedData;
|
|
12778
|
+
console.log("🔄 Restored total manually-edited data:", Object.keys(this._totalManuallyEditedData).length, "concepts");
|
|
12779
|
+
}
|
|
11378
12780
|
if (metadata.periodPreferences) {
|
|
11379
12781
|
if (this._skipPeriodPreferencesRestore) {
|
|
11380
12782
|
console.log("⏭️ Skipping period preferences restoration - using new filter selections");
|
|
@@ -11454,6 +12856,7 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
11454
12856
|
});
|
|
11455
12857
|
this._formData = { ...this._formData, ...restoredFormData };
|
|
11456
12858
|
console.log(`🔄 Restored ${Object.keys(restoredFormData).length} concepts with data`);
|
|
12859
|
+
this._seedLegacyManuallyEditedTotals(restoredFormData);
|
|
11457
12860
|
this._initializeGlobalDecimalsFromRoundingData();
|
|
11458
12861
|
this._periodData = {
|
|
11459
12862
|
...this._periodData,
|
|
@@ -11587,6 +12990,47 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
11587
12990
|
});
|
|
11588
12991
|
console.log(`✅ Field population complete: ${populatedCount} populated, ${notFoundCount} not found`);
|
|
11589
12992
|
}
|
|
12993
|
+
/**
|
|
12994
|
+
* JDF-058: seed the manual-edit dirty flag for any total whose value predates this feature, so
|
|
12995
|
+
* upgrading never silently recomputes a customer's pre-existing, already-filed totals. Walks
|
|
12996
|
+
* `_allSections` (the full pool, including currently-hidden/filtered-out sections — a hidden
|
|
12997
|
+
* total's pre-existing value must stay protected the moment its section becomes visible again),
|
|
12998
|
+
* not just the currently-selected roles. Idempotent: only seeds a cell that has no explicit
|
|
12999
|
+
* `totalManuallyEditedData` entry already (i.e. `metadata.totalManuallyEditedData` didn't cover
|
|
13000
|
+
* it), so re-running on an already-seeded draft is a no-op. Does not touch `restoredFormData`.
|
|
13001
|
+
*/
|
|
13002
|
+
_seedLegacyManuallyEditedTotals(restoredFormData) {
|
|
13003
|
+
const seeded = { ...this._totalManuallyEditedData };
|
|
13004
|
+
let changed = false;
|
|
13005
|
+
const walk = (concepts) => {
|
|
13006
|
+
var _a;
|
|
13007
|
+
for (const concept of concepts) {
|
|
13008
|
+
if (isTotalLabel$1(concept.preferredLabel)) {
|
|
13009
|
+
const values = restoredFormData[concept.id];
|
|
13010
|
+
if (values) {
|
|
13011
|
+
for (const columnId of Object.keys(values)) {
|
|
13012
|
+
const value = values[columnId];
|
|
13013
|
+
const isBlank = value === null || value === void 0 || value === "";
|
|
13014
|
+
if (!isBlank && ((_a = seeded[concept.id]) == null ? void 0 : _a[columnId]) === void 0) {
|
|
13015
|
+
seeded[concept.id] = { ...seeded[concept.id] || {}, [columnId]: true };
|
|
13016
|
+
changed = true;
|
|
13017
|
+
}
|
|
13018
|
+
}
|
|
13019
|
+
}
|
|
13020
|
+
}
|
|
13021
|
+
if (concept.children && concept.children.length > 0) {
|
|
13022
|
+
walk(concept.children);
|
|
13023
|
+
}
|
|
13024
|
+
}
|
|
13025
|
+
};
|
|
13026
|
+
for (const section2 of this._allSections) {
|
|
13027
|
+
walk(section2.concepts || []);
|
|
13028
|
+
}
|
|
13029
|
+
if (changed) {
|
|
13030
|
+
this._totalManuallyEditedData = seeded;
|
|
13031
|
+
console.log("🔒 [JDF-058] Seeded manual-edit protection for pre-existing total values in legacy draft");
|
|
13032
|
+
}
|
|
13033
|
+
}
|
|
11590
13034
|
_restoreCustomColumns(customColumns) {
|
|
11591
13035
|
const columnsBySection = /* @__PURE__ */ new Map();
|
|
11592
13036
|
customColumns.forEach((col) => {
|
|
@@ -13035,6 +14479,8 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
13035
14479
|
.masterData="${this._effectiveMasterData}"
|
|
13036
14480
|
.periodStartDate="${this.periodStartDate}"
|
|
13037
14481
|
.periodEndDate="${this.periodEndDate}"
|
|
14482
|
+
.calculationEnabled="${this.calculationEnabled}"
|
|
14483
|
+
.totalManuallyEditedData="${this._totalManuallyEditedData}"
|
|
13038
14484
|
@field-change="${this._handleFieldChange}"
|
|
13039
14485
|
@period-change="${this._handlePeriodChange}"
|
|
13040
14486
|
@typed-member-change="${this._handleTypedMemberChange}"
|
|
@@ -13182,6 +14628,8 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
13182
14628
|
.masterData="${this._effectiveMasterData}"
|
|
13183
14629
|
.periodStartDate="${this.periodStartDate}"
|
|
13184
14630
|
.periodEndDate="${this.periodEndDate}"
|
|
14631
|
+
.calculationEnabled="${this.calculationEnabled}"
|
|
14632
|
+
.totalManuallyEditedData="${this._totalManuallyEditedData}"
|
|
13185
14633
|
@field-change="${this._handleFieldChange}"
|
|
13186
14634
|
@typed-member-change="${this._handleTypedMemberChange}"
|
|
13187
14635
|
@add-concept-repeat="${this._handleAddConceptRepeat}"
|
|
@@ -13604,7 +15052,18 @@ let JupiterDynamicForm = class extends LitElement {
|
|
|
13604
15052
|
@click="${this._handleFilterDialogCancel}"
|
|
13605
15053
|
></jupiter-filter-roles-dialog>
|
|
13606
15054
|
` : ""}
|
|
13607
|
-
|
|
15055
|
+
|
|
15056
|
+
<!-- Formula Validation Results Dialog (JDF-050) -->
|
|
15057
|
+
${this._showFormulaValidationDialog ? html`
|
|
15058
|
+
<jupiter-formula-validation-dialog
|
|
15059
|
+
?open="${this._showFormulaValidationDialog}"
|
|
15060
|
+
.results="${this._formulaValidationResults}"
|
|
15061
|
+
.summary="${this._formulaValidationSummary}"
|
|
15062
|
+
@dialog-cancel="${this._handleFormulaValidationDialogCancel}"
|
|
15063
|
+
@click="${this._handleFormulaValidationDialogCancel}"
|
|
15064
|
+
></jupiter-formula-validation-dialog>
|
|
15065
|
+
` : ""}
|
|
15066
|
+
|
|
13608
15067
|
<!-- Validation Error Popup -->
|
|
13609
15068
|
${this._showErrorPopup ? html`
|
|
13610
15069
|
<div class="error-popup-overlay" @click="${() => {
|
|
@@ -14518,6 +15977,12 @@ __decorateClass([
|
|
|
14518
15977
|
__decorateClass([
|
|
14519
15978
|
n2({ type: Boolean })
|
|
14520
15979
|
], JupiterDynamicForm.prototype, "readonly", 2);
|
|
15980
|
+
__decorateClass([
|
|
15981
|
+
n2({ type: Boolean, attribute: "calculation-enabled" })
|
|
15982
|
+
], JupiterDynamicForm.prototype, "calculationEnabled", 2);
|
|
15983
|
+
__decorateClass([
|
|
15984
|
+
n2({ type: Boolean, attribute: "formula-enabled" })
|
|
15985
|
+
], JupiterDynamicForm.prototype, "formulaEnabled", 2);
|
|
14521
15986
|
__decorateClass([
|
|
14522
15987
|
n2({ type: String })
|
|
14523
15988
|
], JupiterDynamicForm.prototype, "periodStartDate", 2);
|
|
@@ -14590,6 +16055,9 @@ __decorateClass([
|
|
|
14590
16055
|
__decorateClass([
|
|
14591
16056
|
r()
|
|
14592
16057
|
], JupiterDynamicForm.prototype, "_decimalsData", 2);
|
|
16058
|
+
__decorateClass([
|
|
16059
|
+
r()
|
|
16060
|
+
], JupiterDynamicForm.prototype, "_totalManuallyEditedData", 2);
|
|
14593
16061
|
__decorateClass([
|
|
14594
16062
|
r()
|
|
14595
16063
|
], JupiterDynamicForm.prototype, "_effectiveMasterData", 2);
|
|
@@ -14689,6 +16157,15 @@ __decorateClass([
|
|
|
14689
16157
|
__decorateClass([
|
|
14690
16158
|
r()
|
|
14691
16159
|
], JupiterDynamicForm.prototype, "_validationStatus", 2);
|
|
16160
|
+
__decorateClass([
|
|
16161
|
+
r()
|
|
16162
|
+
], JupiterDynamicForm.prototype, "_formulaValidationResults", 2);
|
|
16163
|
+
__decorateClass([
|
|
16164
|
+
r()
|
|
16165
|
+
], JupiterDynamicForm.prototype, "_formulaValidationSummary", 2);
|
|
16166
|
+
__decorateClass([
|
|
16167
|
+
r()
|
|
16168
|
+
], JupiterDynamicForm.prototype, "_showFormulaValidationDialog", 2);
|
|
14692
16169
|
JupiterDynamicForm = __decorateClass([
|
|
14693
16170
|
t$1("jupiter-dynamic-form")
|
|
14694
16171
|
], JupiterDynamicForm);
|
|
@@ -14703,6 +16180,7 @@ export {
|
|
|
14703
16180
|
JupiterFilterRolesDialog,
|
|
14704
16181
|
JupiterFormField,
|
|
14705
16182
|
JupiterFormSection,
|
|
16183
|
+
JupiterFormulaValidationDialog,
|
|
14706
16184
|
TYPE_INPUT_MAP,
|
|
14707
16185
|
XBRLValidator,
|
|
14708
16186
|
collectEnumerationsFromChain,
|