建立專案骨架(Scaffold)
專案骨架模板與樣板產生工具,適用於常見專案類型,並內建最佳實踐預設值。
專案類型決策樹
你在建置什麼?
│
├─ API / 後端服務
│ ├─ REST API
│ │ ├─ Python → FastAPI(非同步,OpenAPI 自動文件)
│ │ ├─ Node.js → Express 或 Fastify(效能導向選 Fastify)
│ │ ├─ Go → Gin(易用)或 Echo(中介軟體豐富)
│ │ └─ Rust → Axum(tower 生態系,非同步優先)
│ ├─ GraphQL API
│ │ ├─ Python → Strawberry + FastAPI
│ │ ├─ Node.js → Apollo Server 或 Pothos + Yoga
│ │ ├─ Go → gqlgen(程式碼優先)
│ │ └─ Rust → async-graphql + Axum
│ └─ gRPC 服務
│ ├─ Python → grpcio + protobuf
│ ├─ Go → google.golang.org/grpc
│ └─ Rust → tonic
│
├─ Web 應用程式
│ ├─ 全端 SSR
│ │ ├─ React 生態系 → Next.js 14+(App Router)
│ │ ├─ Vue 生態系 → Nuxt 3
│ │ ├─ Svelte 生態系 → SvelteKit
│ │ └─ 內容豐富/多框架 → Astro
│ ├─ SPA(僅客戶端)
│ │ ├─ React → Vite + React + React Router
│ │ ├─ Vue → Vite + Vue + Vue Router
│ │ └─ Svelte → Vite + Svelte + svelte-routing
│ └─ 靜態網站
│ ├─ 部落格/文件 → Astro 或 VitePress
│ └─ 行銷/登陸頁 → Astro 或 Next.js(靜態匯出)
│
├─ CLI 工具
│ ├─ Python → Typer(簡單)或 Click(複雜)
│ ├─ Node.js → Commander + Inquirer
│ ├─ Go → Cobra + Viper
│ └─ Rust → Clap(derive API)
│
├─ 函式庫/套件
│ ├─ npm 套件 → TypeScript + tsup + Vitest
│ ├─ PyPI 套件 → uv + pyproject.toml + pytest
│ ├─ Go 模組 → go mod init + go test
│ └─ Rust crate → cargo init --lib + cargo test
│
└─ 單體倉庫(Monorepo)
├─ JavaScript/TypeScript → Turborepo + pnpm workspaces
├─ 全端 JS → Nx
├─ Go → Go workspaces (go.work)
├─ Rust → Cargo workspaces
└─ Python → uv workspaces 或 hatch
技術棧選擇矩陣
| 專案類型 | 語言 | 框架 | 資料庫 | ORM/查詢工具 | 部署目標 |
|---|
| REST API | Python | FastAPI | PostgreSQL | SQLAlchemy + Alembic | Docker / AWS ECS |
| REST API | Node.js | Fastify | PostgreSQL | Prisma 或 Drizzle | Docker / Vercel |
| REST API | Go | Gin | PostgreSQL | sqlx(原始)或 GORM | Docker / Fly.io |
| REST API | Rust | Axum | PostgreSQL | sqlx | Docker / Fly.io |
| Web App | TypeScript | Next.js 14+ | PostgreSQL | Prisma 或 Drizzle | Vercel / Docker |
| Web App | TypeScript | Nuxt 3 | PostgreSQL | Prisma | Vercel / Netlify |
| Web App | TypeScript | Astro | SQLite / 無 | Drizzle | Cloudflare / Netlify |
| CLI 工具 | Python | Typer | SQLite | sqlite3 標準庫 | PyPI |
| CLI 工具 | Go | Cobra | SQLite / BoltDB | sqlx | GitHub Releases |
| CLI 工具 | Rust | Clap | SQLite | rusqlite | crates.io |
| 函式庫 | TypeScript | tsup | 不適用 | 不適用 | npm |
| 函式庫 | Python | hatch/uv | 不適用 | 不適用 | PyPI |
快速建立指令
Python(API)
mkdir my-api && cd my-api
uv init --python 3.12
uv add fastapi uvicorn sqlalchemy alembic psycopg2-binary pydantic-settings
uv add --dev pytest pytest-asyncio httpx ruff mypy
Node.js(Web App)
npx create-next-app@latest my-app --typescript --tailwind --eslint --app --src-dir --import-alias "@/*"
npm create vite@latest my-app -- --template react-ts
Go(API)
mkdir my-api && cd my-api
go mod init github.com/user/my-api
go get github.com/gin-gonic/gin
go get github.com/jmoiron/sqlx
go get github.com/lib/pq
Rust(CLI)
cargo init my-cli
cd my-cli
cargo add clap --features derive
cargo add serde --features derive
cargo add anyhow tokio --features tokio/full
單體倉庫(Turborepo)
npx create-turbo@latest my-monorepo
mkdir my-monorepo && cd my-monorepo
npm init -y
npm install turbo --save-dev
mkdir -p apps/web apps/api packages/shared
API 專案模板
目錄結構(FastAPI 範例)
my-api/
├── src/
│ └── my_api/
│ ├── __init__.py
│ ├── main.py # FastAPI 應用程式、生命週期、中介軟體
│ ├── config.py # pydantic-settings 配置
│ ├── database.py # SQLAlchemy 引擎、會話
│ ├── dependencies.py # 共享 FastAPI 依賴注入
│ ├── routers/
│ │ ├── __init__.py
│ │ ├── health.py # 健康檢查端點
│ │ └── users.py # 使用者 CRUD 端點
│ ├── models/
│ │ ├── __init__.py
│ │ └── user.py # SQLAlchemy 模型
│ ├── schemas/
│ │ ├── __init__.py
│ │ └── user.py # Pydantic 請求和回應結構定義
│ └── services/
│ ├── __init__.py
│ └── user.py # 業務邏輯
├── alembic/
│ ├── alembic.ini
│ ├── env.py
│ └── versions/
├── tests/
│ ├── conftest.py # 測試用固定裝置:測試資料庫、客戶端、工廠
│ ├── test_health.py
│ └── test_users.py
├── pyproject.toml
├── Dockerfile
├── docker-compose.yml
├── .env.example
├── .gitignore
└── .dockerignore
目錄結構(Express/Fastify 範例)
my-api/
├── src/
│ ├── index.ts # 進入點,伺服器啟動
│ ├── app.ts # Express/Fastify 應用程式設定
│ ├── config.ts # 環境配置搭配 zod 驗證
│ ├── database.ts # Prisma 客戶端或 Drizzle 配置
│ ├── middleware/
│ │ ├── auth.ts
│ │ ├── error-handler.ts
│ │ └── request-logger.ts
│ ├── routes/
│ │ ├── health.ts
│ │ └── users.ts
│ ├── services/
│ │ └── user.service.ts
│ └── types/
│ └── index.ts
├── prisma/
│ └── schema.prisma
├── tests/
│ ├── setup.ts
│ └── routes/
│ └── users.test.ts
├── package.json
├── tsconfig.json
├── Dockerfile
├── docker-compose.yml
├── .env.example
└── .gitignore
Web 應用程式專案模板
目錄結構(Next.js App Router)
my-app/
├── src/
│ ├── app/
│ │ ├── layout.tsx # 根佈局
│ │ ├── page.tsx # 首頁
│ │ ├── loading.tsx # 全域載入 UI
│ │ ├── error.tsx # 全域錯誤邊界
│ │ ├── not-found.tsx # 404 頁面
│ │ ├── globals.css # 全域樣式 + Tailwind
│ │ ├── (auth)/
│ │ │ ├── login/page.tsx
│ │ │ └── register/page.tsx
│ │ ├── dashboard/
│ │ │ ├── layout.tsx
│ │ │ └── page.tsx
│ │ └── api/
│ │ └── health/route.ts
│ ├── components/
│ │ ├── ui/ # 可複用的基本元件
│ │ └── features/ # 特定功能元件
│ ├── lib/
│ │ ├── db.ts # 資料庫客戶端
│ │ ├── auth.ts # 驗證輔助函式
│ │ └── utils.ts # 共用工具函式
│ └── types/
│ └── index.ts
├── public/
│ └── favicon.ico
├── tests/
│ ├── setup.ts
│ └── components/
├── next.config.ts
├── tailwind.config.ts
├── tsconfig.json
├── package.json
├── .env.local.example
└── .gitignore
CLI 工具專案模板
目錄結構(Python / Typer)
my-cli/
├── src/
│ └── my_cli/
│ ├── __init__.py
│ ├── __main__.py # python -m my_cli 進入點
│ ├── cli.py # Typer 應用程式、指令群組
│ ├── commands/
│ │ ├── __init__.py
│ │ ├── init.py # my-cli init
│ │ └── run.py # my-cli run
│ ├── config.py # 設定檔載入(TOML/YAML)
│ └── utils.py
├── tests/
│ ├── conftest.py
│ └── test_commands.py
├── pyproject.toml # [project.scripts] 進入點
├── .gitignore
└── README.md
目錄結構(Go / Cobra)
my-cli/
├── cmd/
│ ├── root.go # 根指令、全域標誌
│ ├── init.go # my-cli init
│ └── run.go # my-cli run
├── internal/
│ ├── config/
│ │ └── config.go # Viper 設定檔載入
│ └── runner/
│ └── runner.go # 核心邏輯
├── main.go # 進入點,呼叫 cmd.Execute()
├── go.mod
├── go.sum
├── Makefile
└── .gitignore
函式庫專案模板
目錄結構(npm 套件)
my-lib/
├── src/
│ ├── index.ts # 公開 API 匯出
│ ├── core.ts # 核心實作
│ └── types.ts # 公開型別定義
├── tests/
│ └── core.test.ts
├── package.json # "type": "module", exports 對應表
├── tsconfig.json # declaration: true, declarationMap: true
├── tsup.config.ts # 建置設定:cjs + esm
├── vitest.config.ts
├── .npmignore
├── .gitignore
├── CHANGELOG.md
└── LICENSE
目錄結構(PyPI 套件)
my-lib/
├── src/
│ └── my_lib/
│ ├── __init__.py # 公開 API,__version__
│ ├── core.py
│ └── py.typed # PEP 561 標記
├── tests/
│ ├── conftest.py
│ └── test_core.py
├── pyproject.toml # 建置系統、中繼資料、工具設定
├── .gitignore
├── CHANGELOG.md
└── LICENSE
單體倉庫模板
Turborepo + pnpm Workspaces
my-monorepo/
├── apps/
│ ├── web/ # Next.js 前端
│ │ ├── src/
│ │ ├── package.json # 相依於 @repo/shared
│ │ └── tsconfig.json # 繼承 ../../tsconfig.base.json
│ └── api/ # Fastify 後端
│ ├── src/
│ ├── package.json
│ └── tsconfig.json
├── packages/
│ ├── shared/ # 共用型別、工具函式、驗證器
│ │ ├── src/
│ │ ├── package.json # "name": "@repo/shared"
│ │ └── tsconfig.json
│ ├── ui/ # 共用 React 元件
│ │ ├── src/
│ │ └── package.json # "name": "@repo/ui"
│ └── config/ # 共用設定
│ ├── eslint/
│ ├── typescript/
│ └── package.json
├── turbo.json # 管線:build, test, lint
├── pnpm-workspace.yaml # packages: ["apps/*", "packages/*"]
├── package.json # 根目錄 devDeps: turbo
├── tsconfig.base.json # 共用 TypeScript 設定
├── .gitignore
└── .npmrc
Cargo Workspaces(Rust)
my-workspace/
├── crates/
│ ├── my-core/ # 核心函式庫
│ │ ├── src/lib.rs
│ │ └── Cargo.toml
│ ├── my-cli/ # CLI 二進位檔
│ │ ├── src/main.rs
│ │ └── Cargo.toml # 相依於 my-core
│ └── my-server/ # API 二進位檔
│ ├── src/main.rs
│ └── Cargo.toml
├── Cargo.toml # [workspace] members = ["crates/*"]
├── Cargo.lock
├── .gitignore
└── rust-toolchain.toml
常見附加項目檢查清單
專案設定完成?加入以下項目:
│
├─ 版本控制
│ ├─ [ ] .gitignore(語言專用)
│ ├─ [ ] .gitattributes(換行符號、二進位檔案)
│ └─ [ ] 分支保護規則
│
├─ CI/CD
│ ├─ [ ] GitHub Actions 工作流程(PR 測試,合併後部署)
│ ├─ [ ] 矩陣測試(作業系統、執行時期版本)
│ └─ [ ] 發佈自動化
│
├─ Docker
│ ├─ [ ] 多階段 Dockerfile
│ ├─ [ ] docker-compose.yml(應用程式 + 資料庫 + 快取)
│ ├─ [ ] .dockerignore
│ └─ [ ] 健康檢查端點
│
├─ 程式碼品質
│ ├─ [ ] Lint 工具(ESLint, Ruff, golangci-lint, Clippy)
│ ├─ [ ] 格式化工具(Prettier, Black/Ruff, gofmt, rustfmt)
│ ├─ [ ] Pre-commit 鉤子(Husky, pre-commit)
│ └─ [ ] 型別檢查(TypeScript strict, mypy, go vet)
│
├─ 測試
│ ├─ [ ] 測試框架已設定(Vitest, pytest, go test)
│ ├─ [ ] 覆蓋率報告
│ ├─ [ ] 測試資料庫設定
│ └─ [ ] CI 測試管線
│
├─ 編輯器
│ ├─ [ ] .editorconfig
│ ├─ [ ] .vscode/settings.json
│ └─ [ ] .vscode/extensions.json
│
└─ 文件
├─ [ ] README.md(專案描述、設定、使用方法)
├─ [ ] CONTRIBUTING.md
└─ [ ] API 文件(OpenAPI, godoc, rustdoc)
組態檔案模板
.editorconfig(通用)
root = true
[*]
indent_style = space
indent_size = 2
end_of_line = lf
charset = utf-8
trim_trailing_whitespace = true
insert_final_newline = true
[*.{py,rs}]
indent_size = 4
[*.go]
indent_style = tab
[*.md]
trim_trailing_whitespace = false
[Makefile]
indent_style = tab
pyproject.toml(Python)
[project]
name = "my-project"
version = "0.1.0"
requires-python = ">=3.12"
[tool.ruff]
target-version = "py312"
line-length = 88
[tool.ruff.lint]
select = ["E", "F", "I", "UP", "B", "SIM"]
[tool.pytest.ini_options]
testpaths = ["tests"]
asyncio_mode = "auto"
[tool.mypy]
strict = true
tsconfig.json(TypeScript - 嚴格模式)
{
"compilerOptions": {
"target": "ES2022",
"module": "NodeNext",
"moduleResolution": "NodeNext",
"strict": true,
"esModuleInterop": true,
"skipLibCheck": true,
"forceConsistentCasingInFileNames": true,
"resolveJsonModule": true,
"declaration": true,
"declarationMap": true,
"sourceMap": true,
"outDir": "./dist",
"rootDir": "./src"
},
"include": ["src"],
"exclude": ["node_modules", "dist"]
}
常見陷阱
| 陷阱 | 原因 | 預防方式 |
|---|
| 語言專用 .gitignore 錯誤 | 使用了通用模板,缺少語言專用條目 | 使用 gitignore.io 或 GitHub 的模板 |
| 忘記建立 .env.example | 團隊成員不知道需要哪些環境變數 | 專案開始時就建立 .env.example,每個變數留空 |
| 未提交 lock 檔案 | 不同環境間相依版本不一致 | 提交 package-lock.json, uv.lock, go.sum, Cargo.lock |
| 程式碼中寫死連接埠/主機 | 在本機可運作,但在 Docker/雲端會失效 | 一律從環境變數讀取,並設定合理的預設值 |
| 測試直接依賴真實資料庫 | 無資料庫時測試會失敗,CI 設定複雜 | 使用測試容器或記憶體中的 SQLite 進行單元測試 |
| 缺少健康檢查端點 | 部署調度工具無法確認服務就緒狀態 | 新增 /health 端點,回傳服務狀態 |