create-einja-app 0.3.2 → 0.3.4

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.
Files changed (65) hide show
  1. package/README.md +33 -0
  2. package/dist/cli.js +60 -64
  3. package/dist/cli.js.map +1 -1
  4. package/package.json +1 -1
  5. package/templates/default/.changeset/config.json +11 -0
  6. package/templates/default/.claude/hooks/einja/plan-mode-skill-loader.sh +5 -1
  7. package/templates/default/.claude/settings.json +14 -4
  8. package/templates/default/.claude/skills/_einja-general-context-loader/SKILL.md +258 -0
  9. package/templates/default/.claude/skills/_einja-output-format/SKILL.md +211 -0
  10. package/templates/default/.claude/skills/_einja-project-overview/SKILL.md +29 -0
  11. package/templates/default/.claude/skills/_einja-spec-context-loader/SKILL.md +181 -0
  12. package/templates/default/.claude/skills/cli-package-specs/SKILL.md +294 -0
  13. package/templates/default/.einja-sync.json +1 -1
  14. package/templates/default/.github/release.yml +10 -0
  15. package/templates/default/.github/workflows/changeset-status.yml +60 -0
  16. package/templates/default/.github/workflows/deploy-stable-branches.yml +289 -59
  17. package/templates/default/CLAUDE.md +50 -10
  18. package/templates/default/README.md +20 -8
  19. package/templates/default/docs/plans/agile-munching-knuth.md +161 -0
  20. package/templates/default/docs/plans/agile-riding-nova.md +158 -0
  21. package/templates/default/docs/plans/agile-wibbling-dusk.md +91 -0
  22. package/templates/default/docs/plans/ancient-watching-otter.md +152 -0
  23. package/templates/default/docs/plans/bright-sauteeing-bumblebee.md +30 -0
  24. package/templates/default/docs/plans/composed-doodling-mountain.md +362 -0
  25. package/templates/default/docs/plans/dazzling-foraging-cascade.md +32 -0
  26. package/templates/default/docs/plans/enchanted-wiggling-ember-agent-a5befd57d0ca4c7c7.md +177 -0
  27. package/templates/default/docs/plans/enchanted-wiggling-ember.md +170 -0
  28. package/templates/default/docs/plans/federated-questing-kahan.md +47 -0
  29. package/templates/default/docs/plans/flickering-pondering-hearth.md +26 -0
  30. package/templates/default/docs/plans/fluttering-snuggling-sprout.md +172 -0
  31. package/templates/default/docs/plans/generic-sleeping-snowglobe-agent-a41d8da.md +179 -0
  32. package/templates/default/docs/plans/generic-sleeping-snowglobe.md +108 -0
  33. package/templates/default/docs/plans/generic-snuggling-pudding.md +57 -0
  34. package/templates/default/docs/plans/glistening-conjuring-cascade.md +42 -0
  35. package/templates/default/docs/plans/idempotent-wiggling-cherny.md +122 -0
  36. package/templates/default/docs/plans/linear-gathering-hejlsberg.md +596 -0
  37. package/templates/default/docs/plans/recursive-fluttering-mitten.md +176 -0
  38. package/templates/default/docs/plans/todo-create-einja-app-ux-fix.md +16 -0
  39. package/templates/default/docs/plans/todo-direnv-hang-fix.md +12 -0
  40. package/templates/default/docs/plans/todo-github-actions-release-workflow.md +34 -0
  41. package/templates/default/docs/plans/todo-glistening-conjuring-cascade.md +20 -0
  42. package/templates/default/docs/plans/todo-issue-spec-rename.md +24 -0
  43. package/templates/default/docs/plans/todo-skill-creator-upgrade.md +18 -0
  44. package/templates/default/docs/plans/todo-unified-crafting-valiant.md +23 -0
  45. package/templates/default/docs/plans/unified-crafting-valiant.md +60 -0
  46. package/templates/default/docs/plans/velvety-chasing-spark.md +28 -0
  47. package/templates/default/docs/plans/wondrous-strolling-crystal-agent-a0615fc.md +215 -0
  48. package/templates/default/docs/plans/wondrous-strolling-crystal.md +182 -0
  49. package/templates/default/docs/plans/zesty-roaming-steele.md +74 -0
  50. package/templates/default/gitignore +6 -2
  51. package/templates/default/package.json +6 -2
  52. package/templates/default/pnpm-lock.yaml +547 -0
  53. package/templates/default/scripts/ensure-serena.sh +28 -9
  54. package/templates/default/scripts/env-rotate-secrets.ts +66 -6
  55. package/templates/default/scripts/init-github.ts +363 -0
  56. package/templates/default/scripts/init.sh +11 -5
  57. package/templates/default/scripts/setup-dev.ts +16 -1
  58. package/templates/default/.claude/hooks/einja/validate-git-commit.sh +0 -239
  59. package/templates/default/.claude/skills/create-einja-app-release/SKILL.md +0 -186
  60. package/templates/default/.claude/skills/dev-cli-release/SKILL.md +0 -173
  61. package/templates/default/.cursor/commands/spec-create.md +0 -227
  62. package/templates/default/.cursor/commands/task-exec.md +0 -287
  63. package/templates/default/.cursor/commands/update-docs-by-task-specs.md +0 -448
  64. package/templates/default/packages/server-core/src/__generated__/fabbrica/index.d.ts +0 -270
  65. package/templates/default/packages/server-core/src/__generated__/fabbrica/index.js +0 -484
@@ -4,12 +4,20 @@ on:
4
4
  push:
5
5
  branches: [main, develop, staging]
6
6
 
7
+ # GITHUB_TOKENで作成されたpushイベントはデフォルトでワークフロー再トリガーしない
8
+ # 念のため明示的にbotコミットを除外(release-productionのバージョンバンプ対策)
9
+
10
+ permissions:
11
+ contents: write
12
+
7
13
  concurrency:
8
14
  group: deploy-${{ github.ref_name }}
9
15
  cancel-in-progress: false
10
16
 
11
17
  jobs:
12
18
  ci:
19
+ # github-actions[bot] のバージョンバンプコミットはスキップ
20
+ if: "!contains(github.event.head_commit.message, 'chore: release v')"
13
21
  runs-on: ubuntu-latest
14
22
  services:
15
23
  postgres:
@@ -89,35 +97,123 @@ jobs:
89
97
  fi
90
98
  echo "matrix=$MATRIX" >> $GITHUB_OUTPUT
91
99
 
92
- migrate:
93
- needs: ci
94
- if: github.ref_name == 'main' || github.ref_name == 'staging'
100
+ # ========================================
101
+ # develop: 環境なし、承認なし、マイグレーションなし
102
+ # ========================================
103
+ deploy-develop:
104
+ needs: [ci, changes]
105
+ if: github.ref_name == 'develop' && needs.changes.outputs.deploy_matrix != '[]'
95
106
  runs-on: ubuntu-latest
107
+ strategy:
108
+ fail-fast: false
109
+ matrix:
110
+ include: ${{ fromJSON(needs.changes.outputs.deploy_matrix) }}
111
+ env:
112
+ VERCEL_TOKEN: ${{ secrets.VERCEL_TOKEN }}
113
+ VERCEL_ORG_ID: ${{ secrets.VERCEL_ORG_ID }}
114
+ TURBO_TOKEN: ${{ secrets.TURBO_TOKEN }}
115
+ TURBO_TEAM: ${{ secrets.TURBO_TEAM }}
96
116
  steps:
97
117
  - uses: actions/checkout@v4
98
118
 
99
- # main: production環境マイグレーション(シード無効)
100
- - name: Migrate production
101
- if: github.ref_name == 'main'
102
- uses: ./.github/actions/migrate
103
- with:
104
- dotenv-file: ${{ github.workspace }}/.env.production
105
- dotenv-private-key: ${{ secrets.DOTENV_PRIVATE_KEY_PRODUCTION }}
106
- run-seed: 'false'
119
+ - name: Setup Environment
120
+ uses: ./.github/actions/setup
121
+
122
+ - name: Resolve Vercel Project ID
123
+ id: resolve
124
+ run: |
125
+ case "${{ matrix.app }}" in
126
+ web) echo "project_id=${{ secrets.VERCEL_PROJECT_ID_WEB }}" >> $GITHUB_OUTPUT ;;
127
+ admin) echo "project_id=${{ secrets.VERCEL_PROJECT_ID_ADMIN }}" >> $GITHUB_OUTPUT ;;
128
+ esac
129
+
130
+ - name: Set VERCEL_PROJECT_ID
131
+ run: echo "VERCEL_PROJECT_ID=${{ steps.resolve.outputs.project_id }}" >> $GITHUB_ENV
132
+
133
+ - name: Install Vercel CLI
134
+ run: pnpm add -g vercel@latest
135
+
136
+ - name: Set deploy environment
137
+ run: |
138
+ echo "DEPLOY_DOTENV_FILE=$GITHUB_WORKSPACE/.env.develop" >> $GITHUB_ENV
139
+ echo "DEPLOY_VERCEL_ENV=preview" >> $GITHUB_ENV
140
+ echo "DEPLOY_PROD_FLAG=" >> $GITHUB_ENV
141
+ echo "DEPLOY_RUN_ALIAS=true" >> $GITHUB_ENV
142
+
143
+ - name: Extract alias domain
144
+ run: |
145
+ case "${{ matrix.app }}" in
146
+ web)
147
+ npx dotenvx run -f ${{ env.DEPLOY_DOTENV_FILE }} -- bash -c '
148
+ echo "VERCEL_ALIAS_DOMAIN=$VERCEL_ALIAS_DOMAIN_WEB" >> "$GITHUB_ENV"
149
+ '
150
+ ;;
151
+ admin)
152
+ npx dotenvx run -f ${{ env.DEPLOY_DOTENV_FILE }} -- bash -c '
153
+ echo "VERCEL_ALIAS_DOMAIN=$VERCEL_ALIAS_DOMAIN_ADMIN" >> "$GITHUB_ENV"
154
+ '
155
+ ;;
156
+ esac
157
+ env:
158
+ DOTENV_PRIVATE_KEY_DEVELOP: ${{ secrets.DOTENV_PRIVATE_KEY_DEVELOP }}
159
+
160
+ - name: Pull Vercel Environment
161
+ run: vercel pull --yes --environment=${{ env.DEPLOY_VERCEL_ENV }} --token=$VERCEL_TOKEN
162
+
163
+ - name: Build Project
164
+ run: |
165
+ npx dotenvx run -f ${{ env.DEPLOY_DOTENV_FILE }} -- \
166
+ vercel build ${{ env.DEPLOY_PROD_FLAG }} --token=$VERCEL_TOKEN
167
+ env:
168
+ DOTENV_PRIVATE_KEY_DEVELOP: ${{ secrets.DOTENV_PRIVATE_KEY_DEVELOP }}
169
+
170
+ - name: Deploy to Vercel
171
+ id: deploy
172
+ run: |
173
+ npx dotenvx run -f $DEPLOY_DOTENV_FILE -- bash -c '
174
+ declare -a ENV_FLAGS=()
175
+ while IFS= read -r key; do
176
+ case "$key" in
177
+ NEON_*|VERCEL_ALIAS_DOMAIN_*|DOTENV_PUBLIC_KEY_*) continue ;;
178
+ esac
179
+ value="${!key}"
180
+ if [ -n "$value" ]; then
181
+ echo "::add-mask::${value}"
182
+ fi
183
+ ENV_FLAGS+=("--env" "${key}=${value}")
184
+ done < <(grep -E "^[A-Z_][A-Z0-9_]*=\"?encrypted:" "$DEPLOY_DOTENV_FILE" | cut -d= -f1)
185
+
186
+ echo "Deploying with ${#ENV_FLAGS[@]} runtime env vars..."
187
+ DEPLOY_URL=$(vercel deploy --prebuilt $DEPLOY_PROD_FLAG "${ENV_FLAGS[@]}" --token="$VERCEL_TOKEN")
188
+ echo "url=$DEPLOY_URL" >> "$GITHUB_OUTPUT"
189
+ '
190
+ env:
191
+ DOTENV_PRIVATE_KEY_DEVELOP: ${{ secrets.DOTENV_PRIVATE_KEY_DEVELOP }}
192
+
193
+ - name: Set Vercel alias
194
+ run: vercel alias ${{ steps.deploy.outputs.url }} "${{ env.VERCEL_ALIAS_DOMAIN }}" --token=$VERCEL_TOKEN
195
+
196
+ # ========================================
197
+ # staging: staging環境、承認なし
198
+ # ========================================
199
+ migrate-staging:
200
+ needs: ci
201
+ if: github.ref_name == 'staging'
202
+ runs-on: ubuntu-latest
203
+ steps:
204
+ - uses: actions/checkout@v4
107
205
 
108
- # staging: ステージング環境マイグレーション(シード無効)
109
206
  - name: Migrate staging
110
- if: github.ref_name == 'staging'
111
207
  uses: ./.github/actions/migrate
112
208
  with:
113
209
  dotenv-file: ${{ github.workspace }}/.env.staging
114
210
  dotenv-private-key: ${{ secrets.DOTENV_PRIVATE_KEY_STAGING }}
115
211
  run-seed: 'false'
116
212
 
117
- # Web/Adminデプロイ(並列実行・変更検知付き)
118
- deploy:
119
- needs: [ci, migrate, changes]
120
- if: always() && needs.ci.result == 'success' && (needs.migrate.result == 'success' || needs.migrate.result == 'skipped') && needs.changes.result == 'success' && needs.changes.outputs.deploy_matrix != '[]'
213
+ deploy-staging:
214
+ needs: [ci, migrate-staging, changes]
215
+ if: github.ref_name == 'staging' && needs.changes.outputs.deploy_matrix != '[]'
216
+ environment: staging
121
217
  runs-on: ubuntu-latest
122
218
  strategy:
123
219
  fail-fast: false
@@ -148,35 +244,14 @@ jobs:
148
244
  - name: Install Vercel CLI
149
245
  run: pnpm add -g vercel@latest
150
246
 
151
- # ブランチ判定 環境変数を $GITHUB_ENV に書き出す
152
- - name: Determine environment
247
+ - name: Set deploy environment
153
248
  run: |
154
- BRANCH="${GITHUB_REF##*/}"
155
- case "$BRANCH" in
156
- main)
157
- echo "DEPLOY_DOTENV_FILE=$GITHUB_WORKSPACE/.env.production" >> $GITHUB_ENV
158
- echo "DEPLOY_VERCEL_ENV=production" >> $GITHUB_ENV
159
- echo "DEPLOY_PROD_FLAG=--prod" >> $GITHUB_ENV
160
- echo "DEPLOY_RUN_ALIAS=false" >> $GITHUB_ENV
161
- ;;
162
- develop)
163
- echo "DEPLOY_DOTENV_FILE=$GITHUB_WORKSPACE/.env.develop" >> $GITHUB_ENV
164
- echo "DEPLOY_VERCEL_ENV=preview" >> $GITHUB_ENV
165
- echo "DEPLOY_PROD_FLAG=" >> $GITHUB_ENV
166
- echo "DEPLOY_RUN_ALIAS=true" >> $GITHUB_ENV
167
- ;;
168
- staging)
169
- echo "DEPLOY_DOTENV_FILE=$GITHUB_WORKSPACE/.env.staging" >> $GITHUB_ENV
170
- echo "DEPLOY_VERCEL_ENV=preview" >> $GITHUB_ENV
171
- echo "DEPLOY_PROD_FLAG=" >> $GITHUB_ENV
172
- echo "DEPLOY_RUN_ALIAS=true" >> $GITHUB_ENV
173
- ;;
174
- esac
175
- echo "Branch: $BRANCH, Environment: $(cat $GITHUB_ENV | grep DEPLOY_VERCEL_ENV)"
249
+ echo "DEPLOY_DOTENV_FILE=$GITHUB_WORKSPACE/.env.staging" >> $GITHUB_ENV
250
+ echo "DEPLOY_VERCEL_ENV=preview" >> $GITHUB_ENV
251
+ echo "DEPLOY_PROD_FLAG=" >> $GITHUB_ENV
252
+ echo "DEPLOY_RUN_ALIAS=true" >> $GITHUB_ENV
176
253
 
177
- # Extract alias domain(自アプリ分のみ)
178
254
  - name: Extract alias domain
179
- if: env.DEPLOY_RUN_ALIAS == 'true'
180
255
  run: |
181
256
  case "${{ matrix.app }}" in
182
257
  web)
@@ -192,15 +267,141 @@ jobs:
192
267
  esac
193
268
  env:
194
269
  DOTENV_PRIVATE_KEY_STAGING: ${{ secrets.DOTENV_PRIVATE_KEY_STAGING }}
195
- DOTENV_PRIVATE_KEY_DEVELOP: ${{ secrets.DOTENV_PRIVATE_KEY_DEVELOP }}
196
270
 
197
- # Vercel pull
198
271
  - name: Pull Vercel Environment
199
272
  run: vercel pull --yes --environment=${{ env.DEPLOY_VERCEL_ENV }} --token=$VERCEL_TOKEN
200
273
 
201
- # Vercel環境変数の自動同期(mainのみ develop/stagingは--env注入)
274
+ - name: Build Project
275
+ run: |
276
+ npx dotenvx run -f ${{ env.DEPLOY_DOTENV_FILE }} -- \
277
+ vercel build ${{ env.DEPLOY_PROD_FLAG }} --token=$VERCEL_TOKEN
278
+ env:
279
+ DOTENV_PRIVATE_KEY_STAGING: ${{ secrets.DOTENV_PRIVATE_KEY_STAGING }}
280
+
281
+ - name: Deploy to Vercel
282
+ id: deploy
283
+ run: |
284
+ npx dotenvx run -f $DEPLOY_DOTENV_FILE -- bash -c '
285
+ declare -a ENV_FLAGS=()
286
+ while IFS= read -r key; do
287
+ case "$key" in
288
+ NEON_*|VERCEL_ALIAS_DOMAIN_*|DOTENV_PUBLIC_KEY_*) continue ;;
289
+ esac
290
+ value="${!key}"
291
+ if [ -n "$value" ]; then
292
+ echo "::add-mask::${value}"
293
+ fi
294
+ ENV_FLAGS+=("--env" "${key}=${value}")
295
+ done < <(grep -E "^[A-Z_][A-Z0-9_]*=\"?encrypted:" "$DEPLOY_DOTENV_FILE" | cut -d= -f1)
296
+
297
+ echo "Deploying with ${#ENV_FLAGS[@]} runtime env vars..."
298
+ DEPLOY_URL=$(vercel deploy --prebuilt $DEPLOY_PROD_FLAG "${ENV_FLAGS[@]}" --token="$VERCEL_TOKEN")
299
+ echo "url=$DEPLOY_URL" >> "$GITHUB_OUTPUT"
300
+ '
301
+ env:
302
+ DOTENV_PRIVATE_KEY_STAGING: ${{ secrets.DOTENV_PRIVATE_KEY_STAGING }}
303
+
304
+ - name: Set Vercel alias
305
+ run: vercel alias ${{ steps.deploy.outputs.url }} "${{ env.VERCEL_ALIAS_DOMAIN }}" --token=$VERCEL_TOKEN
306
+
307
+ # staging: PreRelease作成(changeset未消費)
308
+ release-staging:
309
+ needs: deploy-staging
310
+ if: github.ref_name == 'staging'
311
+ runs-on: ubuntu-latest
312
+ steps:
313
+ - uses: actions/checkout@v4
314
+ with:
315
+ fetch-depth: 0
316
+
317
+ - name: Check for changesets
318
+ id: check
319
+ run: |
320
+ COUNT=$(ls .changeset/*.md 2>/dev/null | grep -cv README.md || echo 0)
321
+ echo "has_changesets=$([[ $COUNT -gt 0 ]] && echo true || echo false)" >> $GITHUB_OUTPUT
322
+
323
+ - name: Create PreRelease tag
324
+ if: steps.check.outputs.has_changesets == 'true'
325
+ id: tag
326
+ run: |
327
+ VERSION=$(node -p "require('./package.json').version")
328
+ TAG="v${VERSION}-rc.${{ github.run_number }}"
329
+ git tag "$TAG"
330
+ git push origin "$TAG"
331
+ echo "tag=$TAG" >> $GITHUB_OUTPUT
332
+
333
+ - name: Create GitHub PreRelease
334
+ if: steps.tag.outputs.tag
335
+ run: |
336
+ PREV=$(git tag --list 'v*-rc.*' --sort=-v:refname | grep -v "${{ steps.tag.outputs.tag }}" | head -1)
337
+ OPTS="--prerelease --target staging --generate-notes"
338
+ [[ -n "$PREV" ]] && OPTS="$OPTS --notes-start-tag $PREV"
339
+ gh release create "${{ steps.tag.outputs.tag }}" --title "Pre-release ${{ steps.tag.outputs.tag }}" $OPTS
340
+ env:
341
+ GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
342
+
343
+ # ========================================
344
+ # main: production環境、1名承認 → migrate → deploy → release
345
+ # ========================================
346
+ migrate-production:
347
+ needs: ci
348
+ if: github.ref_name == 'main'
349
+ environment: production
350
+ runs-on: ubuntu-latest
351
+ steps:
352
+ - uses: actions/checkout@v4
353
+
354
+ - name: Migrate production
355
+ uses: ./.github/actions/migrate
356
+ with:
357
+ dotenv-file: ${{ github.workspace }}/.env.production
358
+ dotenv-private-key: ${{ secrets.DOTENV_PRIVATE_KEY_PRODUCTION }}
359
+ run-seed: 'false'
360
+
361
+ deploy-production:
362
+ needs: [migrate-production, changes]
363
+ if: github.ref_name == 'main' && needs.changes.outputs.deploy_matrix != '[]'
364
+ runs-on: ubuntu-latest
365
+ strategy:
366
+ fail-fast: false
367
+ matrix:
368
+ include: ${{ fromJSON(needs.changes.outputs.deploy_matrix) }}
369
+ env:
370
+ VERCEL_TOKEN: ${{ secrets.VERCEL_TOKEN }}
371
+ VERCEL_ORG_ID: ${{ secrets.VERCEL_ORG_ID }}
372
+ TURBO_TOKEN: ${{ secrets.TURBO_TOKEN }}
373
+ TURBO_TEAM: ${{ secrets.TURBO_TEAM }}
374
+ steps:
375
+ - uses: actions/checkout@v4
376
+
377
+ - name: Setup Environment
378
+ uses: ./.github/actions/setup
379
+
380
+ - name: Resolve Vercel Project ID
381
+ id: resolve
382
+ run: |
383
+ case "${{ matrix.app }}" in
384
+ web) echo "project_id=${{ secrets.VERCEL_PROJECT_ID_WEB }}" >> $GITHUB_OUTPUT ;;
385
+ admin) echo "project_id=${{ secrets.VERCEL_PROJECT_ID_ADMIN }}" >> $GITHUB_OUTPUT ;;
386
+ esac
387
+
388
+ - name: Set VERCEL_PROJECT_ID
389
+ run: echo "VERCEL_PROJECT_ID=${{ steps.resolve.outputs.project_id }}" >> $GITHUB_ENV
390
+
391
+ - name: Install Vercel CLI
392
+ run: pnpm add -g vercel@latest
393
+
394
+ - name: Set deploy environment
395
+ run: |
396
+ echo "DEPLOY_DOTENV_FILE=$GITHUB_WORKSPACE/.env.production" >> $GITHUB_ENV
397
+ echo "DEPLOY_VERCEL_ENV=production" >> $GITHUB_ENV
398
+ echo "DEPLOY_PROD_FLAG=--prod" >> $GITHUB_ENV
399
+ echo "DEPLOY_RUN_ALIAS=false" >> $GITHUB_ENV
400
+
401
+ - name: Pull Vercel Environment
402
+ run: vercel pull --yes --environment=${{ env.DEPLOY_VERCEL_ENV }} --token=$VERCEL_TOKEN
403
+
202
404
  - name: Sync environment variables to Vercel
203
- if: github.ref_name == 'main'
204
405
  run: |
205
406
  npx dotenvx run -f ${{ env.DEPLOY_DOTENV_FILE }} -- bash -c '
206
407
  grep -E "^[A-Z_][A-Z0-9_]*=\"?encrypted:" ${{ env.DEPLOY_DOTENV_FILE }} | cut -d= -f1 | while read -r key; do
@@ -218,22 +419,16 @@ jobs:
218
419
  env:
219
420
  DOTENV_PRIVATE_KEY_PRODUCTION: ${{ secrets.DOTENV_PRIVATE_KEY_PRODUCTION }}
220
421
 
221
- # Re-pull after sync
222
422
  - name: Re-pull Vercel Environment after sync
223
- if: github.ref_name == 'main'
224
423
  run: vercel pull --yes --environment=${{ env.DEPLOY_VERCEL_ENV }} --token=$VERCEL_TOKEN
225
424
 
226
- # Vercel build (dotenvxでアプリ環境変数を注入)
227
425
  - name: Build Project
228
426
  run: |
229
427
  npx dotenvx run -f ${{ env.DEPLOY_DOTENV_FILE }} -- \
230
428
  vercel build ${{ env.DEPLOY_PROD_FLAG }} --token=$VERCEL_TOKEN
231
429
  env:
232
430
  DOTENV_PRIVATE_KEY_PRODUCTION: ${{ secrets.DOTENV_PRIVATE_KEY_PRODUCTION }}
233
- DOTENV_PRIVATE_KEY_STAGING: ${{ secrets.DOTENV_PRIVATE_KEY_STAGING }}
234
- DOTENV_PRIVATE_KEY_DEVELOP: ${{ secrets.DOTENV_PRIVATE_KEY_DEVELOP }}
235
431
 
236
- # Vercel deploy
237
432
  - name: Deploy to Vercel
238
433
  id: deploy
239
434
  run: |
@@ -256,10 +451,45 @@ jobs:
256
451
  '
257
452
  env:
258
453
  DOTENV_PRIVATE_KEY_PRODUCTION: ${{ secrets.DOTENV_PRIVATE_KEY_PRODUCTION }}
259
- DOTENV_PRIVATE_KEY_STAGING: ${{ secrets.DOTENV_PRIVATE_KEY_STAGING }}
260
- DOTENV_PRIVATE_KEY_DEVELOP: ${{ secrets.DOTENV_PRIVATE_KEY_DEVELOP }}
261
454
 
262
- # Alias (develop/stagingのみ)
263
- - name: Set Vercel alias
264
- if: env.DEPLOY_RUN_ALIAS == 'true'
265
- run: vercel alias ${{ steps.deploy.outputs.url }} "${{ env.VERCEL_ALIAS_DOMAIN }}" --token=$VERCEL_TOKEN
455
+ # main: changeset消費 + Release作成
456
+ release-production:
457
+ needs: deploy-production
458
+ if: always() && github.ref_name == 'main' && needs.deploy-production.result != 'failure'
459
+ runs-on: ubuntu-latest
460
+ steps:
461
+ - uses: actions/checkout@v4
462
+ with:
463
+ fetch-depth: 0
464
+
465
+ - name: Setup
466
+ uses: ./.github/actions/setup
467
+
468
+ - name: Check for changesets
469
+ id: check
470
+ run: |
471
+ COUNT=$(ls .changeset/*.md 2>/dev/null | grep -cv README.md || echo 0)
472
+ echo "has_changesets=$([[ $COUNT -gt 0 ]] && echo true || echo false)" >> $GITHUB_OUTPUT
473
+
474
+ - name: Version packages
475
+ if: steps.check.outputs.has_changesets == 'true'
476
+ run: npx changeset version
477
+
478
+ - name: Commit version bump and create Release
479
+ if: steps.check.outputs.has_changesets == 'true'
480
+ id: release
481
+ run: |
482
+ VERSION=$(node -p "require('./package.json').version")
483
+ TAG="v${VERSION}"
484
+ git config user.name "github-actions[bot]"
485
+ git config user.email "41898282+github-actions[bot]@users.noreply.github.com"
486
+ git add -A
487
+ git commit -m "chore: release ${TAG}" || echo "No changes"
488
+ git tag "$TAG"
489
+ git push origin main --follow-tags
490
+ PREV=$(git tag --list 'v*' --sort=-v:refname | grep -v 'rc' | grep -v "$TAG" | head -1)
491
+ OPTS="--target main --generate-notes"
492
+ [[ -n "$PREV" ]] && OPTS="$OPTS --notes-start-tag $PREV"
493
+ gh release create "$TAG" --title "Release ${TAG}" $OPTS
494
+ env:
495
+ GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
@@ -10,6 +10,7 @@
10
10
  3. **影響範囲の最小化**: 変更は必要な箇所のみ。関係ないコードに触れない
11
11
  4. **直接実装の禁止**: あなたは絶対に直接実装を行わない。すべての作業はsubagentに委託し、可能な限り並行で呼び出す。サブエージェントの出力はユーザにも見える場所に出力すること
12
12
  5. **実装品質の自己検証**: 複雑な変更では完了前に「よりエレガントな方法はないか」を自問する。ただし単純な修正には不要
13
+ 6. **Skill-First原則**: 実装着手前に `einja-skill-first` Skillで「Skillを先に作るべきか」を評価する。反復性のある作業はSkill化してから本作業を開始する
13
14
 
14
15
  ## Agent Teams の使用制限
15
16
 
@@ -26,7 +27,6 @@
26
27
 
27
28
  | 作業 | 委託先 |
28
29
  |------|--------|
29
- | コンフリクト解消 | `conflict-resolver` |
30
30
  | Codex作業(レビュー・実装支援等) | `codex-agent` |
31
31
  | フロントエンド アーキテクチャ設計 | `frontend-architect` |
32
32
  | フロントエンド デザイン実装 | `design-engineer` |
@@ -40,11 +40,21 @@
40
40
  | `einja-task-commit` | コミット・プッシュ |
41
41
  | `einja-conflict-resolver` | gitコンフリクト解消 |
42
42
  | `einja-skill-creator` | Skill作成・更新 |
43
- | `einja-skill-first` | 作業前のSkill作成必要性評価(Plan/spec-create時に自動起動) |
43
+ | `einja-skill-first` | 作業前のSkill作成必要性評価(Plan/einja-issue-spec-create時に自動起動) |
44
44
  | `einja-infra-maintenance` | インフラ環境セットアップ・メンテナンス |
45
- | `einja:issue-exec` | Issue全体の階層的並列実行(Manager→Director→Worker) |
46
- | `einja:task-exec` | タスクグループ実行 |
47
- | `einja:spec-create` | 仕様書作成 |
45
+ | `einja:issue-exec` | Issue全体の階層的並列実行(Command) |
46
+ | `einja-task-exec` | タスクグループ実行(Skill tool) |
47
+ | `einja-issue-spec-create` | Issue仕様書作成(Skill tool) |
48
+
49
+ #### サブエージェント質問プロトコル(PENDING_QUESTIONS)
50
+
51
+ サブエージェントではAskUserQuestionが動作しないため、質問が必要な場合は `## PENDING_QUESTIONS` 形式で返却される。
52
+
53
+ サブエージェント出力に `## PENDING_QUESTIONS` が含まれている場合:
54
+ 1. 質問内容を解析し、AskUserQuestionでユーザーに確認する
55
+ 2. Agent toolの `resume` パラメータで同じサブエージェントを再開(コンテキスト維持)
56
+ 3. プロンプトにユーザーの回答を含めて渡す(例: `ユーザーの回答: Q1→A、Q2→B。これを踏まえて作業を継続してください。`)
57
+ 4. 再度PENDING_QUESTIONSがある場合は同様に処理(最大2回まで)
48
58
 
49
59
  ## コード変更時の動作方針
50
60
 
@@ -126,7 +136,7 @@
126
136
  ## プロジェクト概要
127
137
 
128
138
  Turborepoモノレポ構成(pnpm workspaces)。詳細が必要な場合は以下のSkillを参照:
129
- - `einja-project-overview` - 構成、技術スタック、頻出コマンド
139
+ - `_einja-project-overview` - 構成、技術スタック、頻出コマンド
130
140
  - `docs/einja/steering/development/coding-standards.md` - コーディング規約、インポートパス規約
131
141
  - `einja-infra-maintenance` - 開発環境セットアップ、サーバー管理
132
142
 
@@ -165,6 +175,11 @@ Turborepoモノレポ構成(pnpm workspaces)。詳細が必要な場合は
165
175
  - 番号付きリスト: 詳細説明が必要な場合
166
176
  - 推奨オプションには `(推奨)` と理由を付記
167
177
 
178
+ ### 選択肢の記述ルール
179
+ - 各選択肢の `description` に**必ず詳細説明・注意点・補足**を記載する
180
+ - トレードオフ、影響範囲、前提条件など判断に必要な情報を含める
181
+ - ラベルだけで選択させない。ユーザーが十分な情報に基づいて判断できるようにする
182
+
168
183
  ## 報告ルール
169
184
 
170
185
  ### 出力形式
@@ -216,16 +231,29 @@ Turborepoモノレポ構成(pnpm workspaces)。詳細が必要な場合は
216
231
 
217
232
  このセクションはテンプレート生成時に除外され、CLIで他リポジトリにコピーされません。
218
233
 
234
+ ### Skill命名規則(配布制御)
235
+
236
+ | 区分 | ディレクトリ名 | name フィールド | 配布 |
237
+ |------|--------------|----------------|------|
238
+ | ユーザー向け | `einja-{name}/` | `einja-{name}` | される |
239
+ | インナー(内部参照用) | `_einja-{name}/` | `_einja-{name}` | される |
240
+ | リポジトリ固有 | `{name}/` | `{name}` | されない |
241
+
242
+ - Skill作成時は `einja-` プレフィックスをつける(配布対象にするため)
243
+ - インナーSkill(他Skillから内部的に参照されるもの)はディレクトリ名に `_einja-` プレフィックスをつける
244
+ - 配布しないリポジトリ固有Skillはプレフィックスをつけない
245
+ - 配布制御は `copy-presets.mjs` がディレクトリ名の `einja-` / `_einja-` プレフィックスで自動判定する
246
+
219
247
  ### キーワードトリガー(専用Skill使用必須)
220
248
 
221
249
  以下のキーワードを検出したら、**即座に該当Skillを参照**すること:
222
250
 
223
251
  | キーワード | 使用するSkill |
224
252
  |-----------|--------------|
225
- | `einja cli` `@einja/dev-cli` `公開` `リリース` `publish` `release` | `.claude/skills/dev-cli-release/SKILL.md` |
226
- | `create-einja-app` | `.claude/skills/create-einja-app-release/SKILL.md` |
227
- | `インフラ` `環境変数管理` `Vercel` `Neon` `デプロイ設定` `GitHub Secrets` `環境セットアップ` `GitHub Actions` `CI/CD` `ワークフロー` | `.claude/skills/einja-infra-maintenance/SKILL.md` |
253
+ | `einja cli` `@einja/dev-cli` `create-einja-app` `公開` `リリース` `publish` `release` | `.claude/skills/einja-npm-release/SKILL.md` |
254
+ | `インフラ` `環境変数管理` `Vercel` `Neon` `デプロイ設定` `GitHub Secrets` `環境セットアップ` `ローカルセットアップ` `ローカル環境` `セットアップ` `GitHub Actions` `CI/CD` `ワークフロー` | `.claude/skills/einja-infra-maintenance/SKILL.md` |
228
255
  | `Skill作るべき?` `Skill化` `skill-first` `Skill-first` | `.claude/skills/einja-skill-first/SKILL.md` |
256
+ | `prebuild` `copy-presets` `generate-template` `preset:update` `presets/default` `CLAUDE.md.template` `ファイルマッピング` `マーカー仕様` `@einja:excluded` `@einja:managed` `@einja:project-private` `FileCopier` `ビルドパイプライン` `テンプレート仕様` | `.claude/skills/cli-package-specs/SKILL.md` |
229
257
 
230
258
  ### CLIパッケージの二重管理禁止
231
259
 
@@ -235,13 +263,25 @@ Turborepoモノレポ構成(pnpm workspaces)。詳細が必要な場合は
235
263
  |-----|---------|------|
236
264
  | `.claude/agents/einja/` | `presets/default/.claude/agents/einja/` | 単純コピー |
237
265
  | `.claude/commands/einja/` | `presets/default/.claude/commands/einja/` | 単純コピー |
238
- | `.claude/skills/einja-*/` | `presets/default/.claude/skills/einja-*/` | 単純コピー |
266
+ | `.claude/skills/einja-*/` | `presets/default/.claude/skills/` | `einja-*` / `_einja-*` プレフィックスのディレクトリを自動スキャンしてコピー |
239
267
  | `.claude/hooks/einja/` | `presets/default/.claude/hooks/einja/` | 単純コピー |
240
268
  | `.claude/settings.json` | `presets/default/.claude/settings.json` | 単純コピー |
241
269
  | `.vscode/settings.json` | `presets/default/.vscode/settings.json` | 単純コピー |
242
270
  | `docs/einja/` (memory,cli除く) | `presets/default/docs/einja/` | 単純コピー(sync + init対象) |
243
271
  | `CLAUDE.md` | `presets/default/CLAUDE.md.template` | **変換生成** |
244
272
  | `scripts/` (`_`プレフィクス除く) | `presets/default/scripts/` | 単純コピー |
273
+ | `package.json`(ルート) | `presets/default/package.json` | フルコピー |
245
274
 
246
275
  **コピー先のファイルは直接編集禁止**(ビルド時に上書きされる)
276
+
277
+ ### パッケージビルド仕様(テンプレートリポジトリ限定)
278
+
279
+ `@einja/dev-cli` と `create-einja-app` の2パッケージのビルド・テンプレート仕様は、上記キーワードトリガーにより `cli-package-specs` Skillが自動参照される。
280
+
281
+ ### マネージドディレクトリの編集について(テンプレートリポジトリ限定)
282
+
283
+ このリポジトリは `docs/einja/` の**原本(Single Source of Truth)**である。
284
+ 上記「マネージドディレクトリ(編集禁止)」ルールは下流リポジトリ(create-einja-appで生成されたプロジェクト)向けであり、
285
+ **このリポジトリでは `docs/einja/` 配下の全ファイルを編集してよい**。
286
+ 変更はビルド時に `presets/default/` へ自動コピーされる。
247
287
  <!-- @einja:excluded:end -->
@@ -14,13 +14,19 @@ Turborepo + Next.js 15 + Auth.js + Prisma 構成のプロジェクトテンプ
14
14
  ```
15
15
  einja-management-template/
16
16
  ├── apps/
17
- └── web/ # メイン管理画面アプリ
17
+ ├── web/ # メイン管理画面アプリ
18
+ │ │ ├── src/
19
+ │ │ │ ├── app/ # Next.js App Router
20
+ │ │ │ ├── components/ # アプリ固有のコンポーネント
21
+ │ │ │ └── lib/
22
+ │ │ │ ├── auth/ # アプリ固有の認証設定
23
+ │ │ │ └── ... # アプリ固有のユーティリティ
24
+ │ │ ├── package.json
25
+ │ │ └── tsconfig.json
26
+ │ └── admin/ # 管理者画面アプリ
18
27
  │ ├── src/
19
28
  │ │ ├── app/ # Next.js App Router
20
- │ │ ├── components/ # アプリ固有のコンポーネント
21
- │ │ └── lib/
22
- │ │ ├── auth/ # アプリ固有の認証設定
23
- │ │ └── ... # アプリ固有のユーティリティ
29
+ │ │ └── components/ # アプリ固有のコンポーネント
24
30
  │ ├── package.json
25
31
  │ └── tsconfig.json
26
32
  ├── packages/
@@ -38,7 +44,9 @@ einja-management-template/
38
44
  │ │ └── src/
39
45
  │ │ ├── domain/ # ドメイン層
40
46
  │ │ ├── infrastructure/ # Prismaクライアント等
41
- │ │ └── utils/ # 共通ユーティリティ
47
+ │ │ ├── core/ # 共通コアモジュール
48
+ │ │ └── testing/ # テストユーティリティ
49
+ │ ├── admin-ui/ # 管理者画面専用UIコンポーネント
42
50
  │ └── ui/ # 共通UIコンポーネント(shadcn/ui)
43
51
  ├── turbo.json # Turborepoの設定
44
52
  ├── pnpm-workspace.yaml # pnpmワークスペース設定
@@ -61,6 +69,8 @@ einja-management-template/
61
69
 
62
70
  ### 開発環境セットアップ
63
71
 
72
+ > 📖 各コマンドで何が実行されるかの詳細は [セットアップフローガイド](docs/einja/instructions/setup-flow.md) を参照してください。
73
+
64
74
  #### 初回セットアップ(初めての方)
65
75
 
66
76
  ```bash
@@ -171,13 +181,14 @@ pnpm db:studio # Prisma Studio起動
171
181
  # 特定のワークスペースでコマンド実行
172
182
  pnpm --filter @repo/web dev
173
183
  pnpm --filter @repo/web build
184
+ pnpm --filter @repo/admin dev
174
185
  ```
175
186
 
176
187
  ### データベース設定
177
188
 
178
189
  #### Docker Compose サービス
179
190
 
180
- - **postgres**: PostgreSQL 15
191
+ - **postgres**: PostgreSQL 16
181
192
  - ポート: `${POSTGRES_PORT:-25432}` (ホスト) → 5432 (コンテナ)
182
193
  - データベース: ブランチ名から自動生成(例: `main`, `feature_auth`)
183
194
  - ユーザー: `postgres`
@@ -190,7 +201,7 @@ pnpm --filter @repo/web build
190
201
  docker-compose logs -f postgres
191
202
 
192
203
  # データベースに直接接続
193
- docker-compose exec postgres psql -U postgres -d einja_management
204
+ docker-compose exec postgres psql -U postgres -d main
194
205
 
195
206
  # データベースをリセット
196
207
  docker-compose down -v
@@ -220,6 +231,7 @@ pnpm db:studio
220
231
  - **@repo/config**: Biome, TypeScriptの共通設定
221
232
  - **@repo/front-core**: フロントエンド共通層(認証共通設定、hooks、utils、context)
222
233
  - **@repo/server-core**: バックエンド共通層(Prismaクライアント・スキーマ、ドメインロジック)
234
+ - **@repo/admin-ui**: 管理者画面専用UIコンポーネント
223
235
  - **@repo/ui**: 共通UIコンポーネント(shadcn/ui)
224
236
 
225
237
  ### 開発ワークフロー