@salesforce/plugin-bre-to-cml 1.3.0 → 1.3.2

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.
Files changed (50) hide show
  1. package/README.md +117 -4
  2. package/lib/commands/cml/convert/surcharge-rules.d.ts +12 -0
  3. package/lib/commands/cml/convert/surcharge-rules.js +79 -5
  4. package/lib/commands/cml/convert/surcharge-rules.js.map +1 -1
  5. package/lib/commands/cml/convert/underwriting-rules.d.ts +41 -2
  6. package/lib/commands/cml/convert/underwriting-rules.js +141 -17
  7. package/lib/commands/cml/convert/underwriting-rules.js.map +1 -1
  8. package/lib/commands/insurance/import/record-updates.d.ts +66 -0
  9. package/lib/commands/insurance/import/record-updates.js +239 -0
  10. package/lib/commands/insurance/import/record-updates.js.map +1 -0
  11. package/lib/shared/cml-operators.d.ts +9 -1
  12. package/lib/shared/cml-operators.js +23 -5
  13. package/lib/shared/cml-operators.js.map +1 -1
  14. package/lib/shared/insurance/confirm-org-changes.d.ts +49 -0
  15. package/lib/shared/insurance/confirm-org-changes.js +43 -0
  16. package/lib/shared/insurance/confirm-org-changes.js.map +1 -0
  17. package/lib/shared/insurance/insurance-cml-merge.d.ts +100 -13
  18. package/lib/shared/insurance/insurance-cml-merge.js +355 -54
  19. package/lib/shared/insurance/insurance-cml-merge.js.map +1 -1
  20. package/lib/shared/insurance/insurance-context-tags.d.ts +124 -0
  21. package/lib/shared/insurance/insurance-context-tags.js +210 -0
  22. package/lib/shared/insurance/insurance-context-tags.js.map +1 -0
  23. package/lib/shared/insurance/insurance-org.d.ts +12 -0
  24. package/lib/shared/insurance/insurance-org.js +38 -2
  25. package/lib/shared/insurance/insurance-org.js.map +1 -1
  26. package/lib/shared/insurance/insurance-rule-convert-command.d.ts +27 -0
  27. package/lib/shared/insurance/insurance-rule-convert-command.js +57 -4
  28. package/lib/shared/insurance/insurance-rule-convert-command.js.map +1 -1
  29. package/lib/shared/insurance/insurance-rule-generator.d.ts +101 -8
  30. package/lib/shared/insurance/insurance-rule-generator.js +293 -42
  31. package/lib/shared/insurance/insurance-rule-generator.js.map +1 -1
  32. package/lib/shared/insurance/models.d.ts +2 -1
  33. package/lib/shared/insurance/planned-change-mapper.d.ts +15 -0
  34. package/lib/shared/insurance/planned-change-mapper.js +51 -0
  35. package/lib/shared/insurance/planned-change-mapper.js.map +1 -0
  36. package/lib/shared/insurance/planned-change.d.ts +83 -0
  37. package/lib/shared/insurance/planned-change.js +74 -0
  38. package/lib/shared/insurance/planned-change.js.map +1 -0
  39. package/lib/shared/insurance/record-update-apply.d.ts +100 -0
  40. package/lib/shared/insurance/record-update-apply.js +303 -0
  41. package/lib/shared/insurance/record-update-apply.js.map +1 -0
  42. package/lib/shared/insurance/record-update-plan.d.ts +104 -0
  43. package/lib/shared/insurance/record-update-plan.js +397 -0
  44. package/lib/shared/insurance/record-update-plan.js.map +1 -0
  45. package/messages/cml.convert.surcharge-rules.md +3 -1
  46. package/messages/cml.convert.underwriting-rules.md +1 -1
  47. package/messages/insurance.import.record-updates.md +176 -0
  48. package/oclif.lock +28 -28
  49. package/oclif.manifest.json +127 -35
  50. package/package.json +16 -8
@@ -14,11 +14,29 @@ export function doubleQuotedIfNeeded(value, dataType) {
14
14
  const singleValue = value[0];
15
15
  return `${dataType === 'string' ? doubleQuoted(singleValue) ?? '' : singleValue ?? "''"}`;
16
16
  }
17
- export function generateInCmlExpression(left, right) {
17
+ /**
18
+ * Whether values of this resolved CML type are emitted quoted. An absent type means the caller
19
+ * resolved none, and quoting is the conservative direction — an unquoted value reaches the curated
20
+ * model verbatim. (`doubleQuotedIfNeeded` predates this and reads an absent type as non-string;
21
+ * `In`/`NotIn` are new to type-awareness, so an omitted type keeps their long-standing quoting.)
22
+ */
23
+ function quotesValues(dataType) {
24
+ return dataType === undefined || dataType === 'string';
25
+ }
26
+ /**
27
+ * Expands an In list into a chain of `==` comparisons. Because those are equality comparisons, the
28
+ * values follow the same quoting rule Equals follows: quoted only for `string`. Quoting a value
29
+ * against an attribute the model declares `decimal` compares a number with a string literal, and
30
+ * the comparison never fires.
31
+ *
32
+ * `dataType` is optional and last so existing callers that pass none keep emitting quoted values.
33
+ */
34
+ export function generateInCmlExpression(left, right, dataType) {
35
+ const emit = (value) => (quotesValues(dataType) ? doubleQuoted(value) : value);
18
36
  if (typeof right === 'string') {
19
- return `${left} == ${doubleQuoted(right)}`;
37
+ return `${left} == ${emit(right)}`;
20
38
  }
21
- return right.map((r) => `${left} == ${doubleQuoted(r)}`).join(' || ');
39
+ return right.map((r) => `${left} == ${emit(r)}`).join(' || ');
22
40
  }
23
41
  function firstValue(right) {
24
42
  if (right === undefined)
@@ -49,12 +67,12 @@ export function convertToCmlExpression(left, ruleExprOperator, right, dataType)
49
67
  return `!strcontain(${left}, ${doubleQuoted(firstValue(right))})`;
50
68
  case 'In':
51
69
  if (right) {
52
- return `(${generateInCmlExpression(left, right)})`;
70
+ return `(${generateInCmlExpression(left, right, dataType)})`;
53
71
  }
54
72
  return `${left} == null`;
55
73
  case 'NotIn':
56
74
  if (right) {
57
- return `!(${generateInCmlExpression(left, right)})`;
75
+ return `!(${generateInCmlExpression(left, right, dataType)})`;
58
76
  }
59
77
  return `${left} != null`;
60
78
  default: {
@@ -1 +1 @@
1
- {"version":3,"file":"cml-operators.js","sourceRoot":"","sources":["../../src/shared/cml-operators.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"cml-operators.js","sourceRoot":"","sources":["../../src/shared/cml-operators.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,49 @@
1
+ /**
2
+ * The confirmation gate for the org-mutating insurance import commands
3
+ * (export/review/import design, work item W-23654540 §4). Callers MUST have rendered the full
4
+ * PlannedChange[] — built from read-only operations — before calling this, and MUST NOT issue any
5
+ * write until it resolves.
6
+ *
7
+ * Used today by `insurance import record-updates`; the matrix is command-agnostic, so
8
+ * `cml import as-expression-set` can gate on it when that work lands (§7 step 12).
9
+ */
10
+ /** Minimal surface the gate needs, so it is unit-testable without oclif. */
11
+ export type ConfirmHost = {
12
+ warn(message: string): unknown;
13
+ confirm(options: {
14
+ message: string;
15
+ ms?: number;
16
+ defaultAnswer?: boolean;
17
+ }): Promise<boolean>;
18
+ };
19
+ export type ConfirmOptions = {
20
+ noPrompt: boolean;
21
+ /**
22
+ * Whether a human can actually answer. Callers pass
23
+ * `process.stdout.isTTY && process.stdin.isTTY && !this.jsonEnabled()`.
24
+ */
25
+ interactive: boolean;
26
+ };
27
+ export type ConfirmText = {
28
+ /** Warning emitted when `--no-prompt` bypasses the gate. */
29
+ skippingPrompt: string;
30
+ /** The confirmation question (no question mark, no Y/N — `confirm` adds those). */
31
+ confirmApply: string;
32
+ /**
33
+ * Built lazily: the prompt could not run and `--no-prompt` was not passed. Must carry remediation
34
+ * actions, and must name which cause applied — a terminal that cannot prompt and a `--json` run
35
+ * that must not prompt need different remediation.
36
+ */
37
+ confirmationRequired: () => Error;
38
+ /** Built lazily: the operator answered "no". */
39
+ aborted: () => Error;
40
+ };
41
+ /**
42
+ * Applies the confirmation matrix. Returns normally only when the caller may proceed to write.
43
+ *
44
+ * A non-interactive invocation without `--no-prompt` fails fast instead of prompting: `confirm`
45
+ * does not throw on timeout, it returns `defaultAnswer` (false) after `ms`, which in CI reads as a
46
+ * 30-second hang followed by a silent abort. Detecting up front turns that into an immediate,
47
+ * actionable error.
48
+ */
49
+ export declare function confirmOrThrow(host: ConfirmHost, options: ConfirmOptions, text: ConfirmText): Promise<void>;
@@ -0,0 +1,43 @@
1
+ /*
2
+ * Copyright 2026, Salesforce, Inc.
3
+ *
4
+ * Licensed under the Apache License, Version 2.0 (the "License");
5
+ * you may not use this file except in compliance with the License.
6
+ * You may obtain a copy of the License at
7
+ *
8
+ * http://www.apache.org/licenses/LICENSE-2.0
9
+ *
10
+ * Unless required by applicable law or agreed to in writing, software
11
+ * distributed under the License is distributed on an "AS IS" BASIS,
12
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13
+ * See the License for the specific language governing permissions and
14
+ * limitations under the License.
15
+ */
16
+ /** How long to wait for an answer before falling back to the (negative) default. */
17
+ const CONFIRM_TIMEOUT_MS = 30_000;
18
+ /**
19
+ * Applies the confirmation matrix. Returns normally only when the caller may proceed to write.
20
+ *
21
+ * A non-interactive invocation without `--no-prompt` fails fast instead of prompting: `confirm`
22
+ * does not throw on timeout, it returns `defaultAnswer` (false) after `ms`, which in CI reads as a
23
+ * 30-second hang followed by a silent abort. Detecting up front turns that into an immediate,
24
+ * actionable error.
25
+ */
26
+ export async function confirmOrThrow(host, options, text) {
27
+ if (options.noPrompt) {
28
+ host.warn(text.skippingPrompt);
29
+ return;
30
+ }
31
+ if (!options.interactive) {
32
+ throw text.confirmationRequired();
33
+ }
34
+ const proceed = await host.confirm({
35
+ message: text.confirmApply,
36
+ defaultAnswer: false,
37
+ ms: CONFIRM_TIMEOUT_MS,
38
+ });
39
+ if (!proceed) {
40
+ throw text.aborted();
41
+ }
42
+ }
43
+ //# sourceMappingURL=confirm-org-changes.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"confirm-org-changes.js","sourceRoot":"","sources":["../../../src/shared/insurance/confirm-org-changes.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;GAcG;AA0CH,oFAAoF;AACpF,MAAM,kBAAkB,GAAG,MAAM,CAAC;AAElC;;;;;;;GAOG;AACH,MAAM,CAAC,KAAK,UAAU,cAAc,CAAC,IAAiB,EAAE,OAAuB,EAAE,IAAiB;IAChG,IAAI,OAAO,CAAC,QAAQ,EAAE,CAAC;QACrB,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;QAC/B,OAAO;IACT,CAAC;IAED,IAAI,CAAC,OAAO,CAAC,WAAW,EAAE,CAAC;QACzB,MAAM,IAAI,CAAC,oBAAoB,EAAE,CAAC;IACpC,CAAC;IAED,MAAM,OAAO,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC;QACjC,OAAO,EAAE,IAAI,CAAC,YAAY;QAC1B,aAAa,EAAE,KAAK;QACpB,EAAE,EAAE,kBAAkB;KACvB,CAAC,CAAC;IACH,IAAI,CAAC,OAAO,EAAE,CAAC;QACb,MAAM,IAAI,CAAC,OAAO,EAAE,CAAC;IACvB,CAAC;AACH,CAAC"}
@@ -1,5 +1,7 @@
1
1
  import { Connection } from '@salesforce/core';
2
2
  import { ParsedRuleDefinition, RuleRecord } from './models.js';
3
+ import { AttributeDataTypes } from './insurance-rule-generator.js';
4
+ import { ContextTagBindings } from './insurance-context-tags.js';
3
5
  /**
4
6
  * MERGE MODE (insurance-only): instead of building a fresh single-type CML and PATCH-replacing
5
7
  * the org's curated "Gold Standard" ConstraintModel, this module reads the existing model text,
@@ -11,10 +13,36 @@ import { ParsedRuleDefinition, RuleRecord } from './models.js';
11
13
  *
12
14
  * Why pathed keys: when a ProductSurcharge is persisted as ConstraintEngine the platform
13
15
  * auto-generates `RuleKey` as `SC` + sanitize(ProductCode) of every segment in ProductPath (in
14
- * order) + sanitize(apiName), joined by `__`. The Core surcharge engine matches the fired CML rule
15
- * key against that auto-generated RuleKey by exact string, so the CML rule key MUST be pathed too.
16
+ * order) + sanitize(leaf), joined by `__`. The leaf is the parent `Surcharge.Code` (resolved via
17
+ * ProductSurcharge.SurchargeId), NOT the rule apiName — see {@link fetchSurchargeCodes} and
18
+ * {@link buildPathedSurchargeRules}. The Core surcharge engine matches the fired CML rule key
19
+ * against that auto-generated RuleKey by exact string, so the CML rule key MUST be pathed and use
20
+ * the same Code-derived leaf.
16
21
  */
17
22
  export declare const SURCHARGE_RULE_ACTION = "InsuranceSurchargeRule";
23
+ /**
24
+ * A context-tag reference the merge will DECLARE into the model so the rule's expression resolves.
25
+ *
26
+ * Only a BRE `Tag` condition (`attributeId` null) produces one of these, and only when the tag
27
+ * resolved unambiguously against the org's context metadata (see insurance-context-tags.ts). An
28
+ * `Attribute` condition never does: those name product attributes the curated model is expected to
29
+ * already declare, and auto-declaring one would paper over the real cause — usually that the rule
30
+ * targets a type belonging to a different model.
31
+ */
32
+ export type ContextTagDeclaration = {
33
+ /** Raw ContextTag.Title, e.g. `Cause Of Loss`. Carried verbatim by the emitted annotation. */
34
+ tag: string;
35
+ /**
36
+ * `sanitizeName(tag)`, so the CML identifier stays legal even when the title contains spaces or
37
+ * punctuation. The TRUE name is never lost — it travels in the `tagName` / `contextPath`
38
+ * annotation, which is what actually binds the value.
39
+ */
40
+ identifier: string;
41
+ /** CML declaration type from ContextAttribute.DataType (e.g. `date`, `decimal(2)`). */
42
+ cmlType: string;
43
+ /** Which binding form to emit: a top-level `extern`, or an in-type `@(tagName = ...)`. */
44
+ scope: 'transaction' | 'item';
45
+ };
18
46
  export type PathedSurchargeRule = {
19
47
  recordId: string;
20
48
  recordName: string;
@@ -34,6 +62,19 @@ export type PathedSurchargeRule = {
34
62
  statement: string;
35
63
  /** Sanitized attribute names referenced by the rule declaration (for visibility warnings). */
36
64
  referencedAttributes: string[];
65
+ /**
66
+ * The context-tag references this rule needs, resolved against the org. The merge declares each
67
+ * one that the model does not already carry, and treats it as visible for the absent-reference
68
+ * gate. A tag that did NOT resolve is deliberately absent from this list, so it stays invisible to
69
+ * the gate and its rule is withheld exactly as before.
70
+ */
71
+ contextTagDeclarations: ContextTagDeclaration[];
72
+ /**
73
+ * Set when {@link findUnconvertibleConditions} found something in this rule CML cannot express.
74
+ * The merge refuses such a rule outright — `statement` is built anyway (the shapes stay uniform)
75
+ * but must never be placed.
76
+ */
77
+ unconvertibleReason?: string;
37
78
  };
38
79
  export type MergePlacement = {
39
80
  rule: PathedSurchargeRule;
@@ -91,14 +132,23 @@ export type UnderwritingConstraintRule = {
91
132
  name: string;
92
133
  cmlType: string;
93
134
  }>;
135
+ /** See {@link PathedSurchargeRule.unconvertibleReason}. */
136
+ unconvertibleReason?: string;
94
137
  };
95
138
  /**
96
139
  * Builds the pathed surcharge rule key that mirrors the platform's auto-generated
97
140
  * `ProductSurcharge.RuleKey`: prefix + every path-segment product code + apiName.
98
141
  */
99
142
  export declare function buildPathedRuleKey(prefix: string, pathProductCodes: string[], apiName: string, stageTransition?: string): string;
100
- /** Splits a `ProductPath` into its ordered Product2 ids (slash-separated). */
101
- export declare function splitProductPath(productPath: string): string[];
143
+ /**
144
+ * Splits a `ProductPath` into its ordered Product2 ids (slash-separated).
145
+ *
146
+ * ProductPath is nullable in the org even on records that carry a rule, so nullish input yields an
147
+ * empty path rather than throwing. Callers rely on that: an empty path is already a recognized skip
148
+ * (see the empty-ProductPath guard in mergeSurchargeRules), whereas throwing here aborted the whole
149
+ * conversion run before any record could be skipped.
150
+ */
151
+ export declare function splitProductPath(productPath: string | null | undefined): string[];
102
152
  /**
103
153
  * Reads the org's existing ConstraintModel text for the given CML API name, mirroring the lookup
104
154
  * the common import uses (ExpressionSetDefinition.DeveloperName -> ExpressionSetDefinitionVersion).
@@ -115,6 +165,15 @@ export declare function fetchExistingConstraintModel(conn: Connection, cmlApiNam
115
165
  * correct way to find which existing `type` block a surcharge's leaf product nests into.
116
166
  */
117
167
  export declare function fetchProductTypeTags(conn: Connection, productIds: Set<string>): Promise<Map<string, string>>;
168
+ /**
169
+ * Resolves Surcharge id -> Surcharge.Code. The platform builds the LEAF segment of
170
+ * `ProductSurcharge.RuleKey` from the parent Surcharge's Code (e.g. `basictaxcode`), NOT from the
171
+ * rule apiName. `buildPathedSurchargeRules` uses this map so the emitted CML rule key matches the
172
+ * platform-generated RuleKey exactly; without it the surcharge imports cleanly but never fires
173
+ * ("No active rule model found"). Ids with no resolvable Code are omitted (caller warns + falls
174
+ * back to apiName).
175
+ */
176
+ export declare function fetchSurchargeCodes(conn: Connection, surchargeIds: Set<string>): Promise<Map<string, string>>;
118
177
  export declare function escapeRegExp(value: string): string;
119
178
  /**
120
179
  * [Fix #4] Detects the dominant line ending of a CML text by counting CRLF vs bare-LF occurrences.
@@ -132,16 +191,46 @@ export declare function detectDominantLineEnding(cml: string): string;
132
191
  * structural close, which would return a too-early closeIdx and splice a new rule mid-statement.
133
192
  */
134
193
  export declare function matchClosingBrace(cml: string, openIdx: number): number | undefined;
194
+ /**
195
+ * Prefix every merge skip raised by {@link findUnconvertibleConditions} carries, so the commands'
196
+ * skip breakdown can bucket it the way it buckets the other reasons.
197
+ */
198
+ export declare const UNCONVERTIBLE_SKIP_PREFIX = "cannot be expressed in CML";
135
199
  /** Builds the `rule(...)` statement for a surcharge, using the same constraint generator as build mode. */
136
200
  export declare function buildSurchargeRuleStatement(declaration: string, ruleKey: string): string;
201
+ export type BuildPathedSurchargeRulesOptions = {
202
+ /**
203
+ * Surcharge id -> Surcharge.Code (from {@link fetchSurchargeCodes}). The platform derives the
204
+ * LEAF segment of ProductSurcharge.RuleKey from the parent Surcharge's Code, so this is preferred
205
+ * over the rule apiName for the key leaf. When a rule's surchargeId is missing or not present in
206
+ * this map, the leaf falls back to the apiName and {@link onSurchargeCodeFallback} fires.
207
+ */
208
+ surchargeIdToCode?: Map<string, string>;
209
+ /** Called with the rule's recordName when its Surcharge.Code could not be resolved (key leaf fell back to apiName). */
210
+ onSurchargeCodeFallback?: (recordName: string) => void;
211
+ /**
212
+ * Org-resolved attribute types (see {@link AttributeDataTypes}). Required for a numeric picklist
213
+ * to be compared as a number: without it the merged rule compares a decimal attribute — as the
214
+ * curated model already declares it — against a quoted string, and the surcharge never fires.
215
+ */
216
+ attributeDataTypes?: AttributeDataTypes;
217
+ /**
218
+ * Raw context tag -> its org-resolved binding (see {@link fetchContextTagBindings}). Absent or
219
+ * empty means no tag resolves, which leaves every Tag-condition rule to the absent-reference gate
220
+ * — the behaviour before context-tag resolution existed, and still the correct fallback.
221
+ */
222
+ contextTagBindings?: ContextTagBindings;
223
+ };
137
224
  /**
138
225
  * Prepares the pathed-rule descriptors for a set of parsed surcharge records.
139
226
  * `productIdToCode` and `productIdToType` must already cover every ProductPath segment.
227
+ * `options.surchargeIdToCode` should map every rule's parent Surcharge id to its Code so the key
228
+ * leaf matches the platform-generated RuleKey (see {@link fetchSurchargeCodes}).
140
229
  */
141
230
  export declare function buildPathedSurchargeRules(prefix: string, ruleDefs: Array<{
142
231
  record: RuleRecord;
143
232
  ruleDef: ParsedRuleDefinition;
144
- }>, productIdToCode: Map<string, string>, productIdToType: Map<string, string>): PathedSurchargeRule[];
233
+ }>, productIdToCode: Map<string, string>, productIdToType: Map<string, string>, options?: BuildPathedSurchargeRulesOptions): PathedSurchargeRule[];
145
234
  /**
146
235
  * Builds the `constraint <name> = (...)` statement for underwriting eligibility, using the same
147
236
  * constraint generator as build mode's constraint-form branch (see `buildCmlModel`).
@@ -157,7 +246,7 @@ export declare function buildUnderwritingConstraintStatement(constraintName: str
157
246
  export declare function buildUnderwritingConstraintRules(keyPrefix: string, constraintLabel: string, ruleDefs: Array<{
158
247
  record: RuleRecord;
159
248
  ruleDef: ParsedRuleDefinition;
160
- }>, productIdToCode: Map<string, string>, productIdToType: Map<string, string>): UnderwritingConstraintRule[];
249
+ }>, productIdToCode: Map<string, string>, productIdToType: Map<string, string>, attributeDataTypes?: AttributeDataTypes): UnderwritingConstraintRule[];
161
250
  /**
162
251
  * Merges the pathed surcharge `rule(...)` statements into the existing CML text. If the rule key is
163
252
  * already present, the existing statement line is replaced in place (idempotent). Otherwise the
@@ -174,13 +263,11 @@ export declare function mergeSurchargeRules(existingCml: string, rules: PathedSu
174
263
  * statement (from the `constraint` keyword through the terminating `;`) is replaced in place
175
264
  * (idempotent — re-running the merge with the same input reproduces the same output).
176
265
  * - Otherwise the statement is inserted just before the closing brace of the leaf `type` block.
177
- * - Before placing a rule's constraint, any of its `referencedAttributes` not already declared
178
- * anywhere in the leaf `type` block are auto-inserted (as `<cmlType> <attrName>;`) right after
179
- * the block's opening brace, and reported via `attributeWarnings` so the caller can log them —
180
- * unlike surcharge merge (which only WARNS about missing attributes, since injecting into the
181
- * curated model there was judged too risky for a `rule(...)` action statement), underwriting
182
- * constraints reference attributes that must resolve for the constraint to compile, so the
183
- * declaration is added rather than merely flagged.
266
+ * - Any of a rule's `referencedAttributes` not already declared anywhere in the leaf `type` block
267
+ * are reported via `attributeWarnings`; the curated model is never mutated to add them. NOTE: this
268
+ * is weaker than the surcharge merge, which WITHHOLDS such a rule outright — an unresolvable
269
+ * reference makes the solver reject the whole model at deploy, so warning here still lets a
270
+ * model-wide outage through. See findAbsentAttributes.
184
271
  *
185
272
  * Rules with a blank ProductPath, no resolved leaf type tag, an ambiguous/duplicate type block, or
186
273
  * an intra-run duplicate (typeName, constraintName) pair are skipped (reported, never silently