フォルダーを別のフォルダー内に移動するgitコマンド


193

commonたくさんのソースファイルとフォルダーを含むフォルダーを作成しました。

次に、commonフォルダをフォルダに移動して、include次のようにしますinclude/common

私はこれらを試しました:

  1. git add include

  2. git mv common/ include/

    しかし、このエラーで失敗します

    致命的:不正なソース、source = myrepo / common、destination = myrepo / include

  3. 試しましたgit mv common/ include/commonが同じエラーが発生します

これを達成する方法はありますか?

回答:


177

gitの最も優れた点の1つは、ファイル名の変更を明示的に追跡する必要がないことです。Gitはファイルの内容を比較することによってそれを理解します。

だから、あなたの場合、そんなに頑張らないでください:

$ mkdir include
$ mv common include
$ git rm -r common
$ git add include/common

実行git statusすると、次のように表示されます。

$ git status
# On branch master
# Changes to be committed:
#   (use "git reset HEAD <file>..." to unstage)
#
#   renamed:    common/file.txt -> include/common/file.txt
#

43
これは私には機能しません(Windows 7、1.7.6.msysgit.0を使用)。Gitは、古いファイルが削除され、新しいファイルが追加されたと考えています。
Bart

うーん、おそらくgitはいくつかの外部ユーティリティを使用して、Windowsで機能しないファイル同一性を判断しますか?これはgitの実装の中核部分でした。
Andres Jaan Tack

13
@OliverF。修正:git mv同等です。
Andres Jaan Tack

25
「gitの最も優れた点の1つ —この素晴らしい機能の欠点の1つは、名前が大幅に変更されたファイルも変更すると失敗し始め、新しいファイルの削除と追加が表示されることです。なので、率直に言って、明示的な名前変更サポートを代わりに使用したいと思います。
Erik Kaplun、2015年

2
gitが行末を変換すると、@ Bartによって記述される問題が発生します。これを機能させるには、以下を実行する必要があります。git config --global core.autocrlf false
Mariano Dupont

162
 git mv common include

うまくいくはずです。

git mvmanページから:

git mv [-f] [-n] [-k] <source> ... <destination directory>

2番目の形式では、最後の引数は既存のディレクトリでなければなりません。指定されたソースはこのディレクトリに移動されます。
インデックスは正常に完了した後に更新されますが、変更はまだコミットされている必要があります。

移動の前に " git add"を実行しないでください。


注:「git mv A B/Bがディレクトリとして存在しない場合、エラーになるはずですが、ありませんでした。

Git 1.9 / 2.0(2014年第1四半期については、Matthieu Moy(によるコミットc57f628を参照してください。moy

Gitは、末尾のスラッシュをgit mv file no-such-dir削除し、コマンドを ' 'と同等にしてファイルを作成していましたno-such-dir(末尾のスラッシュは、それがディレクトリのみである可能性があることを明示的に示していました)。

このパッチは、宛先パスの末尾のスラッシュ削除をスキップします。
末尾にスラッシュがあるパスはrename(2)に渡され、適切なメッセージでエラーになります。

$ git mv file no-such-dir/
fatal: renaming 'file' failed: Not a directory

2
完璧に動作しました-そして使用git mvははるかに良いアプローチのように見えます!
Tomas Petricek 2015年

23

コマンド:

$ git mv oldFolderName newFolderName

通常は問題なく動作します。

エラー「bad source ...」は、通常、最後のコミット後、ソースディレクトリに名前の変更があったgit mvため、予期したファイルが見つからないことを示しています。

解決策は簡単git mvです。適用する前にコミットするだけです。


15

実行する前に、すべての変更をステージング領域に追加したことを確認してください

git mv oldFolderName newFoldername

gitがエラーで失敗する

fatal: bad source, source=oldFolderName/somepath/somefile.foo, destination=newFolderName/somepath/somefile.foo

未追加のファイルがある場合、私はちょうどそれを見つけました。


「追加されていないファイルがあるので見つけたところです。」-ありがとう!
cacoder

3

ディレクトリ内のすべてのファイルをサブディレクトリに移動する別の方法(gitの履歴を保持):

$ for file in $(ls | grep -v 'subDir'); do git mv $file subDir; done;


3

git mv1つのフォルダーの内容を既存のフォルダーに移動したい場合にも同様の問題があり、次の "単純な"スクリプトで終わりました。

pushd common; for f in $(git ls-files); do newdir="../include/$(dirname $f)"; mkdir -p $newdir; git mv $f $newdir/$(basename "$f"); done; popd

説明

  • git ls-filescommongitにチェックインされた(フォルダー内の)すべてのファイルを検索します
  • newdir="../include/$(dirname $f)"; mkdir -p $newdir;includeと同じディレクトリ構造で、フォルダ内に新しいフォルダを作成しますcommon
  • git mv $f $newdir/$(basename "$f"):ファイルを新しく作成したフォルダーに移動します

これを行う理由は、gitがファイルを既存のフォルダーに移動するのに問題があるようで、存在しないフォルダー(したがってmkdir -p)にファイルを移動しようとした場合にも失敗するためです。

このアプローチの良い点は、すでにgitにチェックインされているファイルのみに触れることです。単にを使用git mvしてフォルダー全体を移動し、フォルダーに段階的な変更が含まれている場合、gitは何をすべきかわかりません。

ファイルを移動した後、リポジトリクリーンアップして、ステージングされていない残りの変更を削除することができます。最初にドライランすることを忘れないでください!

git clean -fd -n

2

「Andres Jaan Tack」の「答え」をコメントする評判が足りなくてすみません。

私のメッセージは削除されると思います((しかし、「ラーシャー」や同じエラーが発生した他の人に警告したいだけです:注意してください)

$ mkdir include
$ mv common include
$ git rm -r common
$ git add include/common

新しいフォルダにプロジェクトのgit履歴が表示されない場合があります。

私が試した

$ git mv oldFolderName newFolderName

得た

fatal: bad source, source=oldFolderName/somepath/__init__.py, dest
ination=ESWProj_Base/ESWProj_DebugControlsMenu/somepath/__init__.py

やった

git rm -r oldFolderName

そして

git add newFolderName

プロジェクトに古いgit履歴が表示されません。少なくとも私のプロジェクトは失われていません。現在、プロジェクトはnewFolderNameにありますが、履歴はありません(

警告したいだけなら、git hsitoryを失いたくない場合は、「Andres Jaan Tack」のアドバイスを使用するように注意してください。


すべての変更が追加されていることを確認してください。追加されていない変更があると、Gitは「悪いソース」と言って失敗するので、私はそれを見つけました。
Kevin Pluck、2015年

0

同様の問題がありましたが、移動したいフォルダに追跡していないファイルがありました。

ファイルがあるとしましょう

a/file1
a/untracked1
b/file2
b/untracked2

そして追跡したファイルのみをサブフォルダーに移動したかったsubdirので、目標は次のとおりです。

subdir/a/file1
subdir/a/untracked1
subdir/b/file2
subdir/b/untracked2

私がしたことは:

  • 新しいフォルダを作成し、移動したいすべてのファイルを移動しました。 mkdir tmpdir && mv a b tmpdir
  • 古いファイルをチェックアウトした git checkout a b
  • 新しいディレクトリを作成し、クリーンなフォルダ(追跡されていないファイルなし)を新しいサブディレクトリに移動しました: mkdir subdir && mv a b subdir
  • サブディレクトリからすべてのファイルを追加しました(Gitは以前に追跡されたファイルのみを追加できました-これはgit add --updateディレクトリ変更のトリックgit add subdirと同じようなものでした):(通常、これは追跡されていないファイルも追加します-これには.gitignoreファイルの作成が必要です)
  • git status 移動したファイルのみを表示
  • 残りのファイルをtmpdirからサブディレクトリに移動しました: mv tmpdir/* subdir
  • git status実行したように見えますgit mv:)

-1

私はこれを行うことでWindowsでこれを解決しました:

  • Power Shellコンソールを開く
  • dirを実行
  • Altキーを押しながらクリックして、ファイル/フォルダー名の列の上にドラッグし、コピーします
  • notepad ++に貼り付け
  • 正規表現に置き換えを実行します置き換える(.*)git mv ".\\\1" ".\\<New_Folder_Here>\"
  • notepad ++からpowershellにすべてのテキストをコピーする
  • Enterキーを押します
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.