@codapult/guard 0.2.0 → 0.4.0
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 +73 -1
- package/dist/adapters/command.d.ts +10 -8
- package/dist/adapters/command.js +23 -2
- package/dist/adapters/project-checks.d.ts +23 -20
- package/dist/cli/commands/guard.d.ts +53 -54
- package/dist/cli/commands/guard.js +155 -32
- package/dist/cli/index.js +41 -5
- package/dist/core/analysis/doctor.d.ts +1 -1
- package/dist/core/analysis/doctor.js +19 -6
- package/dist/core/discovery/discovery.d.ts +27 -13
- package/dist/core/discovery/discovery.js +182 -29
- package/dist/core/errors.d.ts +11 -0
- package/dist/core/errors.js +11 -0
- package/dist/core/guard.d.ts +134 -69
- package/dist/core/guard.js +767 -145
- package/dist/core/history/runs.d.ts +28 -0
- package/dist/core/history/runs.js +59 -0
- package/dist/core/model/types.d.ts +10 -0
- package/dist/core/model/types.js +1 -0
- package/dist/core/policy/schemas.d.ts +81 -0
- package/dist/core/policy/schemas.js +46 -17
- package/dist/core/verification/verify.d.ts +21 -12
- package/dist/core/verification/verify.js +81 -8
- package/dist/index.d.ts +3 -0
- package/dist/index.js +3 -0
- package/dist/mcp/resources.js +64 -29
- package/dist/mcp/tools/guard.js +300 -52
- package/package.json +12 -7
package/dist/core/guard.d.ts
CHANGED
|
@@ -1,33 +1,59 @@
|
|
|
1
|
-
import type
|
|
2
|
-
import { discoverProject, discoverProjectWithMetrics, findGuardRoot } from './discovery/discovery.js';
|
|
1
|
+
import { type ProjectModel } from './discovery/discovery.js';
|
|
2
|
+
import { clearDiscoveryCache, discoverProject, discoverProjectWithMetrics, findGuardRoot } from './discovery/discovery.js';
|
|
3
3
|
import { type GuardImpactAnalysis } from './analysis/impact.js';
|
|
4
|
-
|
|
4
|
+
import type { GuardAdapterName, GuardApprovalMode, GuardContractKind, GuardBudgetMetric, GuardRuleKind, GuardRuleStatus, GuardSeverity, GuardToolMode } from './model/types.js';
|
|
5
|
+
export type { GuardAdapterName, GuardApprovalMode, GuardContractKind, GuardBudgetMetric, GuardRuleKind, GuardRuleStatus, GuardSeverity, GuardToolMode, } from './model/types.js';
|
|
5
6
|
export type GuardOutcomeStatus = 'pass' | 'fail' | 'warning' | 'needs-review' | 'not-configured';
|
|
6
|
-
export
|
|
7
|
-
configured?: boolean;
|
|
8
|
-
errors?: number;
|
|
9
|
-
warnings?: number;
|
|
10
|
-
needsReview?: boolean;
|
|
11
|
-
}
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
7
|
+
export interface GuardOutcomeInput {
|
|
8
|
+
configured?: boolean | undefined;
|
|
9
|
+
errors?: number | undefined;
|
|
10
|
+
warnings?: number | undefined;
|
|
11
|
+
needsReview?: boolean | undefined;
|
|
12
|
+
}
|
|
13
|
+
interface GuardStateLockOptions {
|
|
14
|
+
waitMs?: number | undefined;
|
|
15
|
+
noWait?: boolean | undefined;
|
|
16
|
+
}
|
|
17
|
+
interface GuardBaselineUpdateOptions {
|
|
18
|
+
add?: string[] | undefined;
|
|
19
|
+
remove?: string[] | undefined;
|
|
20
|
+
reason?: string | undefined;
|
|
21
|
+
}
|
|
22
|
+
interface GuardConfigWriteOptions extends GuardStateLockOptions {
|
|
23
|
+
expectedRevision?: number | undefined;
|
|
24
|
+
}
|
|
25
|
+
interface GuardPendingProposal {
|
|
26
|
+
id: string;
|
|
27
|
+
type: 'rule' | 'contract';
|
|
28
|
+
}
|
|
29
|
+
export interface GuardSensitiveText {
|
|
30
|
+
value: string;
|
|
31
|
+
redacted: boolean;
|
|
32
|
+
redactionCount: number;
|
|
33
|
+
}
|
|
34
|
+
export interface GuardInitializationResult {
|
|
35
|
+
config: GuardConfig;
|
|
36
|
+
report: GuardReport;
|
|
37
|
+
}
|
|
38
|
+
export declare function classifyGuardOutcome(input: GuardOutcomeInput): GuardOutcomeStatus;
|
|
15
39
|
export interface GuardContract {
|
|
16
40
|
id: string;
|
|
17
41
|
statement: string;
|
|
18
|
-
kind?: GuardContractKind;
|
|
19
|
-
severity?: GuardSeverity;
|
|
20
|
-
scope?: string[];
|
|
21
|
-
entrypoints?: string[];
|
|
22
|
-
exclude?: string[];
|
|
23
|
-
guidance?: string[];
|
|
24
|
-
references?: string[];
|
|
25
|
-
mustImport?: string[];
|
|
26
|
-
mustNotImport?: string[];
|
|
27
|
-
mustCall?: string[];
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
42
|
+
kind?: GuardContractKind | undefined;
|
|
43
|
+
severity?: GuardSeverity | undefined;
|
|
44
|
+
scope?: string[] | undefined;
|
|
45
|
+
entrypoints?: string[] | undefined;
|
|
46
|
+
exclude?: string[] | undefined;
|
|
47
|
+
guidance?: string[] | undefined;
|
|
48
|
+
references?: string[] | undefined;
|
|
49
|
+
mustImport?: string[] | undefined;
|
|
50
|
+
mustNotImport?: string[] | undefined;
|
|
51
|
+
mustCall?: string[] | undefined;
|
|
52
|
+
fromPackages?: string[] | undefined;
|
|
53
|
+
mustNotImportPackages?: string[] | undefined;
|
|
54
|
+
status?: GuardRuleStatus | undefined;
|
|
55
|
+
confidence?: 'high' | 'medium' | 'low' | undefined;
|
|
56
|
+
evidence?: string[] | undefined;
|
|
31
57
|
}
|
|
32
58
|
export interface GuardRule {
|
|
33
59
|
id: string;
|
|
@@ -35,36 +61,60 @@ export interface GuardRule {
|
|
|
35
61
|
severity: GuardSeverity;
|
|
36
62
|
kind: GuardRuleKind;
|
|
37
63
|
patterns: string[];
|
|
38
|
-
files?: string[];
|
|
39
|
-
status?: GuardRuleStatus;
|
|
40
|
-
confidence?: 'high' | 'medium' | 'low';
|
|
41
|
-
evidence?: string[];
|
|
64
|
+
files?: string[] | undefined;
|
|
65
|
+
status?: GuardRuleStatus | undefined;
|
|
66
|
+
confidence?: 'high' | 'medium' | 'low' | undefined;
|
|
67
|
+
evidence?: string[] | undefined;
|
|
68
|
+
}
|
|
69
|
+
export interface GuardBudget {
|
|
70
|
+
id: string;
|
|
71
|
+
description: string;
|
|
72
|
+
metric: GuardBudgetMetric;
|
|
73
|
+
scope: string[];
|
|
74
|
+
limit: number;
|
|
75
|
+
severity: GuardSeverity;
|
|
76
|
+
reason: string;
|
|
77
|
+
status?: GuardRuleStatus | undefined;
|
|
78
|
+
evidence?: string[] | undefined;
|
|
42
79
|
}
|
|
43
80
|
export interface GuardConfig {
|
|
44
81
|
version: 1;
|
|
82
|
+
revision?: number | undefined;
|
|
83
|
+
contentFingerprint?: string | undefined;
|
|
45
84
|
rules: GuardRule[];
|
|
46
|
-
contracts?: GuardContract[];
|
|
85
|
+
contracts?: GuardContract[] | undefined;
|
|
86
|
+
budgets?: GuardBudget[] | undefined;
|
|
87
|
+
approval?: GuardApprovalPolicy | undefined;
|
|
88
|
+
}
|
|
89
|
+
export interface GuardApprovalPolicy {
|
|
90
|
+
mode: GuardApprovalMode;
|
|
91
|
+
allowMcpApproval: boolean;
|
|
92
|
+
requireDistinctActor: boolean;
|
|
47
93
|
}
|
|
48
94
|
export interface GuardProposalFile {
|
|
49
95
|
version: 1;
|
|
50
96
|
generatedAt: string;
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
97
|
+
generatedBy?: string | undefined;
|
|
98
|
+
proposalId?: string | undefined;
|
|
99
|
+
projectFingerprint?: string | undefined;
|
|
100
|
+
revision?: number | undefined;
|
|
101
|
+
contentFingerprint?: string | undefined;
|
|
55
102
|
rules: GuardRule[];
|
|
56
103
|
contracts: GuardContract[];
|
|
57
104
|
questions: string[];
|
|
58
|
-
decisions?: GuardProposalDecision[];
|
|
105
|
+
decisions?: GuardProposalDecision[] | undefined;
|
|
59
106
|
}
|
|
60
107
|
export interface GuardProposalDecision {
|
|
61
108
|
id: string;
|
|
62
109
|
type: 'rule' | 'contract';
|
|
63
110
|
decision: 'approved' | 'rejected';
|
|
64
111
|
decidedAt: string;
|
|
65
|
-
proposalId?: string;
|
|
66
|
-
proposalFingerprint?: string;
|
|
67
|
-
revision?: number;
|
|
112
|
+
proposalId?: string | undefined;
|
|
113
|
+
proposalFingerprint?: string | undefined;
|
|
114
|
+
revision?: number | undefined;
|
|
115
|
+
source?: 'cli' | 'mcp' | 'external' | undefined;
|
|
116
|
+
actor?: string | undefined;
|
|
117
|
+
commit?: string | undefined;
|
|
68
118
|
}
|
|
69
119
|
export type GuardProposalFreshness = 'current' | 'stale' | 'unknown';
|
|
70
120
|
export interface GuardAgentConfig {
|
|
@@ -81,25 +131,24 @@ export interface GuardAgentConfig {
|
|
|
81
131
|
checks: ('lint' | 'typecheck' | 'test' | 'build')[];
|
|
82
132
|
};
|
|
83
133
|
}
|
|
84
|
-
export type GuardToolMode = 'auto' | 'on' | 'off';
|
|
85
|
-
export type GuardAdapterName = 'dependency-graph' | 'security' | 'dependency-hygiene';
|
|
86
134
|
export interface GuardFinding {
|
|
87
135
|
ruleId: string;
|
|
88
136
|
severity: GuardSeverity;
|
|
89
137
|
file: string;
|
|
90
138
|
line: number;
|
|
91
139
|
importPath: string;
|
|
140
|
+
resolvedPath?: string | undefined;
|
|
92
141
|
message: string;
|
|
93
142
|
fingerprint: string;
|
|
94
143
|
}
|
|
95
144
|
export interface GuardFileChange {
|
|
96
145
|
path: string;
|
|
97
146
|
status: 'added' | 'modified' | 'deleted' | 'renamed';
|
|
98
|
-
previousPath?: string;
|
|
147
|
+
previousPath?: string | undefined;
|
|
99
148
|
}
|
|
100
149
|
export interface GuardContractIssue {
|
|
101
150
|
contractId: string;
|
|
102
|
-
field: 'scope' | 'reference' | 'definition';
|
|
151
|
+
field: 'scope' | 'reference' | 'definition' | 'files';
|
|
103
152
|
value: string;
|
|
104
153
|
message: string;
|
|
105
154
|
}
|
|
@@ -110,24 +159,24 @@ export interface GuardReport {
|
|
|
110
159
|
scannedFiles: number;
|
|
111
160
|
}
|
|
112
161
|
interface ScanGuardOptions {
|
|
113
|
-
changedOnly?: boolean;
|
|
114
|
-
changedFiles?: Set<string
|
|
115
|
-
baseline?: Set<string
|
|
116
|
-
includeArchitectureInsights?: boolean;
|
|
162
|
+
changedOnly?: boolean | undefined;
|
|
163
|
+
changedFiles?: Set<string> | undefined;
|
|
164
|
+
baseline?: Set<string> | undefined;
|
|
165
|
+
includeArchitectureInsights?: boolean | undefined;
|
|
117
166
|
}
|
|
118
167
|
export interface GuardReviewPacket {
|
|
119
168
|
version: 1;
|
|
120
169
|
outcome: GuardOutcomeStatus;
|
|
121
|
-
diffBase?: string;
|
|
170
|
+
diffBase?: string | undefined;
|
|
122
171
|
changedFiles: string[];
|
|
123
172
|
changes: GuardFileChange[];
|
|
124
173
|
diff: string;
|
|
125
174
|
truncated: boolean;
|
|
126
175
|
redacted: boolean;
|
|
127
|
-
diffError?: string;
|
|
176
|
+
diffError?: string | undefined;
|
|
128
177
|
project: ProjectModel;
|
|
129
178
|
contracts: GuardContract[];
|
|
130
|
-
requirement?: string;
|
|
179
|
+
requirement?: string | undefined;
|
|
131
180
|
deterministicFindings: GuardFinding[];
|
|
132
181
|
impact: GuardImpactAnalysis;
|
|
133
182
|
reviewInstructions: string[];
|
|
@@ -143,33 +192,48 @@ export declare const GUARD_CONVENTIONS_FILE: string;
|
|
|
143
192
|
export declare const GUARD_AGENT_FILE: string;
|
|
144
193
|
export declare const GUARD_CONTRACTS_FILE: string;
|
|
145
194
|
export declare const GUARD_PROPOSALS_FILE: string;
|
|
195
|
+
export declare const GUARD_STATE_DIR: string;
|
|
196
|
+
export declare const GUARD_STATE_GENERATIONS_DIR: string;
|
|
197
|
+
export declare const GUARD_STATE_CURRENT_FILE: string;
|
|
146
198
|
export declare const defaultGuardConfig: GuardConfig;
|
|
147
199
|
export declare const defaultGuardAgentConfig: GuardAgentConfig;
|
|
148
200
|
export declare class GuardAlreadyInitializedError extends Error {
|
|
149
201
|
constructor();
|
|
150
202
|
}
|
|
203
|
+
export declare class GuardConfigError extends Error {
|
|
204
|
+
constructor(path: string);
|
|
205
|
+
}
|
|
206
|
+
export declare class GuardStateBusyError extends Error {
|
|
207
|
+
constructor(path: string);
|
|
208
|
+
}
|
|
209
|
+
export declare class GuardStateStaleError extends Error {
|
|
210
|
+
constructor();
|
|
211
|
+
}
|
|
212
|
+
export declare class GuardBaselineReasonError extends Error {
|
|
213
|
+
constructor();
|
|
214
|
+
}
|
|
215
|
+
export declare function withGuardStateLock<T>(root: string, callback: () => T, options?: GuardStateLockOptions): T;
|
|
151
216
|
export declare function isGuardContractsFile(value: unknown): value is {
|
|
152
217
|
version: 1;
|
|
153
218
|
contracts: GuardContract[];
|
|
154
219
|
};
|
|
155
220
|
export declare function isGuardProposalFile(value: unknown): value is GuardProposalFile;
|
|
156
221
|
export declare function fingerprintProjectModel(model: ProjectModel): string;
|
|
222
|
+
export declare function fingerprintGuardConfig(guardConfig: GuardConfig): string;
|
|
157
223
|
export declare function getGuardProposalFreshness(model: ProjectModel, proposals: GuardProposalFile | undefined): GuardProposalFreshness;
|
|
158
224
|
export declare function loadGuardConfig(root: string): GuardConfig | undefined;
|
|
159
225
|
export declare function loadGuardProposals(root: string): GuardProposalFile | undefined;
|
|
160
226
|
export declare function isGuardAgentConfig(value: unknown): value is GuardAgentConfig;
|
|
161
227
|
export declare function loadGuardAgentConfig(root: string): GuardAgentConfig;
|
|
162
228
|
export declare function writeGuardAgentConfig(root: string, agentConfig?: GuardAgentConfig): void;
|
|
163
|
-
export declare function loadGuardArtifact(root: string, relativePath: string): unknown;
|
|
164
229
|
export declare function loadBaseline(root: string): Set<string>;
|
|
165
|
-
export declare function updateBaseline(root: string, options?:
|
|
166
|
-
|
|
167
|
-
remove?: string[];
|
|
168
|
-
reason?: string;
|
|
169
|
-
}): Set<string>;
|
|
170
|
-
export declare function writeGuardConfig(root: string, guardConfig: GuardConfig): void;
|
|
230
|
+
export declare function updateBaseline(root: string, options?: GuardBaselineUpdateOptions): Set<string>;
|
|
231
|
+
export declare function writeGuardConfig(root: string, guardConfig: GuardConfig, options?: GuardConfigWriteOptions): void;
|
|
171
232
|
export declare function writeGuardProposals(root: string, proposals: GuardProposalFile): void;
|
|
172
|
-
export declare function recordGuardProposalDecision(root: string, decisions: Pick<GuardProposalDecision, 'id' | 'type' | 'decision'>[]): void;
|
|
233
|
+
export declare function recordGuardProposalDecision(root: string, decisions: Pick<GuardProposalDecision, 'id' | 'type' | 'decision'>[], options?: Pick<GuardProposalDecision, 'source'>): void;
|
|
234
|
+
export declare function applyGuardProposalDecision(root: string, guardConfig: GuardConfig, decisions: Pick<GuardProposalDecision, 'id' | 'type' | 'decision'>[], options: Pick<GuardProposalDecision, 'source'>): void;
|
|
235
|
+
export declare function validateGuardProposalApproval(policy: GuardApprovalPolicy | undefined, proposals: GuardProposalFile | undefined): string | undefined;
|
|
236
|
+
export declare function getPendingGuardProposals(proposals: GuardProposalFile | undefined): GuardPendingProposal[];
|
|
173
237
|
export declare function buildGuardProposals(model: ProjectModel, guardConfig: GuardConfig): GuardProposalFile;
|
|
174
238
|
export declare function buildArchitectureMemory(model: ProjectModel): Record<string, unknown>;
|
|
175
239
|
export declare function buildConventionsMemory(model: ProjectModel): Record<string, unknown>;
|
|
@@ -178,20 +242,21 @@ export declare function writeGuardMemory(root: string, model: ProjectModel): voi
|
|
|
178
242
|
export declare function writeBaseline(root: string, findings: GuardFinding[], model?: ProjectModel): void;
|
|
179
243
|
export declare function loadProjectModel(root: string): ProjectModel | undefined;
|
|
180
244
|
export declare function writeProjectModel(root: string, model: ProjectModel): void;
|
|
245
|
+
/**
|
|
246
|
+
* Persist all derived project facts as one generation. Legacy root-level files remain as
|
|
247
|
+
* compatibility mirrors, while readers that understand generations always see a coherent set.
|
|
248
|
+
*/
|
|
249
|
+
export declare function writeProjectState(root: string, model: ProjectModel, options?: GuardStateLockOptions): string;
|
|
181
250
|
export declare function writeProjectSnapshot(root: string, model: ProjectModel): string;
|
|
251
|
+
export declare function loadGuardArtifact(root: string, relativePath: string): unknown;
|
|
182
252
|
export declare function validateGuardContracts(root: string, contracts?: GuardContract[]): GuardContractIssue[];
|
|
253
|
+
export declare function validateGuardBudgets(root: string, budgets?: GuardBudget[]): GuardContractIssue[];
|
|
254
|
+
export declare function validateGuardPolicy(root: string, guardConfig: GuardConfig): GuardContractIssue[];
|
|
183
255
|
/** @internal Redacts common credential shapes before a diff enters an AI review packet. */
|
|
184
|
-
export declare function redactSensitiveText(value: string):
|
|
185
|
-
value: string;
|
|
186
|
-
redacted: boolean;
|
|
187
|
-
redactionCount: number;
|
|
188
|
-
};
|
|
256
|
+
export declare function redactSensitiveText(value: string): GuardSensitiveText;
|
|
189
257
|
export declare function scanGuard(root: string, guardConfig: GuardConfig, options?: ScanGuardOptions): GuardReport;
|
|
190
258
|
export declare function buildGuardReviewPacket(root: string, guardConfig: GuardConfig, baseline?: Set<string>, maxDiffChars?: number, changedOnly?: boolean, requirement?: string, base?: string): GuardReviewPacket;
|
|
191
|
-
export declare function initializeGuard(root: string, options?: {
|
|
192
|
-
force?: boolean;
|
|
193
|
-
}):
|
|
194
|
-
|
|
195
|
-
report: GuardReport;
|
|
196
|
-
};
|
|
197
|
-
export { discoverProject, discoverProjectWithMetrics, findGuardRoot };
|
|
259
|
+
export declare function initializeGuard(root: string, options?: GuardConfigWriteOptions & {
|
|
260
|
+
force?: boolean | undefined;
|
|
261
|
+
}): GuardInitializationResult;
|
|
262
|
+
export { clearDiscoveryCache, discoverProject, discoverProjectWithMetrics, findGuardRoot };
|