spect8-vault 0.0.0-stage → 0.1.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 +23 -2
- package/bin/bridge.mjs +76 -0
- package/bin/ctx.js +102034 -0
- package/bin/ctxd.js +143657 -0
- package/bin/spect8.mjs +76 -0
- package/bin/statusline.js +76 -0
- package/package.json +34 -4
- package/prompts/condense.md +10 -0
- package/prompts/fold.md +25 -0
- package/prompts/judge.md +10 -0
- package/prompts/probe-answer.md +2 -0
- package/prompts/probe-fact.md +7 -0
- package/prompts/probe-generate.md +6 -0
- package/prompts/probe-stale.md +8 -0
- package/prompts/redistill.md +9 -0
- package/prompts/reverify-line.md +15 -0
- package/prompts/route-classify.md +7 -0
- package/prompts/topic-propose.md +5 -0
- package/ui/assets/index-B7x_AGvd.css +2 -0
- package/ui/assets/index-DlL849S0.js +16 -0
- package/ui/index.html +18 -0
package/README.md
CHANGED
|
@@ -1,3 +1,24 @@
|
|
|
1
|
-
#
|
|
1
|
+
# Spect8 + Vault
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
Publication candidate — not yet published to npm. Requires Node 22.12 or newer.
|
|
4
|
+
|
|
5
|
+
After publication:
|
|
6
|
+
|
|
7
|
+
```sh
|
|
8
|
+
npm install -g spect8-vault
|
|
9
|
+
spect8-vault setup
|
|
10
|
+
```
|
|
11
|
+
|
|
12
|
+
Setup runs Spect8's existing browser sign-in and IDE configuration, starts the bundled Vault engine, and asks for a device credential from https://www.spect8ai.tech/vault/workspace. Credentials stay in your local `.ctxlayer/spect8-vault.json` file. Do not share this file. Windows users should restrict access to their user profile; POSIX file permissions alone do not set Windows ACLs.
|
|
13
|
+
|
|
14
|
+
Start a supported coding agent through the engine:
|
|
15
|
+
|
|
16
|
+
```sh
|
|
17
|
+
spect8-vault run claude
|
|
18
|
+
```
|
|
19
|
+
|
|
20
|
+
In a second terminal, run `spect8-vault sync`, pick a session, and confirm uploading. Stop with Ctrl+C. Sync is opt-in and runs in the foreground. Revoke the device in the workspace to remove its cloud access. The coding agent and its provider credentials must already be installed/configured. Use `spect8-vault doctor` for diagnostics and `spect8-vault engine --help` for advanced engine commands.
|
|
21
|
+
|
|
22
|
+
## Maintainers
|
|
23
|
+
|
|
24
|
+
Run `pnpm build`, then `node scripts/release/spect8.mjs` from the repository root. Run `npm pack` in `release/out/npm` to produce an installable archive. Validate the archive on supported operating systems before publishing. Confirm npm ownership of `spect8-vault` and availability of dependency `spect8-mcp@0.7.1`, then publish the reviewed archive. This package does not enable automatic background uploading or the librarian.
|
package/bin/bridge.mjs
ADDED
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
import { readFile } from 'node:fs/promises';
|
|
2
|
+
import { homedir } from 'node:os';
|
|
3
|
+
import { join } from 'node:path';
|
|
4
|
+
const cloud = new URL(process.env.VAULT_CLOUD_URL || '');
|
|
5
|
+
if (cloud.protocol !== 'https:' && !['127.0.0.1', 'localhost'].includes(cloud.hostname))
|
|
6
|
+
throw new Error('Cloud URL must use HTTPS');
|
|
7
|
+
const key = process.env.VAULT_DEVICE_KEY;
|
|
8
|
+
const thread = process.env.VAULT_THREAD_ID;
|
|
9
|
+
if (!key || !thread)
|
|
10
|
+
throw new Error(
|
|
11
|
+
'VAULT_DEVICE_KEY and VAULT_THREAD_ID required. Only this explicitly selected thread is uploaded.',
|
|
12
|
+
);
|
|
13
|
+
if (process.env.VAULT_UPLOAD_CONTEXT !== '1')
|
|
14
|
+
throw new Error('Set VAULT_UPLOAD_CONTEXT=1 to consent to uploading this thread context to Spect8.');
|
|
15
|
+
async function request(base, path, token, method = 'GET', body) {
|
|
16
|
+
const destination = new URL(path, base);
|
|
17
|
+
if (path.startsWith('/v1/') && new URL(base).pathname !== '/')
|
|
18
|
+
destination.pathname =
|
|
19
|
+
new URL(base).pathname.replace(/\/$/, '') + destination.pathname.replace(/^\/v1/, '');
|
|
20
|
+
const r = await fetch(destination, {
|
|
21
|
+
method,
|
|
22
|
+
redirect: 'error',
|
|
23
|
+
headers: { Authorization: `Bearer ${token}`, ...(body ? { 'Content-Type': 'application/json' } : {}) },
|
|
24
|
+
...(body ? { body: JSON.stringify(body) } : {}),
|
|
25
|
+
signal: AbortSignal.timeout(20000),
|
|
26
|
+
});
|
|
27
|
+
if (!r.ok) throw new Error(`Request failed (${r.status})`);
|
|
28
|
+
return r.status === 204 ? {} : r.json();
|
|
29
|
+
}
|
|
30
|
+
console.log('Spect8 bridge active for selected thread. Stop with Ctrl+C.');
|
|
31
|
+
let stop = false;
|
|
32
|
+
process.on('SIGINT', () => {
|
|
33
|
+
stop = true;
|
|
34
|
+
});
|
|
35
|
+
process.on('SIGTERM', () => {
|
|
36
|
+
stop = true;
|
|
37
|
+
});
|
|
38
|
+
while (!stop) {
|
|
39
|
+
try {
|
|
40
|
+
const daemon = JSON.parse(
|
|
41
|
+
await readFile(join(process.env.CTX_HOME || join(homedir(), '.ctxlayer'), 'daemon.json'), 'utf8'),
|
|
42
|
+
);
|
|
43
|
+
const base = `http://127.0.0.1:${daemon.port}`;
|
|
44
|
+
const prefix = `/api/threads/${encodeURIComponent(thread)}`;
|
|
45
|
+
const [window, conversation, pending, projected] = await Promise.all(
|
|
46
|
+
['window', 'conversation', 'pending', 'window?view=projected'].map((p) =>
|
|
47
|
+
request(base, `${prefix}/${p}`, daemon.token),
|
|
48
|
+
),
|
|
49
|
+
);
|
|
50
|
+
await request(cloud, '/v1/bridge/snapshot', key, 'PUT', {
|
|
51
|
+
local_id: thread,
|
|
52
|
+
title: thread,
|
|
53
|
+
snapshot: { window, conversation, pending, projected },
|
|
54
|
+
});
|
|
55
|
+
const command = await request(cloud, '/v1/bridge/claim', key, 'POST', { local_id: thread });
|
|
56
|
+
if (command) {
|
|
57
|
+
let status = 'failed',
|
|
58
|
+
result = { message: 'Command belongs to another selected thread' };
|
|
59
|
+
if (command.local_id === thread && ['note', 'apply', 'undo', 'pending'].includes(command.action)) {
|
|
60
|
+
try {
|
|
61
|
+
result = await request(base, `${prefix}/${command.action}`, daemon.token, 'POST', command.payload);
|
|
62
|
+
status = 'done';
|
|
63
|
+
} catch (e) {
|
|
64
|
+
result = { message: e.message };
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
await request(cloud, `/v1/bridge/commands/${command.id}/result`, key, 'POST', {
|
|
68
|
+
status,
|
|
69
|
+
result: result || {},
|
|
70
|
+
});
|
|
71
|
+
}
|
|
72
|
+
} catch (e) {
|
|
73
|
+
console.error(e.message);
|
|
74
|
+
}
|
|
75
|
+
if (!stop) await new Promise((r) => setTimeout(r, 3000));
|
|
76
|
+
}
|