Quand utiliser la barre oblique principale dans gitignore

108

J'essaie de comprendre plus clairement la .gitignoresyntaxe, et en particulier en ce qui concerne https://github.com/github/gitignore gitignores.

Je vois que la barre oblique principale est utilisée pour ne faire correspondre que les chemins d'accès relatifs à l'emplacement du .gitignorefichier (à partir de http://git-scm.com/docs/gitignore ):

Une barre oblique principale correspond au début du chemin. Par exemple, "/*.c" correspond à "cat-file.c" mais pas à "mozilla-sha1 / sha1.c".

Mais que se passe-t-il lorsque je supprime la barre oblique principale? D'après ce que j'ai compris, il y a deux cas:

  1. Si le modèle ne contient pas de barre oblique (ou s'il contient uniquement une barre oblique à la fin, ce qui signifie qu'il doit correspondre à un répertoire), la recherche est effectuée dans toute l'arborescence de répertoires. Par exemple, le modèle dir/correspondra <root>/dir, <root>/a/dir, <root>/a/b/c/.../dir, etc., où <root>est l'emplacement du .gitignorefichier.
  2. Si le modèle contient une barre oblique, qui n'est pas en position de fin (ce n'est pas le dernier caractère), alors il n'est mis en correspondance qu'avec les chemins d'accès relatifs à l' .gitignoreemplacement du fichier.

Voici les exemples que j'ai faits pour vérifier ce comportement:

# Directory structure:
<root>
├─ dir/
│   └─ test
├─ src/
│   ├─ dir/
│   │   └─ test
test file is there only because Git does not track empty directories.

Premier test:

# .gitignore
dir/

# git status
nothing to commit

Donc Git ignore les deux dirrépertoires. Ceci est cohérent avec le cas numéro 1: le modèle n'a pas de barres obliques (à l'exception de la dernière), donc Git surveille toute l'arborescence de répertoires, ignorant tout ce qui correspond au modèle.

Deuxième test:

# .gitignore
/dir/

# git status
Untracked files:
    src/

Ici, Git ignore uniquement le dirrépertoire directement sous le répertoire racine, grâce à la barre oblique principale dans le modèle.

Troisième test:

# .gitignore
dir/*

# git status
Untracked files:
    src/

Ceci est cohérent avec le cas numéro 2: le motif a une barre oblique à l'intérieur, il est donc considéré comme un chemin à partir du répertoire racine.

Il est maintenant temps pour la vraie question. Considérons ce fichier gitignore : lorsqu'ils ignorent le répertoire downloader/, par exemple, n'ignorent- ils pas réellement tous les downloaderrépertoires trouvés dans toute l'arborescence de répertoires? C'est ce que je suis poussé à penser depuis ce que j'ai vu sur le fonctionnement de Git auparavant.

Donc, si j'ai un module personnalisé avec un downloaderrépertoire à l'intérieur de celui-ci, sera-t-il ignoré de manière inattendue ainsi que le module normal à la racine de Magento? C'est un peu une question réthorique car cela m'est déjà arrivé, produisant un bogue vraiment difficile à trouver.

Donc, dans le .gitignorefichier Magento (auquel je ne fais référence qu'à titre d'exemple, btw), beaucoup de modèles contiennent des barres obliques, donc ils sont correctement mis en correspondance avec les noms de chemin à partir de la racine, mais il y a quelques cas, comme downloader/ou errors/ça , si je ne me trompe pas, sont potentiellement dangereux et devraient probablement être remplacés par /downloader/et /errors/.

En tant que question plus générale, dois-je toujours utiliser la barre oblique principale pour les modèles ne contenant pas de barres obliques (à l'exception de la barre oblique finale) lorsque je veux sélectionner un chemin d'accès explicitement à partir de la racine, et ne pas l'utiliser pour les modèles contenant des barres obliques, ou devrais-je utilisez toujours la barre oblique principale pour plus de clarté? Qu'est-ce que tu en penses?

Merci d'avoir lu et désolé pour le long message.

swahnee
la source
8
Excellente question et très belle explication, cela m'a également dérangé et vos recherches m'ont clarifié les choses. Après avoir lu ceci, je dirais que c'est une bonne pratique de toujours commencer les chemins avec une barre oblique s'ils doivent commencer à partir de la racine, cela rend l'intention plus évidente.
Martinsos
4
Merci :) Je suis d'accord avec votre remarque sur l'utilisation de barres obliques pour rendre les intentions plus explicites.
swahnee
8
Cela devrait faire partie de la documentation .gitignore. Beaucoup plus facile à comprendre!
rmorrin le
J'adorerais voir ce super article divisé en sections de questions et réponses ...
Barett

Réponses:

25

Je voulais juste résumer pour une éventuelle référence future rapide - la barre oblique principale ancre la correspondance à la racine. Ainsi, dans l'exemple ci-dessous, sans la barre oblique, le caractère générique exclurait également tout ce qui se trouve dans foo car il prendrait *et se déplacerait récursivement vers le bas de l'arbre. Cependant, avec /*, il exclut tout sauf le dossier foo et son contenu:

$ cat .gitignore
/*
!/foo
solstice333
la source
24

Vous avez entièrement répondu à votre propre question. Si vous regardez de plus près le référentiel github / gitignore, vous verrez que la plupart des fichiers utilisent des règles incohérentes sur l'écriture des modèles; il est très probable que la plupart aient été fournis par des personnes qui n'ont pas pris la peine de lire la documentation ni de tester les choses comme vous l'avez fait.

Donc, si cela aide: vous avez raison, soyez confiant.

Si vous constatez des erreurs dans des projets collaboratifs comme celui-ci, n'hésitez pas à apporter vos connaissances. Il existe même un précédent si vous avez besoin de renforcer votre confiance.

tne
la source