@cybedefend/vibedefend 1.7.0 → 1.8.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 +19 -12
- package/dist/clients/antigravity.js +327 -0
- package/dist/clients/antigravity.js.map +1 -0
- package/dist/clients/registry.js +2 -0
- package/dist/clients/registry.js.map +1 -1
- package/dist/hook-runner.js +902 -227
- package/dist/hooks/install.js +1 -1
- package/dist/hooks/install.js.map +1 -1
- package/dist/hooks/runtime/antigravity-session.js +400 -0
- package/dist/hooks/runtime/antigravity-session.js.map +1 -0
- package/dist/hooks/runtime/emit.js +206 -0
- package/dist/hooks/runtime/emit.js.map +1 -1
- package/dist/hooks/runtime/exit-deadlock-guard.js +46 -0
- package/dist/hooks/runtime/exit-deadlock-guard.js.map +1 -0
- package/dist/hooks/runtime/fetch-rules.js +39 -3
- package/dist/hooks/runtime/fetch-rules.js.map +1 -1
- package/dist/hooks/runtime/pre-invocation.js +45 -0
- package/dist/hooks/runtime/pre-invocation.js.map +1 -0
- package/dist/hooks/runtime/runner-args.js +12 -0
- package/dist/hooks/runtime/runner-args.js.map +1 -0
- package/dist/hooks/runtime/session-activation.js +10 -4
- package/dist/hooks/runtime/session-activation.js.map +1 -1
- package/dist/hooks/runtime/session-review.js +42 -0
- package/dist/hooks/runtime/session-review.js.map +1 -1
- package/dist/hooks/runtime/session-start.js +21 -1
- package/dist/hooks/runtime/session-start.js.map +1 -1
- package/dist/hooks/runtime/sniff.js +325 -70
- package/dist/hooks/runtime/sniff.js.map +1 -1
- package/dist/hooks/runtime/work-dir.js +3 -0
- package/dist/hooks/runtime/work-dir.js.map +1 -1
- package/dist/hooks/shim.js +102 -5
- package/dist/hooks/shim.js.map +1 -1
- package/dist/json-file.js +6 -3
- package/dist/json-file.js.map +1 -1
- package/dist/shim.js +53 -3
- package/dist/utils.js +9 -0
- package/dist/utils.js.map +1 -1
- package/package.json +3 -2
package/dist/hooks/install.js
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
* scripts) with a simpler "copy + write config" pair:
|
|
6
6
|
*
|
|
7
7
|
* 1. Copy the bundled `dist/hook-runner.js` (built by esbuild) to
|
|
8
|
-
* `~/.cybedefend/hook-runner.js`. ONE script for all
|
|
8
|
+
* `~/.cybedefend/hook-runner.js`. ONE script for all 6 agents.
|
|
9
9
|
* 2. Write `~/.cybedefend/runtime-config.json` with the user's region
|
|
10
10
|
* + hook tunables — the runner reads it on every invocation.
|
|
11
11
|
*
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"install.js","sourceRoot":"","sources":["../../src/hooks/install.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"install.js","sourceRoot":"","sources":["../../src/hooks/install.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,400 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Per-conversation on-disk state for Antigravity (BACK-241).
|
|
3
|
+
*
|
|
4
|
+
* Antigravity's hook envelope carries a `conversationId` that is stable for
|
|
5
|
+
* the life of one chat (SessionStart through the matching Stop), but the
|
|
6
|
+
* CLI is re-invoked once per hook call, as a short-lived process with no
|
|
7
|
+
* memory of the calls before it. Three small per-conversation ledgers
|
|
8
|
+
* bridge that gap, under `~/.cybedefend/antigravity/<key>/`, keyed by a
|
|
9
|
+
* hash of the conversation id so no caller-supplied string ever becomes a
|
|
10
|
+
* path component:
|
|
11
|
+
*
|
|
12
|
+
* - `context/*.md` — rule bodies a PreToolUse run stashed because it had
|
|
13
|
+
* nothing to deliver to the model (an Antigravity `allow` answer is
|
|
14
|
+
* never shown to it). Task 11 drains and delivers them at the next
|
|
15
|
+
* call that CAN speak to the model.
|
|
16
|
+
* - `edits.jsonl` — one `{"f": "<path>"}` line per file a PreToolUse
|
|
17
|
+
* run saw edited, read back by the end-of-session review (Task 13).
|
|
18
|
+
* - `reviewed` — a marker a review run leaves so a conversation is
|
|
19
|
+
* never reviewed twice.
|
|
20
|
+
*
|
|
21
|
+
* Antigravity runs tool calls in parallel, so several hook processes can be
|
|
22
|
+
* writing one conversation's state at the same time:
|
|
23
|
+
* - `stashContext` writes to a hidden `.tmp` scratch name in `context/`
|
|
24
|
+
* (`O_CREAT|O_EXCL`, so two concurrent stashes can't collide) and only
|
|
25
|
+
* `renameSync`s it to its final `${Date.now()}-${8 hex}.md` name once
|
|
26
|
+
* it is fully written — `renameSync` is atomic on the same filesystem,
|
|
27
|
+
* so a reader never observes a half-written body under a final name.
|
|
28
|
+
* - `recordEdit` only ever appends, one line per call: concurrent appends
|
|
29
|
+
* interleave at the line boundary, never inside a line.
|
|
30
|
+
* - `readEdits` tolerates a line a concurrent writer has not finished
|
|
31
|
+
* yet — a line that does not parse as `{"f": string}` is skipped, not
|
|
32
|
+
* fatal to the read.
|
|
33
|
+
*
|
|
34
|
+
* Every write refreshes the key directory's own mtime (`ensureLiveKeyDir`):
|
|
35
|
+
* a directory's mtime otherwise only moves when a direct child is added or
|
|
36
|
+
* removed, so a conversation that is active every day but never adds a new
|
|
37
|
+
* TOP-LEVEL entry under its key directory (every `recordEdit` call after
|
|
38
|
+
* the first only appends to an already-existing `edits.jsonl`) would
|
|
39
|
+
* otherwise look as old as its very first write to `pruneStale`.
|
|
40
|
+
*
|
|
41
|
+
* A path under a conversation's key directory may be a symlink an attacker
|
|
42
|
+
* planted before the hook ran (into the key directory's position itself,
|
|
43
|
+
* or into its `context/` subdirectory) to redirect a write or a delete
|
|
44
|
+
* outside the state directory. Every entry point — the three writers, the
|
|
45
|
+
* three readers, and `pruneStale` — checks with `lstatSync` (which never
|
|
46
|
+
* follows a link) before it writes, reads or judges staleness through it,
|
|
47
|
+
* and refuses (does nothing) when the path is not a real directory. The
|
|
48
|
+
* same applies one level down, at `edits.jsonl` and `reviewed` themselves:
|
|
49
|
+
* their names are fixed and the key is a predictable hash of
|
|
50
|
+
* `conversationId`, so an attacker needs no race, just a symlink planted
|
|
51
|
+
* ahead of time in an otherwise-real key directory. `recordEdit` and
|
|
52
|
+
* `markReviewed` open with `O_NOFOLLOW` (an `lstatSync` check where that
|
|
53
|
+
* flag is unavailable — Windows); `readEdits` and `isReviewed` use
|
|
54
|
+
* `lstatSync`, never `existsSync`/`statSync`, and treat a symlink there the
|
|
55
|
+
* same as a conversation with no state yet.
|
|
56
|
+
*
|
|
57
|
+
* No function in this module throws: every filesystem error is swallowed
|
|
58
|
+
* and the caller gets back the same empty value it would get from a
|
|
59
|
+
* conversation that has no state yet.
|
|
60
|
+
*/
|
|
61
|
+
import { appendFileSync, closeSync, constants, lstatSync, mkdirSync, openSync, readdirSync, readFileSync, renameSync, rmSync, unlinkSync, utimesSync, writeFileSync, writeSync, } from 'node:fs';
|
|
62
|
+
import { createHash, randomBytes } from 'node:crypto';
|
|
63
|
+
import { homedir } from 'node:os';
|
|
64
|
+
import { join } from 'node:path';
|
|
65
|
+
/** Stashed rule bodies kept per conversation; the oldest are dropped past this. */
|
|
66
|
+
export const MAX_STASHED_CONTEXTS = 20;
|
|
67
|
+
/** Default staleness window for `pruneStale`, read from a key directory's mtime. */
|
|
68
|
+
export const DEFAULT_MAX_AGE_MS = 7 * 24 * 60 * 60 * 1000;
|
|
69
|
+
/** A final stashed-context filename; `stashContext`'s own `.*.tmp` scratch
|
|
70
|
+
* file (mid-write, or left behind by a crash before the rename) is never
|
|
71
|
+
* mistaken for one by a reader. */
|
|
72
|
+
const STASH_NAME_RE = /^\d+-[0-9a-f]{8}\.md$/;
|
|
73
|
+
const DIR_MODE = 0o700;
|
|
74
|
+
const FILE_MODE = 0o600;
|
|
75
|
+
/**
|
|
76
|
+
* A stable key for `raw.conversationId`: the first 32 hex characters of its
|
|
77
|
+
* sha256, so the id itself (arbitrary, agent-supplied) never becomes a path
|
|
78
|
+
* component. Null for a missing, empty, non-string or longer-than-256 id.
|
|
79
|
+
*/
|
|
80
|
+
export function conversationKey(raw) {
|
|
81
|
+
const id = raw.conversationId;
|
|
82
|
+
if (typeof id !== 'string' || id.length === 0 || id.length > 256)
|
|
83
|
+
return null;
|
|
84
|
+
return createHash('sha256').update(id).digest('hex').slice(0, 32);
|
|
85
|
+
}
|
|
86
|
+
/** `~/.cybedefend/antigravity`, re-read on every call (home can move in tests). */
|
|
87
|
+
export function antigravityStateDir() {
|
|
88
|
+
return join(homedir(), '.cybedefend', 'antigravity');
|
|
89
|
+
}
|
|
90
|
+
function keyDir(key, dir) {
|
|
91
|
+
return join(dir, key);
|
|
92
|
+
}
|
|
93
|
+
function isFinalStashName(name) {
|
|
94
|
+
return STASH_NAME_RE.test(name);
|
|
95
|
+
}
|
|
96
|
+
/**
|
|
97
|
+
* True when `path` exists but is not a real directory (a symlink, a
|
|
98
|
+
* regular file, …). `lstatSync` never follows a link, so a symlink
|
|
99
|
+
* pointing at a real directory elsewhere is still reported unsafe, not
|
|
100
|
+
* silently trusted.
|
|
101
|
+
*/
|
|
102
|
+
function isUnsafePath(path) {
|
|
103
|
+
try {
|
|
104
|
+
return !lstatSync(path).isDirectory();
|
|
105
|
+
}
|
|
106
|
+
catch {
|
|
107
|
+
return false; // doesn't exist yet — nothing unsafe sitting there.
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
/**
|
|
111
|
+
* True when `path` exists but is not a plain regular file (a symlink, a
|
|
112
|
+
* directory, …). `lstatSync` never follows a link, so a symlinked
|
|
113
|
+
* `edits.jsonl` or `reviewed` — fixed names under a predictable, hashed
|
|
114
|
+
* key directory, so an attacker needs no race to plant one — is reported
|
|
115
|
+
* unsafe and never opened through.
|
|
116
|
+
*/
|
|
117
|
+
function isUnsafeFilePath(path) {
|
|
118
|
+
try {
|
|
119
|
+
return !lstatSync(path).isFile();
|
|
120
|
+
}
|
|
121
|
+
catch {
|
|
122
|
+
return false; // doesn't exist yet — nothing unsafe sitting there.
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
/** Whether `O_NOFOLLOW` is available to refuse opening through a symlink at
|
|
126
|
+
* the syscall level. Unavailable on Windows; the two writers below fall
|
|
127
|
+
* back to the same `lstatSync` check the readers use. */
|
|
128
|
+
const NOFOLLOW_SUPPORTED = typeof constants.O_NOFOLLOW === 'number';
|
|
129
|
+
/**
|
|
130
|
+
* Append `line` to the ledger at `path`, refusing to follow a symlink
|
|
131
|
+
* planted there. `O_NOFOLLOW` makes the open itself fail (ELOOP) on a
|
|
132
|
+
* symlink; where it is unavailable (Windows) an `lstatSync` check runs
|
|
133
|
+
* first instead. Either way: unsafe, or any other error, and nothing is
|
|
134
|
+
* written — the caller's own `try/catch` is what swallows it.
|
|
135
|
+
*/
|
|
136
|
+
function appendLedgerLine(path, line) {
|
|
137
|
+
if (NOFOLLOW_SUPPORTED) {
|
|
138
|
+
const fd = openSync(path, constants.O_WRONLY | constants.O_APPEND | constants.O_CREAT | constants.O_NOFOLLOW, FILE_MODE);
|
|
139
|
+
try {
|
|
140
|
+
writeSync(fd, line, null, 'utf8');
|
|
141
|
+
}
|
|
142
|
+
finally {
|
|
143
|
+
closeSync(fd);
|
|
144
|
+
}
|
|
145
|
+
return;
|
|
146
|
+
}
|
|
147
|
+
if (isUnsafeFilePath(path))
|
|
148
|
+
return;
|
|
149
|
+
appendFileSync(path, line, { mode: FILE_MODE });
|
|
150
|
+
}
|
|
151
|
+
/**
|
|
152
|
+
* Overwrite the marker at `path` with `content`, refusing to follow a
|
|
153
|
+
* symlink planted there — same `O_NOFOLLOW` / `lstatSync` fallback as
|
|
154
|
+
* `appendLedgerLine`, but truncating instead of appending.
|
|
155
|
+
*/
|
|
156
|
+
function writeMarkerFile(path, content) {
|
|
157
|
+
if (NOFOLLOW_SUPPORTED) {
|
|
158
|
+
const fd = openSync(path, constants.O_WRONLY | constants.O_CREAT | constants.O_TRUNC | constants.O_NOFOLLOW, FILE_MODE);
|
|
159
|
+
try {
|
|
160
|
+
writeSync(fd, content, null, 'utf8');
|
|
161
|
+
}
|
|
162
|
+
finally {
|
|
163
|
+
closeSync(fd);
|
|
164
|
+
}
|
|
165
|
+
return;
|
|
166
|
+
}
|
|
167
|
+
if (isUnsafeFilePath(path))
|
|
168
|
+
return;
|
|
169
|
+
writeFileSync(path, content, { mode: FILE_MODE });
|
|
170
|
+
}
|
|
171
|
+
/**
|
|
172
|
+
* Create a real directory at `path` if nothing is there yet. Refuses —
|
|
173
|
+
* creates nothing — when something unsafe (a symlink, a file) already
|
|
174
|
+
* occupies that path.
|
|
175
|
+
*/
|
|
176
|
+
function ensureRealDir(path) {
|
|
177
|
+
if (isUnsafePath(path))
|
|
178
|
+
return false;
|
|
179
|
+
mkdirSync(path, { recursive: true, mode: DIR_MODE });
|
|
180
|
+
return true;
|
|
181
|
+
}
|
|
182
|
+
/**
|
|
183
|
+
* Ensure a real key directory exists for `key` under `dir`, and bump its
|
|
184
|
+
* own mtime to `now` on every call — not only when it is first created —
|
|
185
|
+
* so a conversation written to every day never looks idle to `pruneStale`.
|
|
186
|
+
* Refuses — creates and touches nothing — when something other than a real
|
|
187
|
+
* directory already sits at that path (see the module doc).
|
|
188
|
+
*/
|
|
189
|
+
function ensureLiveKeyDir(key, dir, now) {
|
|
190
|
+
const kd = keyDir(key, dir);
|
|
191
|
+
if (!ensureRealDir(kd))
|
|
192
|
+
return null;
|
|
193
|
+
try {
|
|
194
|
+
const t = new Date(now);
|
|
195
|
+
utimesSync(kd, t, t);
|
|
196
|
+
}
|
|
197
|
+
catch {
|
|
198
|
+
// Best-effort — the directory still exists and is usable either way.
|
|
199
|
+
}
|
|
200
|
+
return kd;
|
|
201
|
+
}
|
|
202
|
+
/**
|
|
203
|
+
* Stash a rule body for a conversation that cannot see it right now
|
|
204
|
+
* (Antigravity's PreToolUse `allow` never reaches the model). Keeps the 20
|
|
205
|
+
* newest stashes; older ones are dropped silently.
|
|
206
|
+
*/
|
|
207
|
+
export function stashContext(key, body, dir = antigravityStateDir()) {
|
|
208
|
+
let tmpPath;
|
|
209
|
+
try {
|
|
210
|
+
const now = Date.now();
|
|
211
|
+
const kd = ensureLiveKeyDir(key, dir, now);
|
|
212
|
+
if (!kd)
|
|
213
|
+
return;
|
|
214
|
+
const contextDir = join(kd, 'context');
|
|
215
|
+
if (!ensureRealDir(contextDir))
|
|
216
|
+
return;
|
|
217
|
+
const suffix = randomBytes(4).toString('hex');
|
|
218
|
+
tmpPath = join(contextDir, `.${now}-${suffix}.tmp`);
|
|
219
|
+
// O_EXCL: two concurrent stashes never collide on the same scratch name.
|
|
220
|
+
writeFileSync(tmpPath, body, { mode: FILE_MODE, flag: 'wx' });
|
|
221
|
+
const finalPath = join(contextDir, `${now}-${suffix}.md`);
|
|
222
|
+
renameSync(tmpPath, finalPath); // atomic on the same filesystem
|
|
223
|
+
tmpPath = undefined; // renamed away — nothing left to clean up on error
|
|
224
|
+
const kept = readdirSync(contextDir).filter(isFinalStashName).sort();
|
|
225
|
+
const excess = kept.length - MAX_STASHED_CONTEXTS;
|
|
226
|
+
if (excess > 0) {
|
|
227
|
+
for (const stale of kept.slice(0, excess)) {
|
|
228
|
+
try {
|
|
229
|
+
unlinkSync(join(contextDir, stale));
|
|
230
|
+
}
|
|
231
|
+
catch {
|
|
232
|
+
// Best-effort — a concurrent drain may have removed it already.
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
}
|
|
237
|
+
catch {
|
|
238
|
+
if (tmpPath) {
|
|
239
|
+
try {
|
|
240
|
+
unlinkSync(tmpPath);
|
|
241
|
+
}
|
|
242
|
+
catch {
|
|
243
|
+
// Best-effort.
|
|
244
|
+
}
|
|
245
|
+
}
|
|
246
|
+
}
|
|
247
|
+
}
|
|
248
|
+
/**
|
|
249
|
+
* Every stashed body for a conversation, oldest first, each file deleted as
|
|
250
|
+
* it is read. A body stashed more than once (two PreToolUse runs stashing
|
|
251
|
+
* the same unseen rule) is returned only once. A `.tmp` scratch file still
|
|
252
|
+
* mid-write (or left behind by a crashed stash) is neither read nor
|
|
253
|
+
* deleted — only a final `*.md` name is ever touched.
|
|
254
|
+
*/
|
|
255
|
+
export function drainContext(key, dir = antigravityStateDir()) {
|
|
256
|
+
try {
|
|
257
|
+
const kd = keyDir(key, dir);
|
|
258
|
+
if (isUnsafePath(kd))
|
|
259
|
+
return [];
|
|
260
|
+
const contextDir = join(kd, 'context');
|
|
261
|
+
if (isUnsafePath(contextDir))
|
|
262
|
+
return [];
|
|
263
|
+
const entries = readdirSync(contextDir).filter(isFinalStashName).sort();
|
|
264
|
+
const seen = new Set();
|
|
265
|
+
const bodies = [];
|
|
266
|
+
for (const name of entries) {
|
|
267
|
+
const filePath = join(contextDir, name);
|
|
268
|
+
try {
|
|
269
|
+
const body = readFileSync(filePath, 'utf8');
|
|
270
|
+
if (!seen.has(body)) {
|
|
271
|
+
seen.add(body);
|
|
272
|
+
bodies.push(body);
|
|
273
|
+
}
|
|
274
|
+
}
|
|
275
|
+
catch {
|
|
276
|
+
// Unreadable / half-written — skip the body, still remove the file.
|
|
277
|
+
}
|
|
278
|
+
try {
|
|
279
|
+
unlinkSync(filePath);
|
|
280
|
+
}
|
|
281
|
+
catch {
|
|
282
|
+
// Best-effort.
|
|
283
|
+
}
|
|
284
|
+
}
|
|
285
|
+
return bodies;
|
|
286
|
+
}
|
|
287
|
+
catch {
|
|
288
|
+
return [];
|
|
289
|
+
}
|
|
290
|
+
}
|
|
291
|
+
/** Record that a conversation's PreToolUse run saw `file` edited. */
|
|
292
|
+
export function recordEdit(key, file, dir = antigravityStateDir()) {
|
|
293
|
+
try {
|
|
294
|
+
const now = Date.now();
|
|
295
|
+
const kd = ensureLiveKeyDir(key, dir, now);
|
|
296
|
+
if (!kd)
|
|
297
|
+
return;
|
|
298
|
+
appendLedgerLine(join(kd, 'edits.jsonl'), JSON.stringify({ f: file }) + '\n');
|
|
299
|
+
}
|
|
300
|
+
catch {
|
|
301
|
+
// Best-effort.
|
|
302
|
+
}
|
|
303
|
+
}
|
|
304
|
+
/** The edits recorded for a conversation: how many, and which distinct files, in order. */
|
|
305
|
+
export function readEdits(key, dir = antigravityStateDir()) {
|
|
306
|
+
try {
|
|
307
|
+
const kd = keyDir(key, dir);
|
|
308
|
+
if (isUnsafePath(kd))
|
|
309
|
+
return { count: 0, files: [] };
|
|
310
|
+
const editsPath = join(kd, 'edits.jsonl');
|
|
311
|
+
// A symlinked edits.jsonl — a fixed name under a predictable key
|
|
312
|
+
// directory, no race needed — is treated as absent, never followed.
|
|
313
|
+
if (isUnsafeFilePath(editsPath))
|
|
314
|
+
return { count: 0, files: [] };
|
|
315
|
+
const content = readFileSync(editsPath, 'utf8');
|
|
316
|
+
let count = 0;
|
|
317
|
+
const files = [];
|
|
318
|
+
const seen = new Set();
|
|
319
|
+
for (const line of content.split('\n')) {
|
|
320
|
+
const trimmed = line.trim();
|
|
321
|
+
if (!trimmed)
|
|
322
|
+
continue;
|
|
323
|
+
let parsed;
|
|
324
|
+
try {
|
|
325
|
+
parsed = JSON.parse(trimmed);
|
|
326
|
+
}
|
|
327
|
+
catch {
|
|
328
|
+
continue; // Half-written line — skip it, not the rest of the ledger.
|
|
329
|
+
}
|
|
330
|
+
if (typeof parsed.f !== 'string')
|
|
331
|
+
continue;
|
|
332
|
+
count++;
|
|
333
|
+
if (!seen.has(parsed.f)) {
|
|
334
|
+
seen.add(parsed.f);
|
|
335
|
+
files.push(parsed.f);
|
|
336
|
+
}
|
|
337
|
+
}
|
|
338
|
+
return { count, files };
|
|
339
|
+
}
|
|
340
|
+
catch {
|
|
341
|
+
return { count: 0, files: [] };
|
|
342
|
+
}
|
|
343
|
+
}
|
|
344
|
+
/** Mark a conversation as reviewed (Task 13's end-of-session pass). */
|
|
345
|
+
export function markReviewed(key, dir = antigravityStateDir()) {
|
|
346
|
+
try {
|
|
347
|
+
const now = Date.now();
|
|
348
|
+
const kd = ensureLiveKeyDir(key, dir, now);
|
|
349
|
+
if (!kd)
|
|
350
|
+
return;
|
|
351
|
+
writeMarkerFile(join(kd, 'reviewed'), String(now));
|
|
352
|
+
}
|
|
353
|
+
catch {
|
|
354
|
+
// Best-effort.
|
|
355
|
+
}
|
|
356
|
+
}
|
|
357
|
+
/** Whether `markReviewed` already ran for this conversation. */
|
|
358
|
+
export function isReviewed(key, dir = antigravityStateDir()) {
|
|
359
|
+
try {
|
|
360
|
+
const kd = keyDir(key, dir);
|
|
361
|
+
if (isUnsafePath(kd))
|
|
362
|
+
return false;
|
|
363
|
+
// lstat, not exists/stat: a symlinked `reviewed` is treated as absent.
|
|
364
|
+
return lstatSync(join(kd, 'reviewed')).isFile();
|
|
365
|
+
}
|
|
366
|
+
catch {
|
|
367
|
+
return false;
|
|
368
|
+
}
|
|
369
|
+
}
|
|
370
|
+
/**
|
|
371
|
+
* Remove a conversation's whole state directory once it is older than
|
|
372
|
+
* `maxAgeMs` (default 7 days). Staleness is read with `lstatSync` on the
|
|
373
|
+
* entry itself: a `statSync` would follow a symlink an attacker planted
|
|
374
|
+
* under the state directory and judge staleness by whatever it points to
|
|
375
|
+
* (fresh, dangling, or anything else) instead of by the link's own age.
|
|
376
|
+
* Removing a stale entry that happens to be a symlink removes only the
|
|
377
|
+
* link (`rmSync` never descends into a symlink's target), never whatever
|
|
378
|
+
* it points to.
|
|
379
|
+
*/
|
|
380
|
+
export function pruneStale(dir = antigravityStateDir(), now = Date.now(), maxAgeMs = DEFAULT_MAX_AGE_MS) {
|
|
381
|
+
try {
|
|
382
|
+
const entries = readdirSync(dir);
|
|
383
|
+
for (const name of entries) {
|
|
384
|
+
const entryPath = join(dir, name);
|
|
385
|
+
try {
|
|
386
|
+
const { mtimeMs } = lstatSync(entryPath);
|
|
387
|
+
if (now - mtimeMs > maxAgeMs) {
|
|
388
|
+
rmSync(entryPath, { recursive: true, force: true });
|
|
389
|
+
}
|
|
390
|
+
}
|
|
391
|
+
catch {
|
|
392
|
+
// Best-effort — skip what can't be stat'd or removed.
|
|
393
|
+
}
|
|
394
|
+
}
|
|
395
|
+
}
|
|
396
|
+
catch {
|
|
397
|
+
// Best-effort — e.g. the state dir does not exist yet.
|
|
398
|
+
}
|
|
399
|
+
}
|
|
400
|
+
//# sourceMappingURL=antigravity-session.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"antigravity-session.js","sourceRoot":"","sources":["../../../src/hooks/runtime/antigravity-session.ts"],"names":[],"mappings":"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"}
|