@arnilo/prism-coding-agent 0.0.8 → 0.0.11
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/CHANGELOG.md +37 -6
- package/README.md +22 -7
- package/dist/artifacts.d.ts +6 -0
- package/dist/artifacts.js +35 -0
- package/dist/ask-user-decision.d.ts +160 -0
- package/dist/ask-user-decision.js +471 -0
- package/dist/checks.d.ts +26 -0
- package/dist/checks.js +249 -0
- package/dist/coding-checkpoint.d.ts +159 -0
- package/dist/coding-checkpoint.js +576 -0
- package/dist/git-exec.d.ts +62 -0
- package/dist/git-exec.js +257 -0
- package/dist/git-status.d.ts +30 -0
- package/dist/git-status.js +146 -0
- package/dist/git-tools.d.ts +34 -0
- package/dist/git-tools.js +502 -0
- package/dist/git.d.ts +139 -0
- package/dist/git.js +495 -0
- package/dist/goal-verify.d.ts +66 -0
- package/dist/goal-verify.js +283 -0
- package/dist/index.d.ts +40 -4
- package/dist/index.js +43 -5
- package/dist/limits.d.ts +76 -0
- package/dist/limits.js +81 -0
- package/dist/list.d.ts +14 -0
- package/dist/list.js +144 -0
- package/dist/repository.d.ts +119 -0
- package/dist/repository.js +633 -0
- package/dist/search.d.ts +14 -0
- package/dist/search.js +166 -0
- package/package.json +8 -5
package/dist/list.js
ADDED
|
@@ -0,0 +1,144 @@
|
|
|
1
|
+
import { enforceExecutionPolicy } from "./execution-policy.js";
|
|
2
|
+
import { createLocalRepositoryOperations, resolveRepositoryLimits, RepositoryError, } from "./repository.js";
|
|
3
|
+
import { HARD_MAX_REPO_DEPTH, HARD_MAX_REPO_RESULTS, validateCodingLimit, validateCodingLimitAllowZero } from "./limits.js";
|
|
4
|
+
function errorResult(toolCallId, message) {
|
|
5
|
+
return {
|
|
6
|
+
toolCallId,
|
|
7
|
+
name: "repo_list",
|
|
8
|
+
content: [{ type: "text", text: message }],
|
|
9
|
+
error: { message },
|
|
10
|
+
};
|
|
11
|
+
}
|
|
12
|
+
function formatListText(result) {
|
|
13
|
+
if (result.entries.length === 0) {
|
|
14
|
+
return result.truncated
|
|
15
|
+
? `[truncated by ${result.truncatedBy ?? "limit"} before any entries]`
|
|
16
|
+
: "(no entries)";
|
|
17
|
+
}
|
|
18
|
+
const lines = result.entries.map((entry) => {
|
|
19
|
+
const size = entry.size !== undefined ? `\t${entry.size}` : "";
|
|
20
|
+
return `${entry.kind}\t${entry.path}${size}`;
|
|
21
|
+
});
|
|
22
|
+
if (result.truncated) {
|
|
23
|
+
const next = result.nextOffset !== undefined ? ` Use offset=${result.nextOffset} to continue.` : "";
|
|
24
|
+
lines.push(`[truncated by ${result.truncatedBy ?? "limit"}.${next}]`);
|
|
25
|
+
}
|
|
26
|
+
return lines.join("\n");
|
|
27
|
+
}
|
|
28
|
+
export function createRepoListTool(cwd, options) {
|
|
29
|
+
const limits = resolveRepositoryLimits({
|
|
30
|
+
...options?.repository,
|
|
31
|
+
maxDepth: options?.maxDepth ?? options?.repository?.maxDepth,
|
|
32
|
+
maxResults: options?.maxResults ?? options?.repository?.maxResults,
|
|
33
|
+
exclude: options?.exclude ?? options?.repository?.exclude,
|
|
34
|
+
});
|
|
35
|
+
const ops = options?.operations ?? createLocalRepositoryOperations(limits);
|
|
36
|
+
return {
|
|
37
|
+
name: "repo_list",
|
|
38
|
+
description: `List repository entries under the workspace with deterministic relative paths. Skips hidden names and excluded basenames (default: ${limits.exclude.join(", ")}) unless overridden. Does not follow symlinks. Results paginate with offset/maxResults (default ${limits.maxResults}). Depth default ${limits.maxDepth}.`,
|
|
39
|
+
parameters: {
|
|
40
|
+
type: "object",
|
|
41
|
+
properties: {
|
|
42
|
+
path: {
|
|
43
|
+
type: "string",
|
|
44
|
+
description: "Workspace-relative directory or file to list (default: workspace root)",
|
|
45
|
+
},
|
|
46
|
+
includeHidden: {
|
|
47
|
+
type: "boolean",
|
|
48
|
+
description: "Include dotfile/dotdir names (default false). Excluded basenames still apply.",
|
|
49
|
+
},
|
|
50
|
+
maxDepth: {
|
|
51
|
+
type: "number",
|
|
52
|
+
description: `Maximum directory depth to descend (default ${limits.maxDepth}, hard ${HARD_MAX_REPO_DEPTH})`,
|
|
53
|
+
},
|
|
54
|
+
maxResults: {
|
|
55
|
+
type: "number",
|
|
56
|
+
description: `Maximum entries returned in this page (default ${limits.maxResults}, hard ${HARD_MAX_REPO_RESULTS})`,
|
|
57
|
+
},
|
|
58
|
+
offset: {
|
|
59
|
+
type: "number",
|
|
60
|
+
description: "Number of entries to skip before retaining results (default 0)",
|
|
61
|
+
},
|
|
62
|
+
},
|
|
63
|
+
additionalProperties: false,
|
|
64
|
+
},
|
|
65
|
+
async execute(args, context) {
|
|
66
|
+
const toolCallId = context.toolCallId;
|
|
67
|
+
if (context.signal?.aborted)
|
|
68
|
+
return errorResult(toolCallId, "Operation aborted");
|
|
69
|
+
const path = typeof args.path === "string" ? args.path : undefined;
|
|
70
|
+
const includeHidden = args.includeHidden === true;
|
|
71
|
+
let maxDepth;
|
|
72
|
+
let maxResults;
|
|
73
|
+
let offset = 0;
|
|
74
|
+
try {
|
|
75
|
+
if (args.maxDepth !== undefined) {
|
|
76
|
+
maxDepth = validateCodingLimit("maxDepth", args.maxDepth, HARD_MAX_REPO_DEPTH);
|
|
77
|
+
}
|
|
78
|
+
if (args.maxResults !== undefined) {
|
|
79
|
+
maxResults = validateCodingLimit("maxResults", args.maxResults, HARD_MAX_REPO_RESULTS);
|
|
80
|
+
}
|
|
81
|
+
if (args.offset !== undefined) {
|
|
82
|
+
offset = validateCodingLimitAllowZero("offset", args.offset, limits.maxEntries);
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
catch (error) {
|
|
86
|
+
return errorResult(toolCallId, error instanceof Error ? error.message : String(error));
|
|
87
|
+
}
|
|
88
|
+
const policyCheck = await enforceExecutionPolicy(options?.executionPolicy, {
|
|
89
|
+
kind: "repo_list",
|
|
90
|
+
operation: "list",
|
|
91
|
+
paths: [path ? path : cwd],
|
|
92
|
+
risk: "low",
|
|
93
|
+
metadata: {
|
|
94
|
+
includeHidden,
|
|
95
|
+
maxDepth,
|
|
96
|
+
maxResults,
|
|
97
|
+
offset,
|
|
98
|
+
sessionId: context.sessionId,
|
|
99
|
+
runId: context.runId,
|
|
100
|
+
signal: context.signal,
|
|
101
|
+
},
|
|
102
|
+
}, toolCallId, "repo_list");
|
|
103
|
+
if (!policyCheck.allowed)
|
|
104
|
+
return policyCheck.result;
|
|
105
|
+
try {
|
|
106
|
+
const result = await ops.list({
|
|
107
|
+
root: cwd,
|
|
108
|
+
path,
|
|
109
|
+
includeHidden,
|
|
110
|
+
exclude: limits.exclude,
|
|
111
|
+
maxDepth: maxDepth ?? limits.maxDepth,
|
|
112
|
+
maxResults: maxResults ?? limits.maxResults,
|
|
113
|
+
offset,
|
|
114
|
+
signal: context.signal,
|
|
115
|
+
deadlineMs: limits.maxTimeMs,
|
|
116
|
+
});
|
|
117
|
+
return {
|
|
118
|
+
toolCallId,
|
|
119
|
+
name: "repo_list",
|
|
120
|
+
content: [{ type: "text", text: formatListText(result) }],
|
|
121
|
+
metadata: {
|
|
122
|
+
truncated: result.truncated,
|
|
123
|
+
truncatedBy: result.truncatedBy,
|
|
124
|
+
offset: result.offset,
|
|
125
|
+
nextOffset: result.nextOffset,
|
|
126
|
+
returned: result.entries.length,
|
|
127
|
+
scannedEntries: result.scannedEntries,
|
|
128
|
+
scannedFiles: result.scannedFiles,
|
|
129
|
+
entries: result.entries,
|
|
130
|
+
},
|
|
131
|
+
};
|
|
132
|
+
}
|
|
133
|
+
catch (error) {
|
|
134
|
+
const message = error instanceof RepositoryError
|
|
135
|
+
? error.message
|
|
136
|
+
: error instanceof Error
|
|
137
|
+
? error.message
|
|
138
|
+
: String(error);
|
|
139
|
+
return errorResult(toolCallId, message);
|
|
140
|
+
}
|
|
141
|
+
},
|
|
142
|
+
};
|
|
143
|
+
}
|
|
144
|
+
//# sourceMappingURL=list.js.map
|
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
export type RepoEntryKind = "file" | "directory" | "symlink" | "other";
|
|
2
|
+
export interface RepoListEntry {
|
|
3
|
+
readonly path: string;
|
|
4
|
+
readonly kind: RepoEntryKind;
|
|
5
|
+
readonly size?: number;
|
|
6
|
+
}
|
|
7
|
+
export interface RepositoryListResult {
|
|
8
|
+
readonly entries: readonly RepoListEntry[];
|
|
9
|
+
readonly truncated: boolean;
|
|
10
|
+
readonly truncatedBy: "results" | "entries" | "files" | "depth" | "time" | "abort" | null;
|
|
11
|
+
readonly scannedEntries: number;
|
|
12
|
+
readonly scannedFiles: number;
|
|
13
|
+
readonly nextOffset?: number;
|
|
14
|
+
readonly offset: number;
|
|
15
|
+
}
|
|
16
|
+
export interface RepositorySearchMatch {
|
|
17
|
+
readonly path: string;
|
|
18
|
+
readonly line: number;
|
|
19
|
+
readonly column: number;
|
|
20
|
+
readonly text: string;
|
|
21
|
+
readonly before: readonly string[];
|
|
22
|
+
readonly after: readonly string[];
|
|
23
|
+
}
|
|
24
|
+
export interface RepositorySearchResult {
|
|
25
|
+
readonly matches: readonly RepositorySearchMatch[];
|
|
26
|
+
readonly truncated: boolean;
|
|
27
|
+
readonly truncatedBy: "matches" | "scan" | "file" | "entries" | "files" | "depth" | "time" | "abort" | "pattern" | null;
|
|
28
|
+
readonly scannedBytes: number;
|
|
29
|
+
readonly scannedFiles: number;
|
|
30
|
+
readonly scannedEntries: number;
|
|
31
|
+
readonly filesSkippedBinary: number;
|
|
32
|
+
readonly filesSkippedOversize: number;
|
|
33
|
+
}
|
|
34
|
+
export interface ResolvedRepositoryLimits {
|
|
35
|
+
readonly maxDepth: number;
|
|
36
|
+
readonly maxEntries: number;
|
|
37
|
+
readonly maxFiles: number;
|
|
38
|
+
readonly maxResults: number;
|
|
39
|
+
readonly maxConcurrency: number;
|
|
40
|
+
readonly maxScanBytes: number;
|
|
41
|
+
readonly maxFileBytes: number;
|
|
42
|
+
readonly maxMatches: number;
|
|
43
|
+
readonly maxPatternBytes: number;
|
|
44
|
+
readonly maxLineBytes: number;
|
|
45
|
+
readonly maxContextLines: number;
|
|
46
|
+
readonly maxTimeMs: number;
|
|
47
|
+
readonly binarySniffBytes: number;
|
|
48
|
+
readonly exclude: readonly string[];
|
|
49
|
+
}
|
|
50
|
+
export interface RepositoryLimitOptions {
|
|
51
|
+
readonly maxDepth?: number;
|
|
52
|
+
readonly maxEntries?: number;
|
|
53
|
+
readonly maxFiles?: number;
|
|
54
|
+
readonly maxResults?: number;
|
|
55
|
+
readonly maxConcurrency?: number;
|
|
56
|
+
readonly maxScanBytes?: number;
|
|
57
|
+
readonly maxFileBytes?: number;
|
|
58
|
+
readonly maxMatches?: number;
|
|
59
|
+
readonly maxPatternBytes?: number;
|
|
60
|
+
readonly maxLineBytes?: number;
|
|
61
|
+
readonly maxContextLines?: number;
|
|
62
|
+
readonly maxTimeMs?: number;
|
|
63
|
+
/** Basename denylist skipped during descent (default `.git`, `node_modules`, `dist`). */
|
|
64
|
+
readonly exclude?: readonly string[];
|
|
65
|
+
}
|
|
66
|
+
export interface RepositoryListRequest {
|
|
67
|
+
readonly root: string;
|
|
68
|
+
readonly path?: string;
|
|
69
|
+
readonly includeHidden?: boolean;
|
|
70
|
+
readonly exclude?: readonly string[];
|
|
71
|
+
readonly maxDepth?: number;
|
|
72
|
+
readonly maxResults?: number;
|
|
73
|
+
readonly offset?: number;
|
|
74
|
+
readonly signal?: AbortSignal;
|
|
75
|
+
readonly deadlineMs?: number;
|
|
76
|
+
}
|
|
77
|
+
export interface RepositorySearchRequest {
|
|
78
|
+
readonly root: string;
|
|
79
|
+
readonly query: string;
|
|
80
|
+
readonly path?: string;
|
|
81
|
+
readonly mode?: "literal" | "regex";
|
|
82
|
+
readonly caseSensitive?: boolean;
|
|
83
|
+
readonly includeHidden?: boolean;
|
|
84
|
+
readonly exclude?: readonly string[];
|
|
85
|
+
readonly context?: number;
|
|
86
|
+
readonly maxMatches?: number;
|
|
87
|
+
readonly signal?: AbortSignal;
|
|
88
|
+
readonly deadlineMs?: number;
|
|
89
|
+
}
|
|
90
|
+
export interface RepositoryOperations {
|
|
91
|
+
list(request: RepositoryListRequest): Promise<RepositoryListResult>;
|
|
92
|
+
search(request: RepositorySearchRequest): Promise<RepositorySearchResult>;
|
|
93
|
+
}
|
|
94
|
+
export declare const DEFAULT_REPO_EXCLUDE: readonly string[];
|
|
95
|
+
export declare class RepositoryError extends Error {
|
|
96
|
+
readonly code = "ERR_PRISM_REPOSITORY";
|
|
97
|
+
constructor(message: string);
|
|
98
|
+
}
|
|
99
|
+
export declare function resolveRepositoryLimits(options?: RepositoryLimitOptions): ResolvedRepositoryLimits;
|
|
100
|
+
/** Normalize a workspace-relative path to stable forward-slash form. */
|
|
101
|
+
export declare function toRepoRelative(root: string, absolutePath: string): string;
|
|
102
|
+
/**
|
|
103
|
+
* Resolve a list/search start path under the workspace root.
|
|
104
|
+
* Symlink escapes fail closed after realpath when the path exists.
|
|
105
|
+
*/
|
|
106
|
+
export declare function resolveRepoPath(root: string, inputPath: string | undefined): Promise<{
|
|
107
|
+
absolute: string;
|
|
108
|
+
relative: string;
|
|
109
|
+
rootReal: string;
|
|
110
|
+
}>;
|
|
111
|
+
export declare function isBinaryBuffer(buffer: Buffer): boolean;
|
|
112
|
+
export declare function compileSearchPattern(query: string, mode: "literal" | "regex", caseSensitive: boolean, maxPatternBytes: number): {
|
|
113
|
+
testLine: (line: string) => {
|
|
114
|
+
column: number;
|
|
115
|
+
} | null;
|
|
116
|
+
patternBytes: number;
|
|
117
|
+
};
|
|
118
|
+
/** Local filesystem repository operations (default backend). */
|
|
119
|
+
export declare function createLocalRepositoryOperations(limits?: RepositoryLimitOptions): RepositoryOperations;
|