@tokenade/cli 0.8.10 → 0.8.12
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 +22 -19
- package/package.json +4 -2
- package/uninstall.js +76 -0
package/README.md
CHANGED
|
@@ -108,7 +108,7 @@ When reporting, please include your OS, `tokenade --version`, your coding agent,
|
|
|
108
108
|
| Command | What it does |
|
|
109
109
|
|---|---|
|
|
110
110
|
| `install` | Register Tokenade with your detected agent (hooks). Flags: `--only <agent>`, `--with-hook`, `--with-claude-md`, `--with-lsp-enforcement-hook`, `--with-brevity-skill`, `--dry-run`. |
|
|
111
|
-
| `uninstall
|
|
111
|
+
| `uninstall` | Remove the integration (restores wrapped MCP servers). `--dry-run` to preview. |
|
|
112
112
|
| `login` | Activate via browser device-flow — no key to type. |
|
|
113
113
|
| `activate <key>` | Link this machine to a tokenade.net license (free or paid) with a key. |
|
|
114
114
|
| `upgrade` | Self-update in place (aliases: `self-update`). `--on`/`--off` toggles the 24h background updater. |
|
|
@@ -141,24 +141,27 @@ When reporting, please include your OS, `tokenade --version`, your coding agent,
|
|
|
141
141
|
| Command | What it does |
|
|
142
142
|
|---|---|
|
|
143
143
|
| `wrap <cmd>` | Run a command through the auto-detected compactor (default for noisy commands). |
|
|
144
|
-
| `proxy <cmd...>` | Run a command and emit compressed output (logs savings). |
|
|
145
144
|
| `raw <cmd...>` | Run a command **without** compaction (aliases: `bypass`, `noproxy`). |
|
|
146
145
|
| `filter <cmd...>` | Filter stdin as if it were produced by `<cmd>`. |
|
|
147
146
|
| `execute --lang L --script CODE` | Sandboxed "think-in-code" runner (bash/python/node/jq/awk/ruby/perl) — returns only stdout, redacted + compacted, keeps raw data out of context. |
|
|
148
147
|
| `shell-init` | Print the shell proxy fragment for your shell (`--shell …`, `--all`). |
|
|
149
148
|
| `shellwrap` | TTY-aware alias target for csh/tcsh + cmd.exe. |
|
|
150
149
|
|
|
151
|
-
###
|
|
150
|
+
### Read & compact content
|
|
152
151
|
|
|
153
|
-
`
|
|
152
|
+
`read <file|->` is the content entry point: it auto-detects a blob's format and
|
|
153
|
+
dispatches to the right compactor. Point it at a file (or `-` for stdin) carrying
|
|
154
|
+
JSON, YAML, CSV/TSV, NDJSON, logs, unified diffs, stack traces, env dumps,
|
|
155
|
+
markdown, lockfiles, SQL, OpenAPI/GraphQL, build & CI output, and many more —
|
|
156
|
+
the format is detected automatically. Live command output is compacted the same
|
|
157
|
+
way through `wrap`.
|
|
154
158
|
|
|
155
|
-
|
|
|
159
|
+
| Command | What it does |
|
|
156
160
|
|---|---|
|
|
157
|
-
|
|
|
158
|
-
|
|
|
159
|
-
|
|
|
160
|
-
|
|
|
161
|
-
| **Web & docs** | `web` · `serp` (aliases `google`/`bing`/`ddg`) · `snapshot` · `stealth` · `curl` · `docs` · `pdf` · `notebook` |
|
|
161
|
+
| `read <file\|->` | Auto-detect a blob's format and compact it (**the content entry point**). |
|
|
162
|
+
| `web <file\|->` | Compact an HTML page → markdown (real web content). |
|
|
163
|
+
| `serp <file\|->` | Compact raw SERP HTML (aliases: `google`/`bing`/`ddg`). |
|
|
164
|
+
| `snapshot <file\|->` | Compact a Playwright accessibility-tree snapshot. |
|
|
162
165
|
|
|
163
166
|
**Your own compactors.** `add-compactor --file <rules.toml>` teaches Tokenade to fold output from a command it doesn't cover yet (alias `add-filter`); `add-compactor --list` shows the ones you've added, and `add-compactor --help` prints the file format. Filters shipped INSIDE a repo (`.tokenade/filters/`) apply only after you approve them once with `trust-filters` — a cloned project can't silently rewrite your outputs.
|
|
164
167
|
|
|
@@ -210,7 +213,7 @@ When reporting, please include your OS, `tokenade --version`, your coding agent,
|
|
|
210
213
|
|
|
211
214
|
## Examples & recipes
|
|
212
215
|
|
|
213
|
-
Real commands, real (trimmed) output — so both humans **and coding agents** know exactly what each command does and when to reach for it.
|
|
216
|
+
Real commands, real (trimmed) output — so both humans **and coding agents** know exactly what each command does and when to reach for it. `read` (and every format-aware entry point) reads a file **or `-` for stdin**, so you can pipe: `some-noisy-cmd | tokenade read -`.
|
|
214
217
|
|
|
215
218
|
### Setup & account
|
|
216
219
|
|
|
@@ -263,7 +266,7 @@ $ tokenade incompatibilities
|
|
|
263
266
|
[redundant] rtk
|
|
264
267
|
Output-filtering CLI proxy (filters/compresses bash output)
|
|
265
268
|
→ binary at ~/.cargo/bin/rtk
|
|
266
|
-
fix: Tokenade subsumes rtk: `tokenade
|
|
269
|
+
fix: Tokenade subsumes rtk: `tokenade wrap '<cmd>'` does the same AND
|
|
267
270
|
auto-detects 48 formats — usually with better savings.
|
|
268
271
|
|
|
269
272
|
Run `tokenade install` to interactively migrate & fix the [redundant] /
|
|
@@ -345,20 +348,20 @@ $ tokenade execute --lang python --script 'print(sum(range(101)))'
|
|
|
345
348
|
5050
|
|
346
349
|
```
|
|
347
350
|
|
|
348
|
-
**`
|
|
351
|
+
**`raw <cmd…>`** — run *without* compaction (escape hatch). **`filter <cmd…>`** — treat stdin as if produced by `<cmd>`. **`shell-init`** — print the shell fragment that auto-wraps noisy commands:
|
|
349
352
|
```text
|
|
350
353
|
$ eval "$(tokenade shell-init)" # add to ~/.zshrc — git/cargo/kubectl/… auto-compact
|
|
351
354
|
```
|
|
352
355
|
|
|
353
|
-
###
|
|
356
|
+
### Read & compact content
|
|
354
357
|
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
+
`read` auto-detects a blob's format and dispatches to the right compactor.
|
|
359
|
+
It reads a file or `-` (stdin); live command output is folded the same way
|
|
360
|
+
through `wrap`:
|
|
358
361
|
|
|
359
362
|
```sh
|
|
360
|
-
tokenade
|
|
361
|
-
some-noisy-cmd | tokenade
|
|
363
|
+
tokenade read <file> # auto-detect and compact
|
|
364
|
+
some-noisy-cmd | tokenade read - # …or pipe stdin
|
|
362
365
|
|
|
363
366
|
tokenade add-compactor --file my-rules.toml # teach Tokenade a new compactor
|
|
364
367
|
tokenade add-compactor --list # list the ones you've added
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@tokenade/cli",
|
|
3
|
-
"version": "0.8.
|
|
3
|
+
"version": "0.8.12",
|
|
4
4
|
"description": "Tokenade \u2014 cut your AI coding agent's token bill. Installs the Tokenade CLI (a local, paid token-reduction tool; activate via your browser).",
|
|
5
5
|
"homepage": "https://tokenade.net",
|
|
6
6
|
"license": "UNLICENSED",
|
|
@@ -8,7 +8,8 @@
|
|
|
8
8
|
"tokenade": "bin/tokenade.js"
|
|
9
9
|
},
|
|
10
10
|
"scripts": {
|
|
11
|
-
"postinstall": "node install.js"
|
|
11
|
+
"postinstall": "node install.js",
|
|
12
|
+
"preuninstall": "node uninstall.js"
|
|
12
13
|
},
|
|
13
14
|
"dependencies": {
|
|
14
15
|
"tar": "^7.5.16"
|
|
@@ -16,6 +17,7 @@
|
|
|
16
17
|
"files": [
|
|
17
18
|
"bin/",
|
|
18
19
|
"install.js",
|
|
20
|
+
"uninstall.js",
|
|
19
21
|
"README.md"
|
|
20
22
|
],
|
|
21
23
|
"engines": {
|
package/uninstall.js
ADDED
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* preuninstall — run tokenade's own cleanup BEFORE npm deletes the package
|
|
4
|
+
* files, so that `npm uninstall -g @tokenade/cli` actually restores the
|
|
5
|
+
* machine (unwraps MCPs, strips hooks/CLAUDE.md/shell-proxy, and wipes
|
|
6
|
+
* ~/.tokenade + ~/.cache/tokenade) instead of orphaning integration that then
|
|
7
|
+
* spawns a missing binary on every tool call.
|
|
8
|
+
*
|
|
9
|
+
* We locate the SAME vendored binary that install.js (postinstall) dropped in
|
|
10
|
+
* ./vendor and invoke it as `tokenade uninstall --headless`:
|
|
11
|
+
* --headless → no banner, no next-step guidance, and it does NOT touch the
|
|
12
|
+
* binary itself (npm removes ./vendor right after this script).
|
|
13
|
+
*
|
|
14
|
+
* FAIL-OPEN by construction: every failure path (missing binary, spawn error,
|
|
15
|
+
* timeout, non-zero exit) is swallowed and we ALWAYS `process.exit(0)`. A
|
|
16
|
+
* cleanup that can't run must never block `npm uninstall` or leave the user
|
|
17
|
+
* unable to remove the package.
|
|
18
|
+
*
|
|
19
|
+
* npm lifecycle note: `preuninstall` runs on `npm uninstall` / `npm rm` /
|
|
20
|
+
* `npm remove` (local AND `-g`), and fires while the package files still
|
|
21
|
+
* exist. Caveats we accept: it is skipped when the user passes
|
|
22
|
+
* `--ignore-scripts` (or sets that config), and yarn/pnpm do not guarantee it.
|
|
23
|
+
* In those cases the binary is simply gone and its self-heal / a future
|
|
24
|
+
* `tokenade uninstall` covers the leftover integration.
|
|
25
|
+
*/
|
|
26
|
+
|
|
27
|
+
"use strict";
|
|
28
|
+
|
|
29
|
+
const fs = require("node:fs");
|
|
30
|
+
const path = require("node:path");
|
|
31
|
+
const { spawnSync } = require("node:child_process");
|
|
32
|
+
|
|
33
|
+
// Bound the child so a wedged cleanup can never hang `npm uninstall`.
|
|
34
|
+
const CLEANUP_TIMEOUT_MS =
|
|
35
|
+
Number(process.env.TOKENADE_UNINSTALL_TIMEOUT_MS) || 20000;
|
|
36
|
+
|
|
37
|
+
function binaryPath() {
|
|
38
|
+
const name = process.platform === "win32" ? "tokenade.exe" : "tokenade";
|
|
39
|
+
return path.join(__dirname, "vendor", name);
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
function main() {
|
|
43
|
+
const bin = binaryPath();
|
|
44
|
+
// Missing binary (never installed, --ignore-scripts, half-install) → nothing
|
|
45
|
+
// to run; npm still removes the package. Not an error.
|
|
46
|
+
if (!fs.existsSync(bin)) {
|
|
47
|
+
return;
|
|
48
|
+
}
|
|
49
|
+
try {
|
|
50
|
+
const res = spawnSync(bin, ["uninstall", "--headless"], {
|
|
51
|
+
stdio: "inherit",
|
|
52
|
+
timeout: CLEANUP_TIMEOUT_MS,
|
|
53
|
+
// A cleanup crash must not surface as a throw here.
|
|
54
|
+
windowsHide: true,
|
|
55
|
+
});
|
|
56
|
+
if (res.error) {
|
|
57
|
+
console.error(
|
|
58
|
+
` tokenade cleanup skipped (${res.error.message}); ` +
|
|
59
|
+
"run `tokenade uninstall` manually if any integration lingers.",
|
|
60
|
+
);
|
|
61
|
+
}
|
|
62
|
+
} catch (e) {
|
|
63
|
+
console.error(` tokenade cleanup skipped (${e && e.message});`);
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
try {
|
|
68
|
+
main();
|
|
69
|
+
} catch (e) {
|
|
70
|
+
// Absolute backstop — nothing above should throw, but never let it matter.
|
|
71
|
+
try {
|
|
72
|
+
console.error(` tokenade cleanup skipped (${e && e.message});`);
|
|
73
|
+
} catch {}
|
|
74
|
+
}
|
|
75
|
+
// ALWAYS succeed: npm must be free to remove the package.
|
|
76
|
+
process.exit(0);
|