Как заменить папку с символической ссылкой на сервере - PullRequest
0 голосов
/ 22 ноября 2018

У нас есть git-репозиторий для научного программного обеспечения, в котором нам необходимо поддерживать определенную структуру папок для наших файлов данных.Эти папки должны оставаться пустыми, все, что будет помещено туда, не должно отслеживаться git.Однако необходимо, чтобы эти папки существовали.

Решением для достижения этой цели было добавление файла .gitignore в каждый каталог, который выглядит следующим образом:

*
!.gitignore

, что означает, что все в этой папке игнорируется, кроме .gitignoreфайл.

Это работает очень хорошо.

Мы храним все наши данные на одном конкретном сервере.Наши ученые часто используют этот сервер для своих расчетов.Было бы очень удобно иметь возможность заменить папки данных из репозитория git, которые в настоящее время содержат только файл .gitignore, с символической ссылкой на полные файлы данных на этом сервере.Файлы данных на сервере также имеют файл .gitignore, который выглядит точно так же, как и в каждом хранилище.

Я написал для этого скрипт bash, который выглядит следующим образом:

rm -r path/to/empty/data/in/repository/name
ln -sfn /absolute/path/to/data/on/server/ path/to/empty/data/in/repository

Теперь программа работает отлично, и у вас есть доступ ко всем данным, не копируя их в репозиторий git.

Однако, git теперь запутался.

Если я запускаю git status, то только мои изменения отображаются в списке как и ожидалось.Он не жалуется на новые символические ссылки, которые заменили существующие каталоги.

Как только я запускаю git add . для внесения изменений, символические ссылки отображаются как new file:, а файлы .gitignore в замененной папке отображаются как deleted:.

Это кажется мне проблемой, потому что, как только кто-то отправляет изменения своего кода, которые он сделал на сервере, символические ссылки будут загружены (я думаю), и файлы .gitignore будут удалены, и, таким образом,структура папок не останется.

Можно ли сказать git, что он должен сравнивать содержимое символьных связанных папок, а не саму символьную ссылку?

PS: я знаю, что это похоже на проблему разработки программного обеспечения со статической структурой папок, которая находится внутри git, но я не хочу обсуждать это здесь.Мы все ученые и не программисты, и программное обеспечение разрабатывается уже более 10 лет многими разными людьми.Невозможно изменить код, чтобы сделать его более гибким.

EDIT: этот код bash воспроизводит проблему:

cd ~            #setup
mkdir tmp
cd tmp

mkdir server    #server data folder (this one is full of data)
mkdir server/data
printf '*\n!.gitignore' > server/data/.gitignore
printf 'data file 1' > server/data/data1.txt
printf 'data file 2' > server/data/data2.txt

mkdir repo      #repo data folder (this one only contains .gitignore file)
mkdir repo/data
printf '*\n!.gitignore' > repo/data/.gitignore

cd repo              # create a dummy repo
git init
git add .
git commit -am"commit 1"

git status

cd ..              # replace data folder with server/data folder which hase exactly the same content
rm -r repo/data/
ln -sfn ~/tmp/server/data/ ./repo/

cd repo
git status

В конце состояния git в идеале не должно перечисляться никаких изменений в хранилище.

EDIT: Я нашел обходной путь: вместо того, чтобы связать весь каталог, я теперь связываю содержимое каталога:

ln -sfn /absolute/path/to/data/on/server/* path/to/empty/data/in/repository/

это работает, потому что символические ссылки игнорируются из-за файла .gitignore.Недостатком является то, что он работает только с существующими данными.Как только в каталоге сервера появляется новый файл, мне снова нужно запустить скрипт bash.

1 Ответ

0 голосов
/ 22 ноября 2018

Git отслеживает символические ссылки.То, чего вы пытаетесь достичь, можно сделать с помощью bind mounts.

Замените окончательный ln -sfn ~/tmp/server/data/ ./repo/ на sudo mount --bind $PWD/repo $HOME/tmp/server/data/

...