Gitでマージの競合を解決するにはどうすればよいですか?
git
インストールではそのままでは機能しないコマンドについて言及しています。2017年の今日、SEのスタートページに到達し、130万回の視聴と数千の投票がありました。魅力的です。
Gitでマージの競合を解決するにはどうすればよいですか?
git
インストールではそのままでは機能しないコマンドについて言及しています。2017年の今日、SEのスタートページに到達し、130万回の視聴と数千の投票がありました。魅力的です。
回答:
試してください: git mergetool
競合ごとに手順を示すGUIが開き、マージ方法を選択できます。後で少し手作業で編集する必要がある場合もありますが、通常はそれだけで十分です。手作業ですべてを行うよりもはるかに優れています。
@JoshGloverコメントによると:
コマンド
GUIをインストールしない限り、必ずしもGUIを開くとは限りません。
git mergetool
私のために実行すると、vimdiff
使用されました。あなたが代わりにそれを使用するには、次のいずれかのツールをインストールすることができますmeld
、opendiff
、kdiff3
、tkdiff
、xxdiff
、tortoisemerge
、gvimdiff
、diffuse
、ecmerge
、p4merge
、araxis
、vimdiff
、emerge
。
以下は、vimdiff
マージの競合を解決するために使用するサンプル手順です。このリンクに基づく
ステップ1:端末で次のコマンドを実行する
git config merge.tool vimdiff
git config merge.conflictstyle diff3
git config mergetool.prompt false
これにより、vimdiffがデフォルトのマージツールとして設定されます。
手順2:端末で次のコマンドを実行します
git mergetool
手順3:次の形式でvimdiffディスプレイが表示されます
╔═══════╦══════╦════════╗
║ ║ ║ ║
║ LOCAL ║ BASE ║ REMOTE ║
║ ║ ║ ║
╠═══════╩══════╩════════╣
║ ║
║ MERGED ║
║ ║
╚═══════════════════════╝
これらの4つのビューは
LOCAL –これは現在のブランチからのファイルです
BASE –共通の祖先、両方の変更前のファイルの外観
REMOTE –ブランチにマージするファイル
マージ–マージ結果、これがリポジトリに保存されます
ctrl+ を使用して、これらのビュー間を移動できますw。ctrl+にw続けてを使用して、マージされたビューに直接アクセスできjます。
ステップ4。次の方法でマージされたビューを編集できます
REMOTEから変更を取得する場合
:diffg RE
BASEから変更を取得したい場合
:diffg BA
ローカルから変更を取得したい場合
:diffg LO
ステップ5。保存、終了、コミット、クリーンアップ
:wqa
保存してviを終了
git commit -m "message"
git clean
diffツールで作成された余分なファイル(* .origなど)を削除します。
git mergetool -y
一度に多くのファイルをマージする場合、いくつかのキーストロークを保存するために使用できます。
git mergetool
私のために実行すると、vimdiff
使用されました。代わりに、次のいずれかのツールをインストールして使用できますmeld opendiff kdiff3 tkdiff xxdiff tortoisemerge gvimdiff diffuse ecmerge p4merge araxis vimdiff emerge
。
git mergetool -t bc3
)。
上から考えられる使用例を以下に示します。
あなたはいくつかの変更をプルするつもりですが、おっと、あなたは最新ではありません:
git fetch origin
git pull origin master
From ssh://gitosis@example.com:22/projectname
* branch master -> FETCH_HEAD
Updating a030c3a..ee25213
error: Entry 'filename.c' not uptodate. Cannot merge.
したがって、最新の状態に戻って再試行しますが、競合があります。
git add filename.c
git commit -m "made some wild and crazy changes"
git pull origin master
From ssh://gitosis@example.com:22/projectname
* branch master -> FETCH_HEAD
Auto-merging filename.c
CONFLICT (content): Merge conflict in filename.c
Automatic merge failed; fix conflicts and then commit the result.
したがって、変更を確認することにします。
git mergetool
ああ、ああ、私の上流はいくつかのことを変更しましたが、私の変更を使用するだけです...いいえ...彼らの変更...
git checkout --ours filename.c
git checkout --theirs filename.c
git add filename.c
git commit -m "using theirs"
そして最後に
git pull origin master
From ssh://gitosis@example.com:22/projectname
* branch master -> FETCH_HEAD
Already up-to-date.
たーだ!
git merge --help
this question
マージツールが競合や解決策を理解するのに役立つことはめったにありません。私は通常、テキストエディターで競合マーカーを確認し、補足としてgit logを使用する方がうまくいきます。
ここにいくつかのヒントがあります:
私が見つけた最良のことは、「diff3」マージ競合スタイルを使用することです。
git config merge.conflictstyle diff3
これにより、次のような競合マーカーが生成されます。
<<<<<<<
Changes made on the branch that is being merged into. In most cases,
this is the branch that I have currently checked out (i.e. HEAD).
|||||||
The common ancestor version.
=======
Changes made on the branch that is being merged in. This is often a
feature/topic branch.
>>>>>>>
中央のセクションは、共通の祖先がどのように見えるかです。これは、上位バージョンと下位バージョンと比較して、各ブランチで何が変更されたかをよりよく理解できるため、便利です。これにより、各変更の目的がよりよくわかります。
競合が数行しかない場合、これにより、一般的に競合が非常に明白になります。(競合を修正する方法を知ることは非常に異なります。他の人が取り組んでいることを認識する必要があります。混乱している場合は、その人をあなたの部屋に呼び、彼らがあなたが探しているものを見ることができるようにするのがおそらく最善です。で。)
競合がさらに長い場合は、3つのセクションをそれぞれ切り取り、「mine」、「common」、「theirs」などの3つの個別のファイルに貼り付けます。
次に、次のコマンドを実行して、競合を引き起こした2つの差分ハンクを確認できます。
diff common mine
diff common theirs
これは、マージツールを使用する場合とは異なります。マージツールには、競合しないdiffハンクもすべて含まれるためです。気が散ることがわかります。
誰かがすでにこれについて述べていますが、各diff hunkの背後にある意図を理解することは、一般に、競合がどこから発生し、どのように対処するかを理解するのに非常に役立ちます。
git log --merge -p <name of file>
これは、共通の祖先とマージする2つのヘッドの間でそのファイルに接触したすべてのコミットを示しています。(したがって、マージする前に両方のブランチにすでに存在するコミットは含まれません。)これにより、現在の競合の要因ではないことが明らかなdiff hunkを無視できます。
自動化ツールで変更を確認します。
自動テストがある場合は、それらを実行します。lintがある場合は、それを実行します。ビルド可能なプロジェクトの場合は、コミットする前にビルドするなどしてください。すべての場合において、変更が何かを壊していないことを確認するために、少しテストを行う必要があります。(いや、衝突のないマージでさえ、動作しているコードが壊れる可能性があります。)
事前に計画します。同僚と通信します。
事前に計画を立て、他の人が取り組んでいることを認識することは、マージの競合を防ぎ、かつ/またはそれらをより早く解決するのに役立ちます-詳細はまだ新鮮です。
たとえば、あなたと別の人が両方とも同じファイルセットに影響する異なるリファクタリングに取り組んでいることがわかっている場合は、事前に互いに話し合い、それぞれがどのような種類の変更であるかをよりよく理解する必要があります作る。計画した変更を並行ではなく逐次的に実行すると、時間と労力を大幅に節約できます。
大量のコードにまたがる主要なリファクタリングの場合、逐次作業を強く検討する必要があります。一人が完全なリファクタリングを実行している間、誰もがコードのその領域での作業を停止します。
(時間のプレッシャーなどが原因で)連続して作業できない場合は、予想されるマージの競合について連絡することで、詳細を考慮した上で問題を早期に解決できます。たとえば、同僚が1週間の間に一連の中断を伴うコミットを行っている場合、その週の間に1日に1回または2回、その同僚のブランチをマージ/リベースすることを選択できます。こうすることで、マージ/リベースの競合が見つかった場合、数週間待ってすべてを1つの大きな塊にマージするよりも早く解決できます。
マージが不確かな場合は、強制しないでください。
特に多数の競合するファイルがあり、競合マーカーが数百行をカバーしている場合、マージは圧倒的に感じるかもしれません。多くの場合、ソフトウェアプロジェクトを見積もるとき、危険なマージの処理などのオーバーヘッドアイテムのための十分な時間が含まれていないため、各競合の分析に数時間を費やすのは本当の抵抗のように感じられます。
長期的には、事前に計画を立て、他の人が取り組んでいることを認識することは、マージの競合を予測し、短時間でそれらを正しく解決するための準備をするための最良のツールです。
p4merge
、PERFORCEの他のツール(私は使用していませんが、不満を聞いた)とは別にインストールして使用できます。
git config merge.conflictstyle diff3
- ありがとうございます。これは驚くべきことであり、優れた3方向マージGUIを見つけて(そして$$を支払う)ことから解放されました。IMOは、ローカル/リモートだけでなく、共通の祖先を示しているので、これは良いです、そしてショーは最後にはGUIはしません(私の知る限り)ログの行をコミットします。コミットは、どのコードがどのブランチに属しているかを特定するのに役立ちます。
競合しているファイルを特定します(Gitがこれを通知するはずです)。
各ファイルを開き、差分を調べます。Gitはそれらを区別します。うまくいけば、各ブロックのどのバージョンを保持するかは明らかです。コードをコミットした他の開発者と話し合う必要があるかもしれません。
ファイルの競合を解決したら git add the_file
。
すべての競合を解決しgit rebase --continue
たら、完了時にGitが実行するように指示したコマンドを実行します。
git add
ファイルをインデックスにステージングします。リポジトリには何も追加されません。git commit
リポジトリに追加します。この使用法は、マージにとって意味があります。マージは、自動的にマージできるすべての変更を自動的にステージングします。残りの変更をマージし、完了したらそれらをインデックスに追加するのはユーザーの責任です。
Stack Overflowの質問の回答、Gitでのマージの中止、特に問題のあるファイルのさまざまなバージョンを表示する方法を示すCharles Baileyの回答を確認してください。
# Common base version of the file.
git show :1:some_file.cpp
# 'Ours' version of the file.
git show :2:some_file.cpp
# 'Theirs' version of the file.
git show :3:some_file.cpp
マージの競合は、ファイルに同時に変更が加えられると発生します。これを解決する方法は次のとおりです。
git
CLI競合状態になった場合の簡単な手順は次のとおりです。
git status
下Unmerged paths
セクションの)。次のいずれかの方法で、ファイルごとに競合を個別に解決します。
GUIを使用して競合を解決します:(git mergetool
最も簡単な方法)。
リモート/その他のバージョンを受け入れるには、次を使用しますgit checkout --theirs path/file
。これにより、そのファイルに対して行ったローカルでの変更が拒否されます。
ローカル/私たちのバージョンを受け入れるには、次を使用します: git checkout --ours path/file
ただし、競合するリモート変更が何らかの理由で行われたため、注意が必要です。
競合するファイルを手動で編集し、<<<<<
/の間のコードブロックを探して>>>>>
から、上または下からバージョンを選択します=====
。参照:競合の表示方法。
パスとファイル名の競合はgit add
/ で解決できますgit rm
。
最後に、次のコマンドを使用して、コミットの準備ができているファイルを確認しますgit status
。
の下にまだファイルがありUnmerged paths
、競合を手動で解決した場合は、次の方法で解決したことをGitに知らせますgit add path/file
。
すべての競合が正常に解決された場合は、次の方法で変更をコミットし、git commit -a
通常どおりリモートにプッシュします。
参照:GitHubのコマンドラインからのマージ競合の解決
実際のチュートリアルについては、シナリオ5-Katacodaによるマージの競合の修正を確認してください。
Windows、macOS、Linux / Unixでファイルを視覚的に比較およびマージできるDiffMergeをうまく使用しました。
3つのファイル間の変更をグラフィカルに表示でき、自動マージ(安全な場合)と、結果のファイルの編集を完全に制御できます。
画像ソース:DiffMerge(Linuxスクリーンショット)
単にダウンロードして、次のようにリポジトリで実行します。
git mergetool -t diffmerge .
macOSでは、次の方法でインストールできます。
brew install caskroom/cask/brew-cask
brew cask install diffmerge
そしておそらく(提供されていない場合)PATHに次の追加の単純なラッパーを配置する必要があります(例:) /usr/bin
:
#!/bin/sh
DIFFMERGE_PATH=/Applications/DiffMerge.app
DIFFMERGE_EXE=${DIFFMERGE_PATH}/Contents/MacOS/DiffMerge
exec ${DIFFMERGE_EXE} --nosplash "$@"
その後、次のキーボードショートカットを使用できます。
または、opendiff(Xcode Toolsの一部)を使用して、2つのファイルまたはディレクトリをマージし、3つ目のファイルまたはディレクトリを作成することもできます。
小さなコミットを頻繁に行う場合は、まずでコミットコメントを確認しgit log --merge
ます。次にgit diff
、競合を表示します。
数行を超える競合については、外部GUIツールで何が起こっているかを確認するのが簡単です。私はopendiffが好きです-Gitはvimdiff、gvimdiff、kdiff3、tkdiff、meld、xxdiffもサポートしており、すぐに使用できgit config merge.tool "your.tool"
ます。他のものをインストールできます。選択したツールを設定してからgit mergetool
ます。
競合を解決するためにファイルを編集するたびにgit add filename
、はインデックスを更新し、diffはそれを表示しなくなります。すべての競合が処理され、それらのファイルがgit add
-ed git commit
されると、マージが完了します。
マージの競合マーカーとは何かを理解するには、競合がどのように提示されるか、またはGitのgit merge
ドキュメントを参照してください。
また、「競合を解決する方法」セクションでは、競合を解決する方法について説明しています。
競合が発生した後、次の2つのことを行うことができます。
マージしないことを決定します。必要なクリーンアップは、インデックスファイルを
HEAD
コミットにリセットして2を元に戻し、2と3によって行われた作業ツリーの変更をクリーンアップすることだけです。git merge --abort
これに使用できます。競合を解決します。Gitは作業ツリーで競合をマークします。ファイルを形に編集
git add
し、インデックスに追加します。git commit
契約を結ぶために使用します。多くのツールを使用して競合を回避できます。
mergetoolを使用します。
git mergetool
マージを実行するグラフィカルなマージツールを起動します。差分を見てください。とバージョンの
git diff
両方からの変更を強調する3方向の差分が表示されます。HEAD
MERGE_HEAD
各ブランチの差分を見てください。
git log --merge -p <path>
最初にHEAD
バージョンの差分を表示し、次にMERGE_HEAD
バージョンを表示します。オリジナルを見てください。
git show :1:filename
ショー共通の祖先、git show :2:filename
ショーHEAD
バージョン、およびgit show :3:filename
ショーMERGE_HEAD
バージョン。
私または自分のバージョンを完全なものにするか、個々の変更を確認して、それぞれについて決定する必要があります。
私または彼らのバージョンを完全に受け入れます:
私のバージョンを受け入れる(ローカル、私たちのもの):
git checkout --ours -- <filename>
git add <filename> # Marks conflict as resolved
git commit -m "merged bla bla" # An "empty" commit
彼らのバージョンを受け入れます(リモート、彼ら):
git checkout --theirs -- <filename>
git add <filename>
git commit -m "merged bla bla"
すべての競合ファイルに対して実行したい場合は、以下を実行します。
git merge --strategy-option ours
または
git merge --strategy-option theirs
すべての変更を確認し、個別に受け入れます
git mergetool
git add <filename>
git commit -m "merged bla bla"
デフォルトmergetool
はコマンドラインで動作します。コマンドラインのmergetoolの使い方は別の質問です。
このためのビジュアルツールをインストールして実行することもできmeld
ます。
git mergetool -t meld
ローカルバージョン(ours)、 "base"または "merged"バージョン(現在のマージ結果)、およびリモートバージョン(theirs)が開きます。完了したら、マージしたバージョンを保存し、git mergetool -t meld
「マージする必要のあるファイルがなくなる」まで再度実行し、ステップ3と4に進みます。
マージの競合を半手動で解決したいEmacsユーザーの場合:
git diff --name-status --diff-filter=U
競合解決が必要なすべてのファイルを表示します。
これらのファイルを1つずつ開くか、次のように一度にすべて開きます。
emacs $(git diff --name-only --diff-filter=U)
Emacsで編集が必要なバッファーにアクセスするときは、次のように入力します。
ALT+x vc-resolve-conflicts
これにより、3つのバッファー(mine、theirs、およびoutputバッファー)が開きます。「n」(次の領域)、「p」(プロビジョニング領域)を押して移動します。'a'と 'b'を押して、鉱山またはその地域をそれぞれ出力バッファーにコピーします。または、出力バッファを直接編集します。
終了したら、「q」を押します。Emacsは、このバッファーを保存するかどうかを尋ねます:はい。バッファを完了した後、終端から実行することで解決済みとしてマークします。
git add FILENAME
すべてのバッファタイプが終了したら
git commit
マージを終了します。
上記の回答のプル/フェッチ/マージと言えば、興味深い生産的なトリックを共有したいと思います。
git pull --rebase
この上記のコマンドは、私のgitライフで最も便利なコマンドであり、多くの時間を節約しました。
リモートサーバへ新しくコミット変更をプッシュする前に、してみてくださいgit pull --rebase
というgit pull
とマニュアルmerge
、それが自動的に同期、最新のリモートサーバーの変更(+マージフェッチで)でしょうし、あなたの地元の最新のgitのログに先頭にコミット入れます。手動のプル/マージについて心配する必要はありません。
競合する場合は、
git mergetool
git add conflict_file
git rebase --continue
簡単に言うと、リポジトリの1つでの変更が重要ではないことをよく知っており、他の変更を優先してすべての変更を解決したい場合は、以下を使用します。
git checkout . --ours
リポジトリを優先して変更を解決する、または
git checkout . --theirs
他のリポジトリまたはメインリポジトリを優先して変更を解決します。
または、GUIマージツールを使用してファイルを1つずつステップ実行するか、マージツールがp4merge
であると言うか、すでにインストールした名前を書き込む必要があります
git mergetool -t p4merge
ファイルを完成させたら、保存して閉じる必要があるため、次のファイルが開きます。
次の手順に従って、Gitのマージの競合を修正してください。
Gitステータスを確認します: git status
パッチセットを入手する: git fetch(Gitコミットから適切なパッチをチェックアウト)
ローカルブランチをチェックアウトします(この例ではtemp1): git checkout -b temp1
マスターから最近のコンテンツをプルします: git pull --rebase origin master
mergetoolを起動し、競合をチェックして修正します...そしてリモートブランチの変更を現在のブランチで確認します: git mergetool
ステータスをもう一度確認してください: git status
mergetoolによってローカルに作成された不要なファイルを削除します。通常、mergetoolは* .orig拡張子を持つ追加ファイルを作成します。そのファイルは重複しているため、削除してローカルで変更を修正し、正しいバージョンのファイルを追加してください。 git add #your_changed_correct_files
ステータスをもう一度確認してください: git status
変更を同じコミットIDにコミットします(これにより、新しい個別のパッチセットが回避されます): git commit --amend
マスターブランチにプッシュ: git push(Gitリポジトリに)
3つのステップがあります。
コマンドによって競合を引き起こすファイルを見つける
git status
次のようにマークされた競合が見つかるファイルを確認します
<<<<<<<<head
blablabla
それをあなたが望む方法に変更してから、コマンドでコミットしてください
git add solved_conflicts_files
git commit -m 'merge msg'
他の人が詳しく述べているように、いくつかの方法でマージの競合を修正できます。
本当の鍵は、変更がローカルおよびリモートのリポジトリでどのように流れるかを知ることだと思います。これの鍵は追跡ブランチを理解することです。私は、トラッキングブランチを、ローカルの実際のファイルディレクトリと起点として定義されたリモートとの間の「中間の欠落部分」と考えていることがわかりました。
私は個人的に、これを回避するために2つのことを習慣にしています。
の代わりに:
git add .
git commit -m"some msg"
これには2つの欠点があります-
a)すべての新しい/変更されたファイルが追加されます。これには、不要な変更が含まれる場合があります。
b)最初にファイルリストを確認する必要はありません。
だから代わりに私はします:
git add file,file2,file3...
git commit # Then type the files in the editor and save-quit.
このようにすると、追加するファイルについてより慎重になり、メッセージのエディターを使用しながらリストを確認し、もう少し考えることができます。-m
オプションではなくフルスクリーンエディターを使用すると、コミットメッセージも改善されます。
[更新-時間の経過とともに、次のように切り替えました:
git status # Make sure I know whats going on
git add .
git commit # Then use the editor
]
また、(そしてあなたの状況にもっと関連しています)、私は避けようとします:
git pull
または
git pull origin master.
プルはマージを意味するため、マージしたくない変更がローカルにある場合、マージされたコードやマージされるべきではないコードのマージ競合が簡単に発生する可能性があります。
代わりに私はやろうとします
git checkout master
git fetch
git rebase --hard origin/master # or whatever branch I want.
これも役に立つかもしれません:
git checkout master
と git fetch
して git rebase --hard origin/master
git add .
、それは私たちがフォローアップできるようにローカルの変更を保存しgit checkout master
ますか?それとも2つの異なるシナリオですか?
$ git rebase --hard origin/master b5a30cc159ba8dd error: unknown option
hard 'の使用法:git rebase [-i] [options] [--exec <cmd>] [--onto <newbase>] [<upstream>] [<branch>]または:git rebase [-i] [オプション] [--exec <cmd>] [--onto <newbase>] --root [<branch>]または:git rebase --continue | --abort | --skip | --edit-todo `
CoolAJ86の答えはほとんどすべてを要約しています。同じコードの両方のブランチに変更がある場合は、手動でマージする必要があります。任意のテキストエディタで競合しているファイルを開くと、次の構造が表示されます。
(Code not in Conflict)
>>>>>>>>>>>
(first alternative for conflict starts here)
Multiple code lines here
===========
(second alternative for conflict starts here)
Multiple code lines here too
<<<<<<<<<<<
(Code not in conflict here)
等号と山括弧を削除しながら、新しいコードにしたい方法で、代替案の1つまたは両方の組み合わせを選択します。
git commit -a -m "commit message"
git push origin master
git log --merge -p [[--] path]
私にとって常に機能するとは限らず、通常、2つのブランチ間で異なるすべてのコミットが表示されます。これは、を使用--
してパスをコマンドから分離する場合にも発生します。
この問題を回避するために私が行うことは、2つのコマンドラインを1回の実行で開くことです
git log ..$MERGED_IN_BRANCH --pretty=full -p [path]
そして他の
git log $MERGED_IN_BRANCH.. --pretty=full -p [path]
$MERGED_IN_BRANCH
私がマージしたブランチ[path]
と競合しているファイルで置き換える。このコマンドは、..
2つのコミット間の()間のすべてのコミットをパッチ形式でログに記録します。上記のコマンドのように片側を空のままにすると、gitが自動的に使用しますHEAD
(この場合、マージするブランチ)。
これにより、2つのブランチが分岐した後に、どのコミットがファイルに入ったかを確認できます。通常は、競合の解決がはるかに簡単になります。
patience
patience
マージ再帰戦略を使用して競合を解決することについて他の誰も話していないことに驚いています。大きなマージの競合の場合は、patience
すると良い結果が得られます。アイデアは、個々の行ではなくブロックを照合しようとするというものです。
たとえば、プログラムのインデントを変更すると、デフォルトのGitマージ戦略が{
、さまざまな関数に属する単一の波括弧と一致する場合があります。これはpatience
:
git merge -s recursive -X patience other-branch
ドキュメントから:
With this option, merge-recursive spends a little extra time to avoid
mismerges that sometimes occur due to unimportant matching lines
(e.g., braces from distinct functions). Use this when the branches to
be merged have diverged wildly.
マージの競合があり、他の人がブランチを変更するときに何を考えていたかを確認したい場合は、ブランチ(ブランチではなく)を直接共通の祖先と直接比較する方が簡単な場合があります。そのために使用できますmerge-base
:
git diff $(git merge-base <our-branch> <their-branch>) <their-branch>
通常、特定のファイルの変更のみを確認します。
git diff $(git merge-base <our-branch> <their-branch>) <their-branch> <file>
2016年12月12日以降、ブランチをマージしてgithub.comで競合を解決できます
したがって、古い回答からここに提供されているコマンドラインやサードパーティのツールを使用したくない場合は、GitHubのネイティブツールを使用してください。
このブログ投稿では詳細を説明していますが、基本的には、UIを介して2つのブランチを「マージ」すると、「競合の解決」オプションが表示され、これらのマージの競合に対処できるエディターが表示されます。
ブランチ(テスト)からマスターにマージする場合は、次の手順に従います。
ステップ1:ブランチに行く
git checkout test
ステップ2:
git pull --rebase origin master
ステップ3:競合がある場合は、これらのファイルに移動して変更します。
ステップ4:これらの変更を追加する
git add #your_changes_files
ステップ5:
git rebase --continue
手順6:それでも競合がある場合は、手順3に戻ります。競合がない場合は、以下を実行します。
git push origin +test
ステップ7:テストとマスターの間に競合はありません。直接マージを使用できます。
衝突を避けるために、私は常に以下の手順に従います。
これで、同じことを実行して、必要な数のローカルブランチを維持し、必要に応じてブランチにgitチェックアウトを実行するだけで、同時に作業できます。
マージの競合は、さまざまな状況で発生する可能性があります。
競合を解決するには、Gitと互換性のあるマージツールをインストールする必要があります。個人的にはKDiff3を使用していますが、使いやすく便利です。Windowsバージョンはこちらからダウンロードできます。
https://sourceforge.net/projects/kdiff3/files/
ところで、Git Extensionsをインストールする場合、セットアップウィザードにKdiff3をインストールするオプションがあります。
次にgit configsをセットアップして、Kdiffをmergetoolとして使用します。
$ git config --global --add merge.tool kdiff3
$ git config --global --add mergetool.kdiff3.path "C:/Program Files/KDiff3/kdiff3.exe"
$ git config --global --add mergetool.kdiff3.trustExitCode false
$ git config --global --add diff.guitool kdiff3
$ git config --global --add difftool.kdiff3.path "C:/Program Files/KDiff3/kdiff3.exe"
$ git config --global --add difftool.kdiff3.trustExitCode false
(パスをKdiff exeファイルの実際のパスに置き換えることを忘れないでください。)
次に、マージの競合に遭遇するたびに、次のコマンドを実行する必要があります。
$git mergetool
次に、Kdiff3を開き、最初にマージの競合を自動的に解決しようとします。ほとんどの競合は自然に解決され、残りは手動で修正する必要があります。
Kdiff3は次のようになります。
次に、完了したらファイルを保存し、競合のある次のファイルに移動して、すべての競合が解決されるまで同じことを繰り返します。
すべてが正常にマージされているかどうかを確認するには、mergetoolコマンドを再度実行するだけで、次の結果が得られます。
$git mergetool
No files need merging
これは、エディター内ですべてを実行することを好む、私のようなVIMユーザー向けの代替手段を追加するための答えです。
Tpopeは、VIMのfugitiveと呼ばれるこの素晴らしいプラグインを思い付きました。インストールしたら、実行:Gstatus
して競合のあるファイルをチェックし、:Gdiff
し、3つの方法でGitを開いてマージします。
3ウェイマージに入ると、fugitiveを使用すると、マージするブランチの変更を次の方法で取得できます。
:diffget //2
、元の(HEAD)ブランチから変更を取得します。:diffget //3
、マージブランチから変更を取得します: ファイルのマージが完了したら:Gwrite
、マージされたバッファーに入力します。Vimcastsは、この手順を詳細に説明する素晴らしいビデオをリリースしました。
git fetch
git checkout ブランチ
git rebaseマスター
このステップでは、優先IDEを使用して競合を修正しようとします
このリンクに従って、ファイルhttps://help.github.com/articles/resolving-a-merge-conflict-using-the-command-line/の競合を修正する方法を確認できます
。
git add
git rebase --continue
git commit --amend
git push origin HEAD:refs / drafts / master(ドラフトのようにプッシュ)
今、すべてがうまくいき、あなたのコミットは間違いなく見つかります
これがこの問題に関するすべての人に役立つことを願っています。
競合を解決するより安全な方法は、git-mediateを使用することです mediate(ここで提案されている一般的な解決策は、エラーが発生しやすいです)。
使い方の簡単な紹介については、この投稿を参照してください。
Visual Studio(私の場合は2015)を使用している人向け
VSでプロジェクトを閉じます。特に大きなプロジェクトでは、UIを使用してマージすると、VSが異常動作する傾向があります。
コマンドプロンプトでマージを実行します。
git checkout target_branch
git merge source_branch
次に、VSでプロジェクトを開き、チームエクスプローラー->ブランチに移動します。Mergeが保留中であり、競合するファイルがメッセージのすぐ下にリストされているというメッセージが表示されます。
競合するファイルをクリックすると、マージ、比較、ソースの取得、ターゲットの取得のオプションが表示されます。VSのマージツールは非常に使いやすいです。
IDEとしてintelliJを使用している場合は、親をブランチにマージしてみてください。
git checkout <localbranch>
git merge origin/<remotebranch>
このようなすべての競合が表示されます
A_MBPro:test anu $ git merge origin /自動マージsrc / test / java / com /.../ TestClass.java CONFLICT(コンテンツ):src / test / java / com /.../ TestClass.javaでマージの競合
TestClass.javaファイルがintelliJに赤で表示されることに注意してください。また、gitステータスが表示されます
Unmerged paths:
(use "git add <file>..." to mark resolution)
both modified: src/test/java/com/.../TestClass.java
ファイルをintelliJで開きます。次のセクションがあります。
<<<<<<< HEAD
public void testMethod() {
}
=======
public void testMethod() { ...
}
>>>>>>> origin/<remotebranch>
HEADはローカルブランチでの変更で、origin /はリモートブランチからの変更です。ここで、必要なものを保持し、不要なものを削除します。その後、通常の手順で実行できます。あれは
git add TestClass.java
git commit -m "commit message"
git push