GIT:特定のフォルダーへのチェックアウト


回答:


57

あたりとして(「SVNのエクスポート」のような)「gitの輸出」しますか?

git checkout-indexそのために使用できます。これは低レベルのコマンドです。すべてをエクスポートしたい場合は-a

git checkout-index -a -f --prefix=/destination/path/

manページを引用するには:

最後の "/" [プレフィックス]は重要です。エクスポートされた名前は、文字通り、指定された文字列が前に付けられます。

特定のディレクトリをエクスポートする場合は、いくつかのトリックが関係しています。このコマンドは、ディレクトリではなく、ファイルのみを取ります。ディレクトリに適用するには、「find」コマンドを使用して、出力をgitにパイプします。

find dirname -print0 | git checkout-index --prefix=/path-to/dest/ -f -z --stdin

また、manページから:

ここでは直観性は目標ではありません。再現性です。


悲しいことに、これはさえ--prefixセット:-((gitの1.9.1でテスト済み)との裸のgitリポジトリからの作業、しません
apeiros

1
ベアgitリポジトリのブランチ/コミットをチェックアウトする場合は、GIT_WORK_TREE=../path/to/place git checkout
allicoderを

4
git worktree(下記参照)imhoは今日の正解であり、ここに追加される場合があります。
オタク

213

もう少しクリーンな別の解決策-別の作業ツリーを指定するだけです。

HEAD(インデックスではない)から特定のoutディレクトリまですべてをチェックアウトするには:

git --work-tree=/path/to/outputdir checkout HEAD -- .

HEADから特定のディレクトリにサブディレクトリまたはファイルをチェックアウトするには:

git --work-tree=/path/to/outputdir checkout HEAD -- subdirname

4
マイナーな注意-シェルチルド拡張が発生しないため、絶対パスが必要です。つまり--work-tree=/home/thomasg/okcopy--work-tree=~/okcopy(同じgitツリー内に座っている間に相対パスを使用することもできgit statusますが、R'lyehianには狂気と出力があります)
トムグッドフェロー2014年

10
これは古いコミットでも期待どおりに機能します(たとえば、HEADの代わりにSHAを与える)が、git status多くのmodを表示します(おそらく、インデックスが他のディレクトリと一致し、手つかずの通常の作業ツリーと一致しないためと考えられます)。git resetそれを良い状態に戻しました。
トムグッドフェロー2014年

2
ここで同じことgit statusは多くのモッドを示し、git reset助けにはなりません。そうしなければならなかったgit checkout -f HEADレポの状態を復元するた。
DUzun、2015年

11
FYI:あなたはそうしないと、このエラーを取得し、自分でディレクトリを作成する必要がありますfatal: This operation must be run in a work tree
timaschew

13
これにより、メインの作業ツリーのインデックスが壊滅的に変更されます。@TomGoodfellowが示唆しているようにgit reset、メインの作業ツリーを正常に戻すには十分です。メインの作業ツリー変更せずに、任意のSHA1、ブランチ、またはタグでリポジトリサブディレクトリを安全にエクスポートするには、Charles Baileyの 悪名高いgit archiveソリューションを参照してください。同様に、同時に複数のブランチを安全にチェックアウトするには、新しいgit worktree addサブコマンドがあなたの友達です。
セシルカレー

25

単一ファイルの場合:

git show HEAD:abspath/to/file > file.copy

2
+1および「HEADの代わりに」「特定の以前のコミット」を明確にする:これは、SHA1 IDを介して簡単に見つけることができるものを指しgitkます。私は一時的な場所に「チェックアウト」というファイルを(つまり、元に戻すせず)に必要がある場合は、私が使用しますshow:サブコマンドgit show 82e54378856215ef96c5db1ff1160a741b5dcd70:MyProj/proguard/mapping.txt > myproj_mapping.txt
ef2011

19

ツリーの特定のタグ付きバージョンをチェックアウトする必要があったため、上記の解決策は私にとってはうまくいきませんでした。cvs exportちなみに、それが使用方法です。 git checkout-indexインデックスからファイルをチェックアウトするため、タグ引数を取りません。 git checkout <tag>作業ツリーに関係なくインデックスを変更するため、元のツリーをリセットする必要があります。私にとってうまくいった解決策は、リポジトリを複製することでした。共有クローンは非常に高速で、余計なスペースを取りません。.git必要に応じて、ディレクトリを削除できます。

git clone --shared --no-checkout <repository> <destination>
cd <destination>
git checkout <tag>
rm -rf .git

新しいバージョンのgitはgit clone --branch <tag>、指定されたタグを自動的にチェックアウトすることをサポートする必要があります。

git clone --shared --branch <tag> <repository> <destination>
rm -rf <destination>/.git

3
git --work-tree=/path/to/outputdir checkout <tag> -- .うまくいきませんでしたか?
warvariuc 2013

1
いいえ、ありません。元の作業ディレクトリの実際のファイルは変更されていませんが、ステージングされたバージョンは失われ、タグのバージョンで置き換えられます。ステージングされたバージョンに、慎重に選択された一連の変更が含まれている場合は特に悪いことになります。exportコマンドでインデックス、ピリオドを変更したくありません。
プロスキー2015年

19

自分の機能で作業していて、チェックアウトしてマスターに戻りたくない場合は、次のコマンドを実行できます。

cd ./myrepo

git worktree add ../myrepo_master master

git worktree remove ../myrepo_master

ブランチコミットで../myrepo_masterディレクトリを作成しmaster、作業を続行できます


1
ベストアンサー-シンプルでgit --work-tree=/path/to/outputdir checkout HEAD -- .、インデックスに対して何もしないのとは異なり、選択したブランチを指定した場所にコピーするだけです(.gitファイルを追加します)。
Roger Dueck 2017年

そして、この変更を元に戻すにはどうすればよいですか?
スコットP.

@ ScottP.just myrepo_masterディレクトリを削除
itsnikolay

1
これを元に戻すことはworktreeからサブコマンドです:git worktree remove ../myrepo_master
マルタインDashorst

8

エイドリアンの答えは「致命的:この操作は作業ツリーで実行されなければならない」を投げた。以下は私たちのために働いたものです。

git worktree add <new-dir> --no-checkout --detach
cd <new-dir>
git checkout <some-ref> -- <existing-dir>

ノート:

  • --no-checkout 新しいワークツリーには何もチェックアウトしないでください。
  • --detach 新しいワークツリーの新しいブランチを作成しないでください。
  • <some-ref> たとえば、あらゆるrefで動作します。 HEAD~1ます。
  • によるクリーンアップgit worktree prune

クリーンアップの方法についてコメントするための+1-他の誰もが現在のレポを台無しにして喜んでいます。これだけは副作用がありません。
アンドリューヒル

1

@hasenの回答への追加。チェックアウトするファイルを一覧表示するには、次git ls-filesfindような代わり に使用したい場合があります。

git ls-files -z *.txt | git checkout-index --prefix=/path-to/dest/ -f -z --stdin

正しくご利用いただきありがとうございます-z!特定の種類のインジェクション攻撃に対して脆弱ではないスクリプトを提供できてうれしいです。
ErikE

0

これを実現するためにgitエイリアスを定義しました(この質問を見つける前に)。

これは、現在のパスを保存し、git repoに切り替え、チェックアウトを実行し、開始した場所に戻る短いbash関数です。

git checkto開発〜/ my_project_git

これは、たとえば、開発ブランチを「〜/ my_project_git」ディレクトリにチェックアウトします。

これは内部のエイリアスコードです~/.gitconfig

[alias]
    checkTo = "!f(){ [ -z \"$1\" ] && echo \"Need to specify branch.\" && \
               exit 1; [ -z \"$2\" ] && echo \"Need to specify target\
               dir\" && exit 2; cDir=\"$(pwd)\"; cd \"$2\"; \
               git checkout \"$1\"; cd \"$cDir\"; };f"

0

一時ディレクトリのブランチをチェックアウトするためにこのエイリアスを使用しています:

[alias]
    cot = "!TEMP=$(mktemp -d); f() { git worktree prune && git worktree add $TEMP $1 && zsh -c \"cd $TEMP; zsh\";}; f" # checkout branch in temporary directory

使用法:

git cot mybranch

その後、ブランチで作業できる一時ディレクトリの新しいシェルにドロップされます。このディレクトリでgitコマンドを使用することもできます。

完了したら、ディレクトリを削除して実行します。

git worktree prune

これは、新しいワークツリーを追加する前に、エイリアスでも自動的に行われます。


0

git archive branch-index | tar -x -C your-folder-on-PCブランチを別のフォルダに複製するために使用します。必要なファイルをコピーできると思います

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.