スタック選定
Python / Go / Next.js など言語・FW の選定観点と具体例。
開発スタック(例)
付録的な技術スタック例。既存プロジェクトでは選定し直さない。
技術スタック選定の観点
スタックは「流行」ではなく、制約・チーム・運用・AI 開発のしやすさから逆算して決める。新規プロジェクトでは Phase 1 の前後で確定し、機能単位の理由は docs/<feature>/04_tech_decisions.md、組織横断の大きな判断は ADR に残す。
選定の原則
- 既存プロジェクトでは選定し直さない — 既存スタック・lint・CI・rules に合わせる。逸脱は ADR + 明示的承認
- レイヤごとに決める — 「全部 TypeScript」など一括決定より、言語 / FW / DB / 認証 / 観測を分けて判断する
- 候補はレイヤあたり最大 2 つ — 比較不能なほど選択肢を増やさない。第三候補が必要なら ADR 化
- デフォルトはチーム標準 — 新規でも「理由なく別 FW」は避ける。変更するなら trade-off を文章で残す
- AI 向けに型・テスト・rules を先に決める — スタック確定と同時に
.cursor/rules/の globs と検証コマンド(tsc/pytest/go test)を揃える
7 つの観点軸
各候補を次の軸で 1〜5 段階または「高/中/低」で揃え、弱い軸が許容できるかで絞る。表は Phase 1 や ADR のたたき台にそのまま貼れる。
| 観点 | 見ること | 判断の例 |
|---|---|---|
| 1. プロジェクト制約 | 期限・予算・リリース頻度・規制(金融・医療・個人情報) | 2 週間 MVP なら BaaS + マネージド DB。規制業界なら監査ログ・データ residency が先 |
| 2. チーム熟練度 | 言語・FW・クラウドの経験、オンボーディング人数 | Go 未経験チーム 3 人なら Python/FastAPI を標準に。学習コストは ADR に明記 |
| 3. ドメイン要件 | リアルタイム、バッチ、モバイル、AI/RAG、ファイル処理、多言語 | WebSocket 多め → 長寿命接続に強いランタイム / インフラ。RAG → pgvector 等(RAG 参考) |
| 4. 非機能要件 | 可用性、レイテンシ p99、同時接続、データ量、RPO/RTO | p99 < 100ms が必須なら DB 近接 + キャッシュ設計を先に固定。Serverless のコールドスタートもここ |
| 5. 運用・観測 | 既存 CI/CD、Secret 管理、ログ基盤、オンコール体制 | Datadog 既契約なら OpenTelemetry exporter を統一。trace_id 貫通はフロント/バック共通 |
| 6. エコシステム・保守 | LTS、CVE 対応、採用実績、ライセンス、ベンダーロックイン | Pages Router 廃止方向など「新規非推奨」は採らない。ORM は FW 公式寄りを優先 |
| 7. AI 開発適性 | 型の強さ、テスト速度、rules で縛れるか、ドキュメント量 | TypeScript strict + Zod、Go interface + table test は AI 修正のレビューがしやすい |
レイヤ別の判断ポイント
「何を使うか」の前に、そのレイヤで何を満たす必要があるかを書く。
| レイヤ | 先に決めること | よくある分岐 |
|---|---|---|
| フロントエンド | SEO / SSR 要否、オフライン、管理画面のみか公開サイトか | コンポーネント SPA 中心 → React。routing / SSR / Server Actions 一体 → Next.js |
| バックエンド API | 同期 REST 中心か、gRPC/GraphQL か、長時間ジョブの有無 | CRUD + OpenAPI 型生成 → Go / Python。Django 管理画面込み → Django |
| データ | トランザクション、全文検索、ベクトル、イベントソーシング | PostgreSQL をデフォルト。ベクトルは pgvector または 専用 Vector DB |
| 認証・認可 | IdP 連携、B2B SSO、端末種別、セッション vs JWT | Next.js なら Auth.js / Clerk。API のみなら OIDC + API Gateway |
| 非同期・ジョブ | キュー、スケジュール、再試行、冪等性 | AWS なら SQS + Lambda/ECS(Lambda ガイド)。軽量なら DB ベースキュー |
| ホスティング | トラフィック形状、デプロイ頻度、プレビュー環境 | Next.js → Vercel。既存 AWS 標準 → Lambda / ECS(クラウド比較) |
| 観測 | ログ・メトリクス・トレース・エラー監視の一本化 | OpenTelemetry を共通。Sentry(FE)+ 構造化ログ(BE)が一般的 |
選定手順(新規プロジェクト)
- 制約と非機能を列挙する — 要件すり合わせ の成果物から、期限・SLA・データ分類・既存システム連携を抜き出す
- チーム標準を確認する — 既存リポジトリ、社内テンプレ、契約中 SaaS。あればそれがデフォルト候補
- レイヤごとに候補を 2 つまで絞る — 上記 7 軸でスコアリング。引き分けは「運用コストが低い方」「rules 化しやすい方」
- API 契約の方式を決める — OpenAPI / GraphQL / tRPC のいずれか。モノレポなら型生成パイプラインまでセットで決める
- Phase 1 で rules と CI を生成する — スタック確定後、
AGENTS.md/.cursor/rules/*.mdcに globs・検証コマンド・禁止事項を書く(Phase 1) - 理由を docs に残す — 機能単位は
04_tech_decisions.md、組織に効く判断は ADR。採らなかった案と理由を 3 行以上
言語・FW の trade-off 早見
「正解」は 1 つではない。よくある対比と、こういうときに寄せるの目安。
| 分岐 | 寄せる先(目安) | トレードオフ |
|---|---|---|
| Python vs Go(API) | Python: プロトタイプ・ML 連携・Django 一体 / Go: 高スループット・単一バイナリ・厳格な型 | Python は GIL・型の弱さ。Go は ORM エコシステムが薄い分、sqlc 等で補う |
| FastAPI vs Django | FastAPI: 小さな API・OpenAPI 自動生成 / Django: 管理画面・認証・ORM 一体 | Django は API のみプロジェクトでは重い。FastAPI は admin が別途必要 |
| React vs Next.js | React: 既存 Vite/SPA・埋め込み UI / Next.js: 新規 Web アプリ・SSR・Vercel デプロイ | Next.js はフレームワーク opinion が強い。React のみなら routing 等を自前選定 |
| REST vs GraphQL vs tRPC | REST+OpenAPI: 多言語クライアント / GraphQL: クライアント主導の取得 / tRPC: TS モノレポ | GraphQL は N+1・キャッシュ複雑。tRPC は TS 以外と相性が悪い |
| Monolith vs マイクロサービス | 初期はモノリス(または modular monolith) | 分割はデプロイ独立・チーム分割が本当に必要になってから ADR |
フロントを早めに絞るなら、コンポーネント中心の SPA が主なら React、routing / SSR / Server Actions まで一体なら Next.js を初期候補にする。Next.js 内で React を使う構成なら両方を前提にしてよい。
記録テンプレ(04_tech_decisions)
Phase 3 プロンプトや手動追記で、次の項目を埋める。AI に書かせるときも同じ見出しを指定する。
## 技術選定: <レイヤ名>
### 背景
- 何を満たす必要があるか(非機能・制約)
### 決定
- 採用: <具体名とバージョン目安>
### 検討した代替案
- 案 A: 不採用理由
- 案 B: 不採用理由
### 影響
- CI / rules / デプロイ / セキュリティ / コスト
### 見直し条件
- 例: 月間リクエスト 10x、チーム +5 人、p99 が SLA 超過
例: Python バックエンドの場合
| レイヤ | 選択 | 備考 |
|---|---|---|
| 言語 | Python 3.12+ | 既存プロジェクトに合わせる |
| FW | FastAPI / Django / Flask | プロジェクト方針 |
| DB | PostgreSQL / MySQL | チーム標準 |
| ORM | SQLAlchemy 2.0 / Django ORM | FWに揃える |
| マイグレーション | Alembic / Django migrations | |
| テスト | pytest + pytest-cov + testcontainers | |
| ログ | structlog / 標準logging | チーム標準 |
| メトリクス | OpenTelemetry + Datadog/Grafana | 既存基盤に従う |
| CI | GitHub Actions / GitLab CI | 既存基盤 |
例: Go (Golang) バックエンドの場合
| レイヤ | 選択 | 備考 |
|---|---|---|
| 言語 | Go 1.22+ | log/slog 標準採用のため 1.21+ 推奨 |
| FW | Echo / Gin / Chi / 標準 net/http |
軽量FW派が主流。小規模なら標準ライブラリのみでも可 |
| DB | PostgreSQL / MySQL | チーム標準 |
| DB ドライバ | pgx (PostgreSQL) / go-sql-driver/mysql | 公式 database/sql 経由 |
| クエリ層 | sqlc / sqlx / GORM / ent | sqlc は SQL→型安全コード生成で実務で人気 |
| マイグレーション | golang-migrate / goose / atlas | |
| バリデーション | go-playground/validator | 構造体タグでルール定義 |
| DI | 手書きコンストラクタ注入 / wire (Google) | 重いDIフレームワークは少数派 |
| テスト | 標準 testing + testify + testcontainers-go |
テーブル駆動テストが慣習 |
| モック | gomock / mockery / 手書き | Protocol(interface) を手書きで差し替えるパターンが多い |
| ログ | log/slog (標準, Go 1.21+) / zap / zerolog |
新規なら slog 推奨 |
| メトリクス | OpenTelemetry + Prometheus / Datadog | 標準的 |
| CI | GitHub Actions / GitLab CI | go test ./... / golangci-lint 必須 |
| Lint | golangci-lint | 複数linter統合の事実上標準 |
| パッケージ管理 | Go Modules (go.mod) |
標準 |
Go 特有の .cursor/rules/20-coding-style.mdc 差分例
---
description: Go コーディング規約
globs: **/*.go
---
# Go Coding Style
## 命名
- 公開: PascalCase, 非公開: camelCase
- パッケージ名: 短く小文字 (例: user, order)
- インタフェース名: 通常は -er サフィックス (Reader, Writer, UserRepository)
## エラーハンドリング
- error は早期 return。ネストを深くしない
- 業務エラーは独自型 (`var ErrInsufficientStock = errors.New("...")` または独自struct + `errors.Is/As`)
- パニックは原則使わない (recoverもライブラリ境界のみ)
- ラップは `fmt.Errorf("doing X: %w", err)`
## 並行性
- goroutine の起動箇所には必ず終了条件 (context.Context / chan close) を用意
- channel の close は送信側のみ
- 共有メモリより通信 (channel) を優先、ただし sync.Mutex を恐れない
## context
- 公開関数の第1引数は context.Context
- context は構造体に保持しない
## テスト
- t.Run でサブテスト + テーブル駆動
- t.Parallel() でレース検出
- ヘルパは t.Helper() を呼ぶ
例: Next.js + React フロントエンドの場合
| レイヤ | 選択 | 備考 |
|---|---|---|
| 言語 | TypeScript 5+ | strict: true 必須 |
| FW | Next.js 15+ (App Router) | Pages Routerは新規採用しない |
| UI ライブラリ | React 19 | Server Components + Server Actions 活用 |
| スタイリング | Tailwind CSS + shadcn/ui | カスタムCSSは最小限 |
| 状態管理 (Server) | React Server Components + Server Actions | デフォルトはサーバー側で完結 |
| 状態管理 (Client) | Zustand / Jotai / TanStack Query | グローバル/サーバー状態の使い分け |
| フォーム | React Hook Form + Zod | サーバー側でも Zod で再検証 |
| スキーマ検証 | Zod | API境界・フォーム・環境変数すべてに使う |
| 認証 | Auth.js (NextAuth) / Clerk | プロバイダ対応で選ぶ |
| API クライアント | TanStack Query / SWR / fetch | RSC優先、必要時のみ |
| テスト (ユニット) | Vitest + React Testing Library | Jest互換だが高速 |
| テスト (E2E) | Playwright | Cypressより推奨派が増えている |
| ログ | pino (サーバー) / 標準 console (ブラウザ) | クライアント側はSentry等で集約 |
| 観測 | OpenTelemetry + Vercel Analytics / Sentry | エラー監視は Sentry が一般的 |
| パッケージ管理 | pnpm | 高速・ディスク効率 |
| Lint / Format | ESLint + Prettier / Biome | Biomeは新興だが高速 |
| 型生成 | OpenAPI Generator / GraphQL Codegen / tRPC | バックエンドAPIから型を引く |
| CI | GitHub Actions | tsc --noEmit / lint / test / build |
| ホスティング | Vercel / Cloud Run / 自前Node | Next.js は Vercel が最適化されている |
Next.js 特有の .cursor/rules/20-coding-style.mdc 差分例
---
description: Next.js / React コーディング規約
globs: **/*.{ts,tsx}
---
# Next.js / React Coding Style
## ファイル配置 (App Router)
- ルーティング: app/<segment>/page.tsx
- レイアウト: app/<segment>/layout.tsx
- API: app/api/<endpoint>/route.ts
- 共通コンポーネント: components/
- 業務ロジック: lib/ または domain/
- 型: types/ または同居の types.ts
## サーバー / クライアントの境界
- デフォルトは Server Component
- "use client" は必要最小限のリーフコンポーネントのみ
- Server Action は app/actions/ または同居の actions.ts に集約
- フォームは Server Action 経由を優先
## TypeScript
- any 禁止 (どうしても必要なら unknown + 型ガード)
- 公開関数には引数/戻り値の型を明示
- API境界は Zod で実行時検証
- 環境変数も Zod でパース (process.env.* を直接使わない)
## コンポーネント設計
- Props は interface ではなく type
- children は ReactNode
- 副作用は useEffect 最小化、Server Component で済むなら使わない
- イベントハンドラは on* 命名
## アクセシビリティ
- セマンティックHTML優先 (div の濫用禁止)
- 画像は next/image、alt 必須
- フォームは label + input の関連付け
- キーボード操作可能を維持
## パフォーマンス
- 動的import (`next/dynamic`) で初期バンドル削減
- 画像最適化は next/image 必須
- Suspense + Streaming を活用
- "use client" を上位に置きすぎない (バンドルが膨らむ)
## テスト
- ユニット: Vitest + React Testing Library (`screen.getByRole` 優先、`getByTestId` は最終手段)
- E2E: Playwright で主要動線
- アクセシビリティ: axe / @testing-library/jest-dom
フロント / バックエンド共通の留意点
- モノレポ運用: フロントとバックが同居するなら pnpm workspaces / Turborepo / Nx を検討。Cursor では
.cursor/rules/、Claude Code ではCLAUDE.md/.claude/skills/、Codex ではAGENTS.md/.agents/skills/をサブパッケージ単位で重ねられる - API 契約: OpenAPI / GraphQL / tRPC のいずれかで型を一元化。Go backend + Next.js なら OpenAPI からの自動生成が現実的
- エラー連携: フロント・バック・ログ基盤で
trace_idを貫通させる (OpenTelemetry) - 環境変数: 12-factor app に従い
.envで分離、本番は基盤側のSecret Manager
既存プロジェクトでは選定し直さない。既存スタックに合わせるのが原則。新規導入が必要なら docs/04_tech_decisions.md に理由を残す。