J'ai un repo qui a deux fichiers que j'ai soi-disant changé localement.
Donc, je suis coincé avec ceci:
$ git status
# On branch master
# Changed but not updated:
# (use "git add <file>..." to update what will be committed)
# (use "git checkout -- <file>..." to discard changes in working directory)
#
# modified: dir1/foo.aspx
# modified: dir2/foo.aspx
#
no changes added to commit (use "git add" and/or "git commit -a")
Faire git diff
indique que tout le contenu du fichier a changé, même si cela semble faux (il semble y avoir des gammes de lignes communes que diff ne semble pas voir).
Fait intéressant, je ne me souviens pas d'avoir changé ces fichiers localement. Ce référentiel est utilisé avec un référentiel distant (privé, sur GitHub.com, FWIW).
Peu importe ce que j'ai essayé, je ne peux pas ignorer ces modifications locales. J'ai tout essayé:
$ git checkout -- .
$ git checkout -f
$ git checkout -- dir1/checkout_receipt.aspx
$ git reset --hard HEAD
$ git stash save --keep-index && git stash drop
$ git checkout-index -a -f
En d'autres termes, j'ai essayé tout ce qui est décrit dans Comment supprimer les modifications non mises en scène dans Git? plus plus. Mais les 2 fichiers restent bloqués car "modifiés mais non validés".
Qu'est-ce qui ferait que deux fichiers soient bloqués comme ceci et apparemment "un-revert-table" ??
P.S. Dans la liste ci-dessus montrant les commandes que j'avais déjà essayées, j'ai écrit par erreur git revert
alors que je voulais dire git checkout
. Je suis désolé et merci à ceux d'entre vous qui ont répondu que je devrais essayer checkout
. J'ai édité la question pour la corriger. J'ai certainement déjà essayé checkout
.
Quelles sont les fins de ligne dans les fichiers? Je parie qu'ils sont CRLF. Si tel est le cas, consultez ce guide: http://help.github.com/line-endings/
En bref, vous devez vous assurer que git est configuré pour convertir les fins de ligne en LF lors de la validation, puis valider ces fichiers. Les fichiers dans le référentiel doivent toujours être au format LF, les fichiers extraits doivent être natifs du système d'exploitation, en supposant que vous définissiez git correctement.
J'ai passé des heures à essayer de résoudre un problème similaire - une branche distante que j'avais extraite, qui indiquait obstinément quatre fichiers comme étant "modifiés mais non mis à jour", même en supprimant tous les fichiers et en exécutant à nouveau git checkout -f
(ou d'autres variantes de ce message)!
Ces quatre fichiers étaient nécessaires mais n’avaient certainement pas été modifiés par moi. Ma solution finale - persuader Git qu'ils n'avaient pas été changés. Ce qui suit fonctionne pour tous les fichiers extraits, indiquant le statut 'modifié' - assurez-vous que vous avez déjà validé/stocké ceux qui ont vraiment été modifiés!
git ls-files -m | xargs -i git update-index --assume-unchanged "{}"
Sur Mac OSX, cependant xargs fonctionne un peu différemment (merci Daniel pour le commentaire):
git ls-files -m | xargs -I {} git update-index --assume-unchanged {}
J'ai ajouté ceci comme espace réservé pour moi pour la prochaine fois, mais j'espère que cela aidera aussi quelqu'un d'autre.
-Al
voici comment j'ai résolu le même problème dans mon cas: ouvrir.
* text=auto
à:
#* text=auto
enregistrer et fermer, puis revenir ou réinitialiser, .__, grâce à @Simon East
Une autre possibilité est que la différence (cela vous empêche de restaurer ces fichiers avec une commande d'extraction) est celle du mode fichier. Voilà ce qui m'est arrivé. Sur ma version de git, vous pouvez découvrir cela en utilisant
git diff dir1/foo.aspx
Et il vous montrera les changements de mode de fichier. Il ne vous laissera toujours pas les rétablir, cependant. Pour cette utilisation soit
git config core.filemode false
ou changez votre git .config dans votre éditeur de texte en ajoutant
[coeur]
filemode = false
Après cela, vous pouvez utiliser
réinitialisation git HEAD dir1/foo.aspx
et le fichier devrait disparaître.
(J'ai tout cela de la réponse à Comment puis-je modifier le mode git ignore (chmod)? )
Essayez de annuler les modifications locales :
git checkout -- dir1/foo.aspx
git checkout -- dir2/foo.aspx
Certains de mes fichiers fantômes ont été modifiés, mais ils étaient identiques.
Exécuter cette commande parfois fonctionne:
(Désactive les conversions de fin de ligne "intelligentes" mais souvent inutiles)
git config --local core.autocrlf false
Mais dans un autre cas, j’ai trouvé que cela était dû à un fichier .gitattributes
dans la racine, qui contenait certains paramètres de fin de ligne, qui essayait d’appliquer autocrlf
à certains fichiers même s’il était désactivé. Cela n’a pas été vraiment utile, j’ai donc supprimé .gitattributes
, validé, et le fichier n’a plus été modifié.
git checkout dir1/foo.aspx
git checkout dir2/foo.aspx
Je pense qu’il serait utile de donner un indice sur la manière de reproduire le problème, afin de mieux comprendre le problème:
$ git init
$ echo "*.txt -text" > .gitattributes
$ echo -e "hello\r\nworld" > 1.txt
$ git add 1.txt
$ git commit -m "committed as binary"
$ echo "*.txt text" > .gitattributes
$ echo "change.." >> 1.txt
# Ok let's revert now
$ git checkout -- 1.txt
$ git status
modified: 1.txt
# Oooops, it didn't revert!!
# hm let's diff:
$ git diff
warning: CRLF will be replaced by LF in 1.txt.
The file will have its original line endings in your working
directory.
diff --git a/1.txt b/1.txt
index c78c505..94954ab 100644
--- a/1.txt
+++ b/1.txt
@@ -1,2 +1,2 @@
-hello
+hello
world
# No actual changes. Ahh, let's change the line endings...
$ file 1.txt
1.txt: ASCII text, with CRLF line terminators
$ dos2unix 1.txt
dos2unix: converting file 1.txt to Unix format ...
$ git diff
git diff 1.txt
diff --git a/1.txt b/1.txt
index c78c505..94954ab 100644
--- a/1.txt
+++ b/1.txt
@@ -1,2 +1,2 @@
-hello
+hello
world
# No, it didn't work, file is still considered modified.
# Let's try to revert for once more:
$ git checkout -- 1.txt
$ git status
modified: 1.txt
# Nothing. Let's use a magic command that prints wrongly committed files.
$ git grep -I --files-with-matches --Perl-regexp '\r' HEAD
HEAD:1.txt
2ème façon de reproduire: Dans le script ci-dessus, remplacer cette ligne:echo "*.txt -text" > .gitattributes
avecgit config core.autocrlf=false
et garder le reste des lignes tel quel
Qu'est-ce que tout ce qui précède dit? Un fichier texte peut (dans certaines circonstances) être commis avec CRLF, (par exemple -text
dans .gitattributes
ou core.autocrlf=false
).
Plus tard, lorsque nous voudrons traiter le même fichier en tant que texte (-text
-> text
), il devra être validé à nouveau.
Bien sûr, vous pouvez le retourner temporairement (comme corrigé correctement par Abu Assar ). Dans notre cas:
echo "*.txt -text" > .gitattributes
git checkout -- 1.txt
echo "*.txt text" > .gitattributes
_/La réponse est: voulez-vous vraiment le faire, car le problème sera toujours le même chaque fois que vous modifierez le fichier.
Pour mémoire:
Pour vérifier quels fichiers peuvent causer ce problème dans votre référentiel, exécutez la commande suivante (git doit être compilé avec --with-libpcre):
git grep -I --files-with-matches --Perl-regexp '\r' HEAD
En commettant le (s) fichier (s) (en supposant que vous souhaitiez les traiter comme du texte), vous remplissez les fonctions proposées dans ce lien http://help.github.com/line-endings/ pour résoudre ces problèmes. Mais, au lieu de supprimer .git/index
et d'exécuter reset
, vous pouvez simplement modifier le (s) fichier (s), puis exécuter git checkout -- xyz zyf
, puis valider.
Pour moi, le problème ne concernait pas les fins de ligne. Il s'agissait de changer la casse dans le nom du dossier (Reset_password -> Reset_Password). Cette solution m'a aidé: https://stackoverflow.com/a/34919019/1328513
Vous avez peut-être également eu un problème lié aux répertoires nommant des casses de lettres . Certains de vos collègues auraient pu changer le nom du répertoire myHandler to MyHandler . Si vous avez ensuite poussé et extrait certains des fichiers du répertoire d'origine, vous auriez eu 2 répertoires distincts sur le référentiel distant ET seulement un sur votre ordinateur local puisque sous Windows, vous ne pouvez en avoir qu’un seul. Et vous avez des problèmes.
Pour vérifier si c'est le cas, il suffit de voir si le référentiel distant a une double structure.
Pour résoudre ce problème, faites une copie de sauvegarde du répertoire parent en dehors du référentiel, puis supprimez le répertoire parent, puis appuyez dessus. Faites un pull (c'est ici que le second marqué comme supprimé doit apparaître dans le statut) et Poussez à nouveau . Après cela, recréez toute la structure à partir de votre sauvegarde et Poussez à nouveau les modifications.