@furkankoykiran/contextify-cli 0.4.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/batcher.d.ts +36 -0
- package/dist/batcher.d.ts.map +1 -0
- package/dist/batcher.js +94 -0
- package/dist/batcher.js.map +1 -0
- package/dist/commands/hooks.d.ts +32 -0
- package/dist/commands/hooks.d.ts.map +1 -0
- package/dist/commands/hooks.js +253 -0
- package/dist/commands/hooks.js.map +1 -0
- package/dist/commands/init.d.ts +9 -0
- package/dist/commands/init.d.ts.map +1 -0
- package/dist/commands/init.js +49 -0
- package/dist/commands/init.js.map +1 -0
- package/dist/commands/install-hooks.d.ts +42 -0
- package/dist/commands/install-hooks.d.ts.map +1 -0
- package/dist/commands/install-hooks.js +162 -0
- package/dist/commands/install-hooks.js.map +1 -0
- package/dist/commands/install.d.ts +53 -0
- package/dist/commands/install.d.ts.map +1 -0
- package/dist/commands/install.js +129 -0
- package/dist/commands/install.js.map +1 -0
- package/dist/commands/login.d.ts +9 -0
- package/dist/commands/login.d.ts.map +1 -0
- package/dist/commands/login.js +36 -0
- package/dist/commands/login.js.map +1 -0
- package/dist/commands/prompt.d.ts +17 -0
- package/dist/commands/prompt.d.ts.map +1 -0
- package/dist/commands/prompt.js +141 -0
- package/dist/commands/prompt.js.map +1 -0
- package/dist/commands/ship.d.ts +6 -0
- package/dist/commands/ship.d.ts.map +1 -0
- package/dist/commands/ship.js +20 -0
- package/dist/commands/ship.js.map +1 -0
- package/dist/commands/wrap.d.ts +10 -0
- package/dist/commands/wrap.d.ts.map +1 -0
- package/dist/commands/wrap.js +83 -0
- package/dist/commands/wrap.js.map +1 -0
- package/dist/config.d.ts +16 -0
- package/dist/config.d.ts.map +1 -0
- package/dist/config.js +84 -0
- package/dist/config.js.map +1 -0
- package/dist/credentials.d.ts +34 -0
- package/dist/credentials.d.ts.map +1 -0
- package/dist/credentials.js +68 -0
- package/dist/credentials.js.map +1 -0
- package/dist/identity.d.ts +42 -0
- package/dist/identity.d.ts.map +1 -0
- package/dist/identity.js +201 -0
- package/dist/identity.js.map +1 -0
- package/dist/index.d.ts +9 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +0 -0
- package/dist/index.js.map +1 -0
- package/dist/shipper.d.ts +49 -0
- package/dist/shipper.d.ts.map +1 -0
- package/dist/shipper.js +110 -0
- package/dist/shipper.js.map +1 -0
- package/dist/transcript.d.ts +52 -0
- package/dist/transcript.d.ts.map +1 -0
- package/dist/transcript.js +216 -0
- package/dist/transcript.js.map +1 -0
- package/package.json +69 -0
- package/src/hooks/session-end.sh +5 -0
- package/src/hooks/session-start.sh +5 -0
- package/src/hooks/stop.sh +5 -0
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
import { type ResolvedCredentials } from './credentials.js';
|
|
2
|
+
export interface Batch {
|
|
3
|
+
readonly projectId: string;
|
|
4
|
+
readonly projectName?: string;
|
|
5
|
+
readonly sessionId: string;
|
|
6
|
+
readonly payload: string;
|
|
7
|
+
/**
|
|
8
|
+
* Origin discriminator. Omitted by the legacy wrap path; the API
|
|
9
|
+
* defaults missing values to 'terminal' so old callers keep working.
|
|
10
|
+
*/
|
|
11
|
+
readonly source?: 'terminal' | 'claude-code';
|
|
12
|
+
}
|
|
13
|
+
export interface ShipOptions {
|
|
14
|
+
readonly serverUrl: string;
|
|
15
|
+
readonly cwd: string;
|
|
16
|
+
readonly fetchImpl?: typeof fetch;
|
|
17
|
+
readonly timeoutMs?: number;
|
|
18
|
+
/** When true, skip the network attempt entirely and spool. Useful for tests. */
|
|
19
|
+
readonly forceSpool?: boolean;
|
|
20
|
+
/**
|
|
21
|
+
* Optional explicit credentials. Defaults to resolving via env then
|
|
22
|
+
* `~/.contextify/credentials.json`. When null, the request goes
|
|
23
|
+
* unauthenticated (server falls back to LEGACY_TENANT_ID in dev).
|
|
24
|
+
* Tests can override this to assert the auth header is present.
|
|
25
|
+
*/
|
|
26
|
+
readonly credentials?: ResolvedCredentials | null;
|
|
27
|
+
}
|
|
28
|
+
export interface ShipResult {
|
|
29
|
+
readonly status: 'sent' | 'spooled' | 'error';
|
|
30
|
+
readonly statusCode?: number;
|
|
31
|
+
readonly spoolPath?: string;
|
|
32
|
+
readonly error?: string;
|
|
33
|
+
}
|
|
34
|
+
export declare const SPOOL_DIR = ".contextify/spool";
|
|
35
|
+
export declare function shipBatch(batch: Batch, opts: ShipOptions): Promise<ShipResult>;
|
|
36
|
+
export declare function spoolBatch(batch: Batch, cwd: string, reason: string): Promise<ShipResult>;
|
|
37
|
+
export interface FlushOptions {
|
|
38
|
+
readonly serverUrl: string;
|
|
39
|
+
readonly cwd: string;
|
|
40
|
+
readonly fetchImpl?: typeof fetch;
|
|
41
|
+
readonly timeoutMs?: number;
|
|
42
|
+
}
|
|
43
|
+
export interface FlushResult {
|
|
44
|
+
readonly attempted: number;
|
|
45
|
+
readonly sent: number;
|
|
46
|
+
readonly remaining: number;
|
|
47
|
+
}
|
|
48
|
+
export declare function flushSpool(opts: FlushOptions): Promise<FlushResult>;
|
|
49
|
+
//# sourceMappingURL=shipper.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"shipper.d.ts","sourceRoot":"","sources":["../src/shipper.ts"],"names":[],"mappings":"AAeA,OAAO,EAAiB,KAAK,mBAAmB,EAAE,MAAM,kBAAkB,CAAC;AAE3E,MAAM,WAAW,KAAK;IACpB,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,WAAW,CAAC,EAAE,MAAM,CAAC;IAC9B,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB;;;OAGG;IACH,QAAQ,CAAC,MAAM,CAAC,EAAE,UAAU,GAAG,aAAa,CAAC;CAC9C;AAED,MAAM,WAAW,WAAW;IAC1B,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IACrB,QAAQ,CAAC,SAAS,CAAC,EAAE,OAAO,KAAK,CAAC;IAClC,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;IAC5B,gFAAgF;IAChF,QAAQ,CAAC,UAAU,CAAC,EAAE,OAAO,CAAC;IAC9B;;;;;OAKG;IACH,QAAQ,CAAC,WAAW,CAAC,EAAE,mBAAmB,GAAG,IAAI,CAAC;CACnD;AAED,MAAM,WAAW,UAAU;IACzB,QAAQ,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,GAAG,OAAO,CAAC;IAC9C,QAAQ,CAAC,UAAU,CAAC,EAAE,MAAM,CAAC;IAC7B,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,KAAK,CAAC,EAAE,MAAM,CAAC;CACzB;AAED,eAAO,MAAM,SAAS,sBAAsB,CAAC;AAE7C,wBAAsB,SAAS,CAAC,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE,WAAW,GAAG,OAAO,CAAC,UAAU,CAAC,CAqCpF;AAED,wBAAsB,UAAU,CAAC,KAAK,EAAE,KAAK,EAAE,GAAG,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,UAAU,CAAC,CAc/F;AAED,MAAM,WAAW,YAAY;IAC3B,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IACrB,QAAQ,CAAC,SAAS,CAAC,EAAE,OAAO,KAAK,CAAC;IAClC,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;CAC7B;AAED,MAAM,WAAW,WAAW;IAC1B,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;CAC5B;AAED,wBAAsB,UAAU,CAAC,IAAI,EAAE,YAAY,GAAG,OAAO,CAAC,WAAW,CAAC,CAiCzE"}
|
package/dist/shipper.js
ADDED
|
@@ -0,0 +1,110 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Webhook shipper with disk-spool fallback.
|
|
3
|
+
*
|
|
4
|
+
* The shipper takes a batch envelope and POSTs it gzip-compressed to the
|
|
5
|
+
* server's /api/telemetry/ingest endpoint. If the server is unreachable
|
|
6
|
+
* or returns a non-2xx, the batch is written to `<cwd>/.contextify/spool/`
|
|
7
|
+
* so a later `contextify ship --once` can flush it.
|
|
8
|
+
*
|
|
9
|
+
* The CLI must never block the user's terminal — so all error handling
|
|
10
|
+
* is silent (logs go to stderr only with --verbose, not implemented yet).
|
|
11
|
+
*/
|
|
12
|
+
import { existsSync } from 'node:fs';
|
|
13
|
+
import { mkdir, readdir, readFile, rename, unlink, writeFile } from 'node:fs/promises';
|
|
14
|
+
import { join } from 'node:path';
|
|
15
|
+
import { gzipSync } from 'node:zlib';
|
|
16
|
+
import { resolveApiKey } from './credentials.js';
|
|
17
|
+
export const SPOOL_DIR = '.contextify/spool';
|
|
18
|
+
export async function shipBatch(batch, opts) {
|
|
19
|
+
if (opts.forceSpool) {
|
|
20
|
+
return spoolBatch(batch, opts.cwd, 'forceSpool');
|
|
21
|
+
}
|
|
22
|
+
const fetchImpl = opts.fetchImpl ?? fetch;
|
|
23
|
+
const url = new URL('/api/telemetry/ingest', opts.serverUrl).toString();
|
|
24
|
+
const body = gzipSync(Buffer.from(JSON.stringify(batch), 'utf8'));
|
|
25
|
+
const ctrl = new AbortController();
|
|
26
|
+
const timeout = setTimeout(() => ctrl.abort(), opts.timeoutMs ?? 10_000);
|
|
27
|
+
try {
|
|
28
|
+
// Resolve credentials lazily so call sites can inject test fixtures
|
|
29
|
+
// via `opts.credentials`. `undefined` triggers the default lookup;
|
|
30
|
+
// `null` means "send no Authorization header" (explicit unauth).
|
|
31
|
+
const creds = opts.credentials === undefined ? resolveApiKey() : opts.credentials;
|
|
32
|
+
const headers = {
|
|
33
|
+
'content-type': 'application/json',
|
|
34
|
+
'content-encoding': 'gzip',
|
|
35
|
+
};
|
|
36
|
+
if (creds) {
|
|
37
|
+
headers.authorization = `Bearer ${creds.apiKey}`;
|
|
38
|
+
}
|
|
39
|
+
const res = await fetchImpl(url, {
|
|
40
|
+
method: 'POST',
|
|
41
|
+
headers,
|
|
42
|
+
body,
|
|
43
|
+
signal: ctrl.signal,
|
|
44
|
+
});
|
|
45
|
+
if (!res.ok) {
|
|
46
|
+
return spoolBatch(batch, opts.cwd, `HTTP ${res.status}`);
|
|
47
|
+
}
|
|
48
|
+
return { status: 'sent', statusCode: res.status };
|
|
49
|
+
}
|
|
50
|
+
catch (err) {
|
|
51
|
+
return spoolBatch(batch, opts.cwd, err.message);
|
|
52
|
+
}
|
|
53
|
+
finally {
|
|
54
|
+
clearTimeout(timeout);
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
export async function spoolBatch(batch, cwd, reason) {
|
|
58
|
+
try {
|
|
59
|
+
const dir = join(cwd, SPOOL_DIR);
|
|
60
|
+
if (!existsSync(dir))
|
|
61
|
+
await mkdir(dir, { recursive: true });
|
|
62
|
+
const stamp = `${Date.now()}-${Math.random().toString(36).slice(2, 8)}`;
|
|
63
|
+
const tmp = join(dir, `${stamp}.json.gz.tmp`);
|
|
64
|
+
const final = join(dir, `${stamp}.json.gz`);
|
|
65
|
+
const body = gzipSync(Buffer.from(JSON.stringify(batch), 'utf8'));
|
|
66
|
+
await writeFile(tmp, body);
|
|
67
|
+
await rename(tmp, final);
|
|
68
|
+
return { status: 'spooled', spoolPath: final, error: reason };
|
|
69
|
+
}
|
|
70
|
+
catch (err) {
|
|
71
|
+
return { status: 'error', error: err.message };
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
export async function flushSpool(opts) {
|
|
75
|
+
const dir = join(opts.cwd, SPOOL_DIR);
|
|
76
|
+
if (!existsSync(dir))
|
|
77
|
+
return { attempted: 0, sent: 0, remaining: 0 };
|
|
78
|
+
const files = (await readdir(dir)).filter((f) => f.endsWith('.json.gz'));
|
|
79
|
+
let sent = 0;
|
|
80
|
+
for (const file of files) {
|
|
81
|
+
const full = join(dir, file);
|
|
82
|
+
const raw = await readFile(full);
|
|
83
|
+
let batch;
|
|
84
|
+
try {
|
|
85
|
+
// The spool stores gzipped JSON. We could re-ship the raw gzip body
|
|
86
|
+
// directly but that complicates the request — decompress and let
|
|
87
|
+
// shipBatch re-compress so the wire shape stays consistent.
|
|
88
|
+
const { gunzipSync } = await import('node:zlib');
|
|
89
|
+
batch = JSON.parse(gunzipSync(raw).toString('utf8'));
|
|
90
|
+
}
|
|
91
|
+
catch {
|
|
92
|
+
// Corrupt spool entry — drop it so we don't loop forever.
|
|
93
|
+
await unlink(full).catch(() => { });
|
|
94
|
+
continue;
|
|
95
|
+
}
|
|
96
|
+
const result = await shipBatch(batch, {
|
|
97
|
+
serverUrl: opts.serverUrl,
|
|
98
|
+
cwd: opts.cwd,
|
|
99
|
+
fetchImpl: opts.fetchImpl,
|
|
100
|
+
timeoutMs: opts.timeoutMs,
|
|
101
|
+
});
|
|
102
|
+
if (result.status === 'sent') {
|
|
103
|
+
await unlink(full).catch(() => { });
|
|
104
|
+
sent += 1;
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
const remaining = (await readdir(dir)).filter((f) => f.endsWith('.json.gz')).length;
|
|
108
|
+
return { attempted: files.length, sent, remaining };
|
|
109
|
+
}
|
|
110
|
+
//# sourceMappingURL=shipper.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"shipper.js","sourceRoot":"","sources":["../src/shipper.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Transcript parser.
|
|
3
|
+
*
|
|
4
|
+
* Reads a Claude Code session JSONL (one JSON object per line) and extracts
|
|
5
|
+
* the most recent completed user → assistant turn, including:
|
|
6
|
+
* - the user's text prompt
|
|
7
|
+
* - the assistant's final text response
|
|
8
|
+
* - the sequence of *actions* the assistant executed between them
|
|
9
|
+
* (Bash commands, file Writes/Edits/MultiEdits, WebFetches)
|
|
10
|
+
*
|
|
11
|
+
* Read-only tool calls (Read, Grep, Glob, LS, etc.) are dropped — they're
|
|
12
|
+
* introspection, not durable insight, and they explode payload size for no
|
|
13
|
+
* extraction value. tool_result blocks are likewise dropped (the *action*
|
|
14
|
+
* is what's durable; the output is noise the LLM doesn't need).
|
|
15
|
+
*
|
|
16
|
+
* Pure with respect to I/O: takes the raw JSONL text, returns a turn or null.
|
|
17
|
+
*/
|
|
18
|
+
/** Kinds of actions worth shipping to the worker. */
|
|
19
|
+
export type ActionKind = 'bash' | 'write' | 'edit' | 'multiedit' | 'webfetch';
|
|
20
|
+
export interface DialogAction {
|
|
21
|
+
readonly kind: ActionKind;
|
|
22
|
+
/** Single-line summary of the action (command string, file path, URL, etc.). */
|
|
23
|
+
readonly detail: string;
|
|
24
|
+
}
|
|
25
|
+
export interface DialogTurn {
|
|
26
|
+
readonly userText: string;
|
|
27
|
+
readonly assistantText: string;
|
|
28
|
+
readonly actions: ReadonlyArray<DialogAction>;
|
|
29
|
+
readonly userAt: string | null;
|
|
30
|
+
readonly assistantAt: string | null;
|
|
31
|
+
readonly cwd: string | null;
|
|
32
|
+
readonly transcriptUuid: string;
|
|
33
|
+
}
|
|
34
|
+
export interface ParseOptions {
|
|
35
|
+
/** Cap the assistant text at this many chars (head+tail). */
|
|
36
|
+
readonly maxAssistantChars?: number;
|
|
37
|
+
/** Cap the actions array length. Default 50. */
|
|
38
|
+
readonly maxActions?: number;
|
|
39
|
+
}
|
|
40
|
+
/**
|
|
41
|
+
* Find the latest completed user → assistant text turn in the transcript.
|
|
42
|
+
*
|
|
43
|
+
* Strategy:
|
|
44
|
+
* 1. Walk lines in order, indexing every text-bearing user message.
|
|
45
|
+
* 2. Track the latest assistant message that contains text.
|
|
46
|
+
* 3. Pair the latest-assistant with the closest preceding user-text.
|
|
47
|
+
* 4. Collect every action (Bash / Write / Edit / MultiEdit / WebFetch)
|
|
48
|
+
* from every line *between* those two anchors (inclusive of the
|
|
49
|
+
* assistant message's own tool_use blocks).
|
|
50
|
+
*/
|
|
51
|
+
export declare function parseLatestTurn(jsonl: string, options?: ParseOptions): DialogTurn | null;
|
|
52
|
+
//# sourceMappingURL=transcript.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"transcript.d.ts","sourceRoot":"","sources":["../src/transcript.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AAEH,qDAAqD;AACrD,MAAM,MAAM,UAAU,GAAG,MAAM,GAAG,OAAO,GAAG,MAAM,GAAG,WAAW,GAAG,UAAU,CAAC;AAE9E,MAAM,WAAW,YAAY;IAC3B,QAAQ,CAAC,IAAI,EAAE,UAAU,CAAC;IAC1B,gFAAgF;IAChF,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;CACzB;AAED,MAAM,WAAW,UAAU;IACzB,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAC;IAC/B,QAAQ,CAAC,OAAO,EAAE,aAAa,CAAC,YAAY,CAAC,CAAC;IAC9C,QAAQ,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC;IAC/B,QAAQ,CAAC,WAAW,EAAE,MAAM,GAAG,IAAI,CAAC;IACpC,QAAQ,CAAC,GAAG,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,QAAQ,CAAC,cAAc,EAAE,MAAM,CAAC;CACjC;AAmGD,MAAM,WAAW,YAAY;IAC3B,6DAA6D;IAC7D,QAAQ,CAAC,iBAAiB,CAAC,EAAE,MAAM,CAAC;IACpC,gDAAgD;IAChD,QAAQ,CAAC,UAAU,CAAC,EAAE,MAAM,CAAC;CAC9B;AAKD;;;;;;;;;;GAUG;AACH,wBAAgB,eAAe,CAAC,KAAK,EAAE,MAAM,EAAE,OAAO,GAAE,YAAiB,GAAG,UAAU,GAAG,IAAI,CAgG5F"}
|
|
@@ -0,0 +1,216 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Transcript parser.
|
|
3
|
+
*
|
|
4
|
+
* Reads a Claude Code session JSONL (one JSON object per line) and extracts
|
|
5
|
+
* the most recent completed user → assistant turn, including:
|
|
6
|
+
* - the user's text prompt
|
|
7
|
+
* - the assistant's final text response
|
|
8
|
+
* - the sequence of *actions* the assistant executed between them
|
|
9
|
+
* (Bash commands, file Writes/Edits/MultiEdits, WebFetches)
|
|
10
|
+
*
|
|
11
|
+
* Read-only tool calls (Read, Grep, Glob, LS, etc.) are dropped — they're
|
|
12
|
+
* introspection, not durable insight, and they explode payload size for no
|
|
13
|
+
* extraction value. tool_result blocks are likewise dropped (the *action*
|
|
14
|
+
* is what's durable; the output is noise the LLM doesn't need).
|
|
15
|
+
*
|
|
16
|
+
* Pure with respect to I/O: takes the raw JSONL text, returns a turn or null.
|
|
17
|
+
*/
|
|
18
|
+
/** Concatenate all `type:text` blocks; ignore tool_use/tool_result/etc. */
|
|
19
|
+
function extractText(message) {
|
|
20
|
+
if (!message)
|
|
21
|
+
return '';
|
|
22
|
+
const c = message.content;
|
|
23
|
+
if (typeof c === 'string')
|
|
24
|
+
return c;
|
|
25
|
+
if (!Array.isArray(c))
|
|
26
|
+
return '';
|
|
27
|
+
const parts = [];
|
|
28
|
+
for (const block of c) {
|
|
29
|
+
if (!block || typeof block !== 'object')
|
|
30
|
+
continue;
|
|
31
|
+
const b = block;
|
|
32
|
+
if (b.type === 'text' && typeof b.text === 'string' && b.text.trim().length > 0) {
|
|
33
|
+
parts.push(b.text);
|
|
34
|
+
}
|
|
35
|
+
}
|
|
36
|
+
return parts.join('\n\n');
|
|
37
|
+
}
|
|
38
|
+
const MAX_DETAIL_CHARS = 400;
|
|
39
|
+
/**
|
|
40
|
+
* Map a tool_use block to a DialogAction, or null if it's a read-only
|
|
41
|
+
* inspection tool we want to drop on the floor.
|
|
42
|
+
*/
|
|
43
|
+
function classifyToolUse(block) {
|
|
44
|
+
const name = typeof block.name === 'string' ? block.name : '';
|
|
45
|
+
const input = (block.input ?? {});
|
|
46
|
+
switch (name) {
|
|
47
|
+
case 'Bash': {
|
|
48
|
+
const cmd = typeof input.command === 'string' ? input.command : '';
|
|
49
|
+
if (cmd.trim().length === 0)
|
|
50
|
+
return null;
|
|
51
|
+
return { kind: 'bash', detail: truncateDetail(cmd) };
|
|
52
|
+
}
|
|
53
|
+
case 'Write': {
|
|
54
|
+
const fp = typeof input.file_path === 'string' ? input.file_path : '';
|
|
55
|
+
if (!fp)
|
|
56
|
+
return null;
|
|
57
|
+
return { kind: 'write', detail: truncateDetail(fp) };
|
|
58
|
+
}
|
|
59
|
+
case 'Edit': {
|
|
60
|
+
const fp = typeof input.file_path === 'string' ? input.file_path : '';
|
|
61
|
+
if (!fp)
|
|
62
|
+
return null;
|
|
63
|
+
return { kind: 'edit', detail: truncateDetail(fp) };
|
|
64
|
+
}
|
|
65
|
+
case 'MultiEdit': {
|
|
66
|
+
const fp = typeof input.file_path === 'string' ? input.file_path : '';
|
|
67
|
+
if (!fp)
|
|
68
|
+
return null;
|
|
69
|
+
return { kind: 'multiedit', detail: truncateDetail(fp) };
|
|
70
|
+
}
|
|
71
|
+
case 'WebFetch': {
|
|
72
|
+
const url = typeof input.url === 'string' ? input.url : '';
|
|
73
|
+
if (!url)
|
|
74
|
+
return null;
|
|
75
|
+
return { kind: 'webfetch', detail: truncateDetail(url) };
|
|
76
|
+
}
|
|
77
|
+
// Read-only inspections (Read, Grep, Glob, LS, NotebookRead, etc.) are
|
|
78
|
+
// skipped intentionally — high frequency, low signal.
|
|
79
|
+
default:
|
|
80
|
+
return null;
|
|
81
|
+
}
|
|
82
|
+
}
|
|
83
|
+
function truncateDetail(text) {
|
|
84
|
+
if (text.length <= MAX_DETAIL_CHARS)
|
|
85
|
+
return text;
|
|
86
|
+
return `${text.slice(0, MAX_DETAIL_CHARS - 3)}...`;
|
|
87
|
+
}
|
|
88
|
+
/** Collect tool_use actions from a single message body. */
|
|
89
|
+
function extractActions(message) {
|
|
90
|
+
if (!message)
|
|
91
|
+
return [];
|
|
92
|
+
const c = message.content;
|
|
93
|
+
if (!Array.isArray(c))
|
|
94
|
+
return [];
|
|
95
|
+
const out = [];
|
|
96
|
+
for (const block of c) {
|
|
97
|
+
if (!block || typeof block !== 'object')
|
|
98
|
+
continue;
|
|
99
|
+
const b = block;
|
|
100
|
+
if (b.type !== 'tool_use')
|
|
101
|
+
continue;
|
|
102
|
+
const action = classifyToolUse(b);
|
|
103
|
+
if (action)
|
|
104
|
+
out.push(action);
|
|
105
|
+
}
|
|
106
|
+
return out;
|
|
107
|
+
}
|
|
108
|
+
const DEFAULT_ASSISTANT_CAP = 50_000;
|
|
109
|
+
const DEFAULT_ACTIONS_CAP = 50;
|
|
110
|
+
/**
|
|
111
|
+
* Find the latest completed user → assistant text turn in the transcript.
|
|
112
|
+
*
|
|
113
|
+
* Strategy:
|
|
114
|
+
* 1. Walk lines in order, indexing every text-bearing user message.
|
|
115
|
+
* 2. Track the latest assistant message that contains text.
|
|
116
|
+
* 3. Pair the latest-assistant with the closest preceding user-text.
|
|
117
|
+
* 4. Collect every action (Bash / Write / Edit / MultiEdit / WebFetch)
|
|
118
|
+
* from every line *between* those two anchors (inclusive of the
|
|
119
|
+
* assistant message's own tool_use blocks).
|
|
120
|
+
*/
|
|
121
|
+
export function parseLatestTurn(jsonl, options = {}) {
|
|
122
|
+
const cap = options.maxAssistantChars ?? DEFAULT_ASSISTANT_CAP;
|
|
123
|
+
const actionsCap = options.maxActions ?? DEFAULT_ACTIONS_CAP;
|
|
124
|
+
const lines = jsonl.split(/\r?\n/);
|
|
125
|
+
const userTextAt = [];
|
|
126
|
+
let latestAssistant = null;
|
|
127
|
+
// First pass: find the turn anchors.
|
|
128
|
+
const parsedLines = new Array(lines.length).fill(null);
|
|
129
|
+
for (let index = 0; index < lines.length; index += 1) {
|
|
130
|
+
const raw = lines[index];
|
|
131
|
+
if (!raw)
|
|
132
|
+
continue;
|
|
133
|
+
let parsed;
|
|
134
|
+
try {
|
|
135
|
+
parsed = JSON.parse(raw);
|
|
136
|
+
}
|
|
137
|
+
catch {
|
|
138
|
+
continue;
|
|
139
|
+
}
|
|
140
|
+
if (!parsed || typeof parsed !== 'object')
|
|
141
|
+
continue;
|
|
142
|
+
parsedLines[index] = parsed;
|
|
143
|
+
const role = parsed.message?.role;
|
|
144
|
+
if (parsed.type === 'user' && role === 'user') {
|
|
145
|
+
const text = extractText(parsed.message);
|
|
146
|
+
if (text.trim().length > 0) {
|
|
147
|
+
userTextAt.push({ index, user: { text, ts: parsed.timestamp ?? null } });
|
|
148
|
+
}
|
|
149
|
+
continue;
|
|
150
|
+
}
|
|
151
|
+
if (parsed.type === 'assistant' && role === 'assistant') {
|
|
152
|
+
const text = extractText(parsed.message);
|
|
153
|
+
if (text.trim().length === 0)
|
|
154
|
+
continue;
|
|
155
|
+
const uuid = typeof parsed.uuid === 'string' ? parsed.uuid : '';
|
|
156
|
+
if (!uuid)
|
|
157
|
+
continue;
|
|
158
|
+
latestAssistant = {
|
|
159
|
+
uuid,
|
|
160
|
+
text,
|
|
161
|
+
ts: parsed.timestamp ?? null,
|
|
162
|
+
cwd: typeof parsed.cwd === 'string' ? parsed.cwd : null,
|
|
163
|
+
index,
|
|
164
|
+
};
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
if (!latestAssistant)
|
|
168
|
+
return null;
|
|
169
|
+
const finalAssistant = latestAssistant;
|
|
170
|
+
// Find the closest preceding user-text by file order.
|
|
171
|
+
let pairedUser = null;
|
|
172
|
+
let pairedUserIndex = -1;
|
|
173
|
+
for (let i = userTextAt.length - 1; i >= 0; i -= 1) {
|
|
174
|
+
if (userTextAt[i].index < finalAssistant.index) {
|
|
175
|
+
pairedUser = userTextAt[i].user;
|
|
176
|
+
pairedUserIndex = userTextAt[i].index;
|
|
177
|
+
break;
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
if (!pairedUser)
|
|
181
|
+
return null;
|
|
182
|
+
// Second pass: collect actions in the [pairedUserIndex+1, finalAssistant.index] window.
|
|
183
|
+
// We include the assistant line itself because tool_use can live alongside text
|
|
184
|
+
// in the same assistant message.
|
|
185
|
+
const actions = [];
|
|
186
|
+
for (let i = pairedUserIndex + 1; i <= finalAssistant.index; i += 1) {
|
|
187
|
+
const parsed = parsedLines[i];
|
|
188
|
+
if (!parsed)
|
|
189
|
+
continue;
|
|
190
|
+
if (parsed.message?.role !== 'assistant')
|
|
191
|
+
continue;
|
|
192
|
+
for (const action of extractActions(parsed.message)) {
|
|
193
|
+
if (actions.length >= actionsCap)
|
|
194
|
+
break;
|
|
195
|
+
actions.push(action);
|
|
196
|
+
}
|
|
197
|
+
if (actions.length >= actionsCap)
|
|
198
|
+
break;
|
|
199
|
+
}
|
|
200
|
+
return {
|
|
201
|
+
userText: pairedUser.text,
|
|
202
|
+
assistantText: truncate(finalAssistant.text, cap),
|
|
203
|
+
actions,
|
|
204
|
+
userAt: pairedUser.ts,
|
|
205
|
+
assistantAt: finalAssistant.ts,
|
|
206
|
+
cwd: finalAssistant.cwd,
|
|
207
|
+
transcriptUuid: finalAssistant.uuid,
|
|
208
|
+
};
|
|
209
|
+
}
|
|
210
|
+
function truncate(text, cap) {
|
|
211
|
+
if (text.length <= cap)
|
|
212
|
+
return text;
|
|
213
|
+
const half = Math.floor((cap - 64) / 2);
|
|
214
|
+
return `${text.slice(0, half)}\n... [truncated ${text.length - cap} chars] ...\n${text.slice(-half)}`;
|
|
215
|
+
}
|
|
216
|
+
//# sourceMappingURL=transcript.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"transcript.js","sourceRoot":"","sources":["../src/transcript.ts"],"names":[],"mappings":"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"}
|
package/package.json
ADDED
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@furkankoykiran/contextify-cli",
|
|
3
|
+
"version": "0.4.0",
|
|
4
|
+
"description": "Contextify telemetry CLI — shadows terminal sessions, ships logs to the webhook",
|
|
5
|
+
"homepage": "https://contextify.live",
|
|
6
|
+
"license": "MIT",
|
|
7
|
+
"publishConfig": {
|
|
8
|
+
"access": "public"
|
|
9
|
+
},
|
|
10
|
+
"type": "module",
|
|
11
|
+
"main": "./dist/index.js",
|
|
12
|
+
"bin": {
|
|
13
|
+
"contextify": "./dist/index.js"
|
|
14
|
+
},
|
|
15
|
+
"exports": {
|
|
16
|
+
".": {
|
|
17
|
+
"types": "./dist/index.d.ts",
|
|
18
|
+
"import": "./dist/index.js"
|
|
19
|
+
},
|
|
20
|
+
"./hooks": {
|
|
21
|
+
"types": "./dist/commands/hooks.d.ts",
|
|
22
|
+
"import": "./dist/commands/hooks.js"
|
|
23
|
+
},
|
|
24
|
+
"./transcript": {
|
|
25
|
+
"types": "./dist/transcript.d.ts",
|
|
26
|
+
"import": "./dist/transcript.js"
|
|
27
|
+
},
|
|
28
|
+
"./identity": {
|
|
29
|
+
"types": "./dist/identity.d.ts",
|
|
30
|
+
"import": "./dist/identity.js"
|
|
31
|
+
},
|
|
32
|
+
"./install-hooks": {
|
|
33
|
+
"types": "./dist/commands/install-hooks.d.ts",
|
|
34
|
+
"import": "./dist/commands/install-hooks.js"
|
|
35
|
+
},
|
|
36
|
+
"./install": {
|
|
37
|
+
"types": "./dist/commands/install.d.ts",
|
|
38
|
+
"import": "./dist/commands/install.js"
|
|
39
|
+
},
|
|
40
|
+
"./prompt": {
|
|
41
|
+
"types": "./dist/commands/prompt.d.ts",
|
|
42
|
+
"import": "./dist/commands/prompt.js"
|
|
43
|
+
}
|
|
44
|
+
},
|
|
45
|
+
"files": [
|
|
46
|
+
"dist",
|
|
47
|
+
"src/hooks"
|
|
48
|
+
],
|
|
49
|
+
"scripts": {
|
|
50
|
+
"build": "tsc -p tsconfig.json && chmod +x dist/index.js",
|
|
51
|
+
"start": "node ./dist/index.js",
|
|
52
|
+
"dev": "tsc -p tsconfig.json --watch",
|
|
53
|
+
"clean": "rm -rf dist .turbo *.tsbuildinfo",
|
|
54
|
+
"lint": "eslint src --max-warnings=0",
|
|
55
|
+
"typecheck": "tsc -p tsconfig.json --noEmit",
|
|
56
|
+
"test": "vitest run"
|
|
57
|
+
},
|
|
58
|
+
"devDependencies": {
|
|
59
|
+
"@contextify/eslint-config": "workspace:*",
|
|
60
|
+
"@contextify/tsconfig": "workspace:*",
|
|
61
|
+
"@types/node": "20.14.10",
|
|
62
|
+
"@typescript-eslint/eslint-plugin": "8.18.2",
|
|
63
|
+
"@typescript-eslint/parser": "8.18.2",
|
|
64
|
+
"eslint": "8.57.1",
|
|
65
|
+
"eslint-config-prettier": "9.1.0",
|
|
66
|
+
"typescript": "5.5.4",
|
|
67
|
+
"vitest": "2.1.8"
|
|
68
|
+
}
|
|
69
|
+
}
|