@carllee1983/dbcli 1.54.0 → 1.55.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/.cursor/skills/dbcli/reference.md +15 -0
- package/.github/skills/dbcli/reference.md +15 -0
- package/CHANGELOG.md +20 -0
- package/README.dev.md +10 -7
- package/README.md +34 -20
- package/README.zh-TW.md +31 -20
- package/assets/reference.md +15 -0
- package/dist/cli-runtime.mjs +268 -28
- package/dist/cli.mjs +3 -2
- package/dist/core.d.ts +16 -6
- package/dist/core.mjs +95 -10
- package/package.json +3 -2
- package/plugins/dbcli-agent/INSTALL.md +5 -6
- package/plugins/dbcli-agent/scripts/install-dbcli.sh +6 -6
- package/plugins/dbcli-agent/skills/dbcli/reference.md +15 -0
- package/scripts/postinstall-check-bun.mjs +49 -0
- package/skills/dbcli/reference.md +15 -0
|
@@ -1660,6 +1660,21 @@ shape (`schemaVersion: 1`):
|
|
|
1660
1660
|
Recovery codes (fixed in v1.15.0):
|
|
1661
1661
|
- `CONFIG_MISSING` — no `.dbcli` config; run `dbcli init`.
|
|
1662
1662
|
- `CONN_REFUSED` / `CONN_AUTH_FAILED` / `CONN_TIMEOUT` / `CONN_HOST_NOT_FOUND` / `CONN_UNKNOWN` — connection failure variants.
|
|
1663
|
+
`CONN_TIMEOUT` also covers a statement the server canceled for exceeding the statement
|
|
1664
|
+
timeout (PostgreSQL `57014`, MySQL `3024`, MariaDB `1969`); `details.connectionCode` is
|
|
1665
|
+
`STATEMENT_TIMEOUT` there instead of `ETIMEDOUT`, the plan targets the query (`lint` →
|
|
1666
|
+
`explain` → re-run with `--statement-timeout <ms>`) rather than `doctor`, and no
|
|
1667
|
+
`branches` / `branchFork` / `verify` is emitted. PostgreSQL `57014` only counts as a
|
|
1668
|
+
statement timeout when the server says so — a `pg_cancel_backend()` cancel keeps the
|
|
1669
|
+
verbatim `Database error (57014): …` form instead of claiming a ceiling.
|
|
1670
|
+
The same `details.connectionCode` field distinguishes the other causes that share a
|
|
1671
|
+
connection code: `CONNECTION_LOST` (server closed the connection mid-session — PostgreSQL
|
|
1672
|
+
class 08 and `57P01`/`57P02`, MySQL `1053`), `TOO_MANY_CONNECTIONS` (PostgreSQL `53300`,
|
|
1673
|
+
MySQL `1040` — its plan counts current connections instead of running `doctor`, because
|
|
1674
|
+
rewriting host/port cannot create a slot), `SERVER_NOT_READY` (`57P03`, still starting up),
|
|
1675
|
+
`CONNECTION_REJECTED` (`08004` — the server answered and refused), `EHOSTUNREACH` (resolved
|
|
1676
|
+
but unroutable) and `TLS_ERROR` (handshake failure; reported as `CONN_UNKNOWN` rather than
|
|
1677
|
+
`CONN_AUTH_FAILED`, whose plan re-runs `init` for credentials that are not the problem).
|
|
1663
1678
|
- `PERMISSION_DENIED` — active permission level forbids the operation.
|
|
1664
1679
|
- `BLACKLIST_TABLE` / `BLACKLIST_COLUMN_WRITE` — blacklist violations.
|
|
1665
1680
|
- `SNIPPET_NOT_FOUND` / `SNIPPET_AMBIGUOUS` / `SNIPPET_PARAM_MISSING` — saved-query failures.
|
|
@@ -1660,6 +1660,21 @@ shape (`schemaVersion: 1`):
|
|
|
1660
1660
|
Recovery codes (fixed in v1.15.0):
|
|
1661
1661
|
- `CONFIG_MISSING` — no `.dbcli` config; run `dbcli init`.
|
|
1662
1662
|
- `CONN_REFUSED` / `CONN_AUTH_FAILED` / `CONN_TIMEOUT` / `CONN_HOST_NOT_FOUND` / `CONN_UNKNOWN` — connection failure variants.
|
|
1663
|
+
`CONN_TIMEOUT` also covers a statement the server canceled for exceeding the statement
|
|
1664
|
+
timeout (PostgreSQL `57014`, MySQL `3024`, MariaDB `1969`); `details.connectionCode` is
|
|
1665
|
+
`STATEMENT_TIMEOUT` there instead of `ETIMEDOUT`, the plan targets the query (`lint` →
|
|
1666
|
+
`explain` → re-run with `--statement-timeout <ms>`) rather than `doctor`, and no
|
|
1667
|
+
`branches` / `branchFork` / `verify` is emitted. PostgreSQL `57014` only counts as a
|
|
1668
|
+
statement timeout when the server says so — a `pg_cancel_backend()` cancel keeps the
|
|
1669
|
+
verbatim `Database error (57014): …` form instead of claiming a ceiling.
|
|
1670
|
+
The same `details.connectionCode` field distinguishes the other causes that share a
|
|
1671
|
+
connection code: `CONNECTION_LOST` (server closed the connection mid-session — PostgreSQL
|
|
1672
|
+
class 08 and `57P01`/`57P02`, MySQL `1053`), `TOO_MANY_CONNECTIONS` (PostgreSQL `53300`,
|
|
1673
|
+
MySQL `1040` — its plan counts current connections instead of running `doctor`, because
|
|
1674
|
+
rewriting host/port cannot create a slot), `SERVER_NOT_READY` (`57P03`, still starting up),
|
|
1675
|
+
`CONNECTION_REJECTED` (`08004` — the server answered and refused), `EHOSTUNREACH` (resolved
|
|
1676
|
+
but unroutable) and `TLS_ERROR` (handshake failure; reported as `CONN_UNKNOWN` rather than
|
|
1677
|
+
`CONN_AUTH_FAILED`, whose plan re-runs `init` for credentials that are not the problem).
|
|
1663
1678
|
- `PERMISSION_DENIED` — active permission level forbids the operation.
|
|
1664
1679
|
- `BLACKLIST_TABLE` / `BLACKLIST_COLUMN_WRITE` — blacklist violations.
|
|
1665
1680
|
- `SNIPPET_NOT_FOUND` / `SNIPPET_AMBIGUOUS` / `SNIPPET_PARAM_MISSING` — saved-query failures.
|
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,26 @@ All notable changes to dbcli are documented here.
|
|
|
5
5
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
6
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
7
|
|
|
8
|
+
## [1.55.0] - 2026-08-13 - Packaging: the declared runtime matches the artifact
|
|
9
|
+
|
|
10
|
+
### Removed
|
|
11
|
+
|
|
12
|
+
- **`engines.node` — the runtime declaration now matches the artifact.** `package.json` claimed `node: ">=18.0.0"` since the first release, but measured on Node v22.17.1 against the `v1.54.1` `dist/`, only one published entry point actually loaded. `node dist/cli.mjs` threw `ERR_MODULE_NOT_FOUND` as soon as the launcher reached its dynamic import: `src/cli.ts` keeps the runtime path as a non-literal `'./cli-runtime'` so the `--version` launcher does not inline the heavy runtime, and Bun's resolver appends `.mjs` where Node's ESM resolver requires the extension. `import('dist/core.mjs')` — the `./core` subpath export — threw `Bun is not defined`, the bundle holding 30 Bun global references against `dist/cli-runtime.mjs`'s 143. The `bin` shebang is `#!/usr/bin/env bun` regardless, and the `--version` fast path branches on `import.meta.main`, which is `undefined` before Node 24. `engines` now declares `bun >= 1.3.3` alone. `dist/agent-core.mjs` was and remains Node-importable, and is documented as the one entry point that is. npm and npx stay supported as distribution channels, with the docs stating plainly that the installed executable still runs under Bun. `tests/integration/runtime-contract.test.ts` holds both ends: re-declaring `engines.node` fails unless `dist/cli.mjs` and `dist/core.mjs` really import in a bare Node process, and `dist/agent-core.mjs` must keep importing there whatever else changes. The alternative — `--target node` plus ~169 Bun API replacements in `src/` and a Node runtime CI suite — is rejected and its cost recorded in `docs/adr/0008-dbcli-is-a-bun-program-and-engines-says-so.md` (#65).
|
|
13
|
+
|
|
14
|
+
### Added
|
|
15
|
+
|
|
16
|
+
- **An install on a machine without Bun now says so.** npm validates no `engines` field it does not recognize, so dropping the false `engines.node` would otherwise have left `npm install -g` with no signal at all — success, then a `dbcli` on `PATH` that dies on its shebang. `scripts/postinstall-check-bun.mjs` prints the reason and the Bun install command at that moment, and never fails the install. It runs as `bun … || node … || exit 0` because the primary install path is Bun-only machines, which have no `node` to invoke a postinstall with. `plugins/dbcli-agent/scripts/install-dbcli.sh` stopped falling back to npm when Bun is absent: it used to leave a non-functional `dbcli` behind, and now refuses before changing anything (#65).
|
|
17
|
+
|
|
18
|
+
## [1.54.1] - 2026-08-13 - Error classification: a failure now says which layer broke
|
|
19
|
+
|
|
20
|
+
### Fixed
|
|
21
|
+
|
|
22
|
+
- **A dropped connection, an exhausted connection pool, an unreachable host, and a TLS failure each say so.** `TRANSPORT_CODES` listed seven keys, so `ECONNRESET`, `EPIPE`, `EHOSTUNREACH`, `ENETUNREACH`, TLS certificate codes, PostgreSQL SQLSTATE class `08` and `53300`, and MySQL `1040` all carried a code, skipped the message-pattern fallback (which only runs when there is none), and landed on `Database error (ECONNRESET): …` with hints about `dbcli schema`. They now map to four new categories — `CONNECTION_LOST`, `TOO_MANY_CONNECTIONS`, `EHOSTUNREACH`, `TLS_ERROR` — each with the remedy that actually applies: retry a transient drop, inspect `pg_stat_activity` / `Threads_connected` against `max_connections`, check routing and VPN rather than DNS, or point `caPath` / `rejectUnauthorized` at the right certificate. PostgreSQL class `57` (`57P01` / `57P02` / `57P03`) and MySQL `1053` / `2006` / `2013` join them: restarting the server under a running query was reported as `Database error (57P01)` with hints about confirming the statement's objects. The codeless wordings drivers use for the same event — `Connection terminated unexpectedly`, `server closed the connection`, `server has gone away` — are recognized too. `57P03` (still starting up) and `08004` (the server answered and refused) get their own categories rather than borrowing a message that says the opposite, and TLS is matched by code prefix because enumerating OpenSSL's verify codes would keep missing some. The envelope states each cause in its own words instead of inheriting the shared recovery code's description — `CONN_HOST_NOT_FOUND` says the name could not be resolved, which is the one thing `EHOSTUNREACH` rules out — and TLS failures no longer route to the credentials plan, whose second step re-runs `init` for a certificate it never asks about. The adapter-code-to-envelope-code and the connection-versus-statement tables are both exhaustive `Record`s over the code union now, so a future code cannot silently inherit a generic category, and the REPL's reconnect decision reads the same table instead of its own list of codes and message substrings (#62).
|
|
23
|
+
|
|
24
|
+
- **`insert` / `update` / `delete` / `q` no longer report every failure as "failed to connect".** All four branched on `instanceof ConnectionError` and applied one message key, but that class carries every adapter-level error and only four of its nine codes are transport failures — so a missing table, a syntax error, or a statement timeout all arrived as `Failed to connect to database: …` while the connection was fine. The wording is now chosen by code, and rendering goes through the same `formatCliError` the central presenter uses, so these commands print the stable `Code:` line and the error's hints — both previously dropped on this path — exactly as `query` does (#61).
|
|
25
|
+
|
|
26
|
+
- **A statement the server canceled is no longer reported as a connection failure.** PostgreSQL `57014`, MySQL `3024`, and MariaDB `1969` fell through to `UNKNOWN` / `CONN_UNKNOWN`, so the CLI answered a query that ran out of statement time with connection-troubleshooting hints and a recovery plan that opened with `dbcli doctor` — the one thing that was not broken. They now map to a `STATEMENT_TIMEOUT` adapter code whose hints point at the query (`dbcli lint`, `dbcli explain`, re-run with an explicit `--statement-timeout <ms>`). The `--recovery` envelope keeps `schemaVersion` 1 and reports `CONN_TIMEOUT` with `details.connectionCode: "STATEMENT_TIMEOUT"`; that field selects the query-oriented plan, replaces the network-flavored message with one that states the ceiling that was in force, and suppresses both the `doctor-*` branches — whose `branchFork.after: 1` assumed step 1 was `doctor` — and the `verify` step, since nothing verifies this error except re-running the statement, which only the caller has. PostgreSQL `57014` is `query_canceled`, not only `statement_timeout`, so a `pg_cancel_backend()` or recovery-conflict cancel keeps the verbatim `Database error (57014): …` form rather than asserting a ceiling nobody set.
|
|
27
|
+
|
|
8
28
|
## [1.54.0] - 2026-08-13 - Query engine hardening: timeout semantics, load-on-demand, deterministic builds
|
|
9
29
|
|
|
10
30
|
### Added
|
package/README.dev.md
CHANGED
|
@@ -73,20 +73,22 @@ After publishing:
|
|
|
73
73
|
|
|
74
74
|
1. **Global install:**
|
|
75
75
|
```bash
|
|
76
|
-
|
|
76
|
+
bun install -g @carllee1983/dbcli
|
|
77
77
|
which dbcli
|
|
78
78
|
dbcli --version
|
|
79
79
|
```
|
|
80
|
+
`npm install -g` also works, but the installed executable still runs under Bun via its
|
|
81
|
+
`#!/usr/bin/env bun` shebang — verify on a machine that has Bun on `PATH`.
|
|
80
82
|
|
|
81
|
-
2. **Zero-install (
|
|
83
|
+
2. **Zero-install (bunx / npx):**
|
|
82
84
|
```bash
|
|
83
85
|
cd /tmp && mkdir -p test-dbcli && cd test-dbcli
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
# or:
|
|
86
|
+
bunx @carllee1983/dbcli --help
|
|
87
|
+
bunx @carllee1983/dbcli --version
|
|
88
|
+
# or: npx @carllee1983/dbcli --help
|
|
87
89
|
```
|
|
88
90
|
|
|
89
|
-
3. **Windows (if available):** `npm install -g @carllee1983/dbcli`, then `dbcli --help`. npm creates the `.cmd` stub for the `bin` entry; no hand-written `.cmd` in the repo.
|
|
91
|
+
3. **Windows (if available):** `npm install -g @carllee1983/dbcli`, then `dbcli --help`. npm creates the `.cmd` stub for the `bin` entry; no hand-written `.cmd` in the repo. Bun must be on `PATH` there too.
|
|
90
92
|
|
|
91
93
|
### Rollback (if needed)
|
|
92
94
|
|
|
@@ -104,8 +106,9 @@ Then ship a patch version with the fix. Prefer **deprecate** over **unpublish**
|
|
|
104
106
|
|
|
105
107
|
- **`files` (in `package.json`):** Publishes `dist/`, `assets/`, `README.md`, `CHANGELOG.md`, `LICENSE`. The `assets/` tree is required for `dbcli skill` to copy bundled `SKILL.md` / `reference.md` from the installed package.
|
|
106
108
|
- **`prepublishOnly`:** `bun run build` so `dist/cli.mjs` matches current source.
|
|
107
|
-
- **`engines`:** Declares `
|
|
109
|
+
- **`engines`:** Declares `bun >= 1.3.3` only. `node` was removed because the published bundles cannot run on Node: `dist/cli.mjs` dynamic-imports the extensionless `./cli-runtime` (Bun's resolver appends `.mjs`, Node's does not) and `dist/core.mjs` calls Bun globals. `tests/integration/runtime-contract.test.ts` fails if `engines.node` comes back without the bundles being fixed to match, and if `dist/agent-core.mjs` — the one entry point that is Node-importable — regresses. See `docs/adr/0008-dbcli-is-a-bun-program-and-engines-says-so.md`.
|
|
108
110
|
- **Shebang:** `scripts/build.ts` prepends `#!/usr/bin/env bun` to `dist/cli.mjs`; the `bin` field in `package.json` points at that file.
|
|
111
|
+
- **`postinstall`:** `scripts/postinstall-check-bun.mjs` warns (never fails) when Bun is missing after install — npm ignores `engines.bun`, so this is the only signal an npm-only machine gets before `dbcli` refuses to start. The script command is `bun … || node … || exit 0` so it runs whichever runtime is present: Bun-only machines have no `node` to invoke it with, and a hard `node` dependency there would break the primary install path.
|
|
109
112
|
- **Live DB tests:** `tests/integration/live-db.test.ts` uses project `.dbcli` by default or `LIVE_DB_CONFIG_PATH` when you point at another config directory. Set `SKIP_INTEGRATION_TESTS=true` to skip all integration tests.
|
|
110
113
|
|
|
111
114
|
For contributor workflow and release process, see **[CONTRIBUTING.md](./CONTRIBUTING.md)** and the main **[README.md](./README.md)** Development section.
|
package/README.md
CHANGED
|
@@ -38,16 +38,21 @@ All messages, help text, error messages, and command output respond to the langu
|
|
|
38
38
|
#### Global Installation (Recommended)
|
|
39
39
|
|
|
40
40
|
```bash
|
|
41
|
-
|
|
42
|
-
# or:
|
|
41
|
+
bun install -g @carllee1983/dbcli
|
|
42
|
+
# or: npm install -g @carllee1983/dbcli
|
|
43
43
|
```
|
|
44
44
|
|
|
45
|
+
**dbcli runs on Bun.** npm and npx are supported as distribution channels, but the
|
|
46
|
+
installed `dbcli` executable requires Bun 1.3.3+ on your `PATH` — install it first with
|
|
47
|
+
`curl -fsSL https://bun.sh/install | bash`. Only the `./agent-core` subpath export is
|
|
48
|
+
importable from a plain Node process.
|
|
49
|
+
|
|
45
50
|
#### Zero-Install (No Installation Needed)
|
|
46
51
|
|
|
47
52
|
```bash
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
# or with
|
|
53
|
+
bunx @carllee1983/dbcli init
|
|
54
|
+
bunx @carllee1983/dbcli query "SELECT * FROM users"
|
|
55
|
+
# or with npm: npx @carllee1983/dbcli init
|
|
51
56
|
```
|
|
52
57
|
|
|
53
58
|
#### Update
|
|
@@ -1324,9 +1329,11 @@ After installation, the AI agent will have access to dbcli commands and can use
|
|
|
1324
1329
|
|
|
1325
1330
|
### Platform-Specific Setup
|
|
1326
1331
|
|
|
1332
|
+
Every flow below assumes Bun 1.3.3+ on your `PATH`: the installed `dbcli` executable runs under Bun regardless of which package manager fetched it.
|
|
1333
|
+
|
|
1327
1334
|
#### Claude Code (Anthropic)
|
|
1328
1335
|
|
|
1329
|
-
1. Install dbcli globally: `
|
|
1336
|
+
1. Install dbcli globally: `bun install -g @carllee1983/dbcli`
|
|
1330
1337
|
2. Initialize: `dbcli init` (choose permission level)
|
|
1331
1338
|
3. Install skill: `dbcli skill --install claude`
|
|
1332
1339
|
4. Restart Claude Code extension
|
|
@@ -1338,7 +1345,7 @@ After installation, the AI agent will have access to dbcli commands and can use
|
|
|
1338
1345
|
|
|
1339
1346
|
#### Gemini CLI (Google)
|
|
1340
1347
|
|
|
1341
|
-
1. Install dbcli globally: `
|
|
1348
|
+
1. Install dbcli globally: `bun install -g @carllee1983/dbcli`
|
|
1342
1349
|
2. Initialize: `dbcli init`
|
|
1343
1350
|
3. Install skill: `dbcli skill --install gemini`
|
|
1344
1351
|
4. Start Gemini: `gemini start`
|
|
@@ -1350,7 +1357,7 @@ After installation, the AI agent will have access to dbcli commands and can use
|
|
|
1350
1357
|
|
|
1351
1358
|
#### GitHub Copilot CLI
|
|
1352
1359
|
|
|
1353
|
-
1. Install dbcli globally: `
|
|
1360
|
+
1. Install dbcli globally: `bun install -g @carllee1983/dbcli`
|
|
1354
1361
|
2. Initialize: `dbcli init`
|
|
1355
1362
|
3. Install skill: `dbcli skill --install copilot`
|
|
1356
1363
|
4. Install Copilot CLI: `npm install -g @github-next/github-copilot-cli`
|
|
@@ -1362,7 +1369,7 @@ After installation, the AI agent will have access to dbcli commands and can use
|
|
|
1362
1369
|
|
|
1363
1370
|
#### Cursor IDE
|
|
1364
1371
|
|
|
1365
|
-
1. Install dbcli globally: `
|
|
1372
|
+
1. Install dbcli globally: `bun install -g @carllee1983/dbcli`
|
|
1366
1373
|
2. Initialize: `dbcli init`
|
|
1367
1374
|
3. Install skill: `dbcli skill --install cursor`
|
|
1368
1375
|
4. Open Cursor editor
|
|
@@ -1378,7 +1385,7 @@ After installation, the AI agent will have access to dbcli commands and can use
|
|
|
1378
1385
|
|
|
1379
1386
|
1. Add the marketplace: `codex plugin marketplace add CarlLee1983/dbcli`.
|
|
1380
1387
|
2. Open `/plugins`, select the dbcli Agent marketplace, and install `dbcli-agent`.
|
|
1381
|
-
3. For a persistent CLI, install dbcli globally: `bun install -g @carllee1983/dbcli` or `npm install -g
|
|
1388
|
+
3. For a persistent CLI, install dbcli globally: `bun install -g @carllee1983/dbcli` (or `npm install -g`, which still needs Bun on `PATH`).
|
|
1382
1389
|
4. Without a global install, the plugin skill uses `bunx @carllee1983/dbcli <command>` as its fallback.
|
|
1383
1390
|
5. Initialize: `dbcli init` or `bunx @carllee1983/dbcli init`.
|
|
1384
1391
|
|
|
@@ -1394,7 +1401,7 @@ After installation, the AI agent will have access to dbcli commands and can use
|
|
|
1394
1401
|
|
|
1395
1402
|
```bash
|
|
1396
1403
|
# 1. Install and initialize
|
|
1397
|
-
|
|
1404
|
+
bun install -g @carllee1983/dbcli
|
|
1398
1405
|
dbcli init # Choose "query-only" for safety
|
|
1399
1406
|
|
|
1400
1407
|
# 2. Install skill to Claude Code
|
|
@@ -1590,16 +1597,16 @@ dbcli query "SELECT * FROM users LIMIT 100 OFFSET 100"
|
|
|
1590
1597
|
|
|
1591
1598
|
#### "CLI startup takes 30+ seconds (first run)"
|
|
1592
1599
|
|
|
1593
|
-
npx is downloading and caching package.
|
|
1600
|
+
bunx (or npx) is downloading and caching the package.
|
|
1594
1601
|
|
|
1595
1602
|
**Solution:** This is normal on first run. Subsequent runs are instant:
|
|
1596
1603
|
|
|
1597
1604
|
```bash
|
|
1598
|
-
|
|
1599
|
-
|
|
1605
|
+
bunx @carllee1983/dbcli init # First run: 30s (downloads)
|
|
1606
|
+
bunx @carllee1983/dbcli init # Second run: <1s (cached)
|
|
1600
1607
|
|
|
1601
1608
|
# Or install globally for faster startup
|
|
1602
|
-
|
|
1609
|
+
bun install -g @carllee1983/dbcli
|
|
1603
1610
|
dbcli init # All future runs: <1s
|
|
1604
1611
|
```
|
|
1605
1612
|
|
|
@@ -1609,15 +1616,19 @@ dbcli init # All future runs: <1s
|
|
|
1609
1616
|
|
|
1610
1617
|
#### Windows: "Command not found: dbcli"
|
|
1611
1618
|
|
|
1612
|
-
|
|
1619
|
+
The shim was not created, PATH was not updated, or Bun is missing — `dbcli` runs under
|
|
1620
|
+
Bun on Windows too.
|
|
1613
1621
|
|
|
1614
1622
|
**Solutions:**
|
|
1615
1623
|
|
|
1616
1624
|
```bash
|
|
1625
|
+
# Confirm Bun is installed and on PATH first
|
|
1626
|
+
bun --version
|
|
1627
|
+
|
|
1617
1628
|
# Restart terminal to refresh PATH
|
|
1618
1629
|
# OR reinstall globally
|
|
1619
|
-
|
|
1620
|
-
|
|
1630
|
+
bun uninstall -g @carllee1983/dbcli
|
|
1631
|
+
bun install -g @carllee1983/dbcli
|
|
1621
1632
|
|
|
1622
1633
|
# Verify installation
|
|
1623
1634
|
where dbcli # Windows command to find executable
|
|
@@ -1647,8 +1658,11 @@ chmod +x dist/cli.mjs
|
|
|
1647
1658
|
|
|
1648
1659
|
### Runtime
|
|
1649
1660
|
|
|
1650
|
-
- **
|
|
1651
|
-
|
|
1661
|
+
- **Bun:** 1.3.3+ — required. The published bundles use Bun APIs and Bun module
|
|
1662
|
+
resolution; `dbcli` does not run on Node.
|
|
1663
|
+
- **Node.js:** only for the `./agent-core` subpath export, which is Node-importable
|
|
1664
|
+
(18.0.0+). `npm install -g` / `npx` work as distribution channels but still shell out
|
|
1665
|
+
to Bun at run time.
|
|
1652
1666
|
|
|
1653
1667
|
### Platforms
|
|
1654
1668
|
|
package/README.zh-TW.md
CHANGED
|
@@ -38,16 +38,20 @@ dbcli init
|
|
|
38
38
|
#### 全域安裝(建議)
|
|
39
39
|
|
|
40
40
|
```bash
|
|
41
|
-
|
|
42
|
-
# 或使用
|
|
41
|
+
bun install -g @carllee1983/dbcli
|
|
42
|
+
# 或使用 npm:npm install -g @carllee1983/dbcli
|
|
43
43
|
```
|
|
44
44
|
|
|
45
|
+
**dbcli 執行於 Bun。** npm 與 npx 可作為發布通道,但安裝後的 `dbcli` 執行檔需要 `PATH`
|
|
46
|
+
上有 Bun 1.3.3+,請先以 `curl -fsSL https://bun.sh/install | bash` 安裝。只有
|
|
47
|
+
`./agent-core` 這個 subpath export 能被純 Node 程序 import。
|
|
48
|
+
|
|
45
49
|
#### 免安裝(無需事先安裝)
|
|
46
50
|
|
|
47
51
|
```bash
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
# 或使用
|
|
52
|
+
bunx @carllee1983/dbcli init
|
|
53
|
+
bunx @carllee1983/dbcli query "SELECT * FROM users"
|
|
54
|
+
# 或使用 npm:npx @carllee1983/dbcli init
|
|
51
55
|
```
|
|
52
56
|
|
|
53
57
|
#### 更新
|
|
@@ -1214,9 +1218,11 @@ dbcli skill --install cursor
|
|
|
1214
1218
|
|
|
1215
1219
|
### 各平台設定
|
|
1216
1220
|
|
|
1221
|
+
以下所有流程都假設 `PATH` 上有 Bun 1.3.3+:無論用哪個套件管理器安裝,`dbcli` 執行檔都以 Bun 執行。
|
|
1222
|
+
|
|
1217
1223
|
#### Claude Code(Anthropic)
|
|
1218
1224
|
|
|
1219
|
-
1. 全域安裝 dbcli:`
|
|
1225
|
+
1. 全域安裝 dbcli:`bun install -g @carllee1983/dbcli`
|
|
1220
1226
|
2. 初始化:`dbcli init`(選擇權限等級)
|
|
1221
1227
|
3. 安裝 skill:`dbcli skill --install claude`
|
|
1222
1228
|
4. 重新啟動 Claude Code 擴充
|
|
@@ -1228,7 +1234,7 @@ dbcli skill --install cursor
|
|
|
1228
1234
|
|
|
1229
1235
|
#### Gemini CLI(Google)
|
|
1230
1236
|
|
|
1231
|
-
1. 全域安裝:`
|
|
1237
|
+
1. 全域安裝:`bun install -g @carllee1983/dbcli`
|
|
1232
1238
|
2. 初始化:`dbcli init`
|
|
1233
1239
|
3. 安裝 skill:`dbcli skill --install gemini`
|
|
1234
1240
|
4. 啟動 Gemini:`gemini start`
|
|
@@ -1240,7 +1246,7 @@ dbcli skill --install cursor
|
|
|
1240
1246
|
|
|
1241
1247
|
#### GitHub Copilot CLI
|
|
1242
1248
|
|
|
1243
|
-
1. 全域安裝:`
|
|
1249
|
+
1. 全域安裝:`bun install -g @carllee1983/dbcli`
|
|
1244
1250
|
2. 初始化:`dbcli init`
|
|
1245
1251
|
3. 安裝 skill:`dbcli skill --install copilot`
|
|
1246
1252
|
4. 安裝 Copilot CLI:`npm install -g @github-next/github-copilot-cli`
|
|
@@ -1252,7 +1258,7 @@ dbcli skill --install cursor
|
|
|
1252
1258
|
|
|
1253
1259
|
#### Cursor IDE
|
|
1254
1260
|
|
|
1255
|
-
1. 全域安裝:`
|
|
1261
|
+
1. 全域安裝:`bun install -g @carllee1983/dbcli`
|
|
1256
1262
|
2. 初始化:`dbcli init`
|
|
1257
1263
|
3. 安裝 skill:`dbcli skill --install cursor`
|
|
1258
1264
|
4. 開啟 Cursor
|
|
@@ -1268,7 +1274,7 @@ dbcli skill --install cursor
|
|
|
1268
1274
|
|
|
1269
1275
|
1. 加入 marketplace:`codex plugin marketplace add CarlLee1983/dbcli`。
|
|
1270
1276
|
2. 開啟 `/plugins`,選擇 dbcli Agent marketplace,並安裝 `dbcli-agent`。
|
|
1271
|
-
3. 若要常駐 CLI,請全域安裝 dbcli:`bun install -g @carllee1983/dbcli
|
|
1277
|
+
3. 若要常駐 CLI,請全域安裝 dbcli:`bun install -g @carllee1983/dbcli`(或 `npm install -g`,但仍需 `PATH` 上有 Bun)。
|
|
1272
1278
|
4. 若未全域安裝,plugin 內的 skill 會以 `bunx @carllee1983/dbcli <command>` 作為 fallback。
|
|
1273
1279
|
5. 初始化:`dbcli init` 或 `bunx @carllee1983/dbcli init`。
|
|
1274
1280
|
|
|
@@ -1284,7 +1290,7 @@ dbcli skill --install cursor
|
|
|
1284
1290
|
|
|
1285
1291
|
```bash
|
|
1286
1292
|
# 1. 安裝並初始化
|
|
1287
|
-
|
|
1293
|
+
bun install -g @carllee1983/dbcli
|
|
1288
1294
|
dbcli init # 選擇「query-only」較安全
|
|
1289
1295
|
|
|
1290
1296
|
# 2. 為 Claude Code 安裝 skill
|
|
@@ -1471,16 +1477,16 @@ dbcli query "SELECT * FROM users LIMIT 100 OFFSET 100"
|
|
|
1471
1477
|
|
|
1472
1478
|
#### 「第一次執行 CLI 超過 30 秒」
|
|
1473
1479
|
|
|
1474
|
-
npx
|
|
1480
|
+
bunx(或 npx)正在下載並快取套件。
|
|
1475
1481
|
|
|
1476
1482
|
**處理方式:** 首次較慢屬正常,之後會很快:
|
|
1477
1483
|
|
|
1478
1484
|
```bash
|
|
1479
|
-
|
|
1480
|
-
|
|
1485
|
+
bunx @carllee1983/dbcli init # 首次約 30s
|
|
1486
|
+
bunx @carllee1983/dbcli init # 之後 <1s
|
|
1481
1487
|
|
|
1482
1488
|
# 或全域安裝
|
|
1483
|
-
|
|
1489
|
+
bun install -g @carllee1983/dbcli
|
|
1484
1490
|
dbcli init
|
|
1485
1491
|
```
|
|
1486
1492
|
|
|
@@ -1490,15 +1496,18 @@ dbcli init
|
|
|
1490
1496
|
|
|
1491
1497
|
#### Windows:「Command not found: dbcli」
|
|
1492
1498
|
|
|
1493
|
-
|
|
1499
|
+
shim 未建立、PATH 未更新,或機器上沒有 Bun —— `dbcli` 在 Windows 上同樣以 Bun 執行。
|
|
1494
1500
|
|
|
1495
1501
|
**處理方式:**
|
|
1496
1502
|
|
|
1497
1503
|
```bash
|
|
1504
|
+
# 先確認 Bun 已安裝且在 PATH 上
|
|
1505
|
+
bun --version
|
|
1506
|
+
|
|
1498
1507
|
# 重開終端機以更新 PATH
|
|
1499
1508
|
# 或重新全域安裝
|
|
1500
|
-
|
|
1501
|
-
|
|
1509
|
+
bun uninstall -g @carllee1983/dbcli
|
|
1510
|
+
bun install -g @carllee1983/dbcli
|
|
1502
1511
|
|
|
1503
1512
|
where dbcli
|
|
1504
1513
|
```
|
|
@@ -1527,8 +1536,10 @@ chmod +x dist/cli.mjs
|
|
|
1527
1536
|
|
|
1528
1537
|
### 執行環境
|
|
1529
1538
|
|
|
1530
|
-
- **
|
|
1531
|
-
|
|
1539
|
+
- **Bun:** 1.3.3+ —— 必要。發布的 bundle 使用 Bun API 與 Bun 的模組解析,`dbcli`
|
|
1540
|
+
無法在 Node 上執行。
|
|
1541
|
+
- **Node.js:** 僅 `./agent-core` 這個 subpath export 可被 Node import(18.0.0+)。
|
|
1542
|
+
`npm install -g` / `npx` 可作為發布通道,但執行時仍會轉交給 Bun。
|
|
1532
1543
|
|
|
1533
1544
|
### 平台
|
|
1534
1545
|
|
package/assets/reference.md
CHANGED
|
@@ -1660,6 +1660,21 @@ shape (`schemaVersion: 1`):
|
|
|
1660
1660
|
Recovery codes (fixed in v1.15.0):
|
|
1661
1661
|
- `CONFIG_MISSING` — no `.dbcli` config; run `dbcli init`.
|
|
1662
1662
|
- `CONN_REFUSED` / `CONN_AUTH_FAILED` / `CONN_TIMEOUT` / `CONN_HOST_NOT_FOUND` / `CONN_UNKNOWN` — connection failure variants.
|
|
1663
|
+
`CONN_TIMEOUT` also covers a statement the server canceled for exceeding the statement
|
|
1664
|
+
timeout (PostgreSQL `57014`, MySQL `3024`, MariaDB `1969`); `details.connectionCode` is
|
|
1665
|
+
`STATEMENT_TIMEOUT` there instead of `ETIMEDOUT`, the plan targets the query (`lint` →
|
|
1666
|
+
`explain` → re-run with `--statement-timeout <ms>`) rather than `doctor`, and no
|
|
1667
|
+
`branches` / `branchFork` / `verify` is emitted. PostgreSQL `57014` only counts as a
|
|
1668
|
+
statement timeout when the server says so — a `pg_cancel_backend()` cancel keeps the
|
|
1669
|
+
verbatim `Database error (57014): …` form instead of claiming a ceiling.
|
|
1670
|
+
The same `details.connectionCode` field distinguishes the other causes that share a
|
|
1671
|
+
connection code: `CONNECTION_LOST` (server closed the connection mid-session — PostgreSQL
|
|
1672
|
+
class 08 and `57P01`/`57P02`, MySQL `1053`), `TOO_MANY_CONNECTIONS` (PostgreSQL `53300`,
|
|
1673
|
+
MySQL `1040` — its plan counts current connections instead of running `doctor`, because
|
|
1674
|
+
rewriting host/port cannot create a slot), `SERVER_NOT_READY` (`57P03`, still starting up),
|
|
1675
|
+
`CONNECTION_REJECTED` (`08004` — the server answered and refused), `EHOSTUNREACH` (resolved
|
|
1676
|
+
but unroutable) and `TLS_ERROR` (handshake failure; reported as `CONN_UNKNOWN` rather than
|
|
1677
|
+
`CONN_AUTH_FAILED`, whose plan re-runs `init` for credentials that are not the problem).
|
|
1663
1678
|
- `PERMISSION_DENIED` — active permission level forbids the operation.
|
|
1664
1679
|
- `BLACKLIST_TABLE` / `BLACKLIST_COLUMN_WRITE` — blacklist violations.
|
|
1665
1680
|
- `SNIPPET_NOT_FOUND` / `SNIPPET_AMBIGUOUS` / `SNIPPET_PARAM_MISSING` — saved-query failures.
|