◀ 6.

Git pullの使い方|取込み先・ff-only・競合とstashの注意点

▶

git pullはリモートから取得した履歴を現在のブランチへ取り込む操作です。取込元のmainと、変更される手元のブランチを区別します。

git pullはリモートから取得した履歴を現在のブランチへ取り込む操作です。取込元のmainと、変更される手元のブランチを区別します。

この記事の要点
  • git pull origin main で指定した履歴を現在のbranchへ取り込む。方式と作業状態を確認
  • pull は内部的に git fetch + git merge(または rebase)
  • 未コミット変更が必ず競合するわけではない。作業状態と取込み方法を確認し、必要な退避を先に行う
  • 履歴を分岐させずに進められる場合だけ取り込むなら --ff-only。rebaseは履歴の再適用として別に判断
  • 競合時はstatusで処理を確認。内容を解決・検証してから、mergeとrebaseそれぞれの継続操作を選ぶ

基本: git pull コマンド

リモートリポジトリの最新変更をローカルブランチに取り込む基本コマンド:

この例を読む前に:旧コメントの「ローカル main」はmainをcheckoutしている場合だけです。git pull origin mainはoriginのmainを現在のbranchへ取り込みます。feature上ならfeatureが対象です。以下は選択肢で一括実行しません。ff-onlyは分岐時に拒否しますが、fetch段階の更新までなかったことにはなりません。

# リモート (origin) の main ブランチをローカル main にマージ
git pull origin main

# upstream が設定済なら省略可
git pull

# rebase で取り込む(マージコミット作らない)
git pull --rebase

# fast-forward only(マージできなければエラー)
git pull --ff-only

git pull の中身: fetch + merge

git pull は実は 2 つのコマンドの組み合わせです:

この例を読む前に:この旧例は一般的な設定を単純化しています。fetch origin mainが必ずorigin/mainを更新するとは限らず、remote.origin.fetchの対応付けによって異なります。今回取得した先端はFETCH_HEADで確認できますが、次のfetchで更新されます。pull --rebaseには追跡履歴を使った判断もあり、常にこの2行と完全同一ではありません。

# git pull origin main は内部的に以下と同じ
git fetch origin main      # リモート最新を取得(ローカルブランチには反映しない)
git merge origin/main      # 取得した内容を現在のブランチにマージ

# --rebase オプションの場合
git fetch origin main
git rebase origin/main

動作の違い:

コマンド動作ローカル変更
git fetchリモート最新を取得のみ通常のfetchは作業ツリーを統合しないが、オブジェクト/FETCH_HEAD・設定に対応する参照等を更新
git pullfetch後に指定/設定された方法で統合取込み先は現在のブランチ。拒否や競合停止もある
git pull --rebasefetch + rebaseローカルコミットをリモートの上に積み直す

典型的な作業フロー

この例を読む前に:現在の作業・切替先・未追跡ファイルを確認します。add .は秘密値も追加し得るので差分を点検します。push前のrebaseは必須ではなく、既に共有したfeatureの履歴を無断で積み直しません。

# 1. 作業前にリモート最新を取り込む
git checkout main
git pull origin main

# 2. ブランチを切って作業
git checkout -b feature/new-login
# ... 編集・コミット ...
git add .
git commit -m "Add login feature"

# 3. push 前にリモート最新を取り込む(コンフリクト早期検知)
git pull --rebase origin main

# 4. push
git push origin feature/new-login

未コミット変更があるときの pull

次はローカル変更が統合で上書きされるため拒否された出力例です。同じファイルというだけで常に拒否とは限りません。通常のrebaseは未コミット変更を拒否しますが、autostash等の設定がある場合もあり、終了時の再適用で競合する可能性があります。

error: Your local changes to the following files would be overwritten by merge:
    src/Login.php
Please commit your changes or stash them before you merge.
Aborting

対処2 通り:

この例を読む前に:A/Bは代替案です。既定のstashは未追跡/無視ファイルを含みません。-uや-aも対象範囲が変わるため一律に付けません。popが競合するとstashは残り、再度popせずstatusと内容を確認します。applyは元のstashを残す操作で、dropは復元と検証後の別判断です。WIP commitにも秘密値を含めないでください。

# 方法 A: stash で一時退避
git stash                    # 変更を退避
git pull origin main         # pull
git stash pop                # 退避を戻す(コンフリクト出る可能性あり)

# 方法 B: 先にコミット
git add .
git commit -m "WIP: 作業中"
git pull --rebase origin main  # rebase で履歴を直線化

コンフリクトが出たとき

同じファイルの同じ行を両者が変更していた場合、Git は自動マージできずコンフリクトになります:

Auto-merging src/Login.php
CONFLICT (content): Merge conflict in src/Login.php
Automatic merge failed; fix conflicts and then commit the result.

該当ファイルを開くと:

この例を読む前に:次は通常のmergeの表示例です。rebase時のHEAD側/適用側は、単純な「自分/相手」の思い込みで選びません。マーカーを消すだけでなく、必要な両方の振る舞いを保ちテストします。

<<<<<<< HEAD
$user = User::find($id);      // ← ローカルの変更
=======
$user = User::findOrFail($id); // ← リモートの変更
>>>>>>> origin/main

解決手順:

この例を読む前に:継続と中断は代替操作で、順番に全部実行しません。statusで進行中の処理を確認し、mergeならcommit、rebaseならcontinueを選びます。開始前から未コミット変更があるとmerge --abortでも元の作業を完全には再構築できない場合があるため、事前退避が必要です。

# 1. ファイルを編集してマーカーを削除
# どちらか or 両方を残す形に修正

# 2. 解決済としてマーク
git add src/Login.php

# 3. マージコミット作成(merge の場合)
git commit
# rebase 中の場合
git rebase --continue

# rebase をやめたい場合
git rebase --abort

# merge をやめたい場合
git merge --abort

pull の代わりに fetch + merge を分けて実行

fetchと統合を分けると、取得した履歴を確認してから判断できます。分けただけで安全になるわけではなく、対象refと作業状態・共有済み履歴の確認が必要です。

この例を読む前に:fetchも参照等を更新します。origin/mainが意図した取得先に対応していることを確認します。log HEAD..origin/mainは相手側だけのcommit表示で、自分側の独自commitは表示しません。統合前には両側を確認し、mergeとrebaseを続けて実行しません。

# 1. リモートを取得(ローカルブランチには影響なし)
git fetch origin

# 2. 差分を確認
git log HEAD..origin/main --oneline
git diff HEAD origin/main

# 3. 安全と判断したらマージ
git merge origin/main
# または rebase
git rebase origin/main

よくあるトラブル

症状原因対処
fatal: refusing to merge unrelated histories履歴が無関係のリポジトリまずURLと両履歴を確認。独立した履歴の統合を意図した場合だけ別途設計し、安全機構を一律解除しない
error: pathspec 'main' did not matchpathspecはcheckout等のローカル指定エラーの場合がある失敗したコマンドとローカル/リモートrefを確認。fetchのcould not find remote refとは区別する
毎回マージコミットが増える分岐した履歴をmerge方式で統合している可能性方針と設定を確認。全repoへ影響するglobal変更やrebaseを一律の対処にしない
Your branch is ahead of 'origin/main' by N commits現在の追跡参照より手元が先。追跡参照が古い場合もあるfetchと履歴・送り先を確認。未公開のまま保持する判断もあり、即pushとは限らない

FAQ

Q: pull と fetch、どちらを使うべき?
A: 確認してから統合したい場合は分けられます。pull自体も取込み方法を明示できます。経験年数ではなく、履歴とチームの方針で選びます。

Q: pull で勝手にマージコミットができるのを防ぎたい
A: git pull --ff-onlyは分岐した履歴の統合を拒否します。rebaseは別の選択肢で、共有済みcommitの書換えに注意します。既定動作はGit版や設定に依存するため、このページでは操作ごとに方式を明示します。

Q: 強制的にリモートと同じ状態にしたい(ローカル変更全捨て)
A: 通常のpull失敗の対処としてreset --hardを実行しません。現在のbranch・index/作業ツリーを変更し、未コミットの追跡ファイルや邪魔になる未追跡ファイルを失う場合があります。対象refと保存したい履歴/作業の退避・復旧を先に確認し、削除を伴う同期は別の作業として判断します。reflogだけでは未コミットの内容を復元できません。

新規ローカルrepoで取込み先を確認する

次はBash/Git 2.28以降の練習です。空フォルダから実行し、既存の3パスがあれば停止します。ネットワークや既存repo/global設定には触れません。featureにいる状態でmainをpullし、手元mainは変わらないことを確認します。

set -eu
for path in pull-seed pull-remote.git pull-client; do
    if [ -e "$path" ] || [ -L "$path" ]; then printf 'Already exists: %s\n' "$path" >&2; exit 1; fi
done
git init -b main pull-seed
git -C pull-seed config user.name Training
git -C pull-seed config user.email training@example.invalid
printf 'one\n' > pull-seed/message.txt
git -C pull-seed add message.txt
git -C pull-seed commit -m Initial
git clone --bare pull-seed pull-remote.git
git clone pull-remote.git pull-client
git -C pull-client switch -c feature
old_main=$(git -C pull-client rev-parse main)
printf 'two\n' > pull-seed/message.txt
git -C pull-seed commit -am Update
git -C pull-seed push ../pull-remote.git main
git -C pull-client pull --ff-only origin main
test "$old_main" = "$(git -C pull-client rev-parse main)"
printf 'main kept: yes\n'
git -C pull-client branch --show-current
cat pull-client/message.txt

main保持はyes、現在branchはfeature、message.txtはtwoとなります。実運用では取込み前にstatus、branch --show-current、remoteのURL、log --left-right --oneline HEAD...origin/main等を確認します。確認用出力にも内部情報が含まれ得るので公開時には点検します。

分岐でff-onlyが拒否したら

拒否はデータ破棄の指示ではありません。自分側と取得側のcommitを読み、mergeで両履歴を統合するか、未共有のcommitをrebaseするか、そもそも取込み先が正しいかを確認します。Gitや設定による既定値の違いを避けるため、練習例は--ff-onlyを明示しています。

関連する操作はpull・rebase・push・remote設定へ。Git親ページの子ページから選択してください。

公式資料と検証範囲

2026年10月にpull(2.42)・pull(現行)・fetchのrefspec・stash・mergeと中断を確認しました。元コードと章を保持し、近接注意で旧例の誤りを訂正しています。追加Bash例と取込み/再適用の条件をGit 2.42の隔離ローカルrepoで検査しました。実サービスの認証/保護/CI、共有履歴の移行や全Git版を検証したものではありません。

子ページ

子ページはありません

同階層のページ
  1. 用語一覧
  2. エラー一覧
  3. git本体のインストール(Linux)
  4. Linuxサーバーへのgit導入とクライアントのセットアップ
  5. リモートリポジトリをローカルリポジトリとしてクローンする方法
  6. リモートとローカルのリポジトリを同期(pull)する方法
  7. 設定の確認
  8. gitユーザー名とemailの設定
  9. リモートリポジトリの作成
  10. ローカルリポジトリの作成
  11. 新規ファイル/ディレクトリをインデックスに登録
  12. インデックスの登録状態を確認
  13. ローカルリポジトリの変更をコミット
  14. コミット履歴の確認
  15. クライアントからリモートリポジトリの接続設定、確認、削除
  16. リポジトリへのプッシュ
  17. リモートリポジトリからクライアントへのSSHクローン
  18. リモートとローカルの差分表示
  19. バージョンの確認
  20. プロキシの設定
  21. ローカルをリモートリポジトリの状態に戻す
  22. ブランチの作成, 一覧表示, 切り替え
  23. ブランチのマージと削除
  24. リベース
  25. .gitignoreの書き方
  26. .gitignoreの設定が反映されない場合
  27. 特定のファイルをgitの管理から外す方法
  28. 参照(ORIG_HEAD, HEAD, FETCH_HEAD)
  29. git rm [-r --cached] の取り消し
  30. 一部のディレクトリ/ファイルのみをリポジトリから復元する方法
  31. ローカルとリモートリポジトリの有無を同期
  32. pushの取消し方法
  33. マージツールの起動方法
  34. Gitで「MERGING」の状態

最近更新/作成されたページ