safeword 0.2.4 → 0.2.5
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/dist/check-3NGQ4NR5.js +129 -0
- package/dist/check-3NGQ4NR5.js.map +1 -0
- package/dist/chunk-2XWIUEQK.js +190 -0
- package/dist/chunk-2XWIUEQK.js.map +1 -0
- package/dist/chunk-GZRQL3SX.js +146 -0
- package/dist/chunk-GZRQL3SX.js.map +1 -0
- package/dist/chunk-ORQHKDT2.js +10 -0
- package/dist/chunk-ORQHKDT2.js.map +1 -0
- package/dist/chunk-W66Z3C5H.js +21 -0
- package/dist/chunk-W66Z3C5H.js.map +1 -0
- package/dist/cli.d.ts +1 -0
- package/dist/cli.js +34 -0
- package/dist/cli.js.map +1 -0
- package/dist/diff-Y6QTAW4O.js +166 -0
- package/dist/diff-Y6QTAW4O.js.map +1 -0
- package/dist/index.d.ts +11 -0
- package/dist/index.js +7 -0
- package/dist/index.js.map +1 -0
- package/dist/reset-3ACTIYYE.js +143 -0
- package/dist/reset-3ACTIYYE.js.map +1 -0
- package/dist/setup-RR4M334C.js +266 -0
- package/dist/setup-RR4M334C.js.map +1 -0
- package/dist/upgrade-6AR3DHUV.js +134 -0
- package/dist/upgrade-6AR3DHUV.js.map +1 -0
- package/package.json +44 -19
- package/{.safeword → templates}/hooks/agents-md-check.sh +0 -0
- package/{.safeword → templates}/hooks/post-tool.sh +0 -0
- package/{.safeword → templates}/hooks/pre-commit.sh +0 -0
- package/.claude/commands/arch-review.md +0 -32
- package/.claude/commands/lint.md +0 -6
- package/.claude/commands/quality-review.md +0 -13
- package/.claude/commands/setup-linting.md +0 -6
- package/.claude/hooks/auto-lint.sh +0 -6
- package/.claude/hooks/auto-quality-review.sh +0 -170
- package/.claude/hooks/check-linting-sync.sh +0 -17
- package/.claude/hooks/inject-timestamp.sh +0 -6
- package/.claude/hooks/question-protocol.sh +0 -12
- package/.claude/hooks/run-linters.sh +0 -8
- package/.claude/hooks/run-quality-review.sh +0 -76
- package/.claude/hooks/version-check.sh +0 -10
- package/.claude/mcp/README.md +0 -96
- package/.claude/mcp/arcade.sample.json +0 -9
- package/.claude/mcp/context7.sample.json +0 -7
- package/.claude/mcp/playwright.sample.json +0 -7
- package/.claude/settings.json +0 -62
- package/.claude/skills/quality-reviewer/SKILL.md +0 -190
- package/.claude/skills/safeword-quality-reviewer/SKILL.md +0 -13
- package/.env.arcade.example +0 -4
- package/.env.example +0 -11
- package/.gitmodules +0 -4
- package/.safeword/SAFEWORD.md +0 -33
- package/.safeword/eslint/eslint-base.mjs +0 -101
- package/.safeword/guides/architecture-guide.md +0 -404
- package/.safeword/guides/code-philosophy.md +0 -174
- package/.safeword/guides/context-files-guide.md +0 -405
- package/.safeword/guides/data-architecture-guide.md +0 -183
- package/.safeword/guides/design-doc-guide.md +0 -165
- package/.safeword/guides/learning-extraction.md +0 -515
- package/.safeword/guides/llm-instruction-design.md +0 -239
- package/.safeword/guides/llm-prompting.md +0 -95
- package/.safeword/guides/tdd-best-practices.md +0 -570
- package/.safeword/guides/test-definitions-guide.md +0 -243
- package/.safeword/guides/testing-methodology.md +0 -573
- package/.safeword/guides/user-story-guide.md +0 -237
- package/.safeword/guides/zombie-process-cleanup.md +0 -214
- package/.safeword/planning/002-user-story-quality-evaluation.md +0 -1840
- package/.safeword/planning/003-langsmith-eval-setup-prompt.md +0 -363
- package/.safeword/planning/004-llm-eval-test-cases.md +0 -3226
- package/.safeword/planning/005-architecture-enforcement-system.md +0 -169
- package/.safeword/planning/006-reactive-fix-prevention-research.md +0 -135
- package/.safeword/planning/011-cli-ux-vision.md +0 -330
- package/.safeword/planning/012-project-structure-cleanup.md +0 -154
- package/.safeword/planning/README.md +0 -39
- package/.safeword/planning/automation-plan-v2.md +0 -1225
- package/.safeword/planning/automation-plan-v3.md +0 -1291
- package/.safeword/planning/automation-plan.md +0 -3058
- package/.safeword/planning/design/005-cli-implementation.md +0 -343
- package/.safeword/planning/design/013-cli-self-contained-templates.md +0 -596
- package/.safeword/planning/design/013a-eslint-plugin-suite.md +0 -256
- package/.safeword/planning/design/013b-implementation-snippets.md +0 -385
- package/.safeword/planning/design/013c-config-isolation-strategy.md +0 -242
- package/.safeword/planning/design/code-philosophy-improvements.md +0 -60
- package/.safeword/planning/mcp-analysis.md +0 -545
- package/.safeword/planning/phase2-subagents-vs-skills-analysis.md +0 -451
- package/.safeword/planning/settings-improvements.md +0 -970
- package/.safeword/planning/test-definitions/005-cli-implementation.md +0 -1301
- package/.safeword/planning/test-definitions/cli-self-contained-templates.md +0 -205
- package/.safeword/planning/user-stories/001-guides-review-user-stories.md +0 -1381
- package/.safeword/planning/user-stories/003-reactive-fix-prevention.md +0 -132
- package/.safeword/planning/user-stories/004-technical-constraints.md +0 -86
- package/.safeword/planning/user-stories/005-cli-implementation.md +0 -311
- package/.safeword/planning/user-stories/cli-self-contained-templates.md +0 -172
- package/.safeword/planning/versioned-distribution.md +0 -740
- package/.safeword/prompts/arch-review.md +0 -43
- package/.safeword/prompts/quality-review.md +0 -11
- package/.safeword/scripts/arch-review.sh +0 -235
- package/.safeword/scripts/check-linting-sync.sh +0 -58
- package/.safeword/scripts/setup-linting.sh +0 -559
- package/.safeword/templates/architecture-template.md +0 -136
- package/.safeword/templates/ci/architecture-check.yml +0 -79
- package/.safeword/templates/design-doc-template.md +0 -127
- package/.safeword/templates/test-definitions-feature.md +0 -100
- package/.safeword/templates/ticket-template.md +0 -74
- package/.safeword/templates/user-stories-template.md +0 -82
- package/.safeword/tickets/001-guides-review-user-stories.md +0 -83
- package/.safeword/tickets/002-architecture-enforcement.md +0 -211
- package/.safeword/tickets/003-reactive-fix-prevention.md +0 -57
- package/.safeword/tickets/004-technical-constraints-in-user-stories.md +0 -39
- package/.safeword/tickets/005-cli-implementation.md +0 -248
- package/.safeword/tickets/006-flesh-out-skills.md +0 -43
- package/.safeword/tickets/007-flesh-out-questioning.md +0 -44
- package/.safeword/tickets/008-upgrade-questioning.md +0 -58
- package/.safeword/tickets/009-naming-conventions.md +0 -41
- package/.safeword/tickets/010-safeword-md-cleanup.md +0 -34
- package/.safeword/tickets/011-cursor-setup.md +0 -86
- package/.safeword/tickets/README.md +0 -73
- package/.safeword/version +0 -1
- package/AGENTS.md +0 -59
- package/CLAUDE.md +0 -12
- package/README.md +0 -347
- package/docs/001-cli-implementation-plan.md +0 -856
- package/docs/elite-dx-implementation-plan.md +0 -1034
- package/framework/README.md +0 -131
- package/framework/mcp/README.md +0 -96
- package/framework/mcp/arcade.sample.json +0 -8
- package/framework/mcp/context7.sample.json +0 -6
- package/framework/mcp/playwright.sample.json +0 -6
- package/framework/scripts/arch-review.sh +0 -235
- package/framework/scripts/check-linting-sync.sh +0 -58
- package/framework/scripts/load-env.sh +0 -49
- package/framework/scripts/setup-claude.sh +0 -223
- package/framework/scripts/setup-linting.sh +0 -559
- package/framework/scripts/setup-quality.sh +0 -477
- package/framework/scripts/setup-safeword.sh +0 -550
- package/framework/templates/ci/architecture-check.yml +0 -78
- package/learnings/ai-sdk-v5-breaking-changes.md +0 -178
- package/learnings/e2e-test-zombie-processes.md +0 -231
- package/learnings/milkdown-crepe-editor-property.md +0 -96
- package/learnings/prosemirror-fragment-traversal.md +0 -119
- package/packages/cli/AGENTS.md +0 -1
- package/packages/cli/ARCHITECTURE.md +0 -279
- package/packages/cli/package.json +0 -51
- package/packages/cli/src/cli.ts +0 -63
- package/packages/cli/src/commands/check.ts +0 -166
- package/packages/cli/src/commands/diff.ts +0 -209
- package/packages/cli/src/commands/reset.ts +0 -190
- package/packages/cli/src/commands/setup.ts +0 -325
- package/packages/cli/src/commands/upgrade.ts +0 -163
- package/packages/cli/src/index.ts +0 -3
- package/packages/cli/src/templates/config.ts +0 -58
- package/packages/cli/src/templates/content.ts +0 -18
- package/packages/cli/src/templates/index.ts +0 -12
- package/packages/cli/src/utils/agents-md.ts +0 -66
- package/packages/cli/src/utils/fs.ts +0 -179
- package/packages/cli/src/utils/git.ts +0 -124
- package/packages/cli/src/utils/hooks.ts +0 -29
- package/packages/cli/src/utils/output.ts +0 -60
- package/packages/cli/src/utils/project-detector.test.ts +0 -185
- package/packages/cli/src/utils/project-detector.ts +0 -44
- package/packages/cli/src/utils/version.ts +0 -28
- package/packages/cli/src/version.ts +0 -6
- package/packages/cli/templates/SAFEWORD.md +0 -776
- package/packages/cli/templates/doc-templates/architecture-template.md +0 -136
- package/packages/cli/templates/doc-templates/design-doc-template.md +0 -134
- package/packages/cli/templates/doc-templates/test-definitions-feature.md +0 -131
- package/packages/cli/templates/doc-templates/ticket-template.md +0 -82
- package/packages/cli/templates/doc-templates/user-stories-template.md +0 -92
- package/packages/cli/templates/guides/architecture-guide.md +0 -423
- package/packages/cli/templates/guides/code-philosophy.md +0 -195
- package/packages/cli/templates/guides/context-files-guide.md +0 -457
- package/packages/cli/templates/guides/data-architecture-guide.md +0 -200
- package/packages/cli/templates/guides/design-doc-guide.md +0 -171
- package/packages/cli/templates/guides/learning-extraction.md +0 -552
- package/packages/cli/templates/guides/llm-instruction-design.md +0 -248
- package/packages/cli/templates/guides/llm-prompting.md +0 -102
- package/packages/cli/templates/guides/tdd-best-practices.md +0 -615
- package/packages/cli/templates/guides/test-definitions-guide.md +0 -334
- package/packages/cli/templates/guides/testing-methodology.md +0 -618
- package/packages/cli/templates/guides/user-story-guide.md +0 -256
- package/packages/cli/templates/guides/zombie-process-cleanup.md +0 -219
- package/packages/cli/templates/hooks/agents-md-check.sh +0 -27
- package/packages/cli/templates/hooks/post-tool.sh +0 -4
- package/packages/cli/templates/hooks/pre-commit.sh +0 -10
- package/packages/cli/templates/prompts/arch-review.md +0 -43
- package/packages/cli/templates/prompts/quality-review.md +0 -10
- package/packages/cli/templates/skills/safeword-quality-reviewer/SKILL.md +0 -207
- package/packages/cli/tests/commands/check.test.ts +0 -129
- package/packages/cli/tests/commands/cli.test.ts +0 -89
- package/packages/cli/tests/commands/diff.test.ts +0 -115
- package/packages/cli/tests/commands/reset.test.ts +0 -310
- package/packages/cli/tests/commands/self-healing.test.ts +0 -170
- package/packages/cli/tests/commands/setup-blocking.test.ts +0 -71
- package/packages/cli/tests/commands/setup-core.test.ts +0 -135
- package/packages/cli/tests/commands/setup-git.test.ts +0 -139
- package/packages/cli/tests/commands/setup-hooks.test.ts +0 -334
- package/packages/cli/tests/commands/setup-linting.test.ts +0 -189
- package/packages/cli/tests/commands/setup-noninteractive.test.ts +0 -80
- package/packages/cli/tests/commands/setup-templates.test.ts +0 -181
- package/packages/cli/tests/commands/upgrade.test.ts +0 -215
- package/packages/cli/tests/helpers.ts +0 -243
- package/packages/cli/tests/npm-package.test.ts +0 -83
- package/packages/cli/tests/technical-constraints.test.ts +0 -96
- package/packages/cli/tsconfig.json +0 -25
- package/packages/cli/tsup.config.ts +0 -11
- package/packages/cli/vitest.config.ts +0 -23
- package/promptfoo.yaml +0 -3270
- /package/{framework → templates}/SAFEWORD.md +0 -0
- /package/{packages/cli/templates → templates}/commands/arch-review.md +0 -0
- /package/{packages/cli/templates → templates}/commands/lint.md +0 -0
- /package/{packages/cli/templates → templates}/commands/quality-review.md +0 -0
- /package/{framework/templates → templates/doc-templates}/architecture-template.md +0 -0
- /package/{framework/templates → templates/doc-templates}/design-doc-template.md +0 -0
- /package/{framework/templates → templates/doc-templates}/test-definitions-feature.md +0 -0
- /package/{framework/templates → templates/doc-templates}/ticket-template.md +0 -0
- /package/{framework/templates → templates/doc-templates}/user-stories-template.md +0 -0
- /package/{framework → templates}/guides/architecture-guide.md +0 -0
- /package/{framework → templates}/guides/code-philosophy.md +0 -0
- /package/{framework → templates}/guides/context-files-guide.md +0 -0
- /package/{framework → templates}/guides/data-architecture-guide.md +0 -0
- /package/{framework → templates}/guides/design-doc-guide.md +0 -0
- /package/{framework → templates}/guides/learning-extraction.md +0 -0
- /package/{framework → templates}/guides/llm-instruction-design.md +0 -0
- /package/{framework → templates}/guides/llm-prompting.md +0 -0
- /package/{framework → templates}/guides/tdd-best-practices.md +0 -0
- /package/{framework → templates}/guides/test-definitions-guide.md +0 -0
- /package/{framework → templates}/guides/testing-methodology.md +0 -0
- /package/{framework → templates}/guides/user-story-guide.md +0 -0
- /package/{framework → templates}/guides/zombie-process-cleanup.md +0 -0
- /package/{packages/cli/templates → templates}/hooks/inject-timestamp.sh +0 -0
- /package/{packages/cli/templates → templates}/lib/common.sh +0 -0
- /package/{packages/cli/templates → templates}/lib/jq-fallback.sh +0 -0
- /package/{packages/cli/templates → templates}/markdownlint.jsonc +0 -0
- /package/{framework → templates}/prompts/arch-review.md +0 -0
- /package/{framework → templates}/prompts/quality-review.md +0 -0
- /package/{framework/skills/quality-reviewer → templates/skills/safeword-quality-reviewer}/SKILL.md +0 -0
|
@@ -1,559 +0,0 @@
|
|
|
1
|
-
#!/bin/bash
|
|
2
|
-
################################################################################
|
|
3
|
-
# Claude Code Linting Hook Setup Script
|
|
4
|
-
#
|
|
5
|
-
# Automatically detects project type and configures ESLint + Prettier.
|
|
6
|
-
#
|
|
7
|
-
# Architecture:
|
|
8
|
-
# .safeword/eslint/eslint-base.mjs ← Auto-generated every run. Don't edit.
|
|
9
|
-
# eslint.config.mjs ← Your config. Customize freely.
|
|
10
|
-
#
|
|
11
|
-
# Usage:
|
|
12
|
-
# bash setup-linting.sh # Setup/update linting
|
|
13
|
-
# bash setup-linting.sh --no-typescript # Skip TypeScript detection
|
|
14
|
-
# bash setup-linting.sh --no-react # Skip React detection
|
|
15
|
-
#
|
|
16
|
-
# Auto-detection:
|
|
17
|
-
# - TypeScript: tsconfig.json OR typescript in package.json
|
|
18
|
-
# - React: react in package.json
|
|
19
|
-
# - Astro: astro in package.json
|
|
20
|
-
################################################################################
|
|
21
|
-
|
|
22
|
-
set -e
|
|
23
|
-
|
|
24
|
-
VERSION="v3.1.0"
|
|
25
|
-
|
|
26
|
-
# Parse arguments
|
|
27
|
-
SKIP_TYPESCRIPT=false
|
|
28
|
-
SKIP_REACT=false
|
|
29
|
-
SKIP_ASTRO=false
|
|
30
|
-
|
|
31
|
-
while [[ $# -gt 0 ]]; do
|
|
32
|
-
case $1 in
|
|
33
|
-
--no-typescript|--no-ts) SKIP_TYPESCRIPT=true; shift ;;
|
|
34
|
-
--no-react) SKIP_REACT=true; shift ;;
|
|
35
|
-
--no-astro) SKIP_ASTRO=true; shift ;;
|
|
36
|
-
--help|-h)
|
|
37
|
-
echo "Usage: bash setup-linting.sh [options]"
|
|
38
|
-
echo ""
|
|
39
|
-
echo "Options:"
|
|
40
|
-
echo " --no-typescript Skip TypeScript even if detected"
|
|
41
|
-
echo " --no-react Skip React even if detected"
|
|
42
|
-
echo " --no-astro Skip Astro even if detected"
|
|
43
|
-
echo ""
|
|
44
|
-
echo "Files:"
|
|
45
|
-
echo " $BASE_DIR/eslint-base.mjs - Auto-generated (updated every run)"
|
|
46
|
-
echo " eslint.config.mjs - Your config (created once, never overwritten)"
|
|
47
|
-
exit 0
|
|
48
|
-
;;
|
|
49
|
-
*) echo "Unknown option: $1 (use --help for usage)"; exit 1 ;;
|
|
50
|
-
esac
|
|
51
|
-
done
|
|
52
|
-
|
|
53
|
-
echo "================================="
|
|
54
|
-
echo "Claude Code Linting Setup"
|
|
55
|
-
echo "Version: $VERSION"
|
|
56
|
-
echo "================================="
|
|
57
|
-
echo ""
|
|
58
|
-
|
|
59
|
-
PROJECT_ROOT="$(pwd)"
|
|
60
|
-
echo "Setting up in: $PROJECT_ROOT"
|
|
61
|
-
echo ""
|
|
62
|
-
|
|
63
|
-
# ============================================================================
|
|
64
|
-
# Step 1: Detect project type
|
|
65
|
-
# ============================================================================
|
|
66
|
-
echo "[1/5] Detecting project type..."
|
|
67
|
-
|
|
68
|
-
HAS_TYPESCRIPT=false
|
|
69
|
-
HAS_REACT=false
|
|
70
|
-
HAS_ASTRO=false
|
|
71
|
-
|
|
72
|
-
# Read dependencies from package.json
|
|
73
|
-
if [ -f package.json ] && command -v jq &> /dev/null; then
|
|
74
|
-
DEPS=$(jq -r '(.dependencies // {}), (.devDependencies // {}) | keys[]' package.json 2>/dev/null || echo "")
|
|
75
|
-
elif [ -f package.json ]; then
|
|
76
|
-
DEPS=$(grep -E '"[^"]+"\s*:' package.json | cut -d'"' -f2)
|
|
77
|
-
else
|
|
78
|
-
DEPS=""
|
|
79
|
-
fi
|
|
80
|
-
|
|
81
|
-
# TypeScript detection
|
|
82
|
-
if [ "$SKIP_TYPESCRIPT" = false ]; then
|
|
83
|
-
if [ -f tsconfig.json ] || echo "$DEPS" | grep -qx "typescript"; then
|
|
84
|
-
HAS_TYPESCRIPT=true
|
|
85
|
-
echo " ✓ TypeScript detected"
|
|
86
|
-
fi
|
|
87
|
-
fi
|
|
88
|
-
|
|
89
|
-
# React detection
|
|
90
|
-
if [ "$SKIP_REACT" = false ]; then
|
|
91
|
-
if echo "$DEPS" | grep -qx "react"; then
|
|
92
|
-
HAS_REACT=true
|
|
93
|
-
echo " ✓ React detected"
|
|
94
|
-
fi
|
|
95
|
-
fi
|
|
96
|
-
|
|
97
|
-
# Astro detection
|
|
98
|
-
if [ "$SKIP_ASTRO" = false ]; then
|
|
99
|
-
if echo "$DEPS" | grep -qx "astro"; then
|
|
100
|
-
HAS_ASTRO=true
|
|
101
|
-
echo " ✓ Astro detected"
|
|
102
|
-
fi
|
|
103
|
-
fi
|
|
104
|
-
|
|
105
|
-
[ "$HAS_TYPESCRIPT" = false ] && [ "$HAS_REACT" = false ] && [ "$HAS_ASTRO" = false ] && echo " → JavaScript-only project"
|
|
106
|
-
echo ""
|
|
107
|
-
|
|
108
|
-
# ============================================================================
|
|
109
|
-
# Step 2: Create package.json if needed
|
|
110
|
-
# ============================================================================
|
|
111
|
-
echo "[2/5] Checking package.json..."
|
|
112
|
-
|
|
113
|
-
if [ ! -f package.json ]; then
|
|
114
|
-
cat > package.json << 'EOF'
|
|
115
|
-
{
|
|
116
|
-
"name": "my-project",
|
|
117
|
-
"version": "1.0.0",
|
|
118
|
-
"type": "module",
|
|
119
|
-
"scripts": {},
|
|
120
|
-
"devDependencies": {}
|
|
121
|
-
}
|
|
122
|
-
EOF
|
|
123
|
-
echo " ✓ Created package.json"
|
|
124
|
-
else
|
|
125
|
-
echo " ✓ package.json exists"
|
|
126
|
-
fi
|
|
127
|
-
echo ""
|
|
128
|
-
|
|
129
|
-
# ============================================================================
|
|
130
|
-
# Step 3: Install packages
|
|
131
|
-
# ============================================================================
|
|
132
|
-
echo "[3/5] Installing packages..."
|
|
133
|
-
|
|
134
|
-
# Base packages (always installed)
|
|
135
|
-
PACKAGES="eslint @eslint/js prettier eslint-config-prettier globals"
|
|
136
|
-
PACKAGES+=" eslint-plugin-sonarjs @microsoft/eslint-plugin-sdl eslint-plugin-boundaries"
|
|
137
|
-
|
|
138
|
-
# Conditional packages
|
|
139
|
-
[ "$HAS_TYPESCRIPT" = true ] && PACKAGES+=" typescript-eslint"
|
|
140
|
-
[ "$HAS_REACT" = true ] && PACKAGES+=" @eslint-react/eslint-plugin eslint-plugin-react-hooks eslint-plugin-react-perf"
|
|
141
|
-
[ "$HAS_ASTRO" = true ] && PACKAGES+=" eslint-plugin-astro"
|
|
142
|
-
|
|
143
|
-
echo " Installing: $PACKAGES"
|
|
144
|
-
npm install --save-dev $PACKAGES --silent 2>&1 | grep -v "npm WARN" || true
|
|
145
|
-
echo " ✓ Packages installed"
|
|
146
|
-
echo ""
|
|
147
|
-
|
|
148
|
-
# ============================================================================
|
|
149
|
-
# Step 4: Generate ESLint configs
|
|
150
|
-
# ============================================================================
|
|
151
|
-
echo "[4/5] Generating ESLint configs..."
|
|
152
|
-
|
|
153
|
-
mkdir -p .safeword
|
|
154
|
-
|
|
155
|
-
# --- Always generate .safeword/eslint-base.mjs ---
|
|
156
|
-
BASE_DIR=".safeword/eslint"
|
|
157
|
-
mkdir -p "$BASE_DIR"
|
|
158
|
-
echo " Generating $BASE_DIR/eslint-base.mjs..."
|
|
159
|
-
|
|
160
|
-
# Build the file with prominent header
|
|
161
|
-
cat > "$BASE_DIR/eslint-base.mjs" << 'HEADER'
|
|
162
|
-
////////////////////////////////////////////////////////////////////////////////
|
|
163
|
-
//
|
|
164
|
-
// ██████╗ ██████╗ ███╗ ██╗ ██████╗ ████████╗ ███████╗██████╗ ██╗████████╗
|
|
165
|
-
// ██╔══██╗██╔═══██╗ ████╗ ██║██╔═══██╗╚══██╔══╝ ██╔════╝██╔══██╗██║╚══██╔══╝
|
|
166
|
-
// ██║ ██║██║ ██║ ██╔██╗ ██║██║ ██║ ██║ █████╗ ██║ ██║██║ ██║
|
|
167
|
-
// ██║ ██║██║ ██║ ██║╚██╗██║██║ ██║ ██║ ██╔══╝ ██║ ██║██║ ██║
|
|
168
|
-
// ██████╔╝╚██████╔╝ ██║ ╚████║╚██████╔╝ ██║ ███████╗██████╔╝██║ ██║
|
|
169
|
-
// ╚═════╝ ╚═════╝ ╚═╝ ╚═══╝ ╚═════╝ ╚═╝ ╚══════╝╚═════╝ ╚═╝ ╚═╝
|
|
170
|
-
//
|
|
171
|
-
// AUTO-GENERATED FILE - DO NOT EDIT
|
|
172
|
-
//
|
|
173
|
-
// This file is regenerated every time you run:
|
|
174
|
-
// bash setup-linting.sh
|
|
175
|
-
//
|
|
176
|
-
// To customize ESLint rules, edit eslint.config.mjs instead.
|
|
177
|
-
// Your customizations there are preserved across regenerations.
|
|
178
|
-
//
|
|
179
|
-
////////////////////////////////////////////////////////////////////////////////
|
|
180
|
-
|
|
181
|
-
import { globalIgnores } from 'eslint/config';
|
|
182
|
-
import js from '@eslint/js';
|
|
183
|
-
HEADER
|
|
184
|
-
|
|
185
|
-
[ "$HAS_TYPESCRIPT" = true ] && echo "import tseslint from 'typescript-eslint';" >> "$BASE_DIR/eslint-base.mjs"
|
|
186
|
-
[ "$HAS_REACT" = true ] && cat >> "$BASE_DIR/eslint-base.mjs" << 'REACT_IMPORTS'
|
|
187
|
-
import reactPlugin from '@eslint-react/eslint-plugin';
|
|
188
|
-
import reactHooks from 'eslint-plugin-react-hooks';
|
|
189
|
-
import reactPerf from 'eslint-plugin-react-perf';
|
|
190
|
-
REACT_IMPORTS
|
|
191
|
-
[ "$HAS_ASTRO" = true ] && echo "import astroPlugin from 'eslint-plugin-astro';" >> "$BASE_DIR/eslint-base.mjs"
|
|
192
|
-
|
|
193
|
-
cat >> "$BASE_DIR/eslint-base.mjs" << 'COMMON_IMPORTS'
|
|
194
|
-
import sonarjs from 'eslint-plugin-sonarjs';
|
|
195
|
-
import sdl from '@microsoft/eslint-plugin-sdl';
|
|
196
|
-
import boundaries from 'eslint-plugin-boundaries';
|
|
197
|
-
import prettier from 'eslint-config-prettier';
|
|
198
|
-
import globals from 'globals';
|
|
199
|
-
|
|
200
|
-
export default [
|
|
201
|
-
globalIgnores([
|
|
202
|
-
'**/node_modules/', '**/dist/', '**/build/', '**/.next/', '**/coverage/',
|
|
203
|
-
'**/*.min.js', '**/package-lock.json', '**/yarn.lock', '**/pnpm-lock.yaml',
|
|
204
|
-
]),
|
|
205
|
-
|
|
206
|
-
// Base JavaScript
|
|
207
|
-
{
|
|
208
|
-
name: 'safeword/base-js',
|
|
209
|
-
files: ['**/*.{js,mjs,cjs}'],
|
|
210
|
-
...js.configs.recommended,
|
|
211
|
-
languageOptions: {
|
|
212
|
-
ecmaVersion: 'latest',
|
|
213
|
-
sourceType: 'module',
|
|
214
|
-
globals: { ...globals.browser, ...globals.node, ...globals.es2025 },
|
|
215
|
-
},
|
|
216
|
-
},
|
|
217
|
-
COMMON_IMPORTS
|
|
218
|
-
|
|
219
|
-
# TypeScript block
|
|
220
|
-
[ "$HAS_TYPESCRIPT" = true ] && cat >> "$BASE_DIR/eslint-base.mjs" << 'TS_BLOCK'
|
|
221
|
-
|
|
222
|
-
// TypeScript
|
|
223
|
-
{
|
|
224
|
-
name: 'safeword/typescript',
|
|
225
|
-
files: ['**/*.{ts,tsx}'],
|
|
226
|
-
languageOptions: {
|
|
227
|
-
parser: tseslint.parser,
|
|
228
|
-
},
|
|
229
|
-
plugins: {
|
|
230
|
-
'@typescript-eslint': tseslint.plugin,
|
|
231
|
-
},
|
|
232
|
-
rules: {
|
|
233
|
-
...tseslint.configs.recommended.rules,
|
|
234
|
-
},
|
|
235
|
-
},
|
|
236
|
-
TS_BLOCK
|
|
237
|
-
|
|
238
|
-
# React block
|
|
239
|
-
[ "$HAS_REACT" = true ] && cat >> "$BASE_DIR/eslint-base.mjs" << 'REACT_BLOCK'
|
|
240
|
-
|
|
241
|
-
// React
|
|
242
|
-
{
|
|
243
|
-
name: 'safeword/react',
|
|
244
|
-
files: ['**/*.{jsx,tsx}'],
|
|
245
|
-
...reactPlugin.configs['recommended-typescript'],
|
|
246
|
-
plugins: {
|
|
247
|
-
'react-hooks': reactHooks,
|
|
248
|
-
'react-perf': reactPerf,
|
|
249
|
-
},
|
|
250
|
-
languageOptions: {
|
|
251
|
-
parserOptions: { ecmaFeatures: { jsx: true } },
|
|
252
|
-
},
|
|
253
|
-
rules: {
|
|
254
|
-
...reactHooks.configs.recommended.rules,
|
|
255
|
-
'react-perf/jsx-no-new-object-as-prop': 'warn',
|
|
256
|
-
'react-perf/jsx-no-new-array-as-prop': 'warn',
|
|
257
|
-
'react-perf/jsx-no-new-function-as-prop': 'warn',
|
|
258
|
-
},
|
|
259
|
-
},
|
|
260
|
-
REACT_BLOCK
|
|
261
|
-
|
|
262
|
-
# Astro block
|
|
263
|
-
[ "$HAS_ASTRO" = true ] && cat >> "$BASE_DIR/eslint-base.mjs" << 'ASTRO_BLOCK'
|
|
264
|
-
|
|
265
|
-
// Astro
|
|
266
|
-
...astroPlugin.configs.recommended,
|
|
267
|
-
ASTRO_BLOCK
|
|
268
|
-
|
|
269
|
-
# Determine file pattern for quality/security rules
|
|
270
|
-
FILE_PATTERN="**/*.{js,mjs,cjs"
|
|
271
|
-
[ "$HAS_TYPESCRIPT" = true ] && FILE_PATTERN+=",ts,tsx"
|
|
272
|
-
[ "$HAS_REACT" = true ] && FILE_PATTERN+=",jsx"
|
|
273
|
-
FILE_PATTERN+="}"
|
|
274
|
-
|
|
275
|
-
cat >> "$BASE_DIR/eslint-base.mjs" << QUALITY_BLOCK
|
|
276
|
-
|
|
277
|
-
// Code quality (SonarJS)
|
|
278
|
-
{
|
|
279
|
-
name: 'safeword/sonarjs',
|
|
280
|
-
files: ['$FILE_PATTERN'],
|
|
281
|
-
plugins: { sonarjs },
|
|
282
|
-
rules: sonarjs.configs.recommended.rules,
|
|
283
|
-
},
|
|
284
|
-
|
|
285
|
-
// Security (Microsoft SDL)
|
|
286
|
-
{
|
|
287
|
-
name: 'safeword/security',
|
|
288
|
-
files: ['$FILE_PATTERN'],
|
|
289
|
-
plugins: { '@microsoft/sdl': sdl },
|
|
290
|
-
rules: {
|
|
291
|
-
'@microsoft/sdl/no-insecure-url': 'error',
|
|
292
|
-
'@microsoft/sdl/no-inner-html': 'error',
|
|
293
|
-
'@microsoft/sdl/no-document-write': 'error',
|
|
294
|
-
'@microsoft/sdl/no-html-method': 'error',
|
|
295
|
-
'@microsoft/sdl/no-insecure-random': 'error',
|
|
296
|
-
'@microsoft/sdl/no-postmessage-star-origin': 'error',
|
|
297
|
-
},
|
|
298
|
-
},
|
|
299
|
-
|
|
300
|
-
// Architecture boundaries (default layers - customize in eslint.config.mjs)
|
|
301
|
-
{
|
|
302
|
-
name: 'safeword/boundaries',
|
|
303
|
-
files: ['src/**/*.{js,mjs,cjs,ts,tsx,jsx}'],
|
|
304
|
-
plugins: { boundaries },
|
|
305
|
-
settings: {
|
|
306
|
-
'boundaries/include': ['src/**/*'],
|
|
307
|
-
'boundaries/elements': [
|
|
308
|
-
{ type: 'app', pattern: 'src/app/**/*' },
|
|
309
|
-
{ type: 'domain', pattern: 'src/domain/**/*' },
|
|
310
|
-
{ type: 'infra', pattern: 'src/infra/**/*' },
|
|
311
|
-
{ type: 'shared', pattern: 'src/shared/**/*' },
|
|
312
|
-
],
|
|
313
|
-
},
|
|
314
|
-
rules: {
|
|
315
|
-
'boundaries/element-types': ['error', {
|
|
316
|
-
default: 'disallow',
|
|
317
|
-
rules: [
|
|
318
|
-
{ from: 'app', allow: ['domain', 'infra', 'shared'] },
|
|
319
|
-
{ from: 'domain', allow: ['shared'] },
|
|
320
|
-
{ from: 'infra', allow: ['domain', 'shared'] },
|
|
321
|
-
{ from: 'shared', allow: [] },
|
|
322
|
-
],
|
|
323
|
-
}],
|
|
324
|
-
},
|
|
325
|
-
},
|
|
326
|
-
|
|
327
|
-
// Prettier (must be last in base)
|
|
328
|
-
{
|
|
329
|
-
name: 'safeword/prettier',
|
|
330
|
-
...prettier,
|
|
331
|
-
},
|
|
332
|
-
];
|
|
333
|
-
QUALITY_BLOCK
|
|
334
|
-
|
|
335
|
-
echo " ✓ Generated $BASE_DIR/eslint-base.mjs"
|
|
336
|
-
|
|
337
|
-
# --- Create eslint.config.mjs only if it doesn't exist ---
|
|
338
|
-
if [ -f eslint.config.mjs ]; then
|
|
339
|
-
echo " ✓ eslint.config.mjs exists (your customizations preserved)"
|
|
340
|
-
else
|
|
341
|
-
cat > eslint.config.mjs << 'USER_CONFIG'
|
|
342
|
-
/**
|
|
343
|
-
* ESLint Configuration
|
|
344
|
-
*
|
|
345
|
-
* This file is YOURS to customize. It imports the auto-generated base config
|
|
346
|
-
* and lets you add your own rules, override defaults, and customize boundaries.
|
|
347
|
-
*
|
|
348
|
-
* The base config (.safeword/eslint-base.mjs) auto-detects:
|
|
349
|
-
* - TypeScript, React, Astro from package.json
|
|
350
|
-
* - Regenerated automatically when you run setup-linting.sh
|
|
351
|
-
*/
|
|
352
|
-
import base from './.safeword/eslint/eslint-base.mjs';
|
|
353
|
-
|
|
354
|
-
export default [
|
|
355
|
-
// Include all base configs (TypeScript, React, boundaries, security, etc.)
|
|
356
|
-
...base,
|
|
357
|
-
|
|
358
|
-
// =========================================================================
|
|
359
|
-
// YOUR CUSTOMIZATIONS BELOW
|
|
360
|
-
// =========================================================================
|
|
361
|
-
|
|
362
|
-
// Example: Override boundary rules for your project's layer structure
|
|
363
|
-
// {
|
|
364
|
-
// name: 'my-boundaries',
|
|
365
|
-
// files: ['src/**/*'],
|
|
366
|
-
// settings: {
|
|
367
|
-
// 'boundaries/elements': [
|
|
368
|
-
// { type: 'features', pattern: 'src/features/**/*' },
|
|
369
|
-
// { type: 'pages', pattern: 'src/pages/**/*' },
|
|
370
|
-
// { type: 'shared', pattern: 'src/shared/**/*' },
|
|
371
|
-
// ],
|
|
372
|
-
// },
|
|
373
|
-
// rules: {
|
|
374
|
-
// 'boundaries/element-types': ['error', {
|
|
375
|
-
// default: 'disallow',
|
|
376
|
-
// rules: [
|
|
377
|
-
// { from: 'pages', allow: ['features', 'shared'] },
|
|
378
|
-
// { from: 'features', allow: ['shared'] },
|
|
379
|
-
// { from: 'shared', allow: [] },
|
|
380
|
-
// ],
|
|
381
|
-
// }],
|
|
382
|
-
// },
|
|
383
|
-
// },
|
|
384
|
-
|
|
385
|
-
// Example: Add custom rules
|
|
386
|
-
// {
|
|
387
|
-
// name: 'my-rules',
|
|
388
|
-
// rules: {
|
|
389
|
-
// 'no-console': 'warn',
|
|
390
|
-
// '@typescript-eslint/no-explicit-any': 'off',
|
|
391
|
-
// },
|
|
392
|
-
// },
|
|
393
|
-
];
|
|
394
|
-
USER_CONFIG
|
|
395
|
-
echo " ✓ Created eslint.config.mjs (customize this file)"
|
|
396
|
-
fi
|
|
397
|
-
|
|
398
|
-
echo ""
|
|
399
|
-
|
|
400
|
-
# ============================================================================
|
|
401
|
-
# Step 5: Create supporting files and hooks
|
|
402
|
-
# ============================================================================
|
|
403
|
-
echo "[5/5] Setting up hooks and configs..."
|
|
404
|
-
|
|
405
|
-
# Prettier config
|
|
406
|
-
if [ ! -f .prettierrc ] && [ ! -f .prettierrc.json ] && [ ! -f prettier.config.js ]; then
|
|
407
|
-
cat > .prettierrc << 'EOF'
|
|
408
|
-
{
|
|
409
|
-
"printWidth": 100,
|
|
410
|
-
"tabWidth": 2,
|
|
411
|
-
"useTabs": false,
|
|
412
|
-
"semi": true,
|
|
413
|
-
"singleQuote": true,
|
|
414
|
-
"trailingComma": "all",
|
|
415
|
-
"bracketSpacing": true,
|
|
416
|
-
"arrowParens": "avoid",
|
|
417
|
-
"endOfLine": "lf"
|
|
418
|
-
}
|
|
419
|
-
EOF
|
|
420
|
-
echo " ✓ Created .prettierrc"
|
|
421
|
-
fi
|
|
422
|
-
|
|
423
|
-
# Prettier ignore
|
|
424
|
-
if [ ! -f .prettierignore ]; then
|
|
425
|
-
cat > .prettierignore << 'EOF'
|
|
426
|
-
node_modules
|
|
427
|
-
dist
|
|
428
|
-
build
|
|
429
|
-
.next
|
|
430
|
-
coverage
|
|
431
|
-
*.min.js
|
|
432
|
-
package-lock.json
|
|
433
|
-
EOF
|
|
434
|
-
echo " ✓ Created .prettierignore"
|
|
435
|
-
fi
|
|
436
|
-
|
|
437
|
-
# Add npm scripts
|
|
438
|
-
if command -v jq &> /dev/null; then
|
|
439
|
-
jq '.scripts.lint = "eslint ." | .scripts.format = "prettier --write ."' package.json > package.json.tmp
|
|
440
|
-
mv package.json.tmp package.json
|
|
441
|
-
echo " ✓ Added npm scripts (lint, format)"
|
|
442
|
-
fi
|
|
443
|
-
|
|
444
|
-
# Claude Code hooks
|
|
445
|
-
mkdir -p .claude/hooks .claude/commands
|
|
446
|
-
|
|
447
|
-
cat > .claude/hooks/run-linters.sh << 'EOF'
|
|
448
|
-
#!/bin/bash
|
|
449
|
-
# Shared Linting Script - runs Prettier + ESLint on files
|
|
450
|
-
if [ -n "$CLAUDE_PROJECT_DIR" ]; then cd "$CLAUDE_PROJECT_DIR" || exit 1; fi
|
|
451
|
-
for target in "$@"; do
|
|
452
|
-
[ -e "$target" ] || continue
|
|
453
|
-
npx prettier --write "$target" 2>&1 || true
|
|
454
|
-
npx eslint --fix "$target" 2>&1 || true
|
|
455
|
-
done
|
|
456
|
-
EOF
|
|
457
|
-
chmod +x .claude/hooks/run-linters.sh
|
|
458
|
-
|
|
459
|
-
cat > .claude/hooks/auto-lint.sh << 'EOF'
|
|
460
|
-
#!/bin/bash
|
|
461
|
-
# PostToolUse hook - auto-lint changed files
|
|
462
|
-
input=$(cat)
|
|
463
|
-
file_path=$(echo "$input" | jq -r '.tool_input.file_path // .tool_input.notebook_path // empty')
|
|
464
|
-
[ -n "$file_path" ] && [ -f "$file_path" ] && "$CLAUDE_PROJECT_DIR/.claude/hooks/run-linters.sh" "$file_path"
|
|
465
|
-
exit 0
|
|
466
|
-
EOF
|
|
467
|
-
chmod +x .claude/hooks/auto-lint.sh
|
|
468
|
-
|
|
469
|
-
cat > .claude/commands/lint.md << 'EOF'
|
|
470
|
-
Run linting on all project files.
|
|
471
|
-
|
|
472
|
-
Execute:
|
|
473
|
-
```bash
|
|
474
|
-
bash .claude/hooks/run-linters.sh .
|
|
475
|
-
```
|
|
476
|
-
EOF
|
|
477
|
-
|
|
478
|
-
echo " ✓ Created Claude Code hooks"
|
|
479
|
-
|
|
480
|
-
# Update settings.json
|
|
481
|
-
if [ ! -f .claude/settings.json ]; then
|
|
482
|
-
echo '{"hooks": {}}' > .claude/settings.json
|
|
483
|
-
fi
|
|
484
|
-
|
|
485
|
-
# Add PostToolUse hook for auto-linting
|
|
486
|
-
if ! jq -e '.hooks.PostToolUse[]?.hooks[]? | select(.command == "$CLAUDE_PROJECT_DIR/.claude/hooks/auto-lint.sh")' .claude/settings.json > /dev/null 2>&1; then
|
|
487
|
-
jq '.hooks.PostToolUse = (.hooks.PostToolUse // []) + [{"matcher": "Write|Edit|MultiEdit|NotebookEdit", "hooks": [{"type": "command", "command": "$CLAUDE_PROJECT_DIR/.claude/hooks/auto-lint.sh", "timeout": 15}]}]' \
|
|
488
|
-
.claude/settings.json > .claude/settings.json.tmp
|
|
489
|
-
mv .claude/settings.json.tmp .claude/settings.json
|
|
490
|
-
echo " ✓ Added PostToolUse hook (auto-lint)"
|
|
491
|
-
fi
|
|
492
|
-
|
|
493
|
-
# Create and add SessionStart hook to detect framework changes
|
|
494
|
-
cat > .claude/hooks/check-linting-sync.sh << 'EOF'
|
|
495
|
-
#!/bin/bash
|
|
496
|
-
# SessionStart hook - reminds user to re-run setup if frameworks changed
|
|
497
|
-
[ ! -f ".safeword/eslint/eslint-base.mjs" ] || [ ! -f "package.json" ] && exit 0
|
|
498
|
-
DEPS=$(jq -r '(.dependencies//{}),(.devDependencies//{}) | keys[]' package.json 2>/dev/null || grep -oE '"[^"]+":' package.json | tr -d '":')
|
|
499
|
-
HAS_TS=false; HAS_REACT=false; HAS_ASTRO=false
|
|
500
|
-
{ [ -f "tsconfig.json" ] || echo "$DEPS" | grep -qx "typescript"; } && HAS_TS=true
|
|
501
|
-
echo "$DEPS" | grep -qx "react" && HAS_REACT=true
|
|
502
|
-
echo "$DEPS" | grep -qx "astro" && HAS_ASTRO=true
|
|
503
|
-
CFG_TS=$(grep -q "typescript-eslint" .safeword/eslint/eslint-base.mjs && echo true || echo false)
|
|
504
|
-
CFG_REACT=$(grep -q "@eslint-react" .safeword/eslint/eslint-base.mjs && echo true || echo false)
|
|
505
|
-
CFG_ASTRO=$(grep -q "eslint-plugin-astro" .safeword/eslint/eslint-base.mjs && echo true || echo false)
|
|
506
|
-
MSG=""
|
|
507
|
-
[ "$HAS_TS" != "$CFG_TS" ] && MSG+="TypeScript "
|
|
508
|
-
[ "$HAS_REACT" != "$CFG_REACT" ] && MSG+="React "
|
|
509
|
-
[ "$HAS_ASTRO" != "$CFG_ASTRO" ] && MSG+="Astro "
|
|
510
|
-
[ -n "$MSG" ] && echo "⚠️ ESLint config out of sync (${MSG% }changed). Run: bash .safeword/scripts/setup-linting.sh"
|
|
511
|
-
exit 0
|
|
512
|
-
EOF
|
|
513
|
-
chmod +x .claude/hooks/check-linting-sync.sh
|
|
514
|
-
|
|
515
|
-
if ! jq -e '.hooks.SessionStart[]?.hooks[]? | select(.command == "$CLAUDE_PROJECT_DIR/.claude/hooks/check-linting-sync.sh")' .claude/settings.json > /dev/null 2>&1; then
|
|
516
|
-
jq '.hooks.SessionStart = (.hooks.SessionStart // []) + [{"hooks": [{"type": "command", "command": "$CLAUDE_PROJECT_DIR/.claude/hooks/check-linting-sync.sh"}]}]' \
|
|
517
|
-
.claude/settings.json > .claude/settings.json.tmp
|
|
518
|
-
mv .claude/settings.json.tmp .claude/settings.json
|
|
519
|
-
echo " ✓ Added SessionStart hook (sync check)"
|
|
520
|
-
fi
|
|
521
|
-
|
|
522
|
-
# /setup-linting command
|
|
523
|
-
cat > .claude/commands/setup-linting.md << 'EOF'
|
|
524
|
-
Re-run SAFEWORD linting setup (auto-detects frameworks, regenerates base config).
|
|
525
|
-
|
|
526
|
-
Execute:
|
|
527
|
-
```bash
|
|
528
|
-
bash .safeword/scripts/setup-linting.sh
|
|
529
|
-
```
|
|
530
|
-
EOF
|
|
531
|
-
echo " ✓ Created /setup-linting command"
|
|
532
|
-
|
|
533
|
-
echo ""
|
|
534
|
-
echo "================================="
|
|
535
|
-
echo "✓ Setup Complete!"
|
|
536
|
-
echo "================================="
|
|
537
|
-
echo ""
|
|
538
|
-
echo "Files:"
|
|
539
|
-
echo " .safeword/eslint/eslint-base.mjs - Auto-generated (DO NOT EDIT)"
|
|
540
|
-
echo " eslint.config.mjs - Your config (customize freely)"
|
|
541
|
-
echo ""
|
|
542
|
-
echo "Detected:"
|
|
543
|
-
[ "$HAS_TYPESCRIPT" = true ] && echo " ✓ TypeScript"
|
|
544
|
-
[ "$HAS_REACT" = true ] && echo " ✓ React"
|
|
545
|
-
[ "$HAS_ASTRO" = true ] && echo " ✓ Astro"
|
|
546
|
-
[ "$HAS_TYPESCRIPT" = false ] && [ "$HAS_REACT" = false ] && [ "$HAS_ASTRO" = false ] && echo " → JavaScript only"
|
|
547
|
-
echo ""
|
|
548
|
-
echo "Included:"
|
|
549
|
-
echo " • eslint-plugin-boundaries (architecture)"
|
|
550
|
-
echo " • eslint-plugin-sonarjs (code quality)"
|
|
551
|
-
echo " • @microsoft/eslint-plugin-sdl (security)"
|
|
552
|
-
echo ""
|
|
553
|
-
echo "Commands:"
|
|
554
|
-
echo " npm run lint # Check all files"
|
|
555
|
-
echo " npm run format # Format all files"
|
|
556
|
-
echo ""
|
|
557
|
-
echo "After adding/removing frameworks, just re-run:"
|
|
558
|
-
echo " bash setup-linting.sh"
|
|
559
|
-
echo ""
|
|
@@ -1,136 +0,0 @@
|
|
|
1
|
-
# [Project Name] Architecture
|
|
2
|
-
|
|
3
|
-
**Version:** 1.0
|
|
4
|
-
**Last Updated:** YYYY-MM-DD
|
|
5
|
-
**Status:** Design | Production | Proposed | Deprecated
|
|
6
|
-
|
|
7
|
-
---
|
|
8
|
-
|
|
9
|
-
## Table of Contents
|
|
10
|
-
|
|
11
|
-
- [Overview](#overview)
|
|
12
|
-
- [Layers & Boundaries](#layers--boundaries)
|
|
13
|
-
- [Data Model](#data-model)
|
|
14
|
-
- [Key Decisions](#key-decisions)
|
|
15
|
-
- [Best Practices](#best-practices)
|
|
16
|
-
- [Migration Strategy](#migration-strategy)
|
|
17
|
-
|
|
18
|
-
---
|
|
19
|
-
|
|
20
|
-
## Overview
|
|
21
|
-
|
|
22
|
-
[High-level description of the system architecture, technology choices, and design philosophy.]
|
|
23
|
-
|
|
24
|
-
### Tech Stack
|
|
25
|
-
|
|
26
|
-
| Category | Choice | Rationale |
|
|
27
|
-
|----------|--------|-----------|
|
|
28
|
-
| Language | | |
|
|
29
|
-
| Framework | | |
|
|
30
|
-
| Database | | |
|
|
31
|
-
| State Management | | |
|
|
32
|
-
|
|
33
|
-
---
|
|
34
|
-
|
|
35
|
-
## Layers & Boundaries
|
|
36
|
-
|
|
37
|
-
### Layer Definitions
|
|
38
|
-
|
|
39
|
-
| Layer | Directory | Responsibility |
|
|
40
|
-
|-------|-----------|----------------|
|
|
41
|
-
| app | `src/app/` | UI, routing, composition |
|
|
42
|
-
| domain | `src/domain/` | Business rules, pure logic |
|
|
43
|
-
| infra | `src/infra/` | IO, APIs, DB, external SDKs |
|
|
44
|
-
| shared | `src/shared/` | Utilities usable by all layers |
|
|
45
|
-
|
|
46
|
-
### Allowed Dependencies
|
|
47
|
-
|
|
48
|
-
| From | To | Allowed | Rationale |
|
|
49
|
-
|------|-----|---------|-----------|
|
|
50
|
-
| app | domain | ✅ | UI composes business logic |
|
|
51
|
-
| app | infra | ✅ | UI triggers side effects |
|
|
52
|
-
| app | shared | ✅ | Utilities available everywhere |
|
|
53
|
-
| domain | app | ❌ | Domain must be framework-agnostic |
|
|
54
|
-
| domain | infra | ❌ | Domain contains pure logic only |
|
|
55
|
-
| domain | shared | ✅ | Utilities available everywhere |
|
|
56
|
-
| infra | domain | ✅ | Adapters may use domain types |
|
|
57
|
-
| infra | app | ❌ | Infra should not depend on UI |
|
|
58
|
-
| infra | shared | ✅ | Utilities available everywhere |
|
|
59
|
-
| shared | * | ❌ | Shared has no dependencies (except external libs) |
|
|
60
|
-
|
|
61
|
-
**Note:** This template allows direct app→infra. Alternative: force app→domain→infra for stricter separation (hexagonal/ports-adapters pattern).
|
|
62
|
-
|
|
63
|
-
### Boundary Enforcement
|
|
64
|
-
|
|
65
|
-
Boundaries enforced via `eslint-plugin-boundaries`. See `.safeword/guides/architecture-guide.md` → Enforcement with eslint-plugin-boundaries for setup.
|
|
66
|
-
|
|
67
|
-
---
|
|
68
|
-
|
|
69
|
-
## Data Model
|
|
70
|
-
|
|
71
|
-
### Entities
|
|
72
|
-
|
|
73
|
-
| Entity | Table/Collection | Description |
|
|
74
|
-
|--------|-----------------|-------------|
|
|
75
|
-
| | | |
|
|
76
|
-
|
|
77
|
-
### Relationships
|
|
78
|
-
|
|
79
|
-
```
|
|
80
|
-
[Entity A] 1──n [Entity B]
|
|
81
|
-
[Entity B] n──n [Entity C]
|
|
82
|
-
```
|
|
83
|
-
|
|
84
|
-
### Schema Notes
|
|
85
|
-
|
|
86
|
-
- [Key constraints, indexes, etc.]
|
|
87
|
-
|
|
88
|
-
---
|
|
89
|
-
|
|
90
|
-
## Key Decisions
|
|
91
|
-
|
|
92
|
-
### [Decision Title]
|
|
93
|
-
|
|
94
|
-
**Status:** Active | Superseded | Deprecated
|
|
95
|
-
**Date:** YYYY-MM-DD
|
|
96
|
-
|
|
97
|
-
| Field | Value |
|
|
98
|
-
|-------|-------|
|
|
99
|
-
| What | [The decision in 1-2 sentences] |
|
|
100
|
-
| Why | [Rationale with specifics - numbers, metrics] |
|
|
101
|
-
| Trade-off | [What we gave up or accepted] |
|
|
102
|
-
| Alternatives | [Other options considered and why rejected] |
|
|
103
|
-
| Implementation | [File references: `src/path/file.ts:12-45`] |
|
|
104
|
-
|
|
105
|
-
---
|
|
106
|
-
|
|
107
|
-
## Best Practices
|
|
108
|
-
|
|
109
|
-
### [Pattern Name]
|
|
110
|
-
|
|
111
|
-
**What:** [Brief description]
|
|
112
|
-
**Why:** [Rationale]
|
|
113
|
-
**Example:** See `src/path/example.ts`
|
|
114
|
-
|
|
115
|
-
---
|
|
116
|
-
|
|
117
|
-
## Migration Strategy
|
|
118
|
-
|
|
119
|
-
### From [Previous State] to [Target State]
|
|
120
|
-
|
|
121
|
-
**Trigger:** [When to migrate]
|
|
122
|
-
**Steps:**
|
|
123
|
-
1. [Step 1]
|
|
124
|
-
2. [Step 2]
|
|
125
|
-
|
|
126
|
-
**Rollback:** [How to revert if needed]
|
|
127
|
-
|
|
128
|
-
---
|
|
129
|
-
|
|
130
|
-
## Appendix
|
|
131
|
-
|
|
132
|
-
### References
|
|
133
|
-
|
|
134
|
-
- [Link to relevant docs]
|
|
135
|
-
- [Link to ADRs if migrating from ADR system]
|
|
136
|
-
|