@nimiplatform/nimi-coding 0.1.0 → 0.2.1

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 (126) hide show
  1. package/CHANGELOG.md +19 -0
  2. package/CODE_OF_CONDUCT.md +28 -0
  3. package/CONTRIBUTING.md +45 -0
  4. package/README.md +371 -344
  5. package/README.zh-CN.md +307 -0
  6. package/SECURITY.md +26 -0
  7. package/adapters/oh-my-codex/README.md +8 -9
  8. package/cli/commands/audit-sweep.mjs +10 -10
  9. package/cli/commands/classify-spec-tree.mjs +5 -0
  10. package/cli/commands/closeout.mjs +3 -0
  11. package/cli/commands/generate-spec-derived-docs.mjs +20 -0
  12. package/cli/commands/generate-spec-migration-plan.mjs +30 -0
  13. package/cli/commands/start.mjs +5 -1
  14. package/cli/commands/surface-validator-command.mjs +49 -0
  15. package/cli/commands/sweep-design.mjs +295 -0
  16. package/cli/commands/sweep.mjs +22 -0
  17. package/cli/commands/sync.mjs +132 -0
  18. package/cli/commands/topic-formatters.mjs +8 -8
  19. package/cli/commands/validate-ai-governance.mjs +167 -46
  20. package/cli/commands/validate-domain-admission.mjs +5 -0
  21. package/cli/commands/validate-guidance-bodies.mjs +5 -0
  22. package/cli/commands/validate-placement.mjs +5 -0
  23. package/cli/commands/validate-projection-edges.mjs +5 -0
  24. package/cli/commands/validate-spec-audit.mjs +5 -1
  25. package/cli/commands/validate-table-family.mjs +5 -0
  26. package/cli/commands/validate-tracked-output-admission.mjs +5 -0
  27. package/cli/constants.mjs +5 -49
  28. package/cli/help.mjs +33 -11
  29. package/cli/index.mjs +20 -2
  30. package/cli/lib/audit-sweep-runtime/admissions.mjs +38 -29
  31. package/cli/lib/audit-sweep-runtime/audit-validity.mjs +8 -0
  32. package/cli/lib/audit-sweep-runtime/chunks.mjs +11 -11
  33. package/cli/lib/audit-sweep-runtime/closeout.mjs +8 -8
  34. package/cli/lib/audit-sweep-runtime/codex-auditor-evidence.mjs +3 -3
  35. package/cli/lib/audit-sweep-runtime/codex-auditor.mjs +10 -10
  36. package/cli/lib/audit-sweep-runtime/common.mjs +7 -7
  37. package/cli/lib/audit-sweep-runtime/format.mjs +3 -3
  38. package/cli/lib/audit-sweep-runtime/ingest.mjs +8 -8
  39. package/cli/lib/audit-sweep-runtime/inventory-spec-chunks.mjs +24 -27
  40. package/cli/lib/audit-sweep-runtime/inventory.mjs +58 -18
  41. package/cli/lib/audit-sweep-runtime/ledger.mjs +1 -1
  42. package/cli/lib/audit-sweep-runtime/p0p1-profile.mjs +2 -2
  43. package/cli/lib/audit-sweep-runtime/remediation.mjs +6 -6
  44. package/cli/lib/audit-sweep-runtime/rerun.mjs +6 -6
  45. package/cli/lib/audit-sweep-runtime/status.mjs +1 -1
  46. package/cli/lib/audit-sweep-runtime/validators.mjs +2 -2
  47. package/cli/lib/authority-convergence.mjs +397 -2
  48. package/cli/lib/blueprint-audit.mjs +5 -5
  49. package/cli/lib/closeout.mjs +126 -3
  50. package/cli/lib/contracts.mjs +21 -17
  51. package/cli/lib/handoff.mjs +29 -11
  52. package/cli/lib/high-risk-admission.mjs +60 -11
  53. package/cli/lib/high-risk-decision.mjs +31 -2
  54. package/cli/lib/high-risk-ingest.mjs +5 -1
  55. package/cli/lib/high-risk-review.mjs +5 -1
  56. package/cli/lib/internal/contracts-parse.mjs +195 -24
  57. package/cli/lib/internal/contracts-validators.mjs +3 -2
  58. package/cli/lib/internal/doctor-bootstrap-surface.mjs +82 -35
  59. package/cli/lib/internal/doctor-delegated-surface.mjs +1 -1
  60. package/cli/lib/internal/doctor-finalize.mjs +12 -8
  61. package/cli/lib/internal/doctor-inspectors.mjs +34 -1
  62. package/cli/lib/internal/governance/ai/ai-context-budget-core.mjs +74 -12
  63. package/cli/lib/internal/governance/ai/ai-structure-budget-core.mjs +24 -6
  64. package/cli/lib/internal/governance/ai/check-agents-freshness.mjs +18 -23
  65. package/cli/lib/internal/surface-taxonomy-validators.mjs +931 -0
  66. package/cli/lib/internal/validators-spec.mjs +229 -20
  67. package/cli/lib/sweep-design-runtime/common.mjs +246 -0
  68. package/cli/lib/sweep-design-runtime/engine.mjs +733 -0
  69. package/cli/lib/sweep-design-runtime/fix-topic.mjs +414 -0
  70. package/cli/lib/sweep-design-runtime/lifecycle.mjs +54 -0
  71. package/cli/lib/sweep-design-runtime/results.mjs +324 -0
  72. package/cli/lib/sweep-design.mjs +8 -0
  73. package/cli/lib/sync.mjs +143 -0
  74. package/cli/lib/topic-artifacts.mjs +186 -0
  75. package/cli/lib/topic-authority-coverage.mjs +73 -0
  76. package/cli/lib/topic-closeout.mjs +560 -0
  77. package/cli/lib/topic-common.mjs +404 -0
  78. package/cli/lib/topic-decisions.mjs +332 -0
  79. package/cli/lib/topic-draft-packets.mjs +126 -7
  80. package/cli/lib/topic-execution.mjs +515 -0
  81. package/cli/lib/topic-goal.mjs +112 -33
  82. package/cli/lib/topic-ledger.mjs +281 -0
  83. package/cli/lib/topic-lifecycle-artifacts.mjs +173 -0
  84. package/cli/lib/topic-root-validation.mjs +288 -0
  85. package/cli/lib/topic-runner-commands.mjs +174 -0
  86. package/cli/lib/topic-runner-deferral.mjs +532 -0
  87. package/cli/lib/topic-runner-stale-gates.mjs +114 -0
  88. package/cli/lib/topic-runner-validation.mjs +138 -0
  89. package/cli/lib/topic-runner.mjs +109 -154
  90. package/cli/lib/topic-scaffold.mjs +252 -0
  91. package/cli/lib/topic-waves.mjs +403 -0
  92. package/cli/lib/topic.mjs +81 -93
  93. package/cli/lib/value-helpers.mjs +6 -1
  94. package/cli/seeds/bootstrap.mjs +96 -20
  95. package/cli/seeds/seed-policy.yaml +67 -0
  96. package/config/bootstrap.yaml +1 -1
  97. package/config/skill-manifest.yaml +4 -2
  98. package/config/spec-generation-inputs.yaml +41 -19
  99. package/contracts/audit-remediation-map.schema.yaml +1 -0
  100. package/contracts/audit-sweep-result.yaml +4 -0
  101. package/contracts/domain-admission.schema.yaml +56 -0
  102. package/contracts/migration-inventory.schema.yaml +80 -0
  103. package/contracts/negative-fixtures.yaml +91 -0
  104. package/contracts/placement-contract.schema.yaml +163 -0
  105. package/contracts/projection-edge.schema.yaml +130 -0
  106. package/contracts/shared-enums.yaml +68 -0
  107. package/contracts/spec-generation-audit.schema.yaml +19 -4
  108. package/contracts/spec-generation-inputs.schema.yaml +130 -29
  109. package/contracts/spec-reconstruction-result.yaml +9 -5
  110. package/contracts/surface-taxonomy.schema.yaml +201 -0
  111. package/contracts/sweep-design-result.yaml +349 -0
  112. package/contracts/table-family.schema.yaml +121 -0
  113. package/contracts/topic-goal.schema.yaml +10 -1
  114. package/contracts/tracked-output-admission.schema.yaml +70 -0
  115. package/contracts/workflow-consumer.schema.yaml +112 -0
  116. package/methodology/audit-sweep-p0p1-recall.yaml +1 -1
  117. package/methodology/spec-reconstruction.yaml +53 -30
  118. package/package.json +19 -4
  119. package/spec/_meta/command-gating-matrix.yaml +33 -0
  120. package/spec/_meta/generate-drift-migration-checklist.yaml +44 -62
  121. package/spec/_meta/governance-routing-cutover-checklist.yaml +3 -3
  122. package/spec/_meta/phase2-impacted-surface-matrix.yaml +14 -14
  123. package/spec/_meta/spec-authority-cutover-readiness.yaml +3 -5
  124. package/spec/_meta/spec-tree-model.yaml +104 -36
  125. package/spec/bootstrap-state.yaml +36 -36
  126. package/spec/product-scope.yaml +13 -10
@@ -0,0 +1,404 @@
1
+ import path from "node:path";
2
+ import { loadTopicRuntimeContracts } from "./contracts.mjs";
3
+
4
+ export const TOPIC_ROOT = path.join(".nimi", "topics"),
5
+ TOPIC_ID_PATTERN = /^\d{4}-\d{2}-\d{2}-[a-z0-9]+(?:-[a-z0-9]+)*$/,
6
+ TOPIC_SLUG_PATTERN = /^[a-z0-9]+(?:-[a-z0-9]+)*$/,
7
+ WAVE_ID_PATTERN = /^wave-[a-z0-9]+(?:-[a-z0-9]+)*$/,
8
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY = {
9
+ topicStates: ["proposal", "ongoing", "pending", "closed"],
10
+ minimalRequiredFields: [
11
+ "topic_id",
12
+ "state",
13
+ "created_at",
14
+ "last_transition_at",
15
+ "last_transition_reason",
16
+ ],
17
+ enrichedRequiredFields: [
18
+ "title",
19
+ "mode",
20
+ "posture",
21
+ "design_policy",
22
+ "parallel_truth",
23
+ "layering",
24
+ "risk",
25
+ "applicability",
26
+ "entry_justification",
27
+ "execution_mode",
28
+ "selected_next_target",
29
+ "current_true_close_status",
30
+ "forbidden_shortcuts",
31
+ ],
32
+ topicEnums: {
33
+ mode: ["greenfield", "landed", "superseding"],
34
+ posture: ["no_legacy_hard_cut", "backward_compat"],
35
+ designPolicy: ["complete_contract_first", "mvp_incremental"],
36
+ parallelTruth: ["forbidden", "admitted"],
37
+ layering: ["ontology", "time_phased"],
38
+ risk: ["high", "low"],
39
+ applicability: [
40
+ "authority_bearing",
41
+ "high_risk_refactor",
42
+ "multi_wave_iteration",
43
+ "complex_remediation",
44
+ ],
45
+ executionMode: ["inline_manager_worker", "manager_worker_auditor"],
46
+ trueCloseStatus: ["not_started", "pending", "true_closed", "revoked", "superseded"],
47
+ },
48
+ waveStates: [
49
+ "candidate",
50
+ "preflight_draft",
51
+ "preflight_admitted",
52
+ "implementation_admitted",
53
+ "implementation_active",
54
+ "needs_revision",
55
+ "overflowed",
56
+ "continuation_packet_open",
57
+ "closed",
58
+ "retired",
59
+ "superseded",
60
+ ],
61
+ packetRequiredFields: [
62
+ "packet_id",
63
+ "topic_id",
64
+ "wave_id",
65
+ "packet_kind",
66
+ "status",
67
+ "authority_owner",
68
+ "canonical_seams",
69
+ "forbidden_shortcuts",
70
+ "acceptance_invariants",
71
+ "negative_tests",
72
+ "reopen_conditions",
73
+ ],
74
+ packetFreezeAllowedStatuses: ["draft", "preflight", "candidate"],
75
+ resultVerdicts: ["PASS", "NEEDS_REVISION", "FAIL", "OVERFLOW"],
76
+ resultKinds: ["preflight", "implementation", "audit", "judgement"],
77
+ resultVerifiedAtFormat: "iso8601_utc_timestamp",
78
+ closeoutScopes: ["wave", "topic"],
79
+ closureStates: ["open", "closed", "blocked"],
80
+ closeoutDispositions: ["complete", "partial", "deferred"],
81
+ remediationKinds: ["a", "b", "continuation", "execution_state_closure"],
82
+ decisionDispositions: ["retired", "superseded", "unchanged"],
83
+ pendingNoteRequiredFields: [
84
+ "pending_note_id",
85
+ "topic_id",
86
+ "entered_from_state",
87
+ "reason",
88
+ "summary",
89
+ "status",
90
+ ],
91
+ pendingNoteStatuses: ["active", "resumed", "closed"],
92
+ defaultForbiddenShortcuts: [
93
+ "mvp_subset_contract",
94
+ "legacy_alias",
95
+ "compat_shim",
96
+ "dual_read",
97
+ "dual_write",
98
+ "placeholder_success",
99
+ "happy_path_only_closure",
100
+ "time_phased_layering",
101
+ "app_local_shadow_truth",
102
+ "silent_owner_cut_reopen",
103
+ ],
104
+ recommendedFiles: [
105
+ "README.md",
106
+ "design.md",
107
+ "preflight.md",
108
+ "waves.md",
109
+ "candidate-wave-plan.md",
110
+ "implementation-doctrine.md",
111
+ "admission-checklists.md",
112
+ "manager-session-protocol.md",
113
+ "manager-prompts.md",
114
+ ],
115
+ closureDimensions: ["authority", "semantic", "consumer", "drift_resistance"],
116
+ waveCloseoutEvidence: { requirePacketLineage: true, requireResultLineage: true },
117
+ trueCloseAuditEvidence: {
118
+ requireWaveCloseoutForClosedWaves: true,
119
+ requirePacketLineageForClosedWaves: true,
120
+ requireResultLineageForClosedWaves: true,
121
+ },
122
+ topicStepDecision: {
123
+ stopClasses: [
124
+ "continue",
125
+ "require_human_confirmation",
126
+ "await_external_evidence",
127
+ "blocked",
128
+ "completed",
129
+ ],
130
+ recommendedActions: [
131
+ "admit_wave",
132
+ "freeze_packet",
133
+ "dispatch_worker",
134
+ "dispatch_audit",
135
+ "record_result",
136
+ "open_remediation",
137
+ "continue_overflow",
138
+ "hold_topic",
139
+ "resume_topic",
140
+ "closeout_wave",
141
+ "closeout_topic",
142
+ "no_action",
143
+ ],
144
+ },
145
+ topicRunLedger: {
146
+ eventKinds: [
147
+ "decision_emitted",
148
+ "wave_admitted",
149
+ "packet_frozen",
150
+ "worker_dispatched",
151
+ "audit_dispatched",
152
+ "result_recorded",
153
+ "human_gate_opened",
154
+ "human_gate_resolved",
155
+ "wave_closed",
156
+ "topic_closed",
157
+ "runner_blocked",
158
+ ],
159
+ runStatuses: [
160
+ "running",
161
+ "awaiting_human_confirmation",
162
+ "awaiting_external_evidence",
163
+ "blocked",
164
+ "completed",
165
+ ],
166
+ artifactRefKeys: [
167
+ "decision_ref",
168
+ "packet_ref",
169
+ "prompt_ref",
170
+ "worker_output_ref",
171
+ "audit_output_ref",
172
+ "result_ref",
173
+ "closeout_ref",
174
+ "evidence_ref",
175
+ ],
176
+ retryPostures: [
177
+ "not_applicable",
178
+ "retry_allowed_same_command",
179
+ "retry_requires_new_packet",
180
+ "retry_forbidden_until_human_gate",
181
+ ],
182
+ },
183
+ ignoredTopicValidateSemantics: { status: "report_only", canonicalSuccess: false },
184
+ },
185
+ topicRuntimeAuthorityCache = new Map(),
186
+ PENDING_ENTRY_BLOCKER_STATES = new Set([
187
+ "preflight_admitted",
188
+ "implementation_admitted",
189
+ "implementation_active",
190
+ "needs_revision",
191
+ "overflowed",
192
+ "continuation_packet_open",
193
+ ]);
194
+ export function formatDate(date = new Date()) {
195
+ const year = date.getFullYear(),
196
+ month = String(date.getMonth() + 1).padStart(2, "0"),
197
+ day = String(date.getDate()).padStart(2, "0");
198
+ return `${year}-${month}-${day}`;
199
+ }
200
+ export function toPortableRelativePath(filePath) {
201
+ return filePath.split(path.sep).join("/");
202
+ }
203
+ export function toStringArray(value, fallback) {
204
+ if (!Array.isArray(value)) return fallback;
205
+ const normalized = value
206
+ .filter((entry) => typeof entry == "string" && entry.length > 0)
207
+ .map((entry) => String(entry));
208
+ return normalized.length > 0 ? normalized : fallback;
209
+ }
210
+ export function normalizeBoolean(value, fallback) {
211
+ return typeof value == "boolean" ? value : fallback;
212
+ }
213
+ export async function loadTopicRuntimeAuthority(projectRoot) {
214
+ const cached = topicRuntimeAuthorityCache.get(projectRoot);
215
+ if (cached) return cached;
216
+ const loaded = await loadTopicRuntimeContracts(projectRoot),
217
+ topicSchema = loaded.topicSchema.data ?? {},
218
+ waveSchema = loaded.waveSchema.data ?? {},
219
+ packetSchema = loaded.packetSchema.data ?? {},
220
+ resultSchema = loaded.resultSchema.data ?? {},
221
+ closeoutSchema = loaded.closeoutSchema.data ?? {},
222
+ remediationSchema = loaded.remediationSchema.data ?? {},
223
+ decisionReviewSchema = loaded.decisionReviewSchema.data ?? {},
224
+ pendingNoteSchema = loaded.pendingNoteSchema.data ?? {},
225
+ topicStepDecisionSchema = loaded.topicStepDecisionSchema.data ?? {},
226
+ topicRunLedgerSchema = loaded.topicRunLedgerSchema.data ?? {},
227
+ forbiddenShortcutsCatalog = loaded.forbiddenShortcutsCatalog.data ?? {},
228
+ lifecycleReport = loaded.lifecycleReport.data?.topic_lifecycle_report ?? {},
229
+ fourClosurePolicy = loaded.fourClosurePolicy.data?.four_closure_policy ?? {},
230
+ validationPolicy = loaded.validationPolicy.data?.topic_validation_policy ?? {},
231
+ minimalRequiredFields = toStringArray(
232
+ lifecycleReport.state_evidence?.required_fields,
233
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.minimalRequiredFields,
234
+ ),
235
+ enrichedRequiredFields = toStringArray(
236
+ topicSchema.required,
237
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.enrichedRequiredFields,
238
+ ).filter((field) => !minimalRequiredFields.includes(field)),
239
+ authority = {
240
+ topicStates: toStringArray(
241
+ topicSchema.state_enum,
242
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicStates,
243
+ ),
244
+ minimalRequiredFields,
245
+ enrichedRequiredFields,
246
+ topicEnums: {
247
+ mode: toStringArray(topicSchema.mode_enum, DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicEnums.mode),
248
+ posture: toStringArray(
249
+ topicSchema.posture_enum,
250
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicEnums.posture,
251
+ ),
252
+ designPolicy: toStringArray(
253
+ topicSchema.design_policy_enum,
254
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicEnums.designPolicy,
255
+ ),
256
+ parallelTruth: toStringArray(
257
+ topicSchema.parallel_truth_enum,
258
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicEnums.parallelTruth,
259
+ ),
260
+ layering: toStringArray(
261
+ topicSchema.layering_enum,
262
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicEnums.layering,
263
+ ),
264
+ risk: toStringArray(topicSchema.risk_enum, DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicEnums.risk),
265
+ applicability: toStringArray(
266
+ topicSchema.applicability_enum,
267
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicEnums.applicability,
268
+ ),
269
+ executionMode: toStringArray(
270
+ topicSchema.execution_mode_enum,
271
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicEnums.executionMode,
272
+ ),
273
+ trueCloseStatus: toStringArray(
274
+ topicSchema.true_close_status_enum,
275
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicEnums.trueCloseStatus,
276
+ ),
277
+ },
278
+ waveStates: toStringArray(waveSchema.state_enum, DEFAULT_TOPIC_RUNTIME_AUTHORITY.waveStates),
279
+ packetRequiredFields: toStringArray(
280
+ packetSchema.required,
281
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.packetRequiredFields,
282
+ ),
283
+ packetFreezeAllowedStatuses: toStringArray(
284
+ packetSchema.freeze_allowed_status_enum,
285
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.packetFreezeAllowedStatuses,
286
+ ),
287
+ resultVerdicts: toStringArray(
288
+ resultSchema.verdict_enum,
289
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.resultVerdicts,
290
+ ),
291
+ resultKinds: toStringArray(
292
+ resultSchema.result_kind_enum,
293
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.resultKinds,
294
+ ),
295
+ resultVerifiedAtFormat:
296
+ typeof resultSchema.verified_at_format == "string"
297
+ ? resultSchema.verified_at_format
298
+ : DEFAULT_TOPIC_RUNTIME_AUTHORITY.resultVerifiedAtFormat,
299
+ closeoutScopes: toStringArray(
300
+ closeoutSchema.scope_enum,
301
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.closeoutScopes,
302
+ ),
303
+ closureStates: toStringArray(
304
+ closeoutSchema.closure_enum,
305
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.closureStates,
306
+ ),
307
+ closeoutDispositions: toStringArray(
308
+ closeoutSchema.disposition_enum,
309
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.closeoutDispositions,
310
+ ),
311
+ remediationKinds: toStringArray(
312
+ remediationSchema.kind_enum,
313
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.remediationKinds,
314
+ ),
315
+ decisionDispositions: toStringArray(
316
+ decisionReviewSchema.disposition_enum,
317
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.decisionDispositions,
318
+ ),
319
+ pendingNoteRequiredFields: toStringArray(
320
+ pendingNoteSchema.required,
321
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.pendingNoteRequiredFields,
322
+ ),
323
+ pendingNoteStatuses: toStringArray(
324
+ pendingNoteSchema.status_enum,
325
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.pendingNoteStatuses,
326
+ ),
327
+ defaultForbiddenShortcuts: Array.isArray(forbiddenShortcutsCatalog.entries)
328
+ ? forbiddenShortcutsCatalog.entries
329
+ .map((entry) => (typeof entry?.key == "string" ? entry.key : null))
330
+ .filter(Boolean)
331
+ : DEFAULT_TOPIC_RUNTIME_AUTHORITY.defaultForbiddenShortcuts,
332
+ recommendedFiles: toStringArray(
333
+ lifecycleReport.recommended_files,
334
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.recommendedFiles,
335
+ ).filter((entry) => !entry.includes("*")),
336
+ closureDimensions: toStringArray(
337
+ fourClosurePolicy.closures,
338
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.closureDimensions,
339
+ ),
340
+ waveCloseoutEvidence: {
341
+ requirePacketLineage: normalizeBoolean(
342
+ fourClosurePolicy.wave_closeout_evidence?.require_packet_lineage,
343
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.waveCloseoutEvidence.requirePacketLineage,
344
+ ),
345
+ requireResultLineage: normalizeBoolean(
346
+ fourClosurePolicy.wave_closeout_evidence?.require_result_lineage,
347
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.waveCloseoutEvidence.requireResultLineage,
348
+ ),
349
+ },
350
+ trueCloseAuditEvidence: {
351
+ requireWaveCloseoutForClosedWaves: normalizeBoolean(
352
+ fourClosurePolicy.true_close_audit_evidence?.require_wave_closeout_for_closed_waves,
353
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.trueCloseAuditEvidence.requireWaveCloseoutForClosedWaves,
354
+ ),
355
+ requirePacketLineageForClosedWaves: normalizeBoolean(
356
+ fourClosurePolicy.true_close_audit_evidence?.require_packet_lineage_for_closed_waves,
357
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.trueCloseAuditEvidence.requirePacketLineageForClosedWaves,
358
+ ),
359
+ requireResultLineageForClosedWaves: normalizeBoolean(
360
+ fourClosurePolicy.true_close_audit_evidence?.require_result_lineage_for_closed_waves,
361
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.trueCloseAuditEvidence.requireResultLineageForClosedWaves,
362
+ ),
363
+ },
364
+ topicStepDecision: {
365
+ stopClasses: toStringArray(
366
+ topicStepDecisionSchema.stop_class_enum,
367
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicStepDecision.stopClasses,
368
+ ),
369
+ recommendedActions: toStringArray(
370
+ topicStepDecisionSchema.recommended_action_enum,
371
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicStepDecision.recommendedActions,
372
+ ),
373
+ },
374
+ topicRunLedger: {
375
+ eventKinds: toStringArray(
376
+ topicRunLedgerSchema.event_kind_enum,
377
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicRunLedger.eventKinds,
378
+ ),
379
+ runStatuses: toStringArray(
380
+ topicRunLedgerSchema.run_status_enum,
381
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicRunLedger.runStatuses,
382
+ ),
383
+ artifactRefKeys: toStringArray(
384
+ topicRunLedgerSchema.artifact_ref_keys,
385
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicRunLedger.artifactRefKeys,
386
+ ),
387
+ retryPostures: toStringArray(
388
+ topicRunLedgerSchema.retry_posture_enum,
389
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.topicRunLedger.retryPostures,
390
+ ),
391
+ },
392
+ ignoredTopicValidateSemantics: {
393
+ status:
394
+ typeof validationPolicy.ignored_topic_validate_semantics?.status == "string"
395
+ ? validationPolicy.ignored_topic_validate_semantics.status
396
+ : DEFAULT_TOPIC_RUNTIME_AUTHORITY.ignoredTopicValidateSemantics.status,
397
+ canonicalSuccess: normalizeBoolean(
398
+ validationPolicy.ignored_topic_validate_semantics?.canonical_success,
399
+ DEFAULT_TOPIC_RUNTIME_AUTHORITY.ignoredTopicValidateSemantics.canonicalSuccess,
400
+ ),
401
+ },
402
+ };
403
+ return (topicRuntimeAuthorityCache.set(projectRoot, authority), authority);
404
+ }