команда git для перемещения папки внутри другой - PullRequest
175 голосов
/ 10 октября 2010

Я создал папку common с кучей исходных файлов и папок.

Теперь я хочу переместить папку common в папку include, чтобы она выглядела как include/common

Я пробовал это:

  1. git add include

  2. git mv common/ include/

    но с этой ошибкой происходит сбой

    смертельно: плохой источник, источник = myrepo / common, пункт назначения = myrepo / include

  3. Я попробовал git mv common / include / common, но я получил ту же ошибку

Есть идеи, как этого добиться?

Ответы [ 9 ]

163 голосов
/ 10 октября 2010

Одной из самых приятных особенностей git является то, что вам не нужно явно отслеживать переименования файлов.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
#
142 голосов
/ 10 октября 2010
 git mv common include

должно работать.

Из справочной страницы git mv :

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

Во второй форме последний аргумент должен быть существующим каталогом; указанные источники будут перемещены в этот каталог .
Индекс обновляется после успешного завершения, но изменение все еще должно быть зафиксировано.

Не нужно делать git add до хода.


Примечание: "git mv A B/", когда B не существует в качестве каталога, должно выдавать ошибку, но это не так.

См. коммит c57f628 от Матье Мой (moy) для Git 1,9 / 2,0 (1 квартал 2014 года):

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
17 голосов
/ 13 января 2015

Команда:

$ git mv oldFolderName newFolderName

Обычно она работает нормально.

Ошибка «неверный источник ...» обычно указывает на то, что после последнего коммита в исходном каталоге были некоторые переименования и, следовательно, git mv не может найти ожидаемый файл.

Решение простое - просто подтвердите перед применением git mv.

12 голосов
/ 16 марта 2015

Убедитесь, что вы добавили все свои изменения в область подготовки перед запуском

git mv oldFolderName newFoldername

git завершается ошибкой с ошибкой

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

, если есть какие-либо не добавленные файлы, поэтому я просто нашелвне.

3 голосов
/ 18 августа 2016

У меня была похожая проблема с git mv, когда я хотел переместить содержимое одной папки в существующую папку, и в итоге получил этот «простой» скрипт:

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-files: найти все файлы (в папке common), отмеченные в git
  • 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
3 голосов
/ 18 января 2015

Другой способ переместить все файлы в каталоге в подкаталог (ведет историю git):

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

2 голосов
/ 19 сентября 2014

Извините, у меня недостаточно репутации, чтобы комментировать «ответ» «Андрес Яан Тэк».

Я думаю, что мой messege будет удален (( Но я просто хочу предупредить "lurscher" и других, которые получили ту же ошибку: будьте осторожны, делая

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

Это может привести к тому, что вы не увидите историю изменений вашего проекта в новой папке.

Я попробовал

$ 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

и я не вижу старой истории мерзавцев в моем проекте. По крайней мере, мой проект не потерян. Теперь у меня есть проект в newFolderName, но без истории (

Просто хочу предупредить, будьте осторожны, пользуясь советом "Andres Jaan Tack", если вы не хотите потерять свою мерзавцу.

0 голосов
/ 04 июня 2019

Я решил эту проблему в Windows, выполнив следующее:

  • Откройте консоль Power Shell
  • Запустите dir
  • Удерживая клавишу «Alt», перетащите имя файла / папкистолбец, затем скопируйте
  • Вставьте в блокнот ++
  • запустите заменить на регулярное выражение: замените (.*) на git mv ".\\\1" ".\\<New_Folder_Here>\"
  • скопируйте весь текст из блокнота ++ в powershell
  • нажмите Enter
0 голосов
/ 07 ноября 2013

У меня была похожая проблема, но в папке, которую я хотел переместить, у меня были файлы, которые я не отслеживал.

допустим, у меня есть файлы

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
  • создал новый dir и переместил чистые папки (без неотслеживаемых файлов) в новый subdir: mkdir subdir && mv a b subdir
  • добавил все файлы из subdir (поэтому Git мог добавлять только отслеженные ранее файлы - это было что-то вроде git add --update с изменением каталога трюк ): git add subdir (обычно это добавит даже неотслеживаемые файлы - для этого потребуется создать .gitignore файл)
  • git status показывает теперь только перемещенные файлы
  • перенес остальные файлы из tmpdir в subdir: mv tmpdir/* subdir
  • git status похоже, что мы выполнили git mv:)
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...