@carllee1983/dbcli 9.1.0 → 9.1.2
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/.claude-plugin/plugin.json +1 -1
- package/.codex-plugin/plugin.json +1 -1
- package/.cursor-plugin/plugin.json +1 -1
- package/CHANGELOG.md +94 -0
- package/README.md +18 -45
- package/assets/ui-template.html +24 -24
- package/dist/agent-core.mjs +5 -5
- package/dist/cli-runtime.mjs +2528 -3367
- package/dist/cli.mjs +4 -6
- package/dist/core.mjs +501 -1523
- package/gemini-extension.json +1 -1
- package/package.json +2 -4
- package/plugins/dbcli-agent/.codex-plugin/plugin.json +1 -1
- package/.agents/skills/story-development/SKILL.md +0 -70
package/CHANGELOG.md
CHANGED
|
@@ -5,6 +5,100 @@ 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
|
+
## [9.1.2] - 2026-10-01
|
|
9
|
+
|
|
10
|
+
一個開發依賴的安全公告、工作規格協定從 ForgeFlow 換成 Warrant,以及三個讓測試與建置
|
|
11
|
+
不再依賴執行順序或在磁碟上留下東西的修正。
|
|
12
|
+
|
|
13
|
+
版本為 **9.1.2**。沒有任何指令、旗標、engine 或輸出改變。npm 套件唯一的差別是不再
|
|
14
|
+
附帶 `.agents/skills/story-development/SKILL.md`——那是 dbcli 自己開發流程用的
|
|
15
|
+
skill,不是給使用者的。
|
|
16
|
+
|
|
17
|
+
### Changed
|
|
18
|
+
|
|
19
|
+
- **工作規格改用 Warrant,ForgeFlow 的機制整套移除。** Story 從一個裝著
|
|
20
|
+
`story.md`/`acceptance.md`/`task.md` 的目錄,變成一個只有 Goal、Out of Scope、
|
|
21
|
+
Acceptance Criteria 三節的 `specs/stories/<slug>.md`;核准由人 commit 或在當次
|
|
22
|
+
session 明確指派,完成由 `make verify` 證明。ForgeFlow 留下的每一個決定都是在維護
|
|
23
|
+
協定本身而不是 dbcli:adoption marker、範本、上游 contract job、`Story:` trailer
|
|
24
|
+
對帳與 handoff 結構要彼此一致,代價是 `make verify` 裡的一道門、CI 的第二次
|
|
25
|
+
checkout、三支 checker 加上它們的函式庫與測試。這些都刪掉而不是停用,連同
|
|
26
|
+
`story-development` skill——它隨 `.agents/` 一起打包,所以已安裝的套件裡會少掉
|
|
27
|
+
它。ForgePilot 仍是控制面,`DBCLI-*` 舊目錄原封保留為歷史紀錄。決定記在
|
|
28
|
+
ADR-0040,取代 ADR-0025、0027、0029、0031、0032 與 0036。
|
|
29
|
+
|
|
30
|
+
- **`assets/ui-template.html` 改為建置產物,不再進版控。** 每次 `bun run build` 都會
|
|
31
|
+
重新產生並覆寫它,`prepublishOnly` 也在每次發佈前重建,所以 commit 裡那份從來不是
|
|
32
|
+
使用者拿到的那份,只會跟建置結果漂移——每跑一次 `make verify` 就把 worktree 弄髒。
|
|
33
|
+
現在它和 `dist/` 一樣列在 `.gitignore`,由 `build:determinism` 檢查兩次建置產出
|
|
34
|
+
相同位元組,而每個會渲染 HTML 的測試自己建置所需的東西,不再靠前面的測試檔先建好。
|
|
35
|
+
發佈出去的 template 仍由 `prepublishOnly` 建置,內容不變。決定記在 ADR-0041。
|
|
36
|
+
|
|
37
|
+
### Fixed
|
|
38
|
+
|
|
39
|
+
- **Skill Author Integration Kit 的測試不再依賴執行順序。** 它以套件名
|
|
40
|
+
(`@carllee1983/dbcli/core`)import,解析到的是未進版控的 `dist/core.mjs`;靜態
|
|
41
|
+
import 只在更早的測試檔已建好 `dist/` 時才載入得了,CI 先跑它就在載入模組時失敗。
|
|
42
|
+
改為在 `beforeAll` 建置後動態 import。
|
|
43
|
+
|
|
44
|
+
- **測試套件不再在 OS 暫存目錄留下東西。** 一次完整測試會在 `TMPDIR` 留下約 130 個
|
|
45
|
+
目錄與檔案:每個測試都呼叫的 seed helper、`beforeAll`/`beforeEach` 建了卻沒有對應
|
|
46
|
+
刪除的目錄、只還原 `HOME` 的 `finally`,以及直接寫進 `tmpdir()` 的設定檔。每個會
|
|
47
|
+
外洩的檔案現在都以 repo 既有的寫法清掉自己建的東西;從空的 `TMPDIR` 開始跑,只剩
|
|
48
|
+
第三方的 node-jiti 快取。
|
|
49
|
+
|
|
50
|
+
### Security
|
|
51
|
+
|
|
52
|
+
- **`brace-expansion` 的 override 提高到 `^5.0.12`。** `bun run audit` 在
|
|
53
|
+
`brace-expansion@5.0.9` 回報三個漏洞(兩個 high、一個 moderate):
|
|
54
|
+
GHSA-qhr7-859c-m2p7、GHSA-6j4f-fj2g-mc7p、GHSA-q2hr-2g5m-vwhr。它經由 eslint 與
|
|
55
|
+
typescript-eslint 的 minimatch 引入,只存在於開發依賴,不在發佈的套件裡;提高既有的
|
|
56
|
+
override 就全部清掉。
|
|
57
|
+
|
|
58
|
+
## [9.1.1] - 2026-09-15
|
|
59
|
+
|
|
60
|
+
一個使用者回報的查詢缺陷(#197),一條會把人導向無效權限階的拒絕訊息,以及兩個
|
|
61
|
+
會對同一個 commit 給出兩種答案、或只會叫「東西變了」的測試門檻。
|
|
62
|
+
|
|
63
|
+
版本為 **9.1.1**。沒有新增指令、旗標或 engine;沒有任何一處拒絕先前被接受的輸入。
|
|
64
|
+
唯一改變輸出的是拒絕訊息裡的 `required:` 欄位與它的句子——那個值先前是錯的,照它
|
|
65
|
+
去要權限會被再拒一次,所以修正它不是相容性變更,是讓它開始為真。
|
|
66
|
+
|
|
67
|
+
### Fixed
|
|
68
|
+
|
|
69
|
+
- **snippet 裡重複使用同一個具名參數,在 MySQL / MariaDB / SQLite 上不再炸。**
|
|
70
|
+
`rewriteToBind()` 對每一次 `:name` 出現輸出一個 placeholder,但 bind values 是由
|
|
71
|
+
去重後的名稱清單映射出來的。PostgreSQL 重用 `$1`,一個值對一個索引本來就對;`?`
|
|
72
|
+
沒有索引可以重用,所以 placeholder 數量跟著出現次數走、values 數量跟著相異名稱數
|
|
73
|
+
走,兩者在有重複參數時必然對不上,MariaDB 以 `ER_WRONG_ARGUMENTS` 拒絕整條
|
|
74
|
+
statement。
|
|
75
|
+
|
|
76
|
+
實務影響是「參數為 0 就查全部、否則查單一」這類條件在 snippet 裡寫不出來,只能
|
|
77
|
+
繞道 CTE 讓參數只出現一次。`--dry-run` 看得到 SQL 與 bind values 不匹配,但不會
|
|
78
|
+
報錯,所以問題要到真的執行才炸。非 PostgreSQL 引擎現在每一次出現送一個值,
|
|
79
|
+
PostgreSQL 的去重行為不變。(#197)
|
|
80
|
+
|
|
81
|
+
- **拒絕訊息指向的權限階,現在是真的會通過的那一階。** 無法分類的語句(`REPLACE
|
|
82
|
+
INTO`、`PRAGMA`、`VACUUM`、`REINDEX` 等)在 `query-only` 下被拒時宣稱需要
|
|
83
|
+
`read-write`,但沒有任何一階授予未知語句,取得 read-write 之後會再被拒一次。訊息
|
|
84
|
+
與 `required:` 欄位現在都說 `admin`,en 與 zh-TW 同步。判決完全沒變:本來拒絕的仍
|
|
85
|
+
然拒絕,本來允許的仍然允許。(DBCLI-037)
|
|
86
|
+
|
|
87
|
+
### Changed
|
|
88
|
+
|
|
89
|
+
- **capability catalog 的輸出改由契約守住,不再由 sha256 守住。** 三份渲染
|
|
90
|
+
(JSON/text/Markdown)的凍結雜湊換成結構性斷言:文件在釘住的 schema 版本下
|
|
91
|
+
parse 得過、三份渲染列出同一組 capability、每個 capability 指的 command 是 CLI 真的
|
|
92
|
+
帶得動的。catalog 是從 engine 矩陣推導出來的(ADR-0022),所以每次矩陣變動都會
|
|
93
|
+
移動那三個雜湊,而修法永遠是把現在的值抄回去——連續三次之後,它報告的是 diff
|
|
94
|
+
本來就說了的事。決定與被否決的選項記在 ADR-0039。使用者可見的輸出沒有變。
|
|
95
|
+
(DBCLI-038)
|
|
96
|
+
|
|
97
|
+
- **驗證 artifact 的秘密洩漏檢查改成逐欄檢查。** 原本在整份文件裡搜尋連線 port 的
|
|
98
|
+
四位數字,而 artifact 帶一個隨機後綴的 id,後綴湊出那四位數字時測試會紅——什麼都
|
|
99
|
+
沒洩漏,重跑就過。改為解析後逐欄走訪並指名帶著 port 的欄位;判準仍是包含而非
|
|
100
|
+
相等,藏在連線字串裡的 port 照樣抓得到。(DBCLI-039)
|
|
101
|
+
|
|
8
102
|
## [9.1.0] - 2026-09-11
|
|
9
103
|
|
|
10
104
|
ForgeFlow Story DBCLI-014 到 DBCLI-036 在 `v9.0.0` 之後交付。其中只有最後三張
|
package/README.md
CHANGED
|
@@ -1722,28 +1722,20 @@ below: `package.json` and `src/` never mention them, `.forgepilot/` is
|
|
|
1722
1722
|
gitignored local state, and a clone without any of them runs `make verify`
|
|
1723
1723
|
normally.
|
|
1724
1724
|
|
|
1725
|
-
### How work is specified
|
|
1726
|
-
|
|
1727
|
-
Each unit of work is a Story
|
|
1728
|
-
|
|
1729
|
-
|
|
1730
|
-
|
|
1731
|
-
|
|
1732
|
-
|
|
1733
|
-
`
|
|
1734
|
-
|
|
1735
|
-
|
|
1736
|
-
|
|
1737
|
-
|
|
1738
|
-
|
|
1739
|
-
rather than prose. That rule catches more than wording: clearing the last of it
|
|
1740
|
-
turned up three fixture rows that asserted nothing at all, and one row
|
|
1741
|
-
describing a mechanism that does not exist.
|
|
1742
|
-
|
|
1743
|
-
The exemption list in `scripts/lib/forgeflow-contract.ts` is a ratchet that may
|
|
1744
|
-
shrink and never grow. It is currently empty, so any finding at all fails the
|
|
1745
|
-
gate; adding an entry back requires lowering — never raising — the two counts
|
|
1746
|
-
beside it, which a test enforces.
|
|
1725
|
+
### How work is specified: Warrant
|
|
1726
|
+
|
|
1727
|
+
Each unit of work is a Story: one file, `specs/stories/<slug>.md`, with exactly
|
|
1728
|
+
three sections — Goal, Out of Scope, and Acceptance Criteria. A Story is
|
|
1729
|
+
approved only when a human commits it to the default branch or explicitly
|
|
1730
|
+
assigns it in the current session; an agent never approves its own. The
|
|
1731
|
+
contract agents follow is the `## Warrant` section of `AGENTS.md`, and
|
|
1732
|
+
`specs/stories/README.md` describes the format. The `DBCLI-*` directories under
|
|
1733
|
+
`specs/stories/` are legacy records from an earlier protocol, not pending work.
|
|
1734
|
+
|
|
1735
|
+
Warrant defines what a Story must contain and what counts as evidence: every
|
|
1736
|
+
acceptance criterion needs a reproducible observation, and the requirements,
|
|
1737
|
+
criteria, and scope stay as the human approved them. ForgePilot and
|
|
1738
|
+
`make verify` decide when it is done.
|
|
1747
1739
|
|
|
1748
1740
|
### When work is done: ForgePilot and `make verify`
|
|
1749
1741
|
|
|
@@ -1761,35 +1753,16 @@ no completion command — only a human can approve.
|
|
|
1761
1753
|
|
|
1762
1754
|
A decision that is hard to reverse, surprising without context, or the result of
|
|
1763
1755
|
a real trade-off gets a record in `docs/adr/`, named `ADR-<digits>-<slug>.md`
|
|
1764
|
-
with its status as a `* Status:` bullet rather than front matter.
|
|
1765
|
-
|
|
1766
|
-
|
|
1767
|
-
to be storable.
|
|
1756
|
+
with its status as a `* Status:` bullet rather than front matter. A record that
|
|
1757
|
+
is replaced stays in `docs/adr/` with `* Status: superseded` and a
|
|
1758
|
+
`* Superseded by:` bullet naming its successor. Open questions live there as
|
|
1759
|
+
`status: proposed`; undecided is a state that has to be storable.
|
|
1768
1760
|
|
|
1769
1761
|
Prefer closing a record with a falsification condition — one sentence saying
|
|
1770
1762
|
when the decision would no longer hold — naming the files it depends on in
|
|
1771
1763
|
backticks. Tooling reads the boundary list from those backticks, so the marker
|
|
1772
1764
|
is load-bearing rather than decorative.
|
|
1773
1765
|
|
|
1774
|
-
### The principle behind all of it
|
|
1775
|
-
|
|
1776
|
-
Every gate here is a variation on one lesson: **a declaration nothing compares
|
|
1777
|
-
to anything is not a control.** Delivery claims in the handoff are reconciled
|
|
1778
|
-
against commit trailers; the adopted ForgeFlow version is reconciled against
|
|
1779
|
-
every place that restates it; the ForgeFlow contract itself is run against a
|
|
1780
|
-
pinned upstream revision.
|
|
1781
|
-
|
|
1782
|
-
The lesson has a limit, and finding it cost a decision. A Story's `## Authority`
|
|
1783
|
-
was briefly reconciled against the fact of its delivery, on the reasoning that
|
|
1784
|
-
reaching `main` requires commits on a pushed branch (ADR-0030). It does — but
|
|
1785
|
-
`completed_stories` records that a Story was delivered, not **who** performed
|
|
1786
|
-
each operation, and the normal flow here is an agent that is granted `modify` and
|
|
1787
|
-
a local `commit` handing its branch to a human who pushes and merges. The gate
|
|
1788
|
-
refused that flow by name, so the rule was removed (ADR-0031). Whether an
|
|
1789
|
-
Authority declaration is true is a question this repository cannot observe and
|
|
1790
|
-
Human Review can; a gate that guesses at it is worse than an unchecked
|
|
1791
|
-
declaration, because its verdict looks like evidence.
|
|
1792
|
-
|
|
1793
1766
|
---
|
|
1794
1767
|
|
|
1795
1768
|
## License
|