@deftai/directive-core 0.74.0 → 0.76.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/dist/agents-md-budget/evaluate.d.ts +61 -0
- package/dist/agents-md-budget/evaluate.js +341 -19
- package/dist/agents-md-budget/index.d.ts +1 -0
- package/dist/agents-md-budget/index.js +1 -0
- package/dist/agents-md-budget/skill-frontmatter.d.ts +35 -0
- package/dist/agents-md-budget/skill-frontmatter.js +116 -0
- package/dist/cache/operations.d.ts +2 -0
- package/dist/cache/operations.js +16 -1
- package/dist/content-contracts/skills/helpers.d.ts +0 -1
- package/dist/content-contracts/skills/helpers.js +1 -11
- package/dist/content-contracts/skills/skill-frontmatter.js +8 -1
- package/dist/content-contracts/standards/_helpers.js +4 -2
- package/dist/content-contracts/standards/_taskfile-helpers.d.ts +2 -0
- package/dist/content-contracts/standards/_taskfile-helpers.js +11 -5
- package/dist/doctor/doctor-state.js +2 -1
- package/dist/doctor/paths.js +2 -1
- package/dist/eval-health-relocation/evaluate.d.ts +71 -0
- package/dist/eval-health-relocation/evaluate.js +252 -0
- package/dist/eval-health-relocation/index.d.ts +2 -0
- package/dist/eval-health-relocation/index.js +2 -0
- package/dist/init-deposit/scaffold.js +35 -20
- package/dist/intake/issue-emit.js +2 -2
- package/dist/intake/issue-ingest.js +23 -4
- package/dist/packaging/openpackage-tiers.d.ts +12 -0
- package/dist/packaging/openpackage-tiers.js +42 -0
- package/dist/policy/agents-md-budget.d.ts +23 -0
- package/dist/policy/agents-md-budget.js +75 -4
- package/dist/preflight/evaluate.d.ts +5 -2
- package/dist/preflight/evaluate.js +9 -4
- package/dist/preflight/index.d.ts +1 -1
- package/dist/preflight/index.js +1 -1
- package/dist/release/pipeline-fixture.d.ts +3 -0
- package/dist/release/pipeline-fixture.js +11 -0
- package/dist/release/pipeline.js +4 -0
- package/dist/release/spawn.js +5 -3
- package/dist/scope/decompose.js +4 -3
- package/dist/scope/transition.js +17 -2
- package/dist/scope/vbrief-ref.d.ts +6 -0
- package/dist/scope/vbrief-ref.js +23 -4
- package/dist/session/index.d.ts +1 -0
- package/dist/session/index.js +1 -0
- package/dist/session/posture.d.ts +50 -0
- package/dist/session/posture.js +152 -0
- package/dist/session/ritual-sentinel.d.ts +2 -0
- package/dist/session/ritual-sentinel.js +3 -0
- package/dist/session/session-start.d.ts +8 -0
- package/dist/session/session-start.js +43 -0
- package/dist/session/verify-session-ritual.d.ts +6 -0
- package/dist/session/verify-session-ritual.js +67 -4
- package/dist/swarm/complete-cohort.js +6 -6
- package/dist/swarm/launch.js +2 -2
- package/dist/triage/bootstrap/gitignore.js +8 -4
- package/dist/triage/cache-path.js +16 -3
- package/dist/triage/queue/cache.d.ts +14 -0
- package/dist/triage/queue/cache.js +61 -1
- package/dist/triage/welcome/writers.js +2 -0
- package/dist/ts-check-lane/index.d.ts +1 -1
- package/dist/ts-check-lane/index.js +1 -1
- package/dist/ts-check-lane/run-lane.d.ts +5 -0
- package/dist/ts-check-lane/run-lane.js +15 -0
- package/dist/validate-content/validate-links.js +2 -2
- package/dist/value/readback.d.ts +1 -0
- package/dist/value/readback.js +5 -1
- package/dist/vbrief-build/constants.d.ts +3 -3
- package/dist/vbrief-build/constants.js +4 -3
- package/dist/vbrief-build/index.d.ts +1 -1
- package/dist/vbrief-build/index.js +1 -1
- package/dist/verify-env/toolchain-check.js +20 -5
- package/dist/verify-env/verify-hooks-installed.d.ts +2 -0
- package/dist/verify-env/verify-hooks-installed.js +17 -15
- package/package.json +7 -3
|
@@ -1,9 +1,51 @@
|
|
|
1
|
+
import { type AgentsMdBudget } from "../policy/agents-md-budget.js";
|
|
2
|
+
import { type SkillFrontmatterMeasure } from "./skill-frontmatter.js";
|
|
1
3
|
export type OutputStream = "stdout" | "stderr" | "none";
|
|
4
|
+
/**
|
|
5
|
+
* Layered absolute north-star for the always-on managed surface (#2372 / #2450 / #2452).
|
|
6
|
+
*
|
|
7
|
+
* `ABSOLUTE_MANAGED_MAX_BYTES` is the relocation north-star (<=8192 B / ~2k tok).
|
|
8
|
+
* When `plan.policy.agentsMdBudget.absoluteMaxBytes` is set, growth past that seeded
|
|
9
|
+
* ratchet fails closed; distance-to-north-star is always reported. Optional release-gate
|
|
10
|
+
* north-star enforcement: DEFT_AGENTS_MD_BUDGET_ENFORCE_NORTH_STAR=1 (waiver:
|
|
11
|
+
* DEFT_ALLOW_ABSOLUTE_BUDGET_WAIVER=1).
|
|
12
|
+
*
|
|
13
|
+
* DD-3 (harness-injected skill frontmatter) is measured and itemized (#2463).
|
|
14
|
+
* Managed `absoluteMaxBytes` remains the fail-closed ratchet for the rendered
|
|
15
|
+
* managed section; skill-frontmatter caps are advisory unless
|
|
16
|
+
* `skillFrontmatterMaxBytes` is set (or enforced via env).
|
|
17
|
+
*/
|
|
18
|
+
export declare const ABSOLUTE_MANAGED_MAX_BYTES = 8192;
|
|
19
|
+
export declare const ABSOLUTE_MANAGED_MAX_TOKENS = 2000;
|
|
20
|
+
/** Bootstrap host hooks are 0 B until #2438 ships. */
|
|
21
|
+
export declare const BOOTSTRAP_HOOK_BYTES = 0;
|
|
22
|
+
/** Rough UTF-8 bytes-per-token estimate for advisory reporting (~8192 B ≈ ~2048 tok). */
|
|
23
|
+
export declare const ABSOLUTE_BYTES_PER_TOKEN_ESTIMATE = 4;
|
|
24
|
+
/** Byte + estimated-token measure of the managed section body. */
|
|
25
|
+
export interface ManagedSectionMeasure {
|
|
26
|
+
readonly bytes: number;
|
|
27
|
+
readonly estimatedTokens: number;
|
|
28
|
+
}
|
|
29
|
+
/** Itemized always-on bootstrap surface (managed + DD-3 + hooks). */
|
|
30
|
+
export interface BootstrapMeasure {
|
|
31
|
+
readonly managed: ManagedSectionMeasure;
|
|
32
|
+
readonly skillFrontmatter: SkillFrontmatterMeasure;
|
|
33
|
+
readonly bootstrapHookBytes: number;
|
|
34
|
+
readonly totalBytes: number;
|
|
35
|
+
readonly totalEstimatedTokens: number;
|
|
36
|
+
}
|
|
2
37
|
/** Result of verify:agents-md-budget evaluation; three-state exit contract. */
|
|
3
38
|
export interface EvaluateResult {
|
|
4
39
|
readonly code: 0 | 1 | 2;
|
|
5
40
|
readonly message: string;
|
|
6
41
|
readonly stream: OutputStream;
|
|
42
|
+
/** North-star distance note (#2452); may accompany success or failure paths. */
|
|
43
|
+
readonly northStarMessage?: string;
|
|
44
|
+
readonly northStarStream?: OutputStream;
|
|
45
|
+
/** @deprecated Use northStarMessage — retained for one release of CLI compat. */
|
|
46
|
+
readonly advisoryMessage?: string;
|
|
47
|
+
/** @deprecated Use northStarStream — retained for one release of CLI compat. */
|
|
48
|
+
readonly advisoryStream?: OutputStream;
|
|
7
49
|
}
|
|
8
50
|
export interface EvaluateOptions {
|
|
9
51
|
readonly quiet?: boolean;
|
|
@@ -26,6 +68,25 @@ export declare function countRegions(text: string): {
|
|
|
26
68
|
} | {
|
|
27
69
|
error: string;
|
|
28
70
|
};
|
|
71
|
+
/**
|
|
72
|
+
* Extract the managed-section span (open marker through close marker, inclusive).
|
|
73
|
+
*
|
|
74
|
+
* Returns an empty section when no markers are present — consistent with
|
|
75
|
+
* `countRegions` treating markerless files as entirely unmanaged.
|
|
76
|
+
*/
|
|
77
|
+
export declare function extractManagedSection(text: string): {
|
|
78
|
+
section: string;
|
|
79
|
+
} | {
|
|
80
|
+
error: string;
|
|
81
|
+
};
|
|
82
|
+
/** Measure UTF-8 byte length and a rough token estimate for the managed section. */
|
|
83
|
+
export declare function measureManagedSection(text: string): ManagedSectionMeasure | {
|
|
84
|
+
error: string;
|
|
85
|
+
};
|
|
86
|
+
/** Measure managed + DD-3 skill frontmatter + bootstrap hooks. */
|
|
87
|
+
export declare function measureBootstrapSurface(projectRoot: string, managedText: string, budget: AgentsMdBudget | null): BootstrapMeasure | {
|
|
88
|
+
error: string;
|
|
89
|
+
};
|
|
29
90
|
/**
|
|
30
91
|
* Pure evaluator for the AGENTS.md line-budget ratchet gate (#645).
|
|
31
92
|
*
|
|
@@ -1,7 +1,29 @@
|
|
|
1
1
|
import { existsSync, readFileSync } from "node:fs";
|
|
2
2
|
import { join, resolve } from "node:path";
|
|
3
|
+
import { getOpenPackageDefaultInstallTier, resolveOpenPackageTierSkills, } from "../packaging/openpackage-tiers.js";
|
|
3
4
|
import { AGENTS_MANAGED_CLOSE } from "../platform/constants.js";
|
|
4
|
-
import { resolveAgentsMdBudget } from "../policy/agents-md-budget.js";
|
|
5
|
+
import { resolveAgentsMdBudget, } from "../policy/agents-md-budget.js";
|
|
6
|
+
import { measureSkillFrontmatter } from "./skill-frontmatter.js";
|
|
7
|
+
/**
|
|
8
|
+
* Layered absolute north-star for the always-on managed surface (#2372 / #2450 / #2452).
|
|
9
|
+
*
|
|
10
|
+
* `ABSOLUTE_MANAGED_MAX_BYTES` is the relocation north-star (<=8192 B / ~2k tok).
|
|
11
|
+
* When `plan.policy.agentsMdBudget.absoluteMaxBytes` is set, growth past that seeded
|
|
12
|
+
* ratchet fails closed; distance-to-north-star is always reported. Optional release-gate
|
|
13
|
+
* north-star enforcement: DEFT_AGENTS_MD_BUDGET_ENFORCE_NORTH_STAR=1 (waiver:
|
|
14
|
+
* DEFT_ALLOW_ABSOLUTE_BUDGET_WAIVER=1).
|
|
15
|
+
*
|
|
16
|
+
* DD-3 (harness-injected skill frontmatter) is measured and itemized (#2463).
|
|
17
|
+
* Managed `absoluteMaxBytes` remains the fail-closed ratchet for the rendered
|
|
18
|
+
* managed section; skill-frontmatter caps are advisory unless
|
|
19
|
+
* `skillFrontmatterMaxBytes` is set (or enforced via env).
|
|
20
|
+
*/
|
|
21
|
+
export const ABSOLUTE_MANAGED_MAX_BYTES = 8192;
|
|
22
|
+
export const ABSOLUTE_MANAGED_MAX_TOKENS = 2000;
|
|
23
|
+
/** Bootstrap host hooks are 0 B until #2438 ships. */
|
|
24
|
+
export const BOOTSTRAP_HOOK_BYTES = 0;
|
|
25
|
+
/** Rough UTF-8 bytes-per-token estimate for advisory reporting (~8192 B ≈ ~2048 tok). */
|
|
26
|
+
export const ABSOLUTE_BYTES_PER_TOKEN_ESTIMATE = 4;
|
|
5
27
|
const OPEN_MARKER_PREFIX = "<!-- deft:managed-section";
|
|
6
28
|
/**
|
|
7
29
|
* Split AGENTS.md into managed / unmanaged line counts.
|
|
@@ -42,6 +64,257 @@ export function countRegions(text) {
|
|
|
42
64
|
const managed = closeLine - openLine + 1;
|
|
43
65
|
return { counts: { total, managed, unmanaged: total - managed } };
|
|
44
66
|
}
|
|
67
|
+
/**
|
|
68
|
+
* Extract the managed-section span (open marker through close marker, inclusive).
|
|
69
|
+
*
|
|
70
|
+
* Returns an empty section when no markers are present — consistent with
|
|
71
|
+
* `countRegions` treating markerless files as entirely unmanaged.
|
|
72
|
+
*/
|
|
73
|
+
export function extractManagedSection(text) {
|
|
74
|
+
const normalized = text.replace(/\r\n/g, "\n");
|
|
75
|
+
const lines = normalized.split("\n");
|
|
76
|
+
if (lines.length > 0 && lines[lines.length - 1] === "") {
|
|
77
|
+
lines.pop();
|
|
78
|
+
}
|
|
79
|
+
const openLine = lines.findIndex((l) => l.startsWith(OPEN_MARKER_PREFIX));
|
|
80
|
+
const closeLine = lines.findIndex((l) => l.trim().startsWith(AGENTS_MANAGED_CLOSE));
|
|
81
|
+
const openCount = lines.filter((l) => l.startsWith(OPEN_MARKER_PREFIX)).length;
|
|
82
|
+
const closeCount = lines.filter((l) => l.trim().startsWith(AGENTS_MANAGED_CLOSE)).length;
|
|
83
|
+
if (openLine === -1 && closeLine === -1) {
|
|
84
|
+
return { section: "" };
|
|
85
|
+
}
|
|
86
|
+
if (openLine === -1 ||
|
|
87
|
+
closeLine === -1 ||
|
|
88
|
+
closeLine < openLine ||
|
|
89
|
+
openCount > 1 ||
|
|
90
|
+
closeCount > 1) {
|
|
91
|
+
return {
|
|
92
|
+
error: "AGENTS.md managed-section markers are malformed " +
|
|
93
|
+
`(open@${openLine === -1 ? "none" : openLine + 1}×${openCount}, ` +
|
|
94
|
+
`close@${closeLine === -1 ? "none" : closeLine + 1}×${closeCount}); ` +
|
|
95
|
+
"expected a single <!-- deft:managed-section ... --> ... " +
|
|
96
|
+
"<!-- /deft:managed-section --> pair.",
|
|
97
|
+
};
|
|
98
|
+
}
|
|
99
|
+
return { section: lines.slice(openLine, closeLine + 1).join("\n") };
|
|
100
|
+
}
|
|
101
|
+
/** Measure UTF-8 byte length and a rough token estimate for the managed section. */
|
|
102
|
+
export function measureManagedSection(text) {
|
|
103
|
+
const extracted = extractManagedSection(text);
|
|
104
|
+
if ("error" in extracted) {
|
|
105
|
+
return extracted;
|
|
106
|
+
}
|
|
107
|
+
const bytes = Buffer.byteLength(extracted.section, "utf8");
|
|
108
|
+
return {
|
|
109
|
+
bytes,
|
|
110
|
+
estimatedTokens: Math.ceil(bytes / ABSOLUTE_BYTES_PER_TOKEN_ESTIMATE),
|
|
111
|
+
};
|
|
112
|
+
}
|
|
113
|
+
function resolveHarnessProfile(budget, projectRoot) {
|
|
114
|
+
const env = process.env.DEFT_AGENTS_MD_BUDGET_HARNESS_PROFILE?.trim();
|
|
115
|
+
if (env === "cursor" || env === "none") {
|
|
116
|
+
return env;
|
|
117
|
+
}
|
|
118
|
+
if (budget?.harnessProfile !== undefined) {
|
|
119
|
+
return budget.harnessProfile;
|
|
120
|
+
}
|
|
121
|
+
const skillsRoot = join(projectRoot, "content", "skills");
|
|
122
|
+
if (existsSync(skillsRoot)) {
|
|
123
|
+
return "cursor";
|
|
124
|
+
}
|
|
125
|
+
return "none";
|
|
126
|
+
}
|
|
127
|
+
function resolveBootstrapSkillTier(budget, projectRoot) {
|
|
128
|
+
const env = process.env.DEFT_AGENTS_MD_BUDGET_SKILL_TIER?.trim();
|
|
129
|
+
if (env === "daily-core" || env === "all" || env === "none") {
|
|
130
|
+
return env;
|
|
131
|
+
}
|
|
132
|
+
if (budget?.skillFrontmatterTier !== undefined) {
|
|
133
|
+
return budget.skillFrontmatterTier;
|
|
134
|
+
}
|
|
135
|
+
try {
|
|
136
|
+
if (getOpenPackageDefaultInstallTier(projectRoot) === "daily-core") {
|
|
137
|
+
return "daily-core";
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
catch {
|
|
141
|
+
// No OpenPackage manifest at this project root — fall through.
|
|
142
|
+
}
|
|
143
|
+
return "all";
|
|
144
|
+
}
|
|
145
|
+
/** Measure managed + DD-3 skill frontmatter + bootstrap hooks. */
|
|
146
|
+
export function measureBootstrapSurface(projectRoot, managedText, budget) {
|
|
147
|
+
const managedResult = measureManagedSection(managedText);
|
|
148
|
+
if ("error" in managedResult) {
|
|
149
|
+
return managedResult;
|
|
150
|
+
}
|
|
151
|
+
const harnessProfile = resolveHarnessProfile(budget, projectRoot);
|
|
152
|
+
const tier = resolveBootstrapSkillTier(budget, projectRoot);
|
|
153
|
+
let dailyCoreSkills;
|
|
154
|
+
try {
|
|
155
|
+
dailyCoreSkills = resolveOpenPackageTierSkills(projectRoot, "daily-core");
|
|
156
|
+
}
|
|
157
|
+
catch {
|
|
158
|
+
// Maintainer trees without packaging/openpackage fall back to hardcoded daily-core.
|
|
159
|
+
}
|
|
160
|
+
const skillFrontmatter = measureSkillFrontmatter(projectRoot, {
|
|
161
|
+
harnessProfile,
|
|
162
|
+
tier,
|
|
163
|
+
bytesPerToken: ABSOLUTE_BYTES_PER_TOKEN_ESTIMATE,
|
|
164
|
+
dailyCoreSkills,
|
|
165
|
+
});
|
|
166
|
+
const totalBytes = managedResult.bytes + skillFrontmatter.bytes + BOOTSTRAP_HOOK_BYTES;
|
|
167
|
+
return {
|
|
168
|
+
managed: managedResult,
|
|
169
|
+
skillFrontmatter,
|
|
170
|
+
bootstrapHookBytes: BOOTSTRAP_HOOK_BYTES,
|
|
171
|
+
totalBytes,
|
|
172
|
+
totalEstimatedTokens: Math.ceil(totalBytes / ABSOLUTE_BYTES_PER_TOKEN_ESTIMATE),
|
|
173
|
+
};
|
|
174
|
+
}
|
|
175
|
+
function formatNorthStarOverageBytes(overBytes, overTokens) {
|
|
176
|
+
const parts = [];
|
|
177
|
+
if (overBytes > 0) {
|
|
178
|
+
parts.push(`${overBytes} bytes over`);
|
|
179
|
+
}
|
|
180
|
+
if (overTokens > 0) {
|
|
181
|
+
parts.push(`~${overTokens} tok over`);
|
|
182
|
+
}
|
|
183
|
+
return parts.join(", ");
|
|
184
|
+
}
|
|
185
|
+
function formatNorthStarOverage(measure) {
|
|
186
|
+
return formatNorthStarOverageBytes(measure.bytes - ABSOLUTE_MANAGED_MAX_BYTES, measure.estimatedTokens - ABSOLUTE_MANAGED_MAX_TOKENS);
|
|
187
|
+
}
|
|
188
|
+
function formatCombinedNorthStarOverage(bootstrap) {
|
|
189
|
+
return formatNorthStarOverageBytes(bootstrap.totalBytes - ABSOLUTE_MANAGED_MAX_BYTES, bootstrap.totalEstimatedTokens - ABSOLUTE_MANAGED_MAX_TOKENS);
|
|
190
|
+
}
|
|
191
|
+
function formatNorthStarDistance(measure) {
|
|
192
|
+
const overBytes = measure.bytes - ABSOLUTE_MANAGED_MAX_BYTES;
|
|
193
|
+
const overTokens = measure.estimatedTokens - ABSOLUTE_MANAGED_MAX_TOKENS;
|
|
194
|
+
if (overBytes <= 0 && overTokens <= 0) {
|
|
195
|
+
return (`north-star: managed ${measure.bytes} bytes (~${measure.estimatedTokens} tok) within ` +
|
|
196
|
+
`≤${ABSOLUTE_MANAGED_MAX_BYTES} B / ~${ABSOLUTE_MANAGED_MAX_TOKENS} tok target.`);
|
|
197
|
+
}
|
|
198
|
+
return (`north-star: managed ≤${ABSOLUTE_MANAGED_MAX_BYTES} B / ~${ABSOLUTE_MANAGED_MAX_TOKENS} tok ` +
|
|
199
|
+
`(current ${measure.bytes} bytes / ~${measure.estimatedTokens} tok — ` +
|
|
200
|
+
`${formatNorthStarOverage(measure)}).`);
|
|
201
|
+
}
|
|
202
|
+
function formatCombinedNorthStarDistance(bootstrap) {
|
|
203
|
+
const overBytes = bootstrap.totalBytes - ABSOLUTE_MANAGED_MAX_BYTES;
|
|
204
|
+
const overTokens = bootstrap.totalEstimatedTokens - ABSOLUTE_MANAGED_MAX_TOKENS;
|
|
205
|
+
if (overBytes <= 0 && overTokens <= 0) {
|
|
206
|
+
return (`north-star: combined always-on ${bootstrap.totalBytes} bytes ` +
|
|
207
|
+
`(~${bootstrap.totalEstimatedTokens} tok) within ` +
|
|
208
|
+
`≤${ABSOLUTE_MANAGED_MAX_BYTES} B / ~${ABSOLUTE_MANAGED_MAX_TOKENS} tok target.`);
|
|
209
|
+
}
|
|
210
|
+
return (`north-star: combined always-on ≤${ABSOLUTE_MANAGED_MAX_BYTES} B / ~${ABSOLUTE_MANAGED_MAX_TOKENS} tok ` +
|
|
211
|
+
`(current ${bootstrap.totalBytes} bytes / ~${bootstrap.totalEstimatedTokens} tok — ` +
|
|
212
|
+
`${formatCombinedNorthStarOverage(bootstrap)}).`);
|
|
213
|
+
}
|
|
214
|
+
function formatBootstrapItemization(bootstrap) {
|
|
215
|
+
const { managed, skillFrontmatter, bootstrapHookBytes } = bootstrap;
|
|
216
|
+
const tierLabel = skillFrontmatter.harnessProfile === "none"
|
|
217
|
+
? "none"
|
|
218
|
+
: `${skillFrontmatter.harnessProfile}/${skillFrontmatter.tier}`;
|
|
219
|
+
const skillPart = skillFrontmatter.bytes > 0
|
|
220
|
+
? `skill-frontmatter ${skillFrontmatter.bytes} B (${tierLabel}, ${skillFrontmatter.skillCount} skills)`
|
|
221
|
+
: `skill-frontmatter 0 B (${tierLabel})`;
|
|
222
|
+
return (`bootstrap: managed ${managed.bytes} B, ${skillPart}, hooks ${bootstrapHookBytes} B; ` +
|
|
223
|
+
`combined ${bootstrap.totalBytes} B (~${bootstrap.totalEstimatedTokens} tok)`);
|
|
224
|
+
}
|
|
225
|
+
function formatAbsoluteAdvisory(bootstrap) {
|
|
226
|
+
const measure = bootstrap.managed;
|
|
227
|
+
return (`⚠ verify:agents-md-budget: always-on bootstrap advisory — ` +
|
|
228
|
+
`${formatBootstrapItemization(bootstrap)}.\n` +
|
|
229
|
+
` Managed section alone: ${measure.bytes} bytes (~${measure.estimatedTokens} tok) exceeds the north-star ` +
|
|
230
|
+
`of ${ABSOLUTE_MANAGED_MAX_BYTES} bytes / ~${ABSOLUTE_MANAGED_MAX_TOKENS} tok ` +
|
|
231
|
+
`(OVER: ${formatNorthStarOverage(measure)}).\n` +
|
|
232
|
+
` ${formatCombinedNorthStarDistance(bootstrap)}\n` +
|
|
233
|
+
" Advisory only — set plan.policy.agentsMdBudget.absoluteMaxBytes to enable " +
|
|
234
|
+
"fail-closed managed growth ratchet (#2452).\n" +
|
|
235
|
+
" Optional DD-3 ratchet: plan.policy.agentsMdBudget.skillFrontmatterMaxBytes (#2463).\n" +
|
|
236
|
+
" Tier daily-core skills via OpenPackage or plan.policy.agentsMdBudget.skillFrontmatterTier.\n" +
|
|
237
|
+
" Remediation: UPGRADING.md § Always-on bootstrap budget (DD-3).\n" +
|
|
238
|
+
" The relative line ratchet (#645) remains fail-closed.");
|
|
239
|
+
}
|
|
240
|
+
function formatAbsoluteRefusal(bootstrap, absoluteMaxBytes, projectRoot) {
|
|
241
|
+
const measure = bootstrap.managed;
|
|
242
|
+
const overBytes = measure.bytes - absoluteMaxBytes;
|
|
243
|
+
return (`❌ verify:agents-md-budget: managed section grew past its absolute byte ratchet ` +
|
|
244
|
+
`(project_root=${projectRoot}).\n` +
|
|
245
|
+
` managed section: ${measure.bytes}/${absoluteMaxBytes} bytes (OVER by ${overBytes})\n` +
|
|
246
|
+
` ${formatBootstrapItemization(bootstrap)}\n` +
|
|
247
|
+
` ${formatNorthStarDistance(measure)}\n` +
|
|
248
|
+
` ${formatCombinedNorthStarDistance(bootstrap)}\n` +
|
|
249
|
+
" AGENTS.md is a map, not a manual (#1882): push detail into a\n" +
|
|
250
|
+
" reference doc (main.md / a pack / docs/) and leave a pointer,\n" +
|
|
251
|
+
" rather than expanding AGENTS.md. See REFERENCES.md.\n" +
|
|
252
|
+
" If the growth is deliberate, raise absoluteMaxBytes in\n" +
|
|
253
|
+
" plan.policy.agentsMdBudget in PROJECT-DEFINITION (a reviewed diff). (#2452)");
|
|
254
|
+
}
|
|
255
|
+
function formatSkillFrontmatterRefusal(bootstrap, skillFrontmatterMaxBytes, projectRoot) {
|
|
256
|
+
const { skillFrontmatter } = bootstrap;
|
|
257
|
+
const overBytes = skillFrontmatter.bytes - skillFrontmatterMaxBytes;
|
|
258
|
+
return (`❌ verify:agents-md-budget: skill frontmatter grew past its DD-3 byte ratchet ` +
|
|
259
|
+
`(project_root=${projectRoot}).\n` +
|
|
260
|
+
` skill-frontmatter: ${skillFrontmatter.bytes}/${skillFrontmatterMaxBytes} bytes ` +
|
|
261
|
+
`(OVER by ${overBytes}; tier ${skillFrontmatter.tier}, ${skillFrontmatter.skillCount} skills)\n` +
|
|
262
|
+
` ${formatBootstrapItemization(bootstrap)}\n` +
|
|
263
|
+
` ${formatCombinedNorthStarDistance(bootstrap)}\n` +
|
|
264
|
+
" Tier deferred skills via OpenPackage (daily-core vs advanced) or shorten\n" +
|
|
265
|
+
" SKILL.md descriptions. See UPGRADING.md § Always-on bootstrap budget (DD-3).\n" +
|
|
266
|
+
" If the growth is deliberate, raise skillFrontmatterMaxBytes in\n" +
|
|
267
|
+
" plan.policy.agentsMdBudget in PROJECT-DEFINITION (a reviewed diff). (#2463)");
|
|
268
|
+
}
|
|
269
|
+
function formatNorthStarRefusal(bootstrap, projectRoot) {
|
|
270
|
+
const measure = bootstrap.managed;
|
|
271
|
+
const overBytes = bootstrap.totalBytes - ABSOLUTE_MANAGED_MAX_BYTES;
|
|
272
|
+
return (`❌ verify:agents-md-budget: combined always-on surface exceeds the north-star ceiling ` +
|
|
273
|
+
`(project_root=${projectRoot}, release-gate mode).\n` +
|
|
274
|
+
` ${formatBootstrapItemization(bootstrap)}\n` +
|
|
275
|
+
` managed section: ${measure.bytes}/${ABSOLUTE_MANAGED_MAX_BYTES} bytes\n` +
|
|
276
|
+
` combined OVER by ${overBytes} bytes vs north-star\n` +
|
|
277
|
+
" Thin the managed section and/or tier DD-3 skills toward the <=8192 B target,\n" +
|
|
278
|
+
" or set DEFT_ALLOW_ABSOLUTE_BUDGET_WAIVER=1 for a time-boxed operator waiver (#2452).");
|
|
279
|
+
}
|
|
280
|
+
function enforceNorthStarEnabled() {
|
|
281
|
+
return process.env.DEFT_AGENTS_MD_BUDGET_ENFORCE_NORTH_STAR === "1";
|
|
282
|
+
}
|
|
283
|
+
function northStarWaiverActive() {
|
|
284
|
+
return process.env.DEFT_ALLOW_ABSOLUTE_BUDGET_WAIVER === "1";
|
|
285
|
+
}
|
|
286
|
+
function attachNorthStarNote(result, bootstrap, options) {
|
|
287
|
+
const measure = bootstrap.managed;
|
|
288
|
+
const overManagedBytes = measure.bytes > ABSOLUTE_MANAGED_MAX_BYTES;
|
|
289
|
+
const overManagedTokens = measure.estimatedTokens > ABSOLUTE_MANAGED_MAX_TOKENS;
|
|
290
|
+
const overCombinedBytes = bootstrap.totalBytes > ABSOLUTE_MANAGED_MAX_BYTES;
|
|
291
|
+
const overCombinedTokens = bootstrap.totalEstimatedTokens > ABSOLUTE_MANAGED_MAX_TOKENS;
|
|
292
|
+
if (options.advisoryOnly) {
|
|
293
|
+
if (!overManagedBytes && !overManagedTokens && !overCombinedBytes && !overCombinedTokens) {
|
|
294
|
+
return result;
|
|
295
|
+
}
|
|
296
|
+
return {
|
|
297
|
+
...result,
|
|
298
|
+
northStarMessage: formatAbsoluteAdvisory(bootstrap),
|
|
299
|
+
northStarStream: "stderr",
|
|
300
|
+
advisoryMessage: formatAbsoluteAdvisory(bootstrap),
|
|
301
|
+
advisoryStream: "stderr",
|
|
302
|
+
};
|
|
303
|
+
}
|
|
304
|
+
const distance = `${formatNorthStarDistance(measure)}\n ${formatCombinedNorthStarDistance(bootstrap)}`;
|
|
305
|
+
return {
|
|
306
|
+
...result,
|
|
307
|
+
northStarMessage: distance,
|
|
308
|
+
northStarStream: "stderr",
|
|
309
|
+
advisoryMessage: distance,
|
|
310
|
+
advisoryStream: "stderr",
|
|
311
|
+
};
|
|
312
|
+
}
|
|
313
|
+
function formatAbsoluteSummary(bootstrap, absoluteMaxBytes) {
|
|
314
|
+
const measure = bootstrap.managed;
|
|
315
|
+
return (`absolute managed ${measure.bytes}/${absoluteMaxBytes} bytes (~${measure.estimatedTokens} tok); ` +
|
|
316
|
+
`${formatBootstrapItemization(bootstrap)}`);
|
|
317
|
+
}
|
|
45
318
|
function formatRefusal(counts, managedMax, unmanagedMax, projectRoot) {
|
|
46
319
|
const over = [];
|
|
47
320
|
if (counts.managed > managedMax) {
|
|
@@ -106,19 +379,35 @@ export function evaluate(projectRoot, options = {}) {
|
|
|
106
379
|
};
|
|
107
380
|
}
|
|
108
381
|
const counts = regionResult.counts;
|
|
382
|
+
const bootstrapResult = measureBootstrapSurface(root, text, budgetResult.budget);
|
|
383
|
+
if ("error" in bootstrapResult) {
|
|
384
|
+
return {
|
|
385
|
+
code: 2,
|
|
386
|
+
message: `❌ verify:agents-md-budget: ${bootstrapResult.error}`,
|
|
387
|
+
stream: "stderr",
|
|
388
|
+
};
|
|
389
|
+
}
|
|
390
|
+
const bootstrap = bootstrapResult;
|
|
391
|
+
const measure = bootstrap.managed;
|
|
392
|
+
const absoluteMaxBytes = budgetResult.budget?.absoluteMaxBytes;
|
|
393
|
+
const advisoryOnly = absoluteMaxBytes === undefined;
|
|
394
|
+
const skillFrontmatterMaxBytes = budgetResult.budget?.skillFrontmatterMaxBytes;
|
|
109
395
|
if (budgetResult.source === "unset") {
|
|
110
396
|
if (quiet) {
|
|
111
|
-
return { code: 0, message: "", stream: "none" }
|
|
397
|
+
return attachNorthStarNote({ code: 0, message: "", stream: "none" }, bootstrap, {
|
|
398
|
+
advisoryOnly,
|
|
399
|
+
});
|
|
112
400
|
}
|
|
113
|
-
return {
|
|
401
|
+
return attachNorthStarNote({
|
|
114
402
|
code: 0,
|
|
115
403
|
message: "⚠ verify:agents-md-budget: no plan.policy.agentsMdBudget configured " +
|
|
116
404
|
`(managed=${counts.managed}, unmanaged=${counts.unmanaged} lines).\n` +
|
|
405
|
+
` ${formatBootstrapItemization(bootstrap)}.\n` +
|
|
117
406
|
" Seed a ratchet at current size to freeze growth (#645): set\n" +
|
|
118
407
|
" plan.policy.agentsMdBudget.{managedMaxLines,unmanagedMaxLines} in " +
|
|
119
408
|
"PROJECT-DEFINITION.",
|
|
120
409
|
stream: "stderr",
|
|
121
|
-
};
|
|
410
|
+
}, bootstrap, { advisoryOnly });
|
|
122
411
|
}
|
|
123
412
|
/* v8 ignore start -- defensive: source "typed" always carries a non-null budget. */
|
|
124
413
|
if (budgetResult.budget === null) {
|
|
@@ -132,21 +421,54 @@ export function evaluate(projectRoot, options = {}) {
|
|
|
132
421
|
const budget = budgetResult.budget;
|
|
133
422
|
const overManaged = counts.managed > budget.managedMaxLines;
|
|
134
423
|
const overUnmanaged = counts.unmanaged > budget.unmanagedMaxLines;
|
|
135
|
-
if (
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
message: `✓ verify:agents-md-budget: managed ${counts.managed}/${budget.managedMaxLines}, ` +
|
|
142
|
-
`unmanaged ${counts.unmanaged}/${budget.unmanagedMaxLines} lines (within ratchet).`,
|
|
143
|
-
stream: "stdout",
|
|
144
|
-
};
|
|
424
|
+
if (overManaged || overUnmanaged) {
|
|
425
|
+
return attachNorthStarNote({
|
|
426
|
+
code: 1,
|
|
427
|
+
message: formatRefusal(counts, budget.managedMaxLines, budget.unmanagedMaxLines, root),
|
|
428
|
+
stream: "stderr",
|
|
429
|
+
}, bootstrap, { advisoryOnly });
|
|
145
430
|
}
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
431
|
+
if (absoluteMaxBytes !== undefined && measure.bytes > absoluteMaxBytes) {
|
|
432
|
+
return attachNorthStarNote({
|
|
433
|
+
code: 1,
|
|
434
|
+
message: formatAbsoluteRefusal(bootstrap, absoluteMaxBytes, root),
|
|
435
|
+
stream: "stderr",
|
|
436
|
+
}, bootstrap, { advisoryOnly: false });
|
|
437
|
+
}
|
|
438
|
+
if (skillFrontmatterMaxBytes !== undefined &&
|
|
439
|
+
bootstrap.skillFrontmatter.bytes > skillFrontmatterMaxBytes) {
|
|
440
|
+
return attachNorthStarNote({
|
|
441
|
+
code: 1,
|
|
442
|
+
message: formatSkillFrontmatterRefusal(bootstrap, skillFrontmatterMaxBytes, root),
|
|
443
|
+
stream: "stderr",
|
|
444
|
+
}, bootstrap, { advisoryOnly: false });
|
|
445
|
+
}
|
|
446
|
+
const overNorthStarManaged = measure.bytes > ABSOLUTE_MANAGED_MAX_BYTES ||
|
|
447
|
+
measure.estimatedTokens > ABSOLUTE_MANAGED_MAX_TOKENS;
|
|
448
|
+
const overNorthStarCombined = bootstrap.totalBytes > ABSOLUTE_MANAGED_MAX_BYTES ||
|
|
449
|
+
bootstrap.totalEstimatedTokens > ABSOLUTE_MANAGED_MAX_TOKENS;
|
|
450
|
+
if (enforceNorthStarEnabled() &&
|
|
451
|
+
(overNorthStarManaged || overNorthStarCombined) &&
|
|
452
|
+
!northStarWaiverActive()) {
|
|
453
|
+
return attachNorthStarNote({
|
|
454
|
+
code: 1,
|
|
455
|
+
message: formatNorthStarRefusal(bootstrap, root),
|
|
456
|
+
stream: "stderr",
|
|
457
|
+
}, bootstrap, { advisoryOnly: false });
|
|
458
|
+
}
|
|
459
|
+
const absoluteSummary = absoluteMaxBytes !== undefined ? `; ${formatAbsoluteSummary(bootstrap, absoluteMaxBytes)}` : "";
|
|
460
|
+
const bootstrapSummary = absoluteMaxBytes === undefined ? `; ${formatBootstrapItemization(bootstrap)}` : "";
|
|
461
|
+
if (quiet) {
|
|
462
|
+
return attachNorthStarNote({ code: 0, message: "", stream: "none" }, bootstrap, {
|
|
463
|
+
advisoryOnly,
|
|
464
|
+
});
|
|
465
|
+
}
|
|
466
|
+
return attachNorthStarNote({
|
|
467
|
+
code: 0,
|
|
468
|
+
message: `✓ verify:agents-md-budget: managed ${counts.managed}/${budget.managedMaxLines}, ` +
|
|
469
|
+
`unmanaged ${counts.unmanaged}/${budget.unmanagedMaxLines} lines (within ratchet)` +
|
|
470
|
+
`${absoluteSummary}${bootstrapSummary}.`,
|
|
471
|
+
stream: "stdout",
|
|
472
|
+
}, bootstrap, { advisoryOnly });
|
|
151
473
|
}
|
|
152
474
|
//# sourceMappingURL=evaluate.js.map
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
/** Daily-core tier from spike #2370 / OpenPackage manifest (#2462). */
|
|
2
|
+
export declare const DAILY_CORE_SKILL_NAMES: readonly ["deft-directive-setup", "deft-directive-sync", "deft-directive-build", "deft-directive-pre-pr", "deft-directive-review-cycle", "deft-directive-triage"];
|
|
3
|
+
export type SkillFrontmatterTier = "daily-core" | "all" | "none";
|
|
4
|
+
export type HarnessProfile = "cursor" | "none";
|
|
5
|
+
/** Extract the YAML `description` field from a SKILL.md frontmatter block. */
|
|
6
|
+
export declare function extractSkillDescription(text: string): string;
|
|
7
|
+
/**
|
|
8
|
+
* Cursor `<agent_skill>` injection shape (DD-3 minimum).
|
|
9
|
+
* Uses repo-relative POSIX paths for stable cross-platform byte counts.
|
|
10
|
+
*/
|
|
11
|
+
export declare function formatCursorAgentSkill(relPath: string, description: string): string;
|
|
12
|
+
export interface SkillFrontmatterEntry {
|
|
13
|
+
readonly skillName: string;
|
|
14
|
+
readonly relPath: string;
|
|
15
|
+
readonly bytes: number;
|
|
16
|
+
}
|
|
17
|
+
export interface SkillFrontmatterMeasure {
|
|
18
|
+
readonly bytes: number;
|
|
19
|
+
readonly estimatedTokens: number;
|
|
20
|
+
readonly skillCount: number;
|
|
21
|
+
readonly tier: SkillFrontmatterTier;
|
|
22
|
+
readonly harnessProfile: HarnessProfile;
|
|
23
|
+
readonly entries: readonly SkillFrontmatterEntry[];
|
|
24
|
+
}
|
|
25
|
+
export interface MeasureSkillFrontmatterOptions {
|
|
26
|
+
readonly skillsRoot?: string;
|
|
27
|
+
readonly tier?: SkillFrontmatterTier;
|
|
28
|
+
readonly harnessProfile?: HarnessProfile;
|
|
29
|
+
readonly bytesPerToken?: number;
|
|
30
|
+
/** Override daily-core skill names (from OpenPackage resolveTierSkills). */
|
|
31
|
+
readonly dailyCoreSkills?: readonly string[];
|
|
32
|
+
}
|
|
33
|
+
/** Measure harness-injected skill frontmatter bytes for the configured profile/tier. */
|
|
34
|
+
export declare function measureSkillFrontmatter(projectRoot: string, options?: MeasureSkillFrontmatterOptions): SkillFrontmatterMeasure;
|
|
35
|
+
//# sourceMappingURL=skill-frontmatter.d.ts.map
|
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
import { existsSync, readdirSync, readFileSync } from "node:fs";
|
|
2
|
+
import { join, posix } from "node:path";
|
|
3
|
+
/** Daily-core tier from spike #2370 / OpenPackage manifest (#2462). */
|
|
4
|
+
export const DAILY_CORE_SKILL_NAMES = [
|
|
5
|
+
"deft-directive-setup",
|
|
6
|
+
"deft-directive-sync",
|
|
7
|
+
"deft-directive-build",
|
|
8
|
+
"deft-directive-pre-pr",
|
|
9
|
+
"deft-directive-review-cycle",
|
|
10
|
+
"deft-directive-triage",
|
|
11
|
+
];
|
|
12
|
+
const DAILY_CORE_SET = new Set(DAILY_CORE_SKILL_NAMES);
|
|
13
|
+
/** Extract the YAML `description` field from a SKILL.md frontmatter block. */
|
|
14
|
+
export function extractSkillDescription(text) {
|
|
15
|
+
if (!text.startsWith("---")) {
|
|
16
|
+
return "";
|
|
17
|
+
}
|
|
18
|
+
const closing = text.indexOf("\n---", 3);
|
|
19
|
+
if (closing === -1) {
|
|
20
|
+
return "";
|
|
21
|
+
}
|
|
22
|
+
const frontmatter = text.slice(3, closing).replace(/^\r?\n/, "");
|
|
23
|
+
const lines = frontmatter.split(/\r?\n/);
|
|
24
|
+
for (let i = 0; i < lines.length; i += 1) {
|
|
25
|
+
const line = lines[i] ?? "";
|
|
26
|
+
if (/^description:\s*>(-)?\s*$/.test(line)) {
|
|
27
|
+
const descLines = [];
|
|
28
|
+
for (let j = i + 1; j < lines.length; j += 1) {
|
|
29
|
+
const next = lines[j] ?? "";
|
|
30
|
+
if (!/^[ \t]/.test(next)) {
|
|
31
|
+
break;
|
|
32
|
+
}
|
|
33
|
+
descLines.push(next.replace(/^[ \t]+/, ""));
|
|
34
|
+
}
|
|
35
|
+
return descLines.join("\n").trim();
|
|
36
|
+
}
|
|
37
|
+
const single = line.match(/^description:\s*(.+)$/);
|
|
38
|
+
if (single !== null && single[1] !== undefined) {
|
|
39
|
+
return single[1].trim();
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
return "";
|
|
43
|
+
}
|
|
44
|
+
/**
|
|
45
|
+
* Cursor `<agent_skill>` injection shape (DD-3 minimum).
|
|
46
|
+
* Uses repo-relative POSIX paths for stable cross-platform byte counts.
|
|
47
|
+
*/
|
|
48
|
+
export function formatCursorAgentSkill(relPath, description) {
|
|
49
|
+
const normalized = relPath.replace(/\\/g, "/");
|
|
50
|
+
return `<agent_skill fullPath="${normalized}">${description}</agent_skill>`;
|
|
51
|
+
}
|
|
52
|
+
function defaultSkillsRoot(projectRoot) {
|
|
53
|
+
return join(projectRoot, "content", "skills");
|
|
54
|
+
}
|
|
55
|
+
function listSkillDirs(skillsRoot) {
|
|
56
|
+
if (!existsSync(skillsRoot)) {
|
|
57
|
+
return [];
|
|
58
|
+
}
|
|
59
|
+
return readdirSync(skillsRoot, { withFileTypes: true })
|
|
60
|
+
.filter((entry) => entry.isDirectory())
|
|
61
|
+
.map((entry) => entry.name)
|
|
62
|
+
.sort();
|
|
63
|
+
}
|
|
64
|
+
function skillInSelectedTier(skillName, tier, dailyCore) {
|
|
65
|
+
if (tier === "none") {
|
|
66
|
+
return false;
|
|
67
|
+
}
|
|
68
|
+
if (tier === "all") {
|
|
69
|
+
return true;
|
|
70
|
+
}
|
|
71
|
+
return dailyCore.has(skillName);
|
|
72
|
+
}
|
|
73
|
+
/** Measure harness-injected skill frontmatter bytes for the configured profile/tier. */
|
|
74
|
+
export function measureSkillFrontmatter(projectRoot, options = {}) {
|
|
75
|
+
const harnessProfile = options.harnessProfile ?? "cursor";
|
|
76
|
+
const tier = options.tier ?? "all";
|
|
77
|
+
const bytesPerToken = options.bytesPerToken ?? 4;
|
|
78
|
+
const skillsRoot = options.skillsRoot ?? defaultSkillsRoot(projectRoot);
|
|
79
|
+
const dailyCore = options.dailyCoreSkills !== undefined ? new Set(options.dailyCoreSkills) : DAILY_CORE_SET;
|
|
80
|
+
if (harnessProfile === "none" || tier === "none") {
|
|
81
|
+
return {
|
|
82
|
+
bytes: 0,
|
|
83
|
+
estimatedTokens: 0,
|
|
84
|
+
skillCount: 0,
|
|
85
|
+
tier,
|
|
86
|
+
harnessProfile,
|
|
87
|
+
entries: [],
|
|
88
|
+
};
|
|
89
|
+
}
|
|
90
|
+
const entries = [];
|
|
91
|
+
for (const skillName of listSkillDirs(skillsRoot)) {
|
|
92
|
+
if (!skillInSelectedTier(skillName, tier, dailyCore)) {
|
|
93
|
+
continue;
|
|
94
|
+
}
|
|
95
|
+
const skillPath = join(skillsRoot, skillName, "SKILL.md");
|
|
96
|
+
if (!existsSync(skillPath)) {
|
|
97
|
+
continue;
|
|
98
|
+
}
|
|
99
|
+
const text = readFileSync(skillPath, "utf8");
|
|
100
|
+
const description = extractSkillDescription(text);
|
|
101
|
+
const relPath = posix.join("content", "skills", skillName, "SKILL.md");
|
|
102
|
+
const block = formatCursorAgentSkill(relPath, description);
|
|
103
|
+
const bytes = Buffer.byteLength(block, "utf8");
|
|
104
|
+
entries.push({ skillName, relPath, bytes });
|
|
105
|
+
}
|
|
106
|
+
const bytes = entries.reduce((sum, entry) => sum + entry.bytes, 0);
|
|
107
|
+
return {
|
|
108
|
+
bytes,
|
|
109
|
+
estimatedTokens: Math.ceil(bytes / bytesPerToken),
|
|
110
|
+
skillCount: entries.length,
|
|
111
|
+
tier,
|
|
112
|
+
harnessProfile,
|
|
113
|
+
entries,
|
|
114
|
+
};
|
|
115
|
+
}
|
|
116
|
+
//# sourceMappingURL=skill-frontmatter.js.map
|
|
@@ -1,7 +1,9 @@
|
|
|
1
|
+
import { ProjectionContainmentError } from "../fs/projection-containment.js";
|
|
1
2
|
import { type CacheCaps, type EntryUsage } from "./quota.js";
|
|
2
3
|
import { SCANNER_VERSION } from "./scanner.js";
|
|
3
4
|
import { type Clock } from "./time.js";
|
|
4
5
|
import type { CacheGetOptions, CachePutOptions, GetResult, PutResult } from "./types.js";
|
|
6
|
+
export { ProjectionContainmentError as CacheContainmentError };
|
|
5
7
|
/** Write a cache entry (mirrors `cache.cache_put`). */
|
|
6
8
|
export declare function cachePut(source: string, key: string, raw: Record<string, unknown>, options?: CachePutOptions): PutResult;
|
|
7
9
|
/** Read a cache entry (mirrors `cache.cache_get`). */
|