@neurcode-ai/cli 0.9.44 → 0.9.46
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/README.md +7 -3
- package/dist/commands/contract.js +47 -0
- package/dist/commands/plan.js +40 -0
- package/dist/commands/ship.js +10 -3
- package/dist/commands/verify.d.ts +2 -0
- package/dist/commands/verify.js +251 -118
- package/dist/index.js +41 -5
- package/dist/utils/advisory-signals.d.ts +20 -0
- package/dist/utils/advisory-signals.js +177 -0
- package/dist/utils/change-contract.d.ts +105 -1
- package/dist/utils/change-contract.js +685 -12
- package/dist/utils/diff-symbols.d.ts +10 -0
- package/dist/utils/diff-symbols.js +218 -0
- package/dist/utils/governance.d.ts +1 -0
- package/dist/utils/governance.js +1 -1
- package/dist/utils/plan-symbols.d.ts +17 -0
- package/dist/utils/plan-symbols.js +209 -0
- package/package.json +6 -14
- package/LICENSE +0 -201
- package/dist/api-client.d.ts.map +0 -1
- package/dist/api-client.js.map +0 -1
- package/dist/commands/allow.d.ts.map +0 -1
- package/dist/commands/allow.js.map +0 -1
- package/dist/commands/apply.d.ts.map +0 -1
- package/dist/commands/apply.js.map +0 -1
- package/dist/commands/approve.d.ts.map +0 -1
- package/dist/commands/approve.js.map +0 -1
- package/dist/commands/ask.d.ts.map +0 -1
- package/dist/commands/ask.js.map +0 -1
- package/dist/commands/audit.d.ts.map +0 -1
- package/dist/commands/audit.js.map +0 -1
- package/dist/commands/bootstrap.d.ts.map +0 -1
- package/dist/commands/bootstrap.js.map +0 -1
- package/dist/commands/brain.d.ts.map +0 -1
- package/dist/commands/brain.js.map +0 -1
- package/dist/commands/check.d.ts.map +0 -1
- package/dist/commands/check.js.map +0 -1
- package/dist/commands/config.d.ts.map +0 -1
- package/dist/commands/config.js.map +0 -1
- package/dist/commands/contract.d.ts.map +0 -1
- package/dist/commands/contract.js.map +0 -1
- package/dist/commands/doctor.d.ts.map +0 -1
- package/dist/commands/doctor.js.map +0 -1
- package/dist/commands/feedback.d.ts.map +0 -1
- package/dist/commands/feedback.js.map +0 -1
- package/dist/commands/guard.d.ts.map +0 -1
- package/dist/commands/guard.js.map +0 -1
- package/dist/commands/init.d.ts.map +0 -1
- package/dist/commands/init.js.map +0 -1
- package/dist/commands/login.d.ts.map +0 -1
- package/dist/commands/login.js.map +0 -1
- package/dist/commands/logout.d.ts.map +0 -1
- package/dist/commands/logout.js.map +0 -1
- package/dist/commands/map.d.ts.map +0 -1
- package/dist/commands/map.js.map +0 -1
- package/dist/commands/plan-slo.d.ts.map +0 -1
- package/dist/commands/plan-slo.js.map +0 -1
- package/dist/commands/plan.d.ts.map +0 -1
- package/dist/commands/plan.js.map +0 -1
- package/dist/commands/policy.d.ts.map +0 -1
- package/dist/commands/policy.js.map +0 -1
- package/dist/commands/prompt.d.ts.map +0 -1
- package/dist/commands/prompt.js.map +0 -1
- package/dist/commands/refactor.d.ts.map +0 -1
- package/dist/commands/refactor.js.map +0 -1
- package/dist/commands/remediate.d.ts.map +0 -1
- package/dist/commands/remediate.js.map +0 -1
- package/dist/commands/repo.d.ts.map +0 -1
- package/dist/commands/repo.js.map +0 -1
- package/dist/commands/revert.d.ts.map +0 -1
- package/dist/commands/revert.js.map +0 -1
- package/dist/commands/security.d.ts.map +0 -1
- package/dist/commands/security.js.map +0 -1
- package/dist/commands/session.d.ts.map +0 -1
- package/dist/commands/session.js.map +0 -1
- package/dist/commands/ship.d.ts.map +0 -1
- package/dist/commands/ship.js.map +0 -1
- package/dist/commands/simulate.d.ts.map +0 -1
- package/dist/commands/simulate.js.map +0 -1
- package/dist/commands/verify.d.ts.map +0 -1
- package/dist/commands/verify.js.map +0 -1
- package/dist/commands/watch.d.ts.map +0 -1
- package/dist/commands/watch.js.map +0 -1
- package/dist/commands/whoami.d.ts.map +0 -1
- package/dist/commands/whoami.js.map +0 -1
- package/dist/config.d.ts.map +0 -1
- package/dist/config.js.map +0 -1
- package/dist/index.d.ts.map +0 -1
- package/dist/index.js.map +0 -1
- package/dist/rules.d.ts.map +0 -1
- package/dist/rules.js.map +0 -1
- package/dist/services/integrations/TicketService.d.ts.map +0 -1
- package/dist/services/integrations/TicketService.js.map +0 -1
- package/dist/services/mapper/ProjectScanner.d.ts.map +0 -1
- package/dist/services/mapper/ProjectScanner.js.map +0 -1
- package/dist/services/project-knowledge-service.d.ts.map +0 -1
- package/dist/services/project-knowledge-service.js.map +0 -1
- package/dist/services/security/SecurityGuard.d.ts.map +0 -1
- package/dist/services/security/SecurityGuard.js.map +0 -1
- package/dist/services/toolbox-service.d.ts.map +0 -1
- package/dist/services/toolbox-service.js.map +0 -1
- package/dist/services/watch/BlobStore.d.ts.map +0 -1
- package/dist/services/watch/BlobStore.js.map +0 -1
- package/dist/services/watch/CommandPoller.d.ts.map +0 -1
- package/dist/services/watch/CommandPoller.js.map +0 -1
- package/dist/services/watch/Journal.d.ts.map +0 -1
- package/dist/services/watch/Journal.js.map +0 -1
- package/dist/services/watch/Sentinel.d.ts.map +0 -1
- package/dist/services/watch/Sentinel.js.map +0 -1
- package/dist/services/watch/Syncer.d.ts.map +0 -1
- package/dist/services/watch/Syncer.js.map +0 -1
- package/dist/utils/ROILogger.d.ts.map +0 -1
- package/dist/utils/ROILogger.js.map +0 -1
- package/dist/utils/RelevanceScorer.d.ts.map +0 -1
- package/dist/utils/RelevanceScorer.js.map +0 -1
- package/dist/utils/ai-debt-budget.d.ts.map +0 -1
- package/dist/utils/ai-debt-budget.js.map +0 -1
- package/dist/utils/artifact-signature.d.ts.map +0 -1
- package/dist/utils/artifact-signature.js.map +0 -1
- package/dist/utils/ask-cache.d.ts.map +0 -1
- package/dist/utils/ask-cache.js.map +0 -1
- package/dist/utils/box.d.ts.map +0 -1
- package/dist/utils/box.js.map +0 -1
- package/dist/utils/brain-context.d.ts.map +0 -1
- package/dist/utils/brain-context.js.map +0 -1
- package/dist/utils/breakage-simulator.d.ts.map +0 -1
- package/dist/utils/breakage-simulator.js.map +0 -1
- package/dist/utils/change-contract.d.ts.map +0 -1
- package/dist/utils/change-contract.js.map +0 -1
- package/dist/utils/cli-json.d.ts.map +0 -1
- package/dist/utils/cli-json.js.map +0 -1
- package/dist/utils/custom-policy-rules.d.ts.map +0 -1
- package/dist/utils/custom-policy-rules.js.map +0 -1
- package/dist/utils/git.d.ts.map +0 -1
- package/dist/utils/git.js.map +0 -1
- package/dist/utils/gitignore.d.ts.map +0 -1
- package/dist/utils/gitignore.js.map +0 -1
- package/dist/utils/governance.d.ts.map +0 -1
- package/dist/utils/governance.js.map +0 -1
- package/dist/utils/ignore.d.ts.map +0 -1
- package/dist/utils/ignore.js.map +0 -1
- package/dist/utils/manual-approvals.d.ts.map +0 -1
- package/dist/utils/manual-approvals.js.map +0 -1
- package/dist/utils/messages.d.ts.map +0 -1
- package/dist/utils/messages.js.map +0 -1
- package/dist/utils/neurcode-context.d.ts.map +0 -1
- package/dist/utils/neurcode-context.js.map +0 -1
- package/dist/utils/plan-cache.d.ts.map +0 -1
- package/dist/utils/plan-cache.js.map +0 -1
- package/dist/utils/plan-slo.d.ts.map +0 -1
- package/dist/utils/plan-slo.js.map +0 -1
- package/dist/utils/policy-audit.d.ts.map +0 -1
- package/dist/utils/policy-audit.js.map +0 -1
- package/dist/utils/policy-compiler.d.ts.map +0 -1
- package/dist/utils/policy-compiler.js.map +0 -1
- package/dist/utils/policy-exceptions.d.ts.map +0 -1
- package/dist/utils/policy-exceptions.js.map +0 -1
- package/dist/utils/policy-governance.d.ts.map +0 -1
- package/dist/utils/policy-governance.js.map +0 -1
- package/dist/utils/policy-packs.d.ts.map +0 -1
- package/dist/utils/policy-packs.js.map +0 -1
- package/dist/utils/project-detector.d.ts.map +0 -1
- package/dist/utils/project-detector.js.map +0 -1
- package/dist/utils/project-root.d.ts.map +0 -1
- package/dist/utils/project-root.js.map +0 -1
- package/dist/utils/repo-links.d.ts.map +0 -1
- package/dist/utils/repo-links.js.map +0 -1
- package/dist/utils/restore.d.ts.map +0 -1
- package/dist/utils/restore.js.map +0 -1
- package/dist/utils/runtime-guard.d.ts.map +0 -1
- package/dist/utils/runtime-guard.js.map +0 -1
- package/dist/utils/scope-telemetry.d.ts.map +0 -1
- package/dist/utils/scope-telemetry.js.map +0 -1
- package/dist/utils/secret-masking.d.ts.map +0 -1
- package/dist/utils/secret-masking.js.map +0 -1
- package/dist/utils/state.d.ts.map +0 -1
- package/dist/utils/state.js.map +0 -1
- package/dist/utils/tier.d.ts.map +0 -1
- package/dist/utils/tier.js.map +0 -1
- package/dist/utils/user-context.d.ts.map +0 -1
- package/dist/utils/user-context.js.map +0 -1
package/README.md
CHANGED
|
@@ -49,14 +49,17 @@ neurcode brain mode --storage-mode no-code
|
|
|
49
49
|
neurcode brain doctor "is userid used instead of org id"
|
|
50
50
|
```
|
|
51
51
|
|
|
52
|
-
## Enterprise Governance Signing
|
|
52
|
+
## Enterprise Governance Signing (Optional Hardening)
|
|
53
53
|
|
|
54
54
|
Use signed AI change logs for fail-closed governance in `verify`/`ship`.
|
|
55
55
|
|
|
56
56
|
```bash
|
|
57
|
-
#
|
|
57
|
+
# Optional strict mode: require signed logs (fail closed when key material is missing)
|
|
58
58
|
export NEURCODE_GOVERNANCE_REQUIRE_SIGNED_LOGS=1
|
|
59
59
|
|
|
60
|
+
# Optional: honor org-level signed log requirement from control plane
|
|
61
|
+
export NEURCODE_GOVERNANCE_ENFORCE_ORG_SIGNED_LOG_REQUIREMENT=1
|
|
62
|
+
|
|
60
63
|
# Single-key mode
|
|
61
64
|
export NEURCODE_GOVERNANCE_SIGNING_KEY="<strong-random-secret>"
|
|
62
65
|
export NEURCODE_GOVERNANCE_SIGNING_KEY_ID="kid-prod-2026-03"
|
|
@@ -68,10 +71,11 @@ export NEURCODE_GOVERNANCE_SIGNING_KEY_ID="kid-prod-2026-03"
|
|
|
68
71
|
|
|
69
72
|
Notes:
|
|
70
73
|
- `verify` writes and verifies `.neurcode/ai-change-log.json` with integrity chain checks.
|
|
71
|
-
- If signed
|
|
74
|
+
- If strict signed-log mode is enabled and integrity/signature checks fail, `verify` exits non-zero.
|
|
72
75
|
- `ship` will block deployment when required signed AI logs are missing/invalid.
|
|
73
76
|
- `policy compile` and `plan` auto-sign deterministic artifacts when governance signing keys are configured.
|
|
74
77
|
- Use `--require-signed-artifacts` (or `NEURCODE_VERIFY_REQUIRE_SIGNED_ARTIFACTS=1`) to fail closed on unsigned/tampered artifacts.
|
|
78
|
+
- Default onboarding flow is non-blocking unless strict signing is explicitly enabled.
|
|
75
79
|
|
|
76
80
|
## Docs
|
|
77
81
|
|
|
@@ -12,6 +12,7 @@ const policy_packs_1 = require("../utils/policy-packs");
|
|
|
12
12
|
const policy_compiler_1 = require("../utils/policy-compiler");
|
|
13
13
|
const change_contract_1 = require("../utils/change-contract");
|
|
14
14
|
const artifact_signature_1 = require("../utils/artifact-signature");
|
|
15
|
+
const plan_symbols_1 = require("../utils/plan-symbols");
|
|
15
16
|
let chalk;
|
|
16
17
|
try {
|
|
17
18
|
chalk = require('chalk');
|
|
@@ -60,6 +61,49 @@ function parseAsJsonIfPossible(raw) {
|
|
|
60
61
|
function normalizeProvider(provider) {
|
|
61
62
|
return String(provider || 'generic').trim().toLowerCase();
|
|
62
63
|
}
|
|
64
|
+
function parseBooleanFlag(raw, fallback) {
|
|
65
|
+
if (!raw || !raw.trim())
|
|
66
|
+
return fallback;
|
|
67
|
+
const normalized = raw.trim().toLowerCase();
|
|
68
|
+
if (normalized === '1' || normalized === 'true' || normalized === 'yes' || normalized === 'on')
|
|
69
|
+
return true;
|
|
70
|
+
if (normalized === '0' || normalized === 'false' || normalized === 'no' || normalized === 'off')
|
|
71
|
+
return false;
|
|
72
|
+
return fallback;
|
|
73
|
+
}
|
|
74
|
+
function parseNonNegativeInt(raw) {
|
|
75
|
+
if (!raw || !raw.trim())
|
|
76
|
+
return undefined;
|
|
77
|
+
const parsed = Number(raw);
|
|
78
|
+
if (!Number.isFinite(parsed))
|
|
79
|
+
return undefined;
|
|
80
|
+
const rounded = Math.floor(parsed);
|
|
81
|
+
return rounded >= 0 ? rounded : undefined;
|
|
82
|
+
}
|
|
83
|
+
function resolveChangeContractOptionsFromEnv() {
|
|
84
|
+
const maxUnexpectedFiles = parseNonNegativeInt(process.env.NEURCODE_CHANGE_CONTRACT_MAX_UNEXPECTED_FILES);
|
|
85
|
+
const maxMissingExpectedSymbols = parseNonNegativeInt(process.env.NEURCODE_CHANGE_CONTRACT_MAX_MISSING_EXPECTED_SYMBOLS);
|
|
86
|
+
return {
|
|
87
|
+
enforceExpectedFiles: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_ENFORCE_EXPECTED_FILES, false),
|
|
88
|
+
enforceActionMatching: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_ENFORCE_ACTION_MATCHING, true),
|
|
89
|
+
allowRenameForModify: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_ALLOW_RENAME_FOR_MODIFY, true),
|
|
90
|
+
enforceExpectedSymbols: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_ENFORCE_EXPECTED_SYMBOLS, false),
|
|
91
|
+
enforceSymbolActionMatching: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_ENFORCE_SYMBOL_ACTION_MATCHING, false),
|
|
92
|
+
symbolTypeRelaxedMatching: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_SYMBOL_TYPE_RELAXED_MATCHING, true),
|
|
93
|
+
symbolFileBasenameFallback: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_SYMBOL_FILE_BASENAME_FALLBACK, false),
|
|
94
|
+
...(maxUnexpectedFiles !== undefined ? { maxUnexpectedFiles } : {}),
|
|
95
|
+
...(maxMissingExpectedSymbols !== undefined ? { maxMissingExpectedSymbols } : {}),
|
|
96
|
+
};
|
|
97
|
+
}
|
|
98
|
+
function mapPlanFilesForChangeContract(files) {
|
|
99
|
+
return files
|
|
100
|
+
.map((file) => ({
|
|
101
|
+
path: file.path,
|
|
102
|
+
action: file.action,
|
|
103
|
+
reason: file.reason,
|
|
104
|
+
}))
|
|
105
|
+
.filter((file) => typeof file.path === 'string' && file.path.trim().length > 0);
|
|
106
|
+
}
|
|
63
107
|
function normalizeCandidateLimit(value) {
|
|
64
108
|
if (!Number.isFinite(value))
|
|
65
109
|
return 8;
|
|
@@ -407,6 +451,9 @@ function contractCommand(program) {
|
|
|
407
451
|
projectId: options.projectId || null,
|
|
408
452
|
intent: options.intent || response.plan.summary || 'imported-plan',
|
|
409
453
|
expectedFiles,
|
|
454
|
+
planFiles: mapPlanFilesForChangeContract(response.plan.files),
|
|
455
|
+
expectedSymbols: (0, plan_symbols_1.mapPlanSymbolsForChangeContract)(response.plan),
|
|
456
|
+
options: resolveChangeContractOptionsFromEnv(),
|
|
410
457
|
policyLockFingerprint: policyLock.lock?.effective.fingerprint || null,
|
|
411
458
|
compiledPolicyFingerprint: compiledPolicy.artifact?.fingerprint || null,
|
|
412
459
|
});
|
package/dist/commands/plan.js
CHANGED
|
@@ -55,6 +55,7 @@ const change_contract_1 = require("../utils/change-contract");
|
|
|
55
55
|
const policy_packs_1 = require("../utils/policy-packs");
|
|
56
56
|
const policy_compiler_1 = require("../utils/policy-compiler");
|
|
57
57
|
const artifact_signature_1 = require("../utils/artifact-signature");
|
|
58
|
+
const plan_symbols_1 = require("../utils/plan-symbols");
|
|
58
59
|
// Import chalk with fallback for plain strings if not available
|
|
59
60
|
let chalk;
|
|
60
61
|
try {
|
|
@@ -591,6 +592,39 @@ function parseBooleanFlag(raw, fallback) {
|
|
|
591
592
|
}
|
|
592
593
|
return fallback;
|
|
593
594
|
}
|
|
595
|
+
function parseNonNegativeInt(raw) {
|
|
596
|
+
if (!raw || !raw.trim())
|
|
597
|
+
return undefined;
|
|
598
|
+
const parsed = Number(raw);
|
|
599
|
+
if (!Number.isFinite(parsed))
|
|
600
|
+
return undefined;
|
|
601
|
+
const rounded = Math.floor(parsed);
|
|
602
|
+
return rounded >= 0 ? rounded : undefined;
|
|
603
|
+
}
|
|
604
|
+
function resolveChangeContractOptionsFromEnv() {
|
|
605
|
+
const maxUnexpectedFiles = parseNonNegativeInt(process.env.NEURCODE_CHANGE_CONTRACT_MAX_UNEXPECTED_FILES);
|
|
606
|
+
const maxMissingExpectedSymbols = parseNonNegativeInt(process.env.NEURCODE_CHANGE_CONTRACT_MAX_MISSING_EXPECTED_SYMBOLS);
|
|
607
|
+
return {
|
|
608
|
+
enforceExpectedFiles: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_ENFORCE_EXPECTED_FILES, false),
|
|
609
|
+
enforceActionMatching: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_ENFORCE_ACTION_MATCHING, true),
|
|
610
|
+
allowRenameForModify: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_ALLOW_RENAME_FOR_MODIFY, true),
|
|
611
|
+
enforceExpectedSymbols: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_ENFORCE_EXPECTED_SYMBOLS, false),
|
|
612
|
+
enforceSymbolActionMatching: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_ENFORCE_SYMBOL_ACTION_MATCHING, false),
|
|
613
|
+
symbolTypeRelaxedMatching: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_SYMBOL_TYPE_RELAXED_MATCHING, true),
|
|
614
|
+
symbolFileBasenameFallback: parseBooleanFlag(process.env.NEURCODE_CHANGE_CONTRACT_SYMBOL_FILE_BASENAME_FALLBACK, false),
|
|
615
|
+
...(maxUnexpectedFiles !== undefined ? { maxUnexpectedFiles } : {}),
|
|
616
|
+
...(maxMissingExpectedSymbols !== undefined ? { maxMissingExpectedSymbols } : {}),
|
|
617
|
+
};
|
|
618
|
+
}
|
|
619
|
+
function mapPlanFilesForChangeContract(files) {
|
|
620
|
+
return files
|
|
621
|
+
.map((file) => ({
|
|
622
|
+
path: file.path,
|
|
623
|
+
action: file.action,
|
|
624
|
+
reason: file.reason,
|
|
625
|
+
}))
|
|
626
|
+
.filter((file) => typeof file.path === 'string' && file.path.trim().length > 0);
|
|
627
|
+
}
|
|
594
628
|
function parseConfidenceScoreThreshold(raw) {
|
|
595
629
|
if (!raw)
|
|
596
630
|
return null;
|
|
@@ -854,6 +888,9 @@ function emitCachedPlanHit(input) {
|
|
|
854
888
|
projectId: input.projectId || null,
|
|
855
889
|
intent: input.response.plan.summary || 'cached-plan',
|
|
856
890
|
expectedFiles,
|
|
891
|
+
planFiles: mapPlanFilesForChangeContract(input.response.plan.files),
|
|
892
|
+
expectedSymbols: (0, plan_symbols_1.mapPlanSymbolsForChangeContract)(input.response.plan),
|
|
893
|
+
options: resolveChangeContractOptionsFromEnv(),
|
|
857
894
|
policyLockFingerprint: lockRead.lock?.effective.fingerprint || null,
|
|
858
895
|
compiledPolicyFingerprint: compiledPolicyRead.artifact?.fingerprint || null,
|
|
859
896
|
});
|
|
@@ -2284,6 +2321,9 @@ async function planCommand(intent, options) {
|
|
|
2284
2321
|
projectId: finalProjectId || null,
|
|
2285
2322
|
intent,
|
|
2286
2323
|
expectedFiles,
|
|
2324
|
+
planFiles: mapPlanFilesForChangeContract(response.plan.files),
|
|
2325
|
+
expectedSymbols: (0, plan_symbols_1.mapPlanSymbolsForChangeContract)(response.plan),
|
|
2326
|
+
options: resolveChangeContractOptionsFromEnv(),
|
|
2287
2327
|
policyLockFingerprint: lockRead.lock?.effective.fingerprint || null,
|
|
2288
2328
|
compiledPolicyFingerprint: compiledPolicyRead.artifact?.fingerprint || null,
|
|
2289
2329
|
});
|
package/dist/commands/ship.js
CHANGED
|
@@ -825,6 +825,15 @@ function isEnabledFlag(value) {
|
|
|
825
825
|
const normalized = value.trim().toLowerCase();
|
|
826
826
|
return normalized === '1' || normalized === 'true' || normalized === 'yes' || normalized === 'on';
|
|
827
827
|
}
|
|
828
|
+
function isSignedAiLogsRequired(orgGovernance) {
|
|
829
|
+
const explicitRequirement = isEnabledFlag(process.env.NEURCODE_GOVERNANCE_REQUIRE_SIGNED_LOGS) ||
|
|
830
|
+
isEnabledFlag(process.env.NEURCODE_AI_LOG_REQUIRE_SIGNED);
|
|
831
|
+
if (explicitRequirement) {
|
|
832
|
+
return true;
|
|
833
|
+
}
|
|
834
|
+
const honorOrgRequirement = isEnabledFlag(process.env.NEURCODE_GOVERNANCE_ENFORCE_ORG_SIGNED_LOG_REQUIREMENT);
|
|
835
|
+
return honorOrgRequirement && orgGovernance?.requireSignedAiLogs === true;
|
|
836
|
+
}
|
|
828
837
|
function collectApplyWrittenFiles(output) {
|
|
829
838
|
const clean = stripAnsi(output);
|
|
830
839
|
const files = [];
|
|
@@ -1846,9 +1855,7 @@ async function shipCommand(goal, options) {
|
|
|
1846
1855
|
const manualApprovalBypass = options.manualApproveHighRisk === true || process.env.NEURCODE_MANUAL_APPROVE_HIGH_RISK === '1';
|
|
1847
1856
|
const governanceDecision = finalVerifyPayload.governanceDecision?.decision;
|
|
1848
1857
|
const orgGovernance = finalVerifyPayload.orgGovernance || null;
|
|
1849
|
-
const signedAiLogsRequired = orgGovernance
|
|
1850
|
-
isEnabledFlag(process.env.NEURCODE_GOVERNANCE_REQUIRE_SIGNED_LOGS) ||
|
|
1851
|
-
isEnabledFlag(process.env.NEURCODE_AI_LOG_REQUIRE_SIGNED);
|
|
1858
|
+
const signedAiLogsRequired = isSignedAiLogsRequired(orgGovernance);
|
|
1852
1859
|
const aiLogIntegrity = finalVerifyPayload.aiChangeLog?.integrity;
|
|
1853
1860
|
const signedAiLogsValid = aiLogIntegrity?.valid === true && aiLogIntegrity?.signed === true;
|
|
1854
1861
|
const orgManualApprovalRequired = orgGovernance?.requireManualApproval === true;
|
|
@@ -37,6 +37,8 @@ interface VerifyOptions {
|
|
|
37
37
|
runtimeGuard?: string;
|
|
38
38
|
/** Print detailed AI change justification reasoning. */
|
|
39
39
|
explain?: boolean;
|
|
40
|
+
/** Print extra explanatory output for demos/onboarding. */
|
|
41
|
+
demo?: boolean;
|
|
40
42
|
/** Use queue-backed async verification mode on the API. */
|
|
41
43
|
asyncMode?: boolean;
|
|
42
44
|
/** Poll interval for async verification job status. */
|