日本語版
最新ニュース
科学&テクノロジー

git-浅いクローンの後にgithubにプッシュするのはひどく遅い

TL; DR:使用 --depth 2。その理由を読んでください。 浅いクローン(できる、必ずしもそうではありません しなければならない)重要な最適化を打ち負かす。あなたの場合、これは最初のプッシュのために起こりますが、その後のプッシュではありません。他の敗北ケースが発生する可能性があるため、他のプッシュも遅くなる可能性があります。 私たちは、Gitが本当にコミットについてであるという事実から始めます。1 指向性の非環式グラフに形作られます。グラフには、ハッシュIDをコミットすることにより、番号が付けられている頂点またはノードがあります。ここでは比較的重要ではありませんが、具体性に役立ちますが、ノード間のエッジ /アークは、個別に保持されるのではなく、ノード自体の一部として保存されているという事実です。各ノードは、前身ノードのハッシュIDを保存します。 リポジトリは、これらのコミットオブジェクトのデータベースです。すべてのルートからすべてのチップコミットまで、完全な - ノンシャロー - レポジトリにはグラフ全体があります。 a シングルブランチ クローンはグラフの一部を潜在的にドロップする可能性がありますが、グラフに「ギャップ」はありません。たとえば、与えられます: node--node--tip1 / root--node node--node--tip2 その行のチップとノードのいずれかをドロップすることはできますが、中央の列のノードとルートではありません。これらのすべてのケースでは、Gitが常に行うように、先端から始まり、最終的に根に到達することができます。 ここで重要な各ノードには2つのプロパティがあります。 番号 は 個性的。それは普遍的にユニークなIDです。 いいえ ノードイン どれでも 他のGitリポジトリ(とにかく会うこと)は、そのIDを再利用できます。 データ ノードには厳密に読み取り専用です。これには、発信エッジリンクが含まれます。 これが意味するのは、私たちが持っている場合です ギャップフリー リポジトリ - それは完全に完全であるか、少なくともそれが含むチップに必要なとおりに完全であるかのいずれかで、送信者から受信者への操作の両側には、 送信…

git-浅いクローンの後にgithubにプッシュするのはひどく遅い

1739359945
2025-02-12 08:50:00

TL; DR:使用 --depth 2。その理由を読んでください。

浅いクローン(できる、必ずしもそうではありません しなければならない)重要な最適化を打ち負かす。あなたの場合、これは最初のプッシュのために起こりますが、その後のプッシュではありません。他の敗北ケースが発生する可能性があるため、他のプッシュも遅くなる可能性があります。

私たちは、Gitが本当にコミットについてであるという事実から始めます。1 指向性の非環式グラフに形作られます。グラフには、ハッシュIDをコミットすることにより、番号が付けられている頂点またはノードがあります。ここでは比較的重要ではありませんが、具体性に役立ちますが、ノード間のエッジ /アークは、個別に保持されるのではなく、ノード自体の一部として保存されているという事実です。各ノードは、前身ノードのハッシュIDを保存します。

リポジトリは、これらのコミットオブジェクトのデータベースです。すべてのルートからすべてのチップコミットまで、完全な – ノンシャロー – レポジトリにはグラフ全体があります。 a シングルブランチ クローンはグラフの一部を潜在的にドロップする可能性がありますが、グラフに「ギャップ」はありません。たとえば、与えられます:

           node--node--tip1
          /
root--node
          
           node--node--tip2

その行のチップとノードのいずれかをドロップすることはできますが、中央の列のノードとルートではありません。これらのすべてのケースでは、Gitが常に行うように、先端から始まり、最終的に根に到達することができます。

ここで重要な各ノードには2つのプロパティがあります。

  • 番号個性的。それは普遍的にユニークなIDです。 いいえ ノードイン どれでも 他のGitリポジトリ(とにかく会うこと)は、そのIDを再利用できます。

  • データ ノードには厳密に読み取り専用です。これには、発信エッジリンクが含まれます。

これが意味するのは、私たちが持っている場合です ギャップフリー リポジトリ – それは完全に完全であるか、少なくともそれが含むチップに必要なとおりに完全であるかのいずれかで、送信者から受信者への操作の両側には、 送信 リポジトリは、その数字で、いくつかのコミットセットを単に列挙しています。受信リポジトリがそのコミットを欠いている場合、送信者にそれを送信し、親のコミットの数を伝えるように依頼します。送信者はそれを行い、それらのコミットがあるかどうかを確認します。私たちが不足しているものは、送信者にそれらを送って、親のコミットの数などを教えてくれるように頼みます。

これは、ifを意味します 私たちは 持っている:

           node--node--tip1
          /
root--node
          
           node--node--tip2

そして 彼らは 持っている:

           node--node--tip1--new
          /
root--node

それから 彼らは CommitのハッシュIDを使用するように発表します new。私たちはそれを持っていないので、彼らはそれを送るためのコミットの山にそれを追加し、コミットのハッシュIDを私たちに発表する必要があります tip1 同じように。私たちは する 持っている tip1 だから私たちは彼らに言うだけです: 私たちはすでに持っています tip1:送信する必要はありません。

これが最適化です: 私たちは彼らに話しました 私たちが持っているすべてのコミット から tip1 ずっとさかのぼります root 私たちの ありがとう、私たちはそれを持っています 彼らの返事に申し出ます 私はあなたを送ることができます tip1 1つのコミットとそのファイルだけでなく、すべての前任者のコミットとすべてについても伝えます 彼らの ファイルも。

彼らは今、彼らが私たちにコミットを送るときを知っています new、彼らは、前身のコミットには表示されないツリーとBlob(「ファイル」)オブジェクトのみを送信する必要があります。 さらに、これらのツリーとブロブオブジェクトを、任意のツリーとブロブオブジェクトに対して圧縮できます 前の コミット、から tip1 ずっとさかのぼります root。したがって、送信者は送信できます 遠い すべてのファイルの完全なスナップショットを使用して、それ以外の場合はコミット全体を送信するために必要なデータよりも少ない。


ツリーオブジェクトとブロブオブジェクトが主に見つかります 経由 コミット。注釈付きタグオブジェクトは、写真に1つの小さなしわを追加し、ツリーまたはブロブを直接指す注釈付きタグを使用すると、別のものが追加されますが、どちらも標準の最適化を打ち負かすことはありません。


送信者が浅いリポジトリである場合と比較してください

a 浅いリポジトリ いくつかのコミットがルートコミットであると人為的にマークアップされているものです。コミットオブジェクトは実際には右の親ハッシュIDを持っていますが、このコミットオブジェクトが住んでいるgitにはファイルがあります2 それは言う: 私たちはコミットの親について何も知りません tip1。代わりに、それを見せようとしないでください tip1 親はいないルートコミットです。

これは、次のことをする代わりに、送信gitを意味します。

           node--node--tip1
          /
root--node

ちょうど:

      slightly-mangled-tip1

このリポジトリでは、新しいコミットを追加します。

      slightly-mangled-tip1--new

そして今、私たちは彼らのgitを彼らのgitを呼び起こさせ、それを新しいコミットを提供しています。最初に提供します new。彼らは言います 私はそれを持っていません、あなたは他に何を送ることができますか? 提供します slightly-mangled-tip1、 しかし それはできません 私たちがそれを読んだとき、私たちはそれをマングルするからです。だから私たちは言う: 申し訳ありませんが、それが私たちがあなたのために持っているすべてです。

彼らは言う: それでは、コミットを送ってください new

次に、コミットを検討します new。完全なスナップショットがあります すべてのファイル。彼らが持っているかどうかはわかりません どれでも これらのファイルの。それで、私たちはすべてを梱包して送ります 全て それの。

彼らはそれをすべて受け取り、解き放ち、すでに持っているものの99%を複製し、余分なコピーを無視し、新しいコミットを取り、リポジトリに入れてください。

           node--node--tip1--new
          /
root--node
          
           node--node--tip2

次回実行するとき git push、これがあります:

      slightly-mangled-tip1--new--new2

私たちはそれらを提供します new2;彼らは言います 私はそれを持っていません、その親は何ですか そして、私たちは言います new そして彼らは言います ああ、私はそれを持っています、気にしないでください。今回は、ほぼすべてのファイルが既にあることがわかり、それらのすべてのツリーとブロブオブジェクトの送信を気にしないでください そして 任意の圧縮できます 新しい コミット中のものに基づいたツリーとブロブのオブジェクト new。 (わずかにマンジのTIP1コミットを使用することも、もちろん不足している以前のコミットを使用することはできませんが、すべての変更されていないファイルを排除できることは膨大です。)


2または他のメカニズムですが、現在、それは名前付きファイルです .git/shallow


これについて何ができるか

あなたが走るつもりであることを考えると git push、「浅いグラフトポイントと枝の先端の間に「1つのマングルされていないコミット」があることから、多くの走行距離が得られます。あなたもそうします git clone--depth 2。わずかに大きいクライアントGitリポジトリを取得しますが、最初に git push はるかに速くなります。

つまり、あなたはから始めます:

slightly-mangled-node--tip1

クライアントについて。最初 新しい コミットは次のようになります:

slightly-mangled-node--tip1--new

そして今回はあなたのgitが提供できるでしょう tip1 最初のプッシュ中のGitに、最適化がトリガーされます。

#git浅いクローンの後にgithubにプッシュするのはひどく遅い

執筆者について: nipponese

Nipponese News編集部は、国内外のニュースを日本語で分かりやすくお届けします。