@veewo/gitnexus 1.5.6 → 1.5.8
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/benchmark/analyze-runner.d.ts +0 -2
- package/dist/benchmark/analyze-runner.js +0 -6
- package/dist/benchmark/analyze-runner.test.js +1 -10
- package/dist/benchmark/runner.d.ts +0 -2
- package/dist/benchmark/runner.js +0 -2
- package/dist/benchmark/u2-e2e/neonspark-full-e2e.js +0 -11
- package/dist/benchmark/u2-performance-sampler.js +3 -16
- package/dist/cli/ai-context.js +1 -7
- package/dist/cli/analyze-options.d.ts +19 -6
- package/dist/cli/analyze-options.js +76 -71
- package/dist/cli/analyze-options.test.js +78 -73
- package/dist/cli/analyze-runtime-summary.js +0 -1
- package/dist/cli/analyze-runtime-summary.test.js +0 -2
- package/dist/cli/analyze-summary.d.ts +0 -2
- package/dist/cli/analyze-summary.js +0 -24
- package/dist/cli/analyze-summary.test.js +1 -65
- package/dist/cli/analyze.d.ts +2 -4
- package/dist/cli/analyze.js +14 -30
- package/dist/cli/analyze.test.js +9 -15
- package/dist/cli/benchmark-agent-context.d.ts +0 -2
- package/dist/cli/benchmark-agent-context.js +0 -2
- package/dist/cli/benchmark-agent-safe-query-context.d.ts +0 -2
- package/dist/cli/benchmark-agent-safe-query-context.js +0 -2
- package/dist/cli/benchmark-unity.d.ts +0 -2
- package/dist/cli/benchmark-unity.js +0 -2
- package/dist/cli/clean.d.ts +2 -3
- package/dist/cli/clean.js +4 -25
- package/dist/cli/index.js +1 -12
- package/dist/core/ingestion/pipeline.js +1 -44
- package/dist/mcp/local/agent-safe-response.js +1 -1
- package/dist/mcp/local/local-backend.d.ts +0 -23
- package/dist/mcp/local/local-backend.js +69 -248
- package/dist/mcp/local/runtime-chain-verify.test.js +0 -49
- package/dist/mcp/local/runtime-claim-rule-registry.d.ts +0 -11
- package/dist/mcp/local/runtime-claim-rule-registry.js +0 -159
- package/dist/mcp/local/runtime-claim-rule-registry.test.js +67 -214
- package/dist/mcp/tools.js +0 -70
- package/dist/storage/repo-manager.d.ts +1 -0
- package/dist/types/pipeline.d.ts +0 -3
- package/package.json +1 -1
- package/skills/gitnexus-cli.md +62 -38
- package/vendor/node_modules/node-addon-api/node_addon_api.Makefile +6 -0
- package/vendor/node_modules/node-addon-api/node_addon_api.target.mk +122 -0
- package/vendor/node_modules/node-addon-api/node_addon_api_except.target.mk +126 -0
- package/vendor/node_modules/node-addon-api/node_addon_api_except_all.target.mk +122 -0
- package/vendor/node_modules/node-addon-api/node_addon_api_maybe.target.mk +122 -0
- package/vendor/tree-sitter-dart/build/Release/.deps/node_modules/node-addon-api/node_addon_api_except.stamp.d +1 -0
- package/vendor/tree-sitter-dart/build/node_modules/node-addon-api/node_addon_api_except.stamp +0 -0
- package/vendor/tree-sitter-proto/build/Release/.deps/node_modules/node-addon-api/node_addon_api_except.stamp.d +1 -0
- package/vendor/tree-sitter-proto/build/node_modules/node-addon-api/node_addon_api_except.stamp +0 -0
- package/dist/benchmark/u2-e2e/phase5-rule-lab-acceptance-runner.d.ts +0 -60
- package/dist/benchmark/u2-e2e/phase5-rule-lab-acceptance-runner.js +0 -395
- package/dist/benchmark/u2-e2e/phase5-rule-lab-acceptance-runner.test.d.ts +0 -1
- package/dist/benchmark/u2-e2e/phase5-rule-lab-acceptance-runner.test.js +0 -41
- package/dist/cli/rule-lab.d.ts +0 -38
- package/dist/cli/rule-lab.js +0 -148
- package/dist/cli/rule-lab.test.d.ts +0 -1
- package/dist/cli/rule-lab.test.js +0 -31
- package/dist/cli/scope-manifest-config.d.ts +0 -9
- package/dist/cli/scope-manifest-config.js +0 -37
- package/dist/cli/sync-manifest.d.ts +0 -27
- package/dist/cli/sync-manifest.js +0 -200
- package/dist/cli/sync-manifest.test.d.ts +0 -1
- package/dist/cli/sync-manifest.test.js +0 -88
- package/dist/core/ingestion/unity-runtime-binding-rules.d.ts +0 -26
- package/dist/core/ingestion/unity-runtime-binding-rules.js +0 -408
- package/dist/rule-lab/analyze.d.ts +0 -13
- package/dist/rule-lab/analyze.js +0 -125
- package/dist/rule-lab/analyze.test.d.ts +0 -1
- package/dist/rule-lab/analyze.test.js +0 -246
- package/dist/rule-lab/compile.d.ts +0 -5
- package/dist/rule-lab/compile.js +0 -51
- package/dist/rule-lab/compiled-bundles.d.ts +0 -30
- package/dist/rule-lab/compiled-bundles.js +0 -36
- package/dist/rule-lab/curate.d.ts +0 -33
- package/dist/rule-lab/curate.js +0 -155
- package/dist/rule-lab/curate.test.d.ts +0 -1
- package/dist/rule-lab/curate.test.js +0 -137
- package/dist/rule-lab/curation-input-builder.d.ts +0 -45
- package/dist/rule-lab/curation-input-builder.js +0 -133
- package/dist/rule-lab/discover.d.ts +0 -13
- package/dist/rule-lab/discover.js +0 -74
- package/dist/rule-lab/discover.test.d.ts +0 -1
- package/dist/rule-lab/discover.test.js +0 -42
- package/dist/rule-lab/paths.d.ts +0 -21
- package/dist/rule-lab/paths.js +0 -37
- package/dist/rule-lab/paths.test.d.ts +0 -1
- package/dist/rule-lab/paths.test.js +0 -46
- package/dist/rule-lab/promote.d.ts +0 -26
- package/dist/rule-lab/promote.js +0 -387
- package/dist/rule-lab/promote.test.d.ts +0 -1
- package/dist/rule-lab/promote.test.js +0 -314
- package/dist/rule-lab/regress.d.ts +0 -60
- package/dist/rule-lab/regress.js +0 -122
- package/dist/rule-lab/regress.test.d.ts +0 -1
- package/dist/rule-lab/regress.test.js +0 -68
- package/dist/rule-lab/review-pack.d.ts +0 -34
- package/dist/rule-lab/review-pack.js +0 -165
- package/dist/rule-lab/review-pack.test.d.ts +0 -1
- package/dist/rule-lab/review-pack.test.js +0 -116
- package/dist/rule-lab/types.d.ts +0 -135
- package/dist/rule-lab/types.js +0 -1
- package/skills/_shared/unity-rule-authoring-contract.md +0 -64
- package/skills/gitnexus-unity-rule-gen.md +0 -107
|
@@ -1,37 +0,0 @@
|
|
|
1
|
-
import { normalizeScopeRules, normalizeScopedPath } from '../core/ingestion/scope-filter.js';
|
|
2
|
-
const SUPPORTED_DIRECTIVES = new Set(['extensions', 'repoalias', 'embeddings']);
|
|
3
|
-
export function parseScopeManifestConfig(raw) {
|
|
4
|
-
const scopeRules = [];
|
|
5
|
-
const directives = {};
|
|
6
|
-
const lines = raw.split(/\r?\n/);
|
|
7
|
-
for (const [index, line] of lines.entries()) {
|
|
8
|
-
const trimmed = line.trim();
|
|
9
|
-
if (!trimmed || trimmed.startsWith('#'))
|
|
10
|
-
continue;
|
|
11
|
-
if (trimmed.startsWith('@')) {
|
|
12
|
-
const separatorIndex = trimmed.indexOf('=');
|
|
13
|
-
if (separatorIndex <= 1) {
|
|
14
|
-
throw new Error(`Invalid manifest directive at line ${index + 1}: ${trimmed}`);
|
|
15
|
-
}
|
|
16
|
-
const key = trimmed.slice(1, separatorIndex).trim().toLowerCase();
|
|
17
|
-
const value = trimmed.slice(separatorIndex + 1).trim();
|
|
18
|
-
if (!SUPPORTED_DIRECTIVES.has(key)) {
|
|
19
|
-
throw new Error(`Unknown manifest directive: @${key}`);
|
|
20
|
-
}
|
|
21
|
-
if (key === 'extensions')
|
|
22
|
-
directives.extensions = value;
|
|
23
|
-
else if (key === 'repoalias')
|
|
24
|
-
directives.repoAlias = value;
|
|
25
|
-
else if (key === 'embeddings')
|
|
26
|
-
directives.embeddings = value;
|
|
27
|
-
continue;
|
|
28
|
-
}
|
|
29
|
-
const normalized = normalizeScopedPath(trimmed);
|
|
30
|
-
if (normalized)
|
|
31
|
-
scopeRules.push(normalized);
|
|
32
|
-
}
|
|
33
|
-
return {
|
|
34
|
-
scopeRules: normalizeScopeRules(scopeRules),
|
|
35
|
-
directives,
|
|
36
|
-
};
|
|
37
|
-
}
|
|
@@ -1,27 +0,0 @@
|
|
|
1
|
-
export interface SyncManifestScopeOptions {
|
|
2
|
-
scopeManifest?: string;
|
|
3
|
-
scopePrefix?: string[] | string;
|
|
4
|
-
}
|
|
5
|
-
export type SyncManifestPolicy = 'ask' | 'update' | 'keep' | 'error';
|
|
6
|
-
export interface SyncManifestDiffEntry {
|
|
7
|
-
directive: 'extensions' | 'repoAlias' | 'embeddings';
|
|
8
|
-
manifestValue?: string;
|
|
9
|
-
cliValue: string;
|
|
10
|
-
}
|
|
11
|
-
export interface EnforceSyncManifestConsistencyInput {
|
|
12
|
-
manifestPath?: string;
|
|
13
|
-
extensions?: string;
|
|
14
|
-
repoAlias?: string;
|
|
15
|
-
embeddings?: boolean;
|
|
16
|
-
policy?: SyncManifestPolicy;
|
|
17
|
-
stdinIsTTY?: boolean;
|
|
18
|
-
prompt?: (message: string) => Promise<'update' | 'keep'>;
|
|
19
|
-
}
|
|
20
|
-
export interface EnforceSyncManifestConsistencyResult {
|
|
21
|
-
decision: 'none' | 'update' | 'keep';
|
|
22
|
-
diff: SyncManifestDiffEntry[];
|
|
23
|
-
}
|
|
24
|
-
export declare function resolveDefaultSyncManifestPath(repoPath: string): string;
|
|
25
|
-
export declare function shouldAutoUseSyncManifest(options?: SyncManifestScopeOptions): boolean;
|
|
26
|
-
export declare function resolveScopeManifestForAnalyze(repoPath: string, options?: SyncManifestScopeOptions, pathExists?: (candidatePath: string) => Promise<boolean>): Promise<string | undefined>;
|
|
27
|
-
export declare function enforceSyncManifestConsistency(input: EnforceSyncManifestConsistencyInput): Promise<EnforceSyncManifestConsistencyResult>;
|
|
@@ -1,200 +0,0 @@
|
|
|
1
|
-
import fs from 'node:fs/promises';
|
|
2
|
-
import path from 'node:path';
|
|
3
|
-
import readline from 'node:readline/promises';
|
|
4
|
-
import { stdin as input, stdout as output } from 'node:process';
|
|
5
|
-
import { parseScopeManifestConfig } from './scope-manifest-config.js';
|
|
6
|
-
import { normalizeRepoAlias, parseExtensionList } from './analyze-options.js';
|
|
7
|
-
export function resolveDefaultSyncManifestPath(repoPath) {
|
|
8
|
-
return path.join(repoPath, '.gitnexus', 'sync-manifest.txt');
|
|
9
|
-
}
|
|
10
|
-
export function shouldAutoUseSyncManifest(options) {
|
|
11
|
-
if (options?.scopeManifest)
|
|
12
|
-
return false;
|
|
13
|
-
return parseScopePrefixCount(options?.scopePrefix) === 0;
|
|
14
|
-
}
|
|
15
|
-
export async function resolveScopeManifestForAnalyze(repoPath, options, pathExists = fileExists) {
|
|
16
|
-
if (options?.scopeManifest) {
|
|
17
|
-
return options.scopeManifest;
|
|
18
|
-
}
|
|
19
|
-
if (!shouldAutoUseSyncManifest(options)) {
|
|
20
|
-
return undefined;
|
|
21
|
-
}
|
|
22
|
-
const defaultManifestPath = resolveDefaultSyncManifestPath(repoPath);
|
|
23
|
-
if (await pathExists(defaultManifestPath)) {
|
|
24
|
-
return defaultManifestPath;
|
|
25
|
-
}
|
|
26
|
-
return undefined;
|
|
27
|
-
}
|
|
28
|
-
export async function enforceSyncManifestConsistency(input) {
|
|
29
|
-
if (!input.manifestPath) {
|
|
30
|
-
return { decision: 'none', diff: [] };
|
|
31
|
-
}
|
|
32
|
-
ensureConcreteManifestPath(input.manifestPath);
|
|
33
|
-
const raw = await fs.readFile(input.manifestPath, 'utf-8');
|
|
34
|
-
const parsed = parseScopeManifestConfig(raw);
|
|
35
|
-
const normalizedDirectives = normalizeManifestDirectives(parsed.directives);
|
|
36
|
-
const diff = computeDiff(normalizedDirectives, input);
|
|
37
|
-
const policy = normalizePolicy(input.policy);
|
|
38
|
-
if (diff.length === 0) {
|
|
39
|
-
if (policy === 'update') {
|
|
40
|
-
throw new Error('Sync manifest rewrite requires non-empty diff entries.');
|
|
41
|
-
}
|
|
42
|
-
return { decision: 'none', diff };
|
|
43
|
-
}
|
|
44
|
-
const decision = await resolveDecision(policy, input.manifestPath, diff, input.stdinIsTTY, input.prompt);
|
|
45
|
-
if (decision === 'update') {
|
|
46
|
-
const nextDirectives = mergeDirectivesForUpdate(normalizedDirectives, input);
|
|
47
|
-
const rewritten = renderSyncManifest(parsed.scopeRules, nextDirectives);
|
|
48
|
-
await fs.writeFile(input.manifestPath, rewritten, 'utf-8');
|
|
49
|
-
}
|
|
50
|
-
return {
|
|
51
|
-
decision,
|
|
52
|
-
diff,
|
|
53
|
-
};
|
|
54
|
-
}
|
|
55
|
-
function parseScopePrefixCount(scopePrefix) {
|
|
56
|
-
if (Array.isArray(scopePrefix))
|
|
57
|
-
return scopePrefix.length;
|
|
58
|
-
if (typeof scopePrefix === 'string')
|
|
59
|
-
return scopePrefix.trim() ? 1 : 0;
|
|
60
|
-
return 0;
|
|
61
|
-
}
|
|
62
|
-
async function fileExists(candidatePath) {
|
|
63
|
-
try {
|
|
64
|
-
await fs.stat(candidatePath);
|
|
65
|
-
return true;
|
|
66
|
-
}
|
|
67
|
-
catch {
|
|
68
|
-
return false;
|
|
69
|
-
}
|
|
70
|
-
}
|
|
71
|
-
function normalizePolicy(raw) {
|
|
72
|
-
if (!raw)
|
|
73
|
-
return 'ask';
|
|
74
|
-
if (raw === 'ask' || raw === 'update' || raw === 'keep' || raw === 'error')
|
|
75
|
-
return raw;
|
|
76
|
-
throw new Error(`Invalid --sync-manifest-policy value: ${raw}. Use ask|update|keep|error.`);
|
|
77
|
-
}
|
|
78
|
-
function normalizeManifestDirectives(directives) {
|
|
79
|
-
return {
|
|
80
|
-
extensions: normalizeExtensions(directives.extensions),
|
|
81
|
-
repoAlias: normalizeAlias(directives.repoAlias),
|
|
82
|
-
embeddings: normalizeEmbeddings(directives.embeddings),
|
|
83
|
-
};
|
|
84
|
-
}
|
|
85
|
-
function computeDiff(manifest, input) {
|
|
86
|
-
const diff = [];
|
|
87
|
-
if (input.extensions !== undefined) {
|
|
88
|
-
const cliValue = normalizeExtensions(input.extensions);
|
|
89
|
-
if (cliValue !== manifest.extensions) {
|
|
90
|
-
diff.push({ directive: 'extensions', manifestValue: manifest.extensions, cliValue: cliValue || '' });
|
|
91
|
-
}
|
|
92
|
-
}
|
|
93
|
-
if (input.repoAlias !== undefined) {
|
|
94
|
-
const cliValue = normalizeAlias(input.repoAlias);
|
|
95
|
-
if (cliValue !== manifest.repoAlias) {
|
|
96
|
-
diff.push({ directive: 'repoAlias', manifestValue: manifest.repoAlias, cliValue: cliValue || '' });
|
|
97
|
-
}
|
|
98
|
-
}
|
|
99
|
-
if (input.embeddings !== undefined) {
|
|
100
|
-
const cliValue = input.embeddings ? 'true' : 'false';
|
|
101
|
-
if (cliValue !== manifest.embeddings) {
|
|
102
|
-
diff.push({ directive: 'embeddings', manifestValue: manifest.embeddings, cliValue });
|
|
103
|
-
}
|
|
104
|
-
}
|
|
105
|
-
return diff;
|
|
106
|
-
}
|
|
107
|
-
async function resolveDecision(policy, manifestPath, diff, stdinIsTTY, prompt) {
|
|
108
|
-
if (policy === 'update' || policy === 'keep')
|
|
109
|
-
return policy;
|
|
110
|
-
if (policy === 'error') {
|
|
111
|
-
throw new Error(`${formatMismatchHeader(manifestPath)}\n${formatDiff(diff)}`);
|
|
112
|
-
}
|
|
113
|
-
if (stdinIsTTY === undefined) {
|
|
114
|
-
throw new Error('TTY prompt branch requires concrete stdin.isTTY evidence.');
|
|
115
|
-
}
|
|
116
|
-
const interactive = stdinIsTTY;
|
|
117
|
-
if (!interactive) {
|
|
118
|
-
throw new Error(`${formatMismatchHeader(manifestPath)}\n${formatDiff(diff)}\n` +
|
|
119
|
-
'Non-interactive mode requires --sync-manifest-policy ask|update|keep|error.');
|
|
120
|
-
}
|
|
121
|
-
const promptFn = prompt || defaultPrompt;
|
|
122
|
-
return promptFn([
|
|
123
|
-
formatMismatchHeader(manifestPath),
|
|
124
|
-
formatDiff(diff),
|
|
125
|
-
'Choose: update (rewrite sync-manifest) or keep (continue without rewrite).',
|
|
126
|
-
].join('\n'));
|
|
127
|
-
}
|
|
128
|
-
function mergeDirectivesForUpdate(manifest, input) {
|
|
129
|
-
const merged = { ...manifest };
|
|
130
|
-
if (input.extensions !== undefined) {
|
|
131
|
-
merged.extensions = normalizeExtensions(input.extensions);
|
|
132
|
-
}
|
|
133
|
-
if (input.repoAlias !== undefined) {
|
|
134
|
-
merged.repoAlias = normalizeAlias(input.repoAlias);
|
|
135
|
-
}
|
|
136
|
-
if (input.embeddings !== undefined) {
|
|
137
|
-
merged.embeddings = input.embeddings ? 'true' : 'false';
|
|
138
|
-
}
|
|
139
|
-
return merged;
|
|
140
|
-
}
|
|
141
|
-
function renderSyncManifest(scopeRules, directives) {
|
|
142
|
-
const lines = [...scopeRules];
|
|
143
|
-
if (directives.extensions)
|
|
144
|
-
lines.push(`@extensions=${directives.extensions}`);
|
|
145
|
-
if (directives.repoAlias)
|
|
146
|
-
lines.push(`@repoAlias=${directives.repoAlias}`);
|
|
147
|
-
if (directives.embeddings)
|
|
148
|
-
lines.push(`@embeddings=${directives.embeddings}`);
|
|
149
|
-
return `${lines.join('\n')}\n`;
|
|
150
|
-
}
|
|
151
|
-
function normalizeExtensions(raw) {
|
|
152
|
-
if (raw === undefined)
|
|
153
|
-
return undefined;
|
|
154
|
-
const parsed = parseExtensionList(raw);
|
|
155
|
-
return parsed.length > 0 ? parsed.join(',') : undefined;
|
|
156
|
-
}
|
|
157
|
-
function normalizeAlias(raw) {
|
|
158
|
-
if (raw === undefined)
|
|
159
|
-
return undefined;
|
|
160
|
-
return normalizeRepoAlias(raw);
|
|
161
|
-
}
|
|
162
|
-
function normalizeEmbeddings(raw) {
|
|
163
|
-
if (raw === undefined)
|
|
164
|
-
return undefined;
|
|
165
|
-
const normalized = raw.trim().toLowerCase();
|
|
166
|
-
if (normalized === 'true')
|
|
167
|
-
return 'true';
|
|
168
|
-
if (normalized === 'false')
|
|
169
|
-
return 'false';
|
|
170
|
-
throw new Error(`Invalid @embeddings directive value: ${raw}. Expected true or false.`);
|
|
171
|
-
}
|
|
172
|
-
function formatMismatchHeader(manifestPath) {
|
|
173
|
-
return `Explicit analyze options differ from sync manifest directives: ${manifestPath}`;
|
|
174
|
-
}
|
|
175
|
-
function formatDiff(diff) {
|
|
176
|
-
return diff
|
|
177
|
-
.map((entry) => `- @${entry.directive}: ${entry.manifestValue ?? '<unset>'} -> ${entry.cliValue}`)
|
|
178
|
-
.join('\n');
|
|
179
|
-
}
|
|
180
|
-
async function defaultPrompt(message) {
|
|
181
|
-
const rl = readline.createInterface({ input, output });
|
|
182
|
-
try {
|
|
183
|
-
const answer = await rl.question(`${message}\nUpdate sync-manifest now? [y/N] `);
|
|
184
|
-
return /^y(es)?$/i.test(answer.trim()) ? 'update' : 'keep';
|
|
185
|
-
}
|
|
186
|
-
finally {
|
|
187
|
-
rl.close();
|
|
188
|
-
}
|
|
189
|
-
}
|
|
190
|
-
function ensureConcreteManifestPath(manifestPath) {
|
|
191
|
-
const normalized = manifestPath.trim();
|
|
192
|
-
if (!normalized) {
|
|
193
|
-
throw new Error('Invalid placeholder manifest path: empty value.');
|
|
194
|
-
}
|
|
195
|
-
if (/placeholder/i.test(normalized) ||
|
|
196
|
-
/<\s*path\s*>/i.test(normalized) ||
|
|
197
|
-
/todo/i.test(normalized)) {
|
|
198
|
-
throw new Error(`Invalid placeholder manifest path: ${manifestPath}`);
|
|
199
|
-
}
|
|
200
|
-
}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|
|
@@ -1,88 +0,0 @@
|
|
|
1
|
-
import test from 'node:test';
|
|
2
|
-
import assert from 'node:assert/strict';
|
|
3
|
-
import fs from 'node:fs/promises';
|
|
4
|
-
import os from 'node:os';
|
|
5
|
-
import path from 'node:path';
|
|
6
|
-
import { enforceSyncManifestConsistency } from './sync-manifest.js';
|
|
7
|
-
async function writeManifest(filePath, content) {
|
|
8
|
-
await fs.mkdir(path.dirname(filePath), { recursive: true });
|
|
9
|
-
await fs.writeFile(filePath, content, 'utf-8');
|
|
10
|
-
}
|
|
11
|
-
test('when explicit CLI values differ from manifest, TTY mode asks whether to update manifest', async () => {
|
|
12
|
-
const tmpDir = await fs.mkdtemp(path.join(os.tmpdir(), 'gitnexus-sync-manifest-'));
|
|
13
|
-
const manifestPath = path.join(tmpDir, '.gitnexus', 'sync-manifest.txt');
|
|
14
|
-
await writeManifest(manifestPath, ['Assets/', '@extensions=.cs,.meta', '@repoAlias=demo-repo', '@embeddings=false'].join('\n'));
|
|
15
|
-
let promptMessage = '';
|
|
16
|
-
const result = await enforceSyncManifestConsistency({
|
|
17
|
-
manifestPath,
|
|
18
|
-
extensions: '.ts',
|
|
19
|
-
policy: 'ask',
|
|
20
|
-
stdinIsTTY: true,
|
|
21
|
-
prompt: async (message) => {
|
|
22
|
-
promptMessage = message;
|
|
23
|
-
return 'keep';
|
|
24
|
-
},
|
|
25
|
-
});
|
|
26
|
-
assert.equal(result.decision, 'keep');
|
|
27
|
-
assert.match(promptMessage, /@extensions/i);
|
|
28
|
-
assert.match(promptMessage, /sync-manifest\.txt/i);
|
|
29
|
-
assert.match(promptMessage, /update/i);
|
|
30
|
-
assert.match(promptMessage, /keep/i);
|
|
31
|
-
});
|
|
32
|
-
test('non-TTY without explicit policy exits with actionable error', async () => {
|
|
33
|
-
const tmpDir = await fs.mkdtemp(path.join(os.tmpdir(), 'gitnexus-sync-manifest-'));
|
|
34
|
-
const manifestPath = path.join(tmpDir, '.gitnexus', 'sync-manifest.txt');
|
|
35
|
-
await writeManifest(manifestPath, ['Assets/', '@extensions=.cs,.meta', '@repoAlias=demo-repo', '@embeddings=false'].join('\n'));
|
|
36
|
-
await assert.rejects(enforceSyncManifestConsistency({
|
|
37
|
-
manifestPath,
|
|
38
|
-
extensions: '.ts',
|
|
39
|
-
stdinIsTTY: false,
|
|
40
|
-
}), /--sync-manifest-policy/i);
|
|
41
|
-
});
|
|
42
|
-
test('policy=update rewrites manifest with normalized directives', async () => {
|
|
43
|
-
const tmpDir = await fs.mkdtemp(path.join(os.tmpdir(), 'gitnexus-sync-manifest-'));
|
|
44
|
-
const manifestPath = path.join(tmpDir, '.gitnexus', 'sync-manifest.txt');
|
|
45
|
-
await writeManifest(manifestPath, ['Assets/', 'Packages/', '@extensions=.cs,.meta', '@repoAlias=demo-repo', '@embeddings=false'].join('\n'));
|
|
46
|
-
const result = await enforceSyncManifestConsistency({
|
|
47
|
-
manifestPath,
|
|
48
|
-
extensions: '.ts,.tsx',
|
|
49
|
-
embeddings: true,
|
|
50
|
-
policy: 'update',
|
|
51
|
-
});
|
|
52
|
-
const rewritten = await fs.readFile(manifestPath, 'utf-8');
|
|
53
|
-
assert.equal(result.decision, 'update');
|
|
54
|
-
assert.equal(rewritten, ['Assets', 'Packages', '@extensions=.ts,.tsx', '@repoAlias=demo-repo', '@embeddings=true', ''].join('\n'));
|
|
55
|
-
});
|
|
56
|
-
test('rejects placeholder manifest path values', async () => {
|
|
57
|
-
const tmpDir = await fs.mkdtemp(path.join(os.tmpdir(), 'gitnexus-sync-manifest-placeholder-'));
|
|
58
|
-
const manifestPath = path.join(tmpDir, '.gitnexus', 'sync-manifest-placeholder.txt');
|
|
59
|
-
await writeManifest(manifestPath, ['Assets/', '@extensions=.cs,.meta', '@repoAlias=demo-repo', '@embeddings=false'].join('\n'));
|
|
60
|
-
await assert.rejects(enforceSyncManifestConsistency({
|
|
61
|
-
manifestPath,
|
|
62
|
-
extensions: '.ts',
|
|
63
|
-
policy: 'keep',
|
|
64
|
-
}), /placeholder manifest path/i);
|
|
65
|
-
});
|
|
66
|
-
test('TTY prompt branch requires concrete stdin.isTTY evidence', async () => {
|
|
67
|
-
const tmpDir = await fs.mkdtemp(path.join(os.tmpdir(), 'gitnexus-sync-manifest-tty-evidence-'));
|
|
68
|
-
const manifestPath = path.join(tmpDir, '.gitnexus', 'sync-manifest.txt');
|
|
69
|
-
await writeManifest(manifestPath, ['Assets/', '@extensions=.cs,.meta', '@repoAlias=demo-repo', '@embeddings=false'].join('\n'));
|
|
70
|
-
await assert.rejects(enforceSyncManifestConsistency({
|
|
71
|
-
manifestPath,
|
|
72
|
-
extensions: '.ts',
|
|
73
|
-
policy: 'ask',
|
|
74
|
-
prompt: async () => 'keep',
|
|
75
|
-
}), /stdin\.isTTY evidence/i);
|
|
76
|
-
});
|
|
77
|
-
test('manifest rewrite requires non-empty diff entries', async () => {
|
|
78
|
-
const tmpDir = await fs.mkdtemp(path.join(os.tmpdir(), 'gitnexus-sync-manifest-noop-'));
|
|
79
|
-
const manifestPath = path.join(tmpDir, '.gitnexus', 'sync-manifest.txt');
|
|
80
|
-
await writeManifest(manifestPath, ['Assets/', '@extensions=.cs,.meta', '@repoAlias=demo-repo', '@embeddings=false'].join('\n'));
|
|
81
|
-
await assert.rejects(enforceSyncManifestConsistency({
|
|
82
|
-
manifestPath,
|
|
83
|
-
extensions: '.cs,.meta',
|
|
84
|
-
repoAlias: 'demo-repo',
|
|
85
|
-
embeddings: false,
|
|
86
|
-
policy: 'update',
|
|
87
|
-
}), /non-empty diff/i);
|
|
88
|
-
});
|
|
@@ -1,26 +0,0 @@
|
|
|
1
|
-
import type { KnowledgeGraph } from '../graph/types.js';
|
|
2
|
-
import type { RuntimeClaimRule } from '../../mcp/local/runtime-claim-rule-registry.js';
|
|
3
|
-
import type { UnityConfig } from '../config/unity-config.js';
|
|
4
|
-
export interface UnityRuntimeBindingResult {
|
|
5
|
-
edgesInjected: number;
|
|
6
|
-
ruleResults: Array<{
|
|
7
|
-
ruleId: string;
|
|
8
|
-
edgesInjected: number;
|
|
9
|
-
}>;
|
|
10
|
-
diagnostics: UnityRuntimeBindingDiagnostics;
|
|
11
|
-
}
|
|
12
|
-
export interface UnityRuntimeBindingDiagnostics {
|
|
13
|
-
rulesEvaluated: number;
|
|
14
|
-
bindingsEvaluated: number;
|
|
15
|
-
bindingsByKind: Record<string, number>;
|
|
16
|
-
methodLookupCalls: number;
|
|
17
|
-
methodLookupCacheHits: number;
|
|
18
|
-
sceneRuntimeTraversalCalls: number;
|
|
19
|
-
sceneRuntimeTraversalCacheHits: number;
|
|
20
|
-
sceneRuntimeResourcesVisited: number;
|
|
21
|
-
anomalies: string[];
|
|
22
|
-
shouldAgentReport: boolean;
|
|
23
|
-
agentReportReason: string;
|
|
24
|
-
summary: string[];
|
|
25
|
-
}
|
|
26
|
-
export declare function applyUnityRuntimeBindingRules(graph: KnowledgeGraph, rules: RuntimeClaimRule[], config: UnityConfig): UnityRuntimeBindingResult;
|