spec-runner 1.0.6 → 1.0.8
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 +36 -184
- package/bin/spec-runner.js +157 -703
- package/install.sh +6 -12
- package/package.json +3 -7
- package/templates/.spec-runner/hooks/pre-commit +47 -0
- package/templates/.spec-runner/hooks/pre-push +9 -0
- package/templates/.spec-runner/project.json.example +27 -0
- package/templates/.spec-runner/scripts/branch/uc-next-start.sh +172 -0
- package/templates/.spec-runner/scripts/check.sh +403 -0
- package/templates/.spec-runner/scripts/spec-runner-core.sh +411 -0
- package/templates/.spec-runner/scripts/test/require-tests-green.sh +27 -0
- package/templates/.spec-runner/spec-runner.sh +30 -0
- package/templates/.spec-runner/steps/steps.json +171 -0
- package/templates/.spec-runner/steps//343/201/235/343/201/256/344/273/226/344/275/234/346/245/255.md +34 -0
- package/templates/.spec-runner/steps//343/202/277/343/202/271/343/202/257/344/270/200/350/246/247.md +95 -0
- package/templates/.spec-runner/steps//343/203/201/343/202/247/343/203/203/343/202/257/343/203/252/343/202/271/343/203/210.md +80 -0
- package/templates/.spec-runner/steps//343/203/206/343/202/271/343/203/210/350/250/255/350/250/210.md +57 -0
- package/templates/.spec-runner/steps//343/203/211/343/203/241/343/202/244/343/203/263/350/250/255/350/250/210.md +52 -0
- package/templates/.spec-runner/steps//344/273/225/346/247/230/347/255/226/345/256/232.md +173 -0
- package/templates/.spec-runner/steps//345/210/206/346/236/220.md +104 -0
- package/templates/.spec-runner/steps//345/256/237/350/243/205.md +79 -0
- package/templates/.spec-runner/steps//345/256/237/350/243/205/350/250/210/347/224/273.md +96 -0
- package/templates/.spec-runner/steps//346/206/262/347/253/240.md +95 -0
- package/templates/.spec-runner/steps//346/233/226/346/230/247/343/201/225/350/247/243/346/266/210.md +99 -0
- package/templates/.spec-runner/templates/UC-N-MMDD-/345/210/244/346/226/255/350/250/230/351/214/262/343/203/206/343/203/263/343/203/227/343/203/254.md +33 -0
- package/templates/.spec-runner/templates/UC-N-/343/203/246/343/203/274/343/202/271/343/202/261/343/203/274/343/202/271/345/220/215.md +20 -0
- package/templates/.spec-runner/templates/grade-history.json +5 -0
- package/templates/.spec-runner/templates/phase-locks.json +29 -0
- package/templates/.spec-runner/templates//343/203/211/343/203/241/343/202/244/343/203/263/343/203/242/343/203/207/343/203/253.md +21 -0
- package/templates/.spec-runner/templates//343/203/246/343/203/223/343/202/255/343/202/277/343/202/271/350/250/200/350/252/236/350/276/236/346/233/270.md +16 -0
- package/templates/.spec-runner/templates//346/206/262/347/253/240.md +51 -0
- package/templates/.spec-runner/templates//351/233/206/347/264/204.md +46 -0
- package/templates/spec-runner-command.md +42 -0
- package/templates/base/.github/PULL_REQUEST_TEMPLATE.md +0 -43
- package/templates/base/.github/workflows/phase-gate-check.yml +0 -216
- package/templates/base/scripts/spec-runner.sh +0 -1144
- package/templates/base/templates/01_/350/246/201/344/273/266/345/256/232/347/276/251//343/201/262/343/201/252/345/275/242.md +0 -40
- package/templates/base/templates/03_/350/251/263/347/264/260/350/250/255/350/250/210//343/202/244/343/203/263/343/203/225/343/203/251.md +0 -14
- package/templates/base/templates/03_/350/251/263/347/264/260/350/250/255/350/250/210//343/203/206/343/203/274/343/203/226/343/203/253.md +0 -17
- package/templates/base/templates/03_/350/251/263/347/264/260/350/250/255/350/250/210//343/203/211/343/203/241/343/202/244/343/203/263.md +0 -18
- package/templates/base/templates/03_/350/251/263/347/264/260/350/250/255/350/250/210//343/203/246/343/203/274/343/202/271/343/202/261/343/203/274/343/202/271.md +0 -12
- package/templates/base/templates/99_/350/250/255/350/250/210/345/210/244/346/226/255/350/250/230/351/214/262//343/201/262/343/201/252/345/275/242.md +0 -46
- package/templates/base/templates/README.md +0 -32
- package/templates/base/templates//345/210/235/346/234/237/343/203/211/343/202/255/343/203/245/343/203/241/343/203/263/343/203/210/01_/346/206/262/347/253/240.md +0 -48
- package/templates/base/templates//345/210/235/346/234/237/343/203/211/343/202/255/343/203/245/343/203/241/343/203/263/343/203/210/02_/344/273/225/346/247/230.md +0 -39
- package/templates/base/templates//345/210/235/346/234/237/343/203/211/343/202/255/343/203/245/343/203/241/343/203/263/343/203/210/03_/347/224/250/350/252/236/351/233/206.md +0 -51
- package/templates/base/templates//345/210/235/346/234/237/343/203/211/343/202/255/343/203/245/343/203/241/343/203/263/343/203/210/99_/350/250/255/350/250/210/345/210/244/346/226/255/350/250/230/351/214/262/.gitkeep +0 -0
- package/templates/base/templates//345/210/235/346/234/237/343/203/211/343/202/255/343/203/245/343/203/241/343/203/263/343/203/210//343/203/206/343/203/263/343/203/227/343/203/254/343/203/274/343/203/210/344/270/200/350/246/247.md +0 -14
- package/templates/base/templates//345/210/235/346/234/237/343/203/211/343/202/255/343/203/245/343/203/241/343/203/263/343/203/210//346/214/257/343/202/212/350/277/224/343/202/212//350/262/240/345/202/265.md +0 -8
- package/templates/claude/.claude/commands/sr-/343/202/262/343/203/274/343/203/210/350/250/255/345/256/232.md +0 -9
- package/templates/claude/.claude/commands/sr-/343/203/206/343/202/271/343/203/210/350/250/255/350/250/210.md +0 -9
- package/templates/claude/.claude/commands/sr-/343/203/254/343/203/223/343/203/245/343/203/274.md +0 -9
- package/templates/claude/.claude/commands/sr-/344/273/225/346/247/230.md +0 -9
- package/templates/claude/.claude/commands/sr-/344/277/256/346/255/243.md +0 -9
- package/templates/claude/.claude/commands/sr-/345/210/235/346/234/237/345/214/226.md +0 -10
- package/templates/claude/.claude/commands/sr-/345/256/237/350/243/205.md +0 -9
- package/templates/claude/.claude/commands/sr-/346/206/262/347/253/240.md +0 -9
- package/templates/claude/.claude/commands/sr-/346/246/202/350/246/201/350/250/255/350/250/210.md +0 -9
- package/templates/claude/.claude/commands/sr-/347/212/266/346/205/213.md +0 -9
- package/templates/claude/.claude/commands/sr-/347/267/212/346/200/245/344/277/256/346/255/243.md +0 -9
- package/templates/claude/.claude/commands/sr-/350/250/255/345/256/232.md +0 -11
- package/templates/claude/.claude/commands/sr-/350/251/263/347/264/260/350/250/255/350/250/210.md +0 -9
- package/templates/claude/.claude/hooks/pre-tool-use.sh +0 -79
- package/templates/claude/.claude/settings.json +0 -29
- package/templates/claude/CLAUDE.md +0 -141
- package/templates/copilot/.github/copilot-instructions.md +0 -25
- package/templates/copilot/.github/prompts/sr-/343/202/262/343/203/274/343/203/210/350/250/255/345/256/232.prompt.md +0 -14
- package/templates/copilot/.github/prompts/sr-/343/203/206/343/202/271/343/203/210/350/250/255/350/250/210.prompt.md +0 -13
- package/templates/copilot/.github/prompts/sr-/343/203/254/343/203/223/343/203/245/343/203/274.prompt.md +0 -14
- package/templates/copilot/.github/prompts/sr-/344/273/225/346/247/230.prompt.md +0 -13
- package/templates/copilot/.github/prompts/sr-/344/277/256/346/255/243.prompt.md +0 -14
- package/templates/copilot/.github/prompts/sr-/345/210/235/346/234/237/345/214/226.prompt.md +0 -15
- package/templates/copilot/.github/prompts/sr-/345/256/237/350/243/205.prompt.md +0 -13
- package/templates/copilot/.github/prompts/sr-/346/206/262/347/253/240.prompt.md +0 -13
- package/templates/copilot/.github/prompts/sr-/346/246/202/350/246/201/350/250/255/350/250/210.prompt.md +0 -13
- package/templates/copilot/.github/prompts/sr-/347/212/266/346/205/213.prompt.md +0 -13
- package/templates/copilot/.github/prompts/sr-/347/267/212/346/200/245/344/277/256/346/255/243.prompt.md +0 -14
- package/templates/copilot/.github/prompts/sr-/350/250/255/345/256/232.prompt.md +0 -13
- package/templates/copilot/.github/prompts/sr-/350/251/263/347/264/260/350/250/255/350/250/210.prompt.md +0 -14
- package/templates/cursor/.cursor/commands/sr-/343/202/262/343/203/274/343/203/210/350/250/255/345/256/232.md +0 -11
- package/templates/cursor/.cursor/commands/sr-/343/203/206/343/202/271/343/203/210/350/250/255/350/250/210.md +0 -9
- package/templates/cursor/.cursor/commands/sr-/343/203/254/343/203/223/343/203/245/343/203/274.md +0 -9
- package/templates/cursor/.cursor/commands/sr-/344/273/225/346/247/230.md +0 -9
- package/templates/cursor/.cursor/commands/sr-/344/277/256/346/255/243.md +0 -9
- package/templates/cursor/.cursor/commands/sr-/345/210/235/346/234/237/345/214/226.md +0 -35
- package/templates/cursor/.cursor/commands/sr-/345/256/237/350/243/205.md +0 -9
- package/templates/cursor/.cursor/commands/sr-/346/206/262/347/253/240.md +0 -9
- package/templates/cursor/.cursor/commands/sr-/346/246/202/350/246/201/350/250/255/350/250/210.md +0 -9
- package/templates/cursor/.cursor/commands/sr-/347/212/266/346/205/213.md +0 -9
- package/templates/cursor/.cursor/commands/sr-/347/267/212/346/200/245/344/277/256/346/255/243.md +0 -9
- package/templates/cursor/.cursor/commands/sr-/350/250/255/345/256/232.md +0 -20
- package/templates/cursor/.cursor/commands/sr-/350/251/263/347/264/260/350/250/255/350/250/210.md +0 -9
- package/templates/cursor/.cursorrules +0 -26
package/install.sh
CHANGED
|
@@ -1,13 +1,11 @@
|
|
|
1
1
|
#!/usr/bin/env bash
|
|
2
|
-
#
|
|
3
|
-
# spec-runner インストーラー (curl 方式)
|
|
2
|
+
# spec-runner 用インストーラ(curl 用)
|
|
4
3
|
#
|
|
5
4
|
# 使い方:
|
|
6
|
-
# curl -sSL https://raw.githubusercontent.com/
|
|
5
|
+
# curl -sSL https://raw.githubusercontent.com/TEEE88/spec-runner/main/install.sh | bash
|
|
7
6
|
#
|
|
8
7
|
# または wget:
|
|
9
|
-
# wget -qO- https://raw.githubusercontent.com/
|
|
10
|
-
# =============================================================================
|
|
8
|
+
# wget -qO- https://raw.githubusercontent.com/TEEE88/spec-runner/main/install.sh | bash
|
|
11
9
|
|
|
12
10
|
set -e
|
|
13
11
|
|
|
@@ -25,12 +23,11 @@ die() { echo -e "${RED}ERROR:${NC} $*" >&2; exit 1; }
|
|
|
25
23
|
|
|
26
24
|
echo ""
|
|
27
25
|
echo -e "${BOLD}╔════════════════════════════════════════╗${NC}"
|
|
28
|
-
echo -e "${BOLD}║ spec-runner
|
|
29
|
-
echo -e "${BOLD}║
|
|
26
|
+
echo -e "${BOLD}║ spec-runner インストーラ ║${NC}"
|
|
27
|
+
echo -e "${BOLD}║ フェーズ駆動 / 次のステップ方式 ║${NC}"
|
|
30
28
|
echo -e "${BOLD}╚════════════════════════════════════════╝${NC}"
|
|
31
29
|
echo ""
|
|
32
30
|
|
|
33
|
-
# ── Node.js チェック ──────────────────────────────────────────────────────────
|
|
34
31
|
if command -v node &>/dev/null; then
|
|
35
32
|
NODE_VERSION=$(node --version | sed 's/v//')
|
|
36
33
|
NODE_MAJOR=$(echo "$NODE_VERSION" | cut -d. -f1)
|
|
@@ -42,7 +39,6 @@ else
|
|
|
42
39
|
die "Node.js がインストールされていません。\n https://nodejs.org からインストールしてください"
|
|
43
40
|
fi
|
|
44
41
|
|
|
45
|
-
# ── jq チェック ───────────────────────────────────────────────────────────────
|
|
46
42
|
if command -v jq &>/dev/null; then
|
|
47
43
|
ok "jq $(jq --version)"
|
|
48
44
|
else
|
|
@@ -56,10 +52,9 @@ else
|
|
|
56
52
|
else
|
|
57
53
|
die "jq を手動でインストールしてください: https://stedolan.github.io/jq/download/"
|
|
58
54
|
fi
|
|
59
|
-
ok "jq
|
|
55
|
+
ok "jq インストール済み"
|
|
60
56
|
fi
|
|
61
57
|
|
|
62
|
-
# ── git チェック ──────────────────────────────────────────────────────────────
|
|
63
58
|
if command -v git &>/dev/null; then
|
|
64
59
|
ok "git $(git --version | awk '{print $3}')"
|
|
65
60
|
else
|
|
@@ -70,7 +65,6 @@ echo ""
|
|
|
70
65
|
info "npx spec-runner を実行します..."
|
|
71
66
|
echo ""
|
|
72
67
|
|
|
73
|
-
# ── npm/npx で実行 ────────────────────────────────────────────────────────────
|
|
74
68
|
if command -v npx &>/dev/null; then
|
|
75
69
|
npx spec-runner@latest
|
|
76
70
|
elif command -v npm &>/dev/null; then
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "spec-runner",
|
|
3
|
-
"version": "1.0.
|
|
4
|
-
"description": "
|
|
3
|
+
"version": "1.0.8",
|
|
4
|
+
"description": "フェーズ駆動で設計先行を強制。npx で .spec-runner を展開し、次のステップ .md に従って進める",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"bin": {
|
|
7
7
|
"spec-runner": "bin/spec-runner.js"
|
|
@@ -22,6 +22,7 @@
|
|
|
22
22
|
"nextjs",
|
|
23
23
|
"spec-kit"
|
|
24
24
|
],
|
|
25
|
+
"scripts": {},
|
|
25
26
|
"files": [
|
|
26
27
|
"bin/",
|
|
27
28
|
"templates/",
|
|
@@ -29,11 +30,6 @@
|
|
|
29
30
|
"README.md",
|
|
30
31
|
"LICENSE"
|
|
31
32
|
],
|
|
32
|
-
"dependencies": {
|
|
33
|
-
"chalk": "^4.1.2",
|
|
34
|
-
"enquirer": "^2.3.6",
|
|
35
|
-
"ora": "^5.4.1"
|
|
36
|
-
},
|
|
37
33
|
"repository": {
|
|
38
34
|
"type": "git",
|
|
39
35
|
"url": "git+https://github.com/TEEE88/spec-runner.git"
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
#!/bin/bash
|
|
2
|
+
# spec-runner pre-commit: ブランチ名チェック + 命名規則チェック(Section 8-4)
|
|
3
|
+
|
|
4
|
+
set -e
|
|
5
|
+
REPO_ROOT="$(git rev-parse --show-toplevel 2>/dev/null)"
|
|
6
|
+
[[ -n "$REPO_ROOT" ]] || exit 0
|
|
7
|
+
|
|
8
|
+
branch=$(git branch --show-current)
|
|
9
|
+
|
|
10
|
+
pj="$REPO_ROOT/.spec-runner/project.json"
|
|
11
|
+
[[ -f "$pj" ]] || { echo "pre-commit: project.json がありません: $pj" >&2; exit 1; }
|
|
12
|
+
command -v jq >/dev/null 2>&1 || { echo "pre-commit: jq が必要です(brew install jq)" >&2; exit 1; }
|
|
13
|
+
bp="$(jq -r '.naming.branch_prefix // "feature"' "$pj" 2>/dev/null)"
|
|
14
|
+
uc_id_pat="$(jq -r '.naming.uc_id_pattern // "UC-[0-9]+"' "$pj" 2>/dev/null)"
|
|
15
|
+
other_work="$(jq -r '.naming.other_work_prefixes[]? | . + "/.+"' "$pj" 2>/dev/null | tr '\n' '|' | sed 's/|$//')"
|
|
16
|
+
[[ -z "$other_work" ]] && other_work="work/.+|infra/.+|cicd/.+"
|
|
17
|
+
valid_pattern="^(main|develop|${bp}/(${uc_id_pat}-.+|${other_work})|fix/${uc_id_pat}-.+|release/[0-9]+\\.[0-9]+\\.[0-9]+.*|hotfix/[0-9]+\\.[0-9]+\\.[0-9]+-.+)$"
|
|
18
|
+
|
|
19
|
+
if ! echo "$branch" | grep -qE "$valid_pattern"; then
|
|
20
|
+
echo "❌ ブランチ名が規則違反: $branch"
|
|
21
|
+
echo " 正しい形式:"
|
|
22
|
+
if [[ -f "$REPO_ROOT/.spec-runner/project.json" ]] && command -v jq >/dev/null 2>&1; then
|
|
23
|
+
bp=$(jq -r '.naming.branch_prefix // "feature"' "$REPO_ROOT/.spec-runner/project.json" 2>/dev/null || echo "feature")
|
|
24
|
+
else
|
|
25
|
+
bp="feature"
|
|
26
|
+
fi
|
|
27
|
+
echo " ${bp}/{UC-ID}-{kebab-description} (新規UC、UC-IDは project.json の uc_id_pattern)"
|
|
28
|
+
echo " ${bp}/cicd/xxx ${bp}/infra/xxx (その他作業、project.json の other_work_prefixes)"
|
|
29
|
+
echo " fix/{UC-ID}-{kebab-description} (修正)"
|
|
30
|
+
echo " release/{semver} (リリース)"
|
|
31
|
+
echo " hotfix/{semver}-{kebab-description} (緊急修正)"
|
|
32
|
+
exit 1
|
|
33
|
+
fi
|
|
34
|
+
|
|
35
|
+
# 命名規則チェック(.spec-runner スクリプトがある場合のみ実行)
|
|
36
|
+
if [[ -d "$REPO_ROOT/src" ]]; then
|
|
37
|
+
while IFS= read -r dir; do
|
|
38
|
+
[[ -z "$dir" ]] && continue
|
|
39
|
+
base=$(basename "$dir")
|
|
40
|
+
if ! echo "$base" | grep -qE '^[a-z][a-z0-9-]*$'; then
|
|
41
|
+
echo "NAMING: フォルダ名「$dir」はkebab-caseで命名してください" >&2
|
|
42
|
+
exit 1
|
|
43
|
+
fi
|
|
44
|
+
done < <(find "$REPO_ROOT/src/" -type d 2>/dev/null || true)
|
|
45
|
+
fi
|
|
46
|
+
|
|
47
|
+
exit 0
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
{
|
|
2
|
+
"_comment": "AI が編集して作成。other_work_prefixes は UC 以外の作業用ブランチ(例: feature/cicd/xxx)。",
|
|
3
|
+
"_comment_required_docs": "required_docs は steps.json を単一ソースにするため、\"steps:<common.docsキー>[/suffix]\" を指定できる(例: steps:openapi, steps:domain_root/集約.md)。",
|
|
4
|
+
"naming": {
|
|
5
|
+
"branch_prefix": "feature",
|
|
6
|
+
"uc_id_pattern": "UC-[0-9]+",
|
|
7
|
+
"uc_spec_basename": "{uc_id}-{slug}.md",
|
|
8
|
+
"adr_basename": "MMDD-{title}.md",
|
|
9
|
+
"docs_05_categories": true,
|
|
10
|
+
"other_work_prefixes": ["work", "infra", "cicd"]
|
|
11
|
+
},
|
|
12
|
+
"required_docs": {
|
|
13
|
+
"charter": ["steps:charter"],
|
|
14
|
+
"domain": ["steps:domain_root/ユビキタス言語辞書.md", "steps:domain_root/ドメインモデル.md", "steps:domain_root/集約.md"],
|
|
15
|
+
"architecture": ["steps:architecture_root/パターン選定.md", "steps:architecture_root/インフラ方針.md", "steps:architecture_root/設計判断記録"],
|
|
16
|
+
"grade_a": ["steps:infra_root/schema.dbml"],
|
|
17
|
+
"gate3_openapi": ["steps:openapi"]
|
|
18
|
+
},
|
|
19
|
+
"test_design": {
|
|
20
|
+
"dir": "tests",
|
|
21
|
+
"pattern": "*.spec.*",
|
|
22
|
+
"require_uc_prefixed_tests": true
|
|
23
|
+
},
|
|
24
|
+
"test_command": {
|
|
25
|
+
"run": "npm test"
|
|
26
|
+
}
|
|
27
|
+
}
|
|
@@ -0,0 +1,172 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
# 次の UC を開始する: main に切り替え、feature/UC-N-xxx ブランチを作成する。
|
|
3
|
+
# 使用例:
|
|
4
|
+
# ./uc-next-start.sh # 次 UC 番号を自動検出。説明はプロンプトまたは "next-uc" で作成
|
|
5
|
+
# ./uc-next-start.sh task-update # 次 UC 番号 + 説明 "task-update" でブランチ作成
|
|
6
|
+
# ./uc-next-start.sh task-update 認証 # 次 UC 番号 + 説明 + カテゴリ
|
|
7
|
+
# ./uc-next-start.sh UC-2 task-update # 指定 UC + 説明
|
|
8
|
+
# ./uc-next-start.sh UC-2 task-update 認証 # 指定 UC + 説明 + カテゴリ
|
|
9
|
+
# ./uc-next-start.sh --yes task-update # 確認なしで実行
|
|
10
|
+
# 実行後は次のステップに進む旨を案内する。
|
|
11
|
+
|
|
12
|
+
set -e
|
|
13
|
+
REPO_ROOT="${REPO_ROOT:-$(git rev-parse --show-toplevel 2>/dev/null || echo ".")}"
|
|
14
|
+
cd "$REPO_ROOT"
|
|
15
|
+
BRANCH_DIR="$(cd "$(dirname "$0")" && pwd)"
|
|
16
|
+
|
|
17
|
+
YES_MODE=false
|
|
18
|
+
ARGS=()
|
|
19
|
+
for a in "$@"; do
|
|
20
|
+
case "$a" in
|
|
21
|
+
--yes|-y) YES_MODE=true ;;
|
|
22
|
+
*) ARGS+=("$a") ;;
|
|
23
|
+
esac
|
|
24
|
+
done
|
|
25
|
+
|
|
26
|
+
PROJECT_JSON="$REPO_ROOT/.spec-runner/project.json"
|
|
27
|
+
[[ -f "$PROJECT_JSON" ]] || { echo "uc-next-start: project.json がありません: $PROJECT_JSON" >&2; exit 1; }
|
|
28
|
+
command -v jq >/dev/null 2>&1 || { echo "uc-next-start: jq が必要です(brew install jq)" >&2; exit 1; }
|
|
29
|
+
UC_ID_RE="$(jq -r '.naming.uc_id_pattern' "$PROJECT_JSON")"
|
|
30
|
+
BRANCH_PREFIX="$(jq -r '.naming.branch_prefix' "$PROJECT_JSON")"
|
|
31
|
+
[[ -n "$UC_ID_RE" && "$UC_ID_RE" != "null" && -n "$BRANCH_PREFIX" && "$BRANCH_PREFIX" != "null" ]] || {
|
|
32
|
+
echo "uc-next-start: project.json の naming.uc_id_pattern / branch_prefix が未設定です" >&2
|
|
33
|
+
exit 1
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
next_uc_id() {
|
|
37
|
+
# docs/02_ユースケース仕様/<カテゴリ>/UC-*.md から次に使う UC-N を返す
|
|
38
|
+
local dir="$REPO_ROOT/docs/02_ユースケース仕様"
|
|
39
|
+
mkdir -p "$dir"
|
|
40
|
+
local max=0
|
|
41
|
+
for f in "$dir"/*/UC-*.md; do
|
|
42
|
+
[[ -e "$f" ]] || continue
|
|
43
|
+
base=$(basename "$f" .md)
|
|
44
|
+
if [[ "$base" =~ ^(${UC_ID_RE})- ]]; then
|
|
45
|
+
uc_id="${BASH_REMATCH[1]}"
|
|
46
|
+
digits=$(echo "$uc_id" | tr -cd '0-9')
|
|
47
|
+
[[ -z "$digits" ]] && continue
|
|
48
|
+
n=$((10#$digits))
|
|
49
|
+
[[ $n -gt $max ]] && max=$n
|
|
50
|
+
fi
|
|
51
|
+
done
|
|
52
|
+
printf "UC-%d\n" $((max + 1))
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
NEXT_UC="$(next_uc_id)"
|
|
56
|
+
DESC=""
|
|
57
|
+
CATEGORY=""
|
|
58
|
+
|
|
59
|
+
# ファイル題名は日本語優先にするため、スクリプト引数の「生の説明」を保持する
|
|
60
|
+
RAW_DESC=""
|
|
61
|
+
if [[ ${#ARGS[@]} -ge 2 ]] && [[ "${ARGS[0]}" =~ ^${UC_ID_RE}$ ]]; then
|
|
62
|
+
NEXT_UC="${ARGS[0]}"
|
|
63
|
+
DESC="${ARGS[1]}"
|
|
64
|
+
RAW_DESC="${ARGS[1]}"
|
|
65
|
+
CATEGORY="${ARGS[2]:-}"
|
|
66
|
+
elif [[ ${#ARGS[@]} -ge 1 ]]; then
|
|
67
|
+
DESC="${ARGS[0]}"
|
|
68
|
+
RAW_DESC="${ARGS[0]}"
|
|
69
|
+
CATEGORY="${ARGS[1]:-}"
|
|
70
|
+
fi
|
|
71
|
+
|
|
72
|
+
# 説明が無ければデフォルト(next-uc や UC 番号ベース)
|
|
73
|
+
if [[ -z "$DESC" ]]; then
|
|
74
|
+
if [[ "$YES_MODE" == true ]]; then
|
|
75
|
+
DESC="next-uc"
|
|
76
|
+
else
|
|
77
|
+
echo "次の UC 用ブランチを作成します。"
|
|
78
|
+
echo " UC: $NEXT_UC"
|
|
79
|
+
echo -n " 説明(英数字・ハイフン推奨。日本語のみの場合は uc-001 等にフォールバック。Enter で \"next-uc\"): "
|
|
80
|
+
read -r DESC
|
|
81
|
+
DESC="${DESC:-next-uc}"
|
|
82
|
+
fi
|
|
83
|
+
fi
|
|
84
|
+
|
|
85
|
+
# 説明は英小文字・ハイフン(Git ブランチ名は ASCII のみ)。日本語など非 ASCII はサニタイズで除去される
|
|
86
|
+
# macOS(BSD sed) でも動くように、連続ハイフンは 's/--*/-/g' で圧縮する
|
|
87
|
+
DESC=$(echo "$DESC" | tr '[:upper:]' '[:lower:]' | sed 's/[^a-z0-9]/-/g' | sed 's/--*/-/g' | sed 's/^-*//' | sed 's/-*$//')
|
|
88
|
+
# サニタイズ後に空(日本語のみの説明など)の場合は UC 番号ベースのスラグでフォールバック
|
|
89
|
+
[[ -z "$DESC" ]] && DESC="uc-$(echo "$NEXT_UC" | sed 's/^UC-//')"
|
|
90
|
+
BRANCH_NAME="${BRANCH_PREFIX}/${NEXT_UC}-${DESC}"
|
|
91
|
+
|
|
92
|
+
# UC 仕様書ファイル名は必ず日本語にする(題名が ASCII のみなら「要確認」にする)
|
|
93
|
+
DOC_TITLE="$RAW_DESC"
|
|
94
|
+
if [[ -z "$DOC_TITLE" ]]; then
|
|
95
|
+
DOC_TITLE="要確認"
|
|
96
|
+
else
|
|
97
|
+
# 非ASCIIが無い(= 英数字/記号のみ)なら、日本語題名が無い扱いにして要確認へ
|
|
98
|
+
if echo "$DOC_TITLE" | LC_ALL=C grep -q '^[ -~]*$'; then
|
|
99
|
+
DOC_TITLE="要確認"
|
|
100
|
+
fi
|
|
101
|
+
fi
|
|
102
|
+
# ファイル名に危険な文字が入らないように除去(日本語は許可)
|
|
103
|
+
DOC_TITLE=$(echo "$DOC_TITLE" | sed 's/[\\\\\\/\\:\\*\\?\\\"\\<\\>\\|]/ /g' | sed 's/[[:space:]]\\+/ /g' | sed 's/^ *//; s/ *$//')
|
|
104
|
+
[[ -z "$DOC_TITLE" ]] && DOC_TITLE="要確認"
|
|
105
|
+
|
|
106
|
+
# カテゴリ(省略時はデフォルト)。日本語カテゴリは許可し、危険文字だけ除去。
|
|
107
|
+
CATEGORY="${CATEGORY:-ユースケース}"
|
|
108
|
+
CATEGORY=$(echo "$CATEGORY" | sed 's/[^a-zA-Z0-9_ーぁ-んァ-ン一-龥\-]//g')
|
|
109
|
+
[[ -z "$CATEGORY" ]] && CATEGORY="ユースケース"
|
|
110
|
+
|
|
111
|
+
if git rev-parse --verify "$BRANCH_NAME" >/dev/null 2>&1; then
|
|
112
|
+
echo "Error: ブランチ '$BRANCH_NAME' は既に存在します。" >&2
|
|
113
|
+
exit 1
|
|
114
|
+
fi
|
|
115
|
+
|
|
116
|
+
CURRENT=$(git branch --show-current 2>/dev/null || echo "")
|
|
117
|
+
MAIN_BRANCH="main"
|
|
118
|
+
if ! git rev-parse --verify "$MAIN_BRANCH" >/dev/null 2>&1; then
|
|
119
|
+
MAIN_BRANCH="master"
|
|
120
|
+
if ! git rev-parse --verify "$MAIN_BRANCH" >/dev/null 2>&1; then
|
|
121
|
+
echo "Error: main も master も存在しません。" >&2
|
|
122
|
+
exit 1
|
|
123
|
+
fi
|
|
124
|
+
fi
|
|
125
|
+
|
|
126
|
+
if [[ "$YES_MODE" != true ]]; then
|
|
127
|
+
echo "次の UC を開始する準備をします。"
|
|
128
|
+
echo " $MAIN_BRANCH にチェックアウトし、ブランチ \"$BRANCH_NAME\" を作成します。"
|
|
129
|
+
echo -n " 実行してよろしいですか? [y/N]: "
|
|
130
|
+
read -r ans
|
|
131
|
+
case "$ans" in
|
|
132
|
+
[yY]|[yY][eE][sS]) ;;
|
|
133
|
+
*) echo "キャンセルしました。"; exit 0 ;;
|
|
134
|
+
esac
|
|
135
|
+
fi
|
|
136
|
+
|
|
137
|
+
git checkout "$MAIN_BRANCH"
|
|
138
|
+
git pull --ff-only 2>/dev/null || true
|
|
139
|
+
|
|
140
|
+
# ブランチ作成 + UC 仕様書作成(統合)
|
|
141
|
+
UC_ID_PATTERN="^${UC_ID_RE}$"
|
|
142
|
+
if ! echo "$NEXT_UC" | grep -qE "$UC_ID_PATTERN"; then
|
|
143
|
+
echo "Error: UC-ID が命名規則に合いません: $NEXT_UC(期待: $UC_ID_PATTERN)" >&2
|
|
144
|
+
exit 1
|
|
145
|
+
fi
|
|
146
|
+
valid_uc_pattern="^${BRANCH_PREFIX}/${UC_ID_RE}-[a-z0-9-]+\$"
|
|
147
|
+
if ! echo "$BRANCH_NAME" | grep -qE "$valid_uc_pattern"; then
|
|
148
|
+
echo "Error: ブランチ名が命名規則に合いません: $BRANCH_NAME(期待: ${BRANCH_PREFIX}/<UC-ID>-kebab-description)" >&2
|
|
149
|
+
exit 1
|
|
150
|
+
fi
|
|
151
|
+
|
|
152
|
+
git checkout -b "$BRANCH_NAME"
|
|
153
|
+
echo "Created branch: $BRANCH_NAME"
|
|
154
|
+
|
|
155
|
+
FEATURE_DIR="docs/02_ユースケース仕様/${CATEGORY}"
|
|
156
|
+
UC_DOC="${FEATURE_DIR}/${NEXT_UC}-${DOC_TITLE}.md"
|
|
157
|
+
mkdir -p "$FEATURE_DIR"
|
|
158
|
+
# UC ごとの判断ログ置き場(任意だが、作成しておくと運用が安定する)
|
|
159
|
+
mkdir -p "${FEATURE_DIR}/判断記録"
|
|
160
|
+
# テンプレ: 修正・改善は .spec-runner/templates/UC-N-ユースケース名.md を編集。プレースホルダ UC-N → UC番号, {ユースケース名} → 題名
|
|
161
|
+
TEMPLATE="$REPO_ROOT/.spec-runner/templates/UC-N-ユースケース名.md"
|
|
162
|
+
if [[ -f "$TEMPLATE" ]]; then
|
|
163
|
+
sed "s/UC-N/${NEXT_UC}/g; s/{ユースケース名}/${DOC_TITLE}/g" "$TEMPLATE" > "$UC_DOC"
|
|
164
|
+
echo "Created: $UC_DOC"
|
|
165
|
+
else
|
|
166
|
+
touch "$UC_DOC"
|
|
167
|
+
echo "# ${NEXT_UC}: ${DOC_TITLE}" >> "$UC_DOC"
|
|
168
|
+
echo "Created: $UC_DOC"
|
|
169
|
+
fi
|
|
170
|
+
|
|
171
|
+
echo ""
|
|
172
|
+
echo "次の UC 用ブランチの準備ができました。次のステップに進んでください。"
|