@qijenchen/design-system 0.1.0-beta.50 → 0.1.0-beta.52
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/ds-canonical/hooks/check_story_invariants.sh +1 -1
- package/ds-canonical/hooks/stop_self_audit.sh +7 -4
- package/ds-canonical/hooks/tests/test_check_consumer_ds_primitive_misuse.sh +27 -1
- package/ds-canonical/hooks/tests/test_stop_self_audit.sh +10 -3
- package/ds-canonical/rules/self-verify.md +4 -4
- package/ds-story-manifest.json +1 -1
- package/package.json +1 -1
|
@@ -552,7 +552,7 @@ rule_story_archetype_registry() {
|
|
|
552
552
|
*/Sidebar/*|*/DataTable/*|*/header-canonical/*|*/Dialog/*|*/Sheet/*|*/Popover/*) return 0 ;;
|
|
553
553
|
esac
|
|
554
554
|
|
|
555
|
-
local REGISTRY="
|
|
555
|
+
local REGISTRY="${CLAUDE_PROJECT_DIR:-.}/.claude/references/story-baseline-registry.json"
|
|
556
556
|
[ -f "$REGISTRY" ] || return 0
|
|
557
557
|
|
|
558
558
|
local CONTENT=""
|
|
@@ -74,14 +74,17 @@ if [ -n "$TRANSCRIPT_PATH" ] && [ -f "$TRANSCRIPT_PATH" ]; then
|
|
|
74
74
|
fi
|
|
75
75
|
fi
|
|
76
76
|
|
|
77
|
-
# ── Mechanism
|
|
77
|
+
# ── Mechanism 7: Completeness-claim without DS-wide scan gate(2026-06-03 user-authorized)──
|
|
78
78
|
# Why: 重複 failure mode — AI 在「剛做完那件事」邊界就宣告「全做完/全部完成」,沒先跑 M10
|
|
79
79
|
# 「改一處看三處」全庫 stale-ref 掃描 → user 問「真的做完?」才補掃出 loose end(CF model 漏 3 ref
|
|
80
80
|
# / iceberg 等)。觸發器該是「我要宣告全做完」自己,不是 user pushback。
|
|
81
81
|
# per self-verify.md Pre-final + meta-patterns M10 + mindset #6「tell me once」。
|
|
82
82
|
if [ "${LAST_USER_LINE:-0}" -gt 0 ] && [ -n "$LAST_ASSISTANT" ]; then
|
|
83
83
|
COMPLETION_CLAIM_RE='(全做完|全部做完|都做完了|全部完成|所有任務.{0,6}(做完|完成)|100%.{0,4}完整|真的.{0,4}做完|全做到完)'
|
|
84
|
-
|
|
84
|
+
# 否定/免責排除(對齊 Mechanism 1 RETRACT_RE 精神,2026-06-03 修 M7 自身 false-positive):
|
|
85
|
+
# 宣告含「還沒說全做完」「沒資格說全做完」「核心做完…待跑」「等 X 才全做完/落地」等 disclaimer = 非完成宣告 → 不 fire。
|
|
86
|
+
COMPLETION_NEG_RE='(還沒.{0,6}(說|宣告|算|到)|沒.{0,3}(說|算|資格).{0,8}(全做完|完整)|未.{0,3}全做完|不(敢|算|是|該).{0,6}全做完|核心做完|完整性(掃描)?待|待.{0,4}(跑|落地|驗)|等.{0,18}(才|再).{0,8}(全做完|完整|落地|上架)|尚未.{0,4}完成)'
|
|
87
|
+
if echo "$LAST_ASSISTANT" | grep -qE "$COMPLETION_CLAIM_RE" && ! echo "$LAST_ASSISTANT" | grep -qE "$COMPLETION_NEG_RE"; then
|
|
85
88
|
THIS_TURN_FULL=$(tail -n +$((LAST_USER_LINE+1)) "$TRANSCRIPT_PATH" 2>/dev/null)
|
|
86
89
|
EDIT_COUNT=$(echo "$THIS_TURN_FULL" | grep -oE '"name":"(Edit|Write|MultiEdit)"' | wc -l | tr -d ' ')
|
|
87
90
|
HAS_COMMIT=$(echo "$THIS_TURN_FULL" | grep -cE 'git commit|git merge --ff')
|
|
@@ -494,7 +497,7 @@ if [ "${CRITICAL_CODEX_TRANSPORT:-0}" = "1" ] && [ -n "$LAST_ASSISTANT" ]; then
|
|
|
494
497
|
fi
|
|
495
498
|
fi
|
|
496
499
|
|
|
497
|
-
# ── BLOCKER for Mechanism
|
|
500
|
+
# ── BLOCKER for Mechanism 7 completeness-claim-without-scan(2026-06-03 user-authorized)──
|
|
498
501
|
if [ "${CRITICAL_COMPLETENESS:-0}" = "1" ] && [ -n "$LAST_ASSISTANT" ]; then
|
|
499
502
|
COMPLETE_HASH=$(echo "$LAST_ASSISTANT" | tail -c 200 | shasum -a 256 | cut -c1-16)
|
|
500
503
|
LAST_BLOCKED_COMPLETE_FILE="$PROJECT_DIR/.claude/logs/.last-blocked-completeness.txt"
|
|
@@ -503,7 +506,7 @@ if [ "${CRITICAL_COMPLETENESS:-0}" = "1" ] && [ -n "$LAST_ASSISTANT" ]; then
|
|
|
503
506
|
if [ "$COMPLETE_HASH" != "$LAST_BLOCKED_COMPLETE" ]; then
|
|
504
507
|
echo "$COMPLETE_HASH" > "$LAST_BLOCKED_COMPLETE_FILE" 2>/dev/null || true
|
|
505
508
|
REASON=$(printf '%s' \
|
|
506
|
-
"🚨 COMPLETENESS-CLAIM-WITHOUT-SCAN BLOCKER(
|
|
509
|
+
"🚨 COMPLETENESS-CLAIM-WITHOUT-SCAN BLOCKER(M7,2026-06-03 user-authorized):你宣告「全做完/全部完成」+ 本 turn 實質多檔改動,但無「全庫掃描」證據。per self-verify.md Pre-final + M10「改一處看三處」+ mindset #6:宣告全做完前必先自己跑 (1) DS-wide stale-ref grep(對你改的東西掃連帶 reference)(2) claim-verify 表(每『done』對應證據)。立刻補跑 OR 把『全做完』改成『核心做完,完整性掃描待跑』。否則 turn 不結束。" \
|
|
507
510
|
"本機制起因:重複 failure — user 每次問『真的全做完?』我才補掃出 loose end(CF model 漏 3 ref / iceberg)。觸發器改成『宣告完成』本身,非 user pushback。")
|
|
508
511
|
printf '{"decision":"block","reason":%s}\n' "$(printf '%s' "$REASON" | jq -Rs .)"
|
|
509
512
|
exit 0
|
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
# 排除 `packages/design-system/src/` + `node_modules/`
|
|
9
9
|
# - Content:tool_input.new_string // tool_input.content
|
|
10
10
|
# - Global escape:content 含 `@ds-misuse-allow:` → silent exit 0
|
|
11
|
-
# -
|
|
11
|
+
# - 7 anti-patterns(P1-P5 + P8 任何 .tsx/.ts;P6 僅 .stories.tsx):
|
|
12
12
|
# P1 <DS.CircularProgress size={N}> literal number override default 24
|
|
13
13
|
# P2 <DS.RadioGroupItem> 沒 wrap SelectionItem 且無 label=
|
|
14
14
|
# P3 <DS.DataTable columns={[single-col]}> minimal one-column
|
|
@@ -192,6 +192,32 @@ expect_silent "19. P6 nearmiss story <Dialog defaultOpen> → silent"
|
|
|
192
192
|
run_hook "$PROD_TSX" 'export const L = () => <DS.CircularProgress size={48} />' "Edit"
|
|
193
193
|
expect_block "20. Edit(new_string)<CircularProgress size={48}> → BLOCK"
|
|
194
194
|
|
|
195
|
+
# ── P8 硬寫色值/字級/shadow 繞 token(broad-vs-narrow symmetry,2026-06-02 CF conformance 主防線)──
|
|
196
|
+
|
|
197
|
+
# 21. POSITIVE:硬寫 hex 色 bg-[#hex] → BLOCK
|
|
198
|
+
run_hook "$PROD_TSX" 'export const C = () => <div className="bg-[#3b82f6] text-white">x</div>'
|
|
199
|
+
expect_block "21. P8 硬寫 hex 色 bg-[#hex] → BLOCK"
|
|
200
|
+
|
|
201
|
+
# 22. NEGATIVE over-broad guard:用 token bg-[var(--color-blue-6)] → silent
|
|
202
|
+
run_hook "$PROD_TSX" 'export const C = () => <div className="bg-[var(--color-blue-6)] text-body">x</div>'
|
|
203
|
+
expect_silent "22. P8 nearmiss bg-[var(--color-blue-6)] + text-body → silent"
|
|
204
|
+
|
|
205
|
+
# 23. POSITIVE:硬寫字級 text-[14px] → BLOCK
|
|
206
|
+
run_hook "$PROD_TSX" 'export const C = () => <p className="text-[14px]">x</p>'
|
|
207
|
+
expect_block "23. P8 硬寫字級 text-[14px] → BLOCK"
|
|
208
|
+
|
|
209
|
+
# 24. POSITIVE:raw shadow-md → BLOCK
|
|
210
|
+
run_hook "$PROD_TSX" 'export const C = () => <div className="shadow-md rounded">x</div>'
|
|
211
|
+
expect_block "24. P8 raw shadow-md → BLOCK"
|
|
212
|
+
|
|
213
|
+
# 25. NEGATIVE:用 elevation token shadow-[var(--elevation-100)] → silent
|
|
214
|
+
run_hook "$PROD_TSX" 'export const C = () => <div className="shadow-[var(--elevation-100)] rounded">x</div>'
|
|
215
|
+
expect_silent "25. P8 nearmiss shadow-[var(--elevation-100)] → silent"
|
|
216
|
+
|
|
217
|
+
# 26. NEGATIVE over-broad guard:arbitrary 非色/字級值(max-w-[600px] / grid layout)不該誤攔 → silent
|
|
218
|
+
run_hook "$PROD_TSX" 'export const C = () => <div className="max-w-[600px] grid-cols-[1fr_2fr]">x</div>'
|
|
219
|
+
expect_silent "26. P8 nearmiss max-w-[600px]/grid-cols-[...](非色字 shadow)→ silent"
|
|
220
|
+
|
|
195
221
|
echo ""
|
|
196
222
|
echo "=== Summary ==="
|
|
197
223
|
echo "Passed: $PASS / $((PASS + FAIL))"
|
|
@@ -69,12 +69,12 @@ T6="$USER_MSG
|
|
|
69
69
|
"'{"message":{"role":"assistant","content":[{"type":"text","text":"我這次明確不 claim verified,只 tsc 過,實際 browser 行為要 user 驗"}]}}'
|
|
70
70
|
run_test "Test 6: preemptive claim denial → no block" 0 "$T6"
|
|
71
71
|
|
|
72
|
-
# Test 7: Mechanism
|
|
72
|
+
# Test 7: Mechanism 7 完整性宣告閘 — 宣告「全部做完」+ 2 edits + 無全庫掃描 → BLOCK
|
|
73
73
|
T7="$USER_MSG
|
|
74
74
|
"'{"message":{"role":"assistant","content":[{"type":"tool_use","name":"Edit","input":{}}]}}
|
|
75
75
|
{"message":{"role":"assistant","content":[{"type":"tool_use","name":"Write","input":{}}]}}
|
|
76
76
|
{"message":{"role":"assistant","content":[{"type":"text","text":"全部做完了,beta 已上架,tree 乾淨。"}]}}'
|
|
77
|
-
run_test "Test 7:
|
|
77
|
+
run_test "Test 7: M7 完整性宣告+多改+無掃描 → block" 1 "$T7"
|
|
78
78
|
|
|
79
79
|
# Test 8: 同上但本 turn 有 grep -rn 全庫掃描 → no block(掃描證據被認列)
|
|
80
80
|
T8="$USER_MSG
|
|
@@ -82,7 +82,14 @@ T8="$USER_MSG
|
|
|
82
82
|
{"message":{"role":"assistant","content":[{"type":"tool_use","name":"Bash","input":{"command":"grep -rn foo .claude packages"}}]}}
|
|
83
83
|
{"message":{"role":"assistant","content":[{"type":"tool_use","name":"Write","input":{}}]}}
|
|
84
84
|
{"message":{"role":"assistant","content":[{"type":"text","text":"全部做完了,已全庫掃描確認無 loose end。"}]}}'
|
|
85
|
-
run_test "Test 8:
|
|
85
|
+
run_test "Test 8: M7 完整性宣告+多改+有全庫掃描 → no block" 0 "$T8"
|
|
86
|
+
|
|
87
|
+
# Test 9: M7 negation 排除 — 含「全做完」字串但是 disclaimer(還沒說全做完)+ 多改 + 無掃描 → NO block
|
|
88
|
+
T9="$USER_MSG
|
|
89
|
+
"'{"message":{"role":"assistant","content":[{"type":"tool_use","name":"Edit","input":{}}]}}
|
|
90
|
+
{"message":{"role":"assistant","content":[{"type":"tool_use","name":"Write","input":{}}]}}
|
|
91
|
+
{"message":{"role":"assistant","content":[{"type":"text","text":"還沒說「全做完」——等 beta.51 落地 + 最後掃過才有資格。核心做完,完整性掃描待跑。"}]}}'
|
|
92
|
+
run_test "Test 9: M7 negation disclaimer(還沒說全做完)→ no block" 0 "$T9"
|
|
86
93
|
|
|
87
94
|
# Cleanup state file
|
|
88
95
|
rm -f "$PROJECT_DIR"/.claude/logs/.last-blocked-*.txt 2>/dev/null
|
|
@@ -33,7 +33,8 @@
|
|
|
33
33
|
|
|
34
34
|
- **Pre-edit**:`check_substantive_edit_approval_preflight.sh`(production code)+ `stop_self_audit.sh`(spec/canonical 補位)+ `check_ds_anchor_preflight.sh`(M29 anchor)
|
|
35
35
|
- **Post-edit**:`stop_self_audit.sh` Mechanism 1(claim-verify-gap)BLOCKER
|
|
36
|
-
- **Pre-final(宣告完成前)**:`stop_self_audit.sh` Mechanism
|
|
36
|
+
- **Pre-final(宣告完成前)**:`stop_self_audit.sh` Mechanism 7(完整性宣告閘)BLOCKER — 宣告「全做完 / 全部完成」+ 本 turn 實質改動但**無全庫 stale-ref 掃描證據** → block。**觸發器 = 「宣告完成」本身,非等 user 問第二次**(2026-06-03 user-authorized,根治重複 failure)
|
|
37
|
+
- **Pre-final(重大 / SSOT / 模型 / 跨多檔改動)**:除 M7 自掃外,**宣告完成前必跑「獨立對抗稽核」**(multi-agent Workflow,每路假設「還有 loose end」主動去找 + cite 證據)。**理由**:self-grep 系統性漏(self-assessment unreliable,對齊 `feedback_ai_ground_truth_unreliable_mechanical_primary`)+ 信任機械閘(preflight / R4 / hook BLOCKER)勝於自評。**小改 = M7 自掃即可**,不需對抗稽核(避免過度)。2026-06-03 user-authorized,根治「宣告做完 → user 問第 N 次 → 才補掃出 loose end」
|
|
37
38
|
- **Pre-commit**:`scripts/audit-content-quality.mjs --check` + `scripts/extract-canonical-rules.mjs` 各 fail = block
|
|
38
39
|
|
|
39
40
|
## Anti-pattern(永久 ban)
|
|
@@ -43,9 +44,8 @@
|
|
|
43
44
|
- ❌ 改 hook 沒跑 syntax check + smoke test
|
|
44
45
|
- ❌「下個 session 補」defer 可做的 verify(M33 違反)
|
|
45
46
|
- ❌ pass-through Explore / codex propose 沒 own-version 比稿
|
|
46
|
-
- ❌ 宣告「全做完 / 全部完成」前沒自己跑 M10「改一處看三處」全庫 stale-ref 掃描 → 等 user 問「真的做完?」才補掃出 loose end(
|
|
47
|
-
|
|
48
|
-
## 對齊歷史
|
|
47
|
+
- ❌ 宣告「全做完 / 全部完成」前沒自己跑 M10「改一處看三處」全庫 stale-ref 掃描 → 等 user 問「真的做完?」才補掃出 loose end(M7 BLOCKER;anchor:CF model 改完漏 3 ref / iceberg)
|
|
48
|
+
- ❌ **重大 / SSOT / 模型改動只靠自 grep 就宣告完成** → 漏 fragility / 沒貫徹到 consumer。2026-06-03 anchor:R8 用相對路徑讀 registry 非 root cwd 靜默失效、CF 模型修沒貫徹到 App.tsx marker — **全是 4-agent 對抗稽核 + preflight/R4 機械閘抓到,自 grep 漏了**。重大改動宣告前必跑獨立對抗稽核 + 信任機械 preflight 勝於自評
|
|
49
49
|
|
|
50
50
|
- Linux kernel:`scripts/checkpatch.pl` pre-submit + `git log --oneline | head -3` 後 sign-off
|
|
51
51
|
- Toyota TPS:Jidoka(自働化)— 機器發現異常自己停,人別繼續(對應 hook BLOCKER)
|
package/ds-story-manifest.json
CHANGED
|
@@ -7,7 +7,7 @@
|
|
|
7
7
|
"scripts/composition-fidelity-visual-diff.mjs",
|
|
8
8
|
"product-workspace apps/template/src/AllDsComponents.stories.tsx (DsCanonicalPortal)"
|
|
9
9
|
],
|
|
10
|
-
"generatedAt": "2026-06-
|
|
10
|
+
"generatedAt": "2026-06-03T00:56:52.022Z"
|
|
11
11
|
},
|
|
12
12
|
"components": {
|
|
13
13
|
"accordion": {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@qijenchen/design-system",
|
|
3
|
-
"version": "0.1.0-beta.
|
|
3
|
+
"version": "0.1.0-beta.52",
|
|
4
4
|
"private": false,
|
|
5
5
|
"description": "World-class design system — components, patterns, tokens, hooks (single source of truth for team distribution).",
|
|
6
6
|
"type": "module",
|