%%{ init: {
'theme': 'default',
'themeVariables': {
'fontFamily': 'Meiryo'
},
'gitGraph': {
'orientation': 'LR',
'nodeSpacing': 150,
'mainBranchName': 'main'
}
} }%%
gitGraph
commit id: "" tag: "v1.0.0"
branch hotfix
checkout hotfix
commit id: "BUGFIX"
checkout main
branch develop
checkout develop
commit id: "開発開始"
branch feature/0001/login
checkout feature/0001/login
commit id: ""
checkout main
merge hotfix tag: "v1.0.1"
checkout develop
merge hotfix
commit id: "incorporate hotfix"
checkout develop
merge feature/0001/login
commit id: "ログイン機能実装"
branch release/1.1.x
checkout release/1.1.x
commit id: "リリース準備"
commit id: "bugfix"
checkout develop
merge release/1.1.x
checkout main
merge release/1.1.x tag: "v1.1.0"
checkout develop
commit id: "FEATURE"
1. Branch Strategy
- Git Flow をベースにしたブランチ戦略を採用
- リリース系列ブランチ,
developを統合ブランチとするが,Issue規模・リリース運用の実態に合わせて,Issue用の統合ブランチを活用
2. ブランチの種類
Basic Syntax
<branch-type>/<issue-number>/<task-description>release 系列ブランチや hotfix ブランチなど,Issue番号を含まない場合もあります.その場合は
release/<major>.<minor>.<patch>
hotfix/<task-description>命名規則
| ブランチ種別 | 命名規則 | 目的 |
|---|---|---|
| 本番用 | main |
本番デプロイ可能な安定版コード.常にリリース済みの状態を保持 |
| 開発用 | develop |
全機能・修正の統合先(メイン開発ブランチ) |
| 機能追加 | feature/<issue番号>/<タスク> |
新機能開発や改善タスク.小規模IssueはこのままdevelopへPR |
| 機能改善 | enhancement/<issue番号>/<タスク> |
既存機能の改善タスク.UX改善・処理最適化など |
| バグ修正 | bugfix/<issue番号>/<タスク> |
不具合修正用ブランチ.テスト後developへ統合 |
| Issue統合 | issue/<issue番号> |
中〜大規模Issueの場合のみ作成.複数サブタスクを統合するための統合ブランチ |
| リリース系列 | release/<major>.<minor>.x |
特定マイナー系列(例: 1.1.x)の安定維持・軽微修正対応用(長寿命) |
| リリース準備 | release/<version>/create-release-note |
リリースノート作成・バージョン確定・タグ準備用(短命) |
| 緊急修正 | hotfix/<issue番号> |
本番環境向けの即時修正.修正後 main / develop 両方に反映 |
| テスト検証用 | test/<issue番号>/<タスク> |
一時的なテストコード・検証用ブランチ.検証完了後削除 |
| ドキュメント整備 | docs/<issue番号>/<タスク> |
ドキュメント・ガイド・README更新などのためのブランチ |
| リファクタリング | refactor/<issue番号>/<タスク> |
挙動を変えずに内部構造を改善するためのブランチ |
| 検証・試作用 | sandbox/<タスク> |
新しいアイデアやPoCを試すための実験的ブランチ(非公式).安定版にマージしない前提 |
命名例
| ブランチ名 | 用途 |
|---|---|
feature/0123-add-login |
新機能 |
bugfix/0123-fix-login-error |
修正 |
issue/0123 |
複数サブタスクを含むIssue統合 |
release/1.1.x |
1.1 系列のリリース維持 |
release/1.1.1/create-release-note |
1.1.1 リリース準備 |
hotfix/0145-critical-fix |
緊急対応 |
3. 開発フロー
Step 1. サブタスク開発
各Issueに対して、必要なサブタスクごとにブランチを切ります.
git switch develop
git switch -c feature/0123/add-login
git switch -c bugfix/0123/fix-login-error- 小規模Issueなら、このまま develop に直接PR(Step3へ)
- 中〜大規模Issueなら,Issue統合ブランチを作成し,サブタスクをまとめる (Step 2へ)
Step 2. 中〜大規模Issueの統合ブランチ(任意)
複数のサブタスクをまとめてレビューしたい場合にのみ作成します.
git switch develop
git switch -c issue/0123
git merge feature/0123/add-login
git merge bugfix/0123/fix-login-error
git push -u origin issue/0123- 統合PRを作成:
issue/0123→develop - チーム単位でまとめてレビュー/テストを実施
Step 3. developへの統合
- Issue単位またはサブタスク単位で
developにPR作成 - ローカルで実行する場合は
git merge --no-ffで対応
Step 4. リリース系列ブランチ作成
- 開発が安定したタイミングでマイナー系列ブランチを作成
- ブランチ作成は開発規模に応じて,
git switch -cまたは GitHub Actionsで実施
git switch develop
git switch -c release/1.1.x
git push -u origin release/1.1.xStep 5. リリース準備ブランチ
git switch release/1.1.x
git switch -c release/1.1.1/0130/create-release-note- 作業内容例:
- リリースノート更新
- バージョン番号更新 (
__version__.pyなど) - 最終テスト、修正
- PR作成:
release/1.1.1/create-release-note→release/1.1.x
Step 6. リリース確定
- GitHub Release ページに正式リリースノートを公開
- git タグを付与し,
mainブランチにマージ
Step 7. main / develop への反映
# 本番用
git switch main
git merge --ff release/1.1.x
git push origin main
# 開発用
git switch develop
git merge --ff release/1.1.x
git push origin develop| 対象 | ブランチ命名規則 | 用途・対象範囲 | 運用方針 |
|---|---|---|---|
| 小規模 Issue | feature/<issue番号>-<タスク> |
小規模な新機能・修正 develop に直接 PR |
単一タスク・軽微修正に適用 |
| 中〜大規模 Issue | issue/<issue番号> |
複数サブタスクを統合 | サブタスクを統合して develop に PR feature / bugfix をまとめてレビュー |
| リリース系列ブランチ | release/<major>.<minor>.x |
特定マイナー系列(例: 1.1.x) | 安定版維持・軽微修正対応 長寿命ブランチ.保守・検証に利用 |
| リリース準備ブランチ | release/<version>/<subtask> |
各パッチリリース(例: 1.1.1) | リリースノート作成・バージョン確定・PR作成など 短命ブランチ.完了後削除 |
4. ブランチ削除ポリシー
| ブランチ種別 | 削除タイミング | 備考 |
|---|---|---|
feature / bugfix / issue |
develop マージ後 | 即削除(必要ならタグで履歴追跡) |
release/<version>/<subtask> |
main・develop 反映後 | 削除 |
release/<series>.x |
次マイナー系列発足時 | 継続保守中は残す |
5. 注意事項
- ブランチ名は常に小文字で記述
- 大文字を含めると,ファイルシステムが大文字・小文字を区別する環境がある
- 単語の区切りにはハイフン(
-)を使用
📘 Example
- ✅ Good:
feature/user-login - ❌ Avoid:
Feature_UserLogin,FeatUserLogin
- 各ブランチ名は、目的を示すカテゴリトークンから始めます。
- トークンの例:
feature(新機能開発)bugfix(バグ修正)docs(ドキュメント更新)
- トークンと説明文はスラッシュ(
/)で区切る
📘 Example
- ✅ Example:
bugfix/payment-timeout - ❌ Avoid:
payment-timeout(purpose unclear)
活用例
# Listing branches by token
$ git branch --list "feature/*"
# Pushing or mapping branches with tokens
$ git push origin 'refs/heads/feature/*'
# Deleting multiple branches by token
$ git branch -D $(git branch --list "feature/*")- 意図を説明できる範囲で,長すぎる名前は避ける
- 長すぎるブランチ名は,ログ表示の一行に収まらず,可視性が下がるため
📘 Example
- ✅ 良い例:
refactor/api-headers - ❌ 悪い例:
refactor/update-the-way-we-handle-request-headers-in-api
git switch -c featureのように意図が不明瞭な名前や既存ブランチと衝突する可能性のある名前は避ける- Gitは内部的に ブランチ名をパス(ディレクトリ構造)として管理しているため,
featureが作成されているとfeature/login-v2が名前衝突して作成できなくなってしまう- 同じ階層にファイルとディレクトリを同時に作れないため
📘 Example
$ git switch -c bugfix/0123/fix-login-error
Switched to a new branch 'bugfix/0123/fix-login-error'
$ ls .git/refs/heads/bugfix/0123
fix-login-errorAppendix: なぜbranchは名前衝突するのか?
Commit Object
Gitのコアの部分はシンプルなキー・バリュー型データストアです.Gitで追跡されているファイル(blob)はディレクトリの状態(ツリー)と合わせて圧縮された .git/objects にオブジェクトファイルとして保存されます. git commit を実行すると,commit時点でのその状態をスナップショットとして
- 誰が(
user.name,user.email) - いつ(現在のタイムスタンプ)
- どんなメッセージを残して
- どのcommitのあとに(=親コミット情報)
- コミットが作成された時点のスナップショットのトップレベルのツリー
を記録します.これがコミットオブジェクトです.このコミットオブジェクトをvalueとすると,それに対応するSHA-1ハッシュ値がキーとなります.
.git/HEAD
│
└─ ref: refs/heads/main
│
└─ SHA-1 commit object (latest commit)
│
├─ tree object
│ ├─ blob (file1)
│ └─ blob (file2)
└─ parent commit(s)ブランチはポインター
各ブランチはブランチ自体が実体を持っているのではなく,どのcommit objectを参照しているか?で状態が管理されています.ここで登場するのが refs/heads/<branch-name> です. main ブランチが参照するCommit Objectは .git/refs/heads/main に記録されており
% cat .git/refs/heads/main
35f61422e59fb8b34bf3a85f82a71669c1eeec30git add & git commit を実行すると,この値が新たなCommit Objectへの参照へと書き換わります.
なぜブランチは名前衝突するのか?
上記のようにブランチの情報は .git/refs/heads/<branch-name> で管理されています.git switch -c develop とすると
% git switch -c develop
Switched to a new branch 'develop'
% cat .git/refs/heads/develop
35f61422e59fb8b34bf3a85f82a71669c1eeec30とファイルが生成されます.しかし,ブランチ名に / を含む場合だと
% git switch -c bugfix/0001/test
Switched to a new branch 'bugfix/0001/test'
% tree .git/refs/heads/
.git/refs/heads/
├── bugfix
│ └── 0001
│ └── test
├── develop
└── mainと bugfix/0001/test の/(スラッシュ)がディレクトリ区切りと解釈されてしまします.developブランチがある状態で develop/test を作成しようとすると, .git/refs/heads/develop/ ディレクトリを作成してから,その下に test ファイルを作成しようとしますが,すでにdevelop ファイルが存在する = 同姓同名のディレクトリを同じ層では作成できないという状態が発生します
そのため,
% git switch -c develop/test
fatal: cannot lock ref 'refs/heads/develop/test': 'refs/heads/develop' exists; cannot create 'refs/heads/develop/test'というエラーが発生します.