Zachowaj plik w repozytorium Git, ale nie śledź zmian

305

Mam kilka plików w witrynie CodeIgniter, które będę chciał mieć w repozytorium, ale nie będę śledził żadnych zmian.

Na przykład wdrażam nową instalację tego frameworka na nowym kliencie, chcę pobrać następujące pliki (mają wartości domyślne CHANGEME) i muszę tylko wprowadzić zmiany specyficzne dla tego klienta (poświadczenia bazy danych, informacje o adresie e-mail, niestandardowe CSS).

// the production config files i want the files but they need to be updated to specific client needs
application/config/production/config.php
application/config/production/database.php
application/config/production/tank_auth.php
// index page, defines the environment (production|development)
/index.php
// all of the css/js cache (keep the folder but not the contents)
/assets/cache/*
// production user based styling (color, fonts etc) needs to be updated specific to client needs
/assets/frontend/css/user/frontend-user.css

Obecnie jeśli uruchomię

git clone [email protected]:user123/myRepo.git httpdocs

a następnie edytuj pliki powyżej, wszystko jest świetne. Do momentu wydania poprawki lub poprawki i uruchomienia git pull. Wszystkie moje zmiany są następnie nadpisywane.

gorelative
źródło
Możesz po prostu zignorować pliki poświadczeń / konfiguracji klienta i poprosić program o utworzenie domyślnych plików, jeśli brakuje ich podczas instalowania repozytorium?
MatthewG

Odpowiedzi:

618

git ma na to inne rozwiązanie. Najpierw zmień plik, którego nie chcesz śledzić, i użyj następującego polecenia:

git update-index --assume-unchanged FILE_NAME

a jeśli chcesz ponownie śledzić zmiany, użyj tego polecenia:

git update-index --no-assume-unchanged FILE_NAME

Dokumentacja git-update-index

nasirkhan
źródło
Zrobiłem to, co mówisz, ale status git ciągle mówi, że plik został zmodyfikowany
rraallvv
7
Tak, powinna to być „odpowiedź zaakceptowana”. Pracował dla mnie.
joshmcode
34
Zgodnie z Junio ​​Hamano (opiekunem Git): „Zakładaj, że niezmieniony nie powinien być nadużywany w celu zignorowania mechanizmu. [...] Git nie obiecuje, że Git zawsze będzie uważał, że te ścieżki są niezmodyfikowane --- jeśli Git może określić ścieżkę oznaczoną jako zakładająca niezmienioną, że uległa zmianie bez ponoszenia dodatkowych kosztów lstat (2), zastrzega sobie prawo do zgłoszenia modyfikacji ścieżki (w wyniku tego „git commit -a” może to zatwierdzić zmiana)." Innymi słowy, zakładanie niezmienionego dotyczy tylko lokalnych problemów z wydajnością. Jeśli Git może ustalić, że te pliki zmieniły się w lżejszy sposób, zrobi to.
Alejandro García Iglesias
41
Czytając informacje na ten temat, myślę, że ta --skip-worktreeopcja lepiej pasuje do tej pracy niż --assume-unchanged.
PJSCopeland,
26
--skip-worktree jest rzeczywiście lepszą opcją. Więcej informacji: stackoverflow.com/questions/13630849/…
Dostosuj
80

Aby wyciągnąć odpowiedź z komentarzy do innej odpowiedzi:

$ git update-index --skip-worktree FILENAME

Wydaje się być lepszą opcją niż --assume-unchanged

Więcej informacji na ten temat można znaleźć tutaj: Git - różnica między „zakładaj niezmienione” a „pomiń”

Anthony
źródło
Gdy to zrobię, a następnie spróbuję zmienić gałęzie, otrzymuję komunikat „Następujące nieśledzone działające pliki drzewa zostaną nadpisane przez kasę ... Proszę je przenieść lub usunąć przed zmianą gałęzi”. Wszelkie pomysły, jak tego uniknąć?
Patrick Szalapski,
Artykuł przywołany przez @aexl został przeniesiony do compiledsuccessfully.dev/git-skip-worktree
Andrew Keeton
1
W docs powiedzieć, że jest to zły pomysł. „Użytkownicy często próbują użyć bitów„ zakładaj niezmienione ”i„ pomiń ”, aby powiedzieć Gitowi, aby ignorował zmiany w śledzonych plikach. Nie działa to zgodnie z oczekiwaniami, ponieważ Git może nadal sprawdzać pliki drzewa roboczego względem indeksu podczas wykonywania niektórych operacji. Ogólnie rzecz biorąc, Git nie umożliwia ignorowania zmian w śledzonych plikach, dlatego zalecane są alternatywne rozwiązania. ”
Curtis Blackwell
58

W przypadku moich projektów Code Igniter przechowuję database.php.example i config.php.example w repozytorium.

Następnie dodam config.php i applications / config / database.php do pliku .gitignore .

Wreszcie, kiedy wdrażam, mogę skopiować pliki .example (do config.php i database.php), dostosować je i nie będą śledzone przez GIT.

superiggy
źródło
12
Dobre rozwiązanie, ale myślę, że odpowiedź nasirkhan jest najlepsza.
wordsforthewise
To nie jest dobre rozwiązanie. Jeśli opróżnisz swój indeks git, zaczniesz śledzić zmiany, kiedy nie chcesz. Zobacz odpowiedź @nasirkhans, aby dowiedzieć się, jak to zrobić.
Brian Melton-Grace - MSFT
3
Nie zgadzam się z poprzednimi komentarzami. W ten sposób o wiele łatwiej jest zaktualizować „domyślne” wartości bez konieczności ich sprawdzania i kopiowania lokalnej konfiguracji w innym miejscu, aby później ją przywrócić. Dotyczy to również wszystkich repozytoriów, więc nie musisz powtarzać repozytoriów.
OskarD90
1
jeśli jest w gitignore, dlaczego miałby zacząć śledzić zmiany ponownie
Shapeshifter
Rozwiązuje problem PO, ale tak naprawdę nie odpowiada na pytanie.
Travis Wilson,
1

Umieściłbym je w twoim .gitignorepliku i po prostu skopiowałem je ręcznie w razie potrzeby.

Więc szkieletowa nazwa pliku byłaby w git, ignorowane nazwy plików nie byłyby w git (ale byłyby w .gitignore). W ten sposób, gdy ręczny krok do skopiowania ich do „faktycznego” z „szablonu” (być może lepszej nazwy niż szkielet) jest natychmiast ignorowany.

Michael Durrant
źródło
1
nie ma sposobu, aby dodać je najpierw do repo, a następnie dodać je do .gitignore? Byłoby wspaniale, gdyby istniało rozwiązanie polegające na włączeniu plików, ale bez zmian po określonym zatwierdzeniu lub coś takiego.
gorelative
1
@mklauber Chcę zachować je na czas nieokreślony, dopóki nie uruchomię git rm <file>. Celem jest IE: plik config.php. Chcę zachować plik konfiguracyjny, ale oczywiście nie chcę śledzić poświadczeń bazy danych od klienta do klienta, ponieważ są one różne.
gorelative
1
Tak, mam problem z plikiem rails database.yml. Trzymamy szkielet, a następnie go kopiujemy i zmieniamy.
Michael Durrant,
jeśli utworzę te pliki konfiguracyjne „Szkielet”, czy dodasz je do początkowego zatwierdzenia? a następnie modyfikowanie .gitignore, aby zignorować plik? W efekcie przechowywanie pliku w repozytorium, ale jako szkielet?
gorelative
10
Masz dwie opcje: Dodaj plik, git add file1a następnie edytuj .gitignoreplik. Zatwierdzony plik pozostanie tam i nie będzie aktualizowany. Lub: Możesz dodać plik do, .gitignorea następnie dodać za pomocą, git add --force file1aby zmusić plik. Możesz użyć drugiej opcji, ilekroć musisz zastąpić plik
klaustopher
1

Podane odpowiedzi tylko częściowo rozwiązują problem, ale wprowadzają jeszcze więcej problemów.

Musiałem zachować plik „Web.Local.config”. Jedynym rozwiązaniem, które działało dla mnie, było:

1. Wyklucz plik z projektu

2. Utwórz osobną kopię pliku jako Web.LocalTemplate.config

Teraz, gdy „Web.LocalTemplate.config” jest śledzony przez Git, wszyscy programiści mogą go używać jako punktu wyjścia. Jednak „Web.Local.config”, nie będący częścią projektu, zostanie automatycznie zignorowany.

Hrvoje Matić
źródło
W jaki sposób git update-index --skip-worktree FILENAMErozwiązujesz problem tylko częściowo, a nawet dodajesz więcej problemów? Rozwiązuje dokładnie to, co próbujesz zrobić. Próbowałeś?
Amir Asyraf