Comment supprimer une balise distante?


3422

Comment supprimer une balise Git qui a déjà été poussée?

Réponses:


5756

Il vous suffit de pousser une référence «vide» au nom de la balise distante:

git push origin :tagname

Ou, plus expressivement, utilisez l' --deleteoption (ou -dsi votre version git est antérieure à 1.8.0):

git push --delete origin tagname

Notez que git a un espace de noms de balise et un espace de noms de branche, vous pouvez donc utiliser le même nom pour une branche et pour une balise. Si vous voulez vous assurer que vous ne pouvez pas supprimer accidentellement la branche au lieu de la balise, vous pouvez spécifier une référence complète qui ne supprimera jamais une branche:

git push origin :refs/tags/tagname

Si vous devez également supprimer la balise locale, utilisez:

git tag --delete tagname

Contexte

Pousser une branche, une balise ou une autre référence vers un référentiel distant implique de spécifier "quel dépôt, quelle source, quelle destination?"

git push remote-repo source-ref:destination-ref

Un exemple réel où vous poussez votre branche principale vers la branche principale d'origine est:

git push origin refs/heads/master:refs/heads/master

Qui, en raison des chemins par défaut, peut être raccourci en:

git push origin master:master

Les balises fonctionnent de la même manière:

git push origin refs/tags/release-1.0:refs/tags/release-1.0

Qui peut également être raccourci en:

git push origin release-1.0:release-1.0

En omettant la référence source (la partie avant les deux points), vous poussez «rien» vers la destination, supprimant la référence à l'extrémité distante.


187
+1 pour répondre à la question et expliquer le cas général, et détailler le sens de la syntaxe intégrale
Peter Host

77
Et juste au cas où quelqu'un se demanderait comment supprimer plusieurs balises à la fois, vous les listez simplement en utilisant un espace blanc, par exemple git push --delete origin tag1 tag2. Il en va de même pour la suppression des balises localesgit tag -d tag1 tag2
dVaffection

8
Si le nom du tag entre en collision avec un nom de branche, vous risquez de supprimer votre branche. Ha-ha. Voir la deuxième réponse - c'est plus écologique
zuba

1
@EmmaHe A tagest attaché à un seul commit uniquement. Pour cette raison, le nom de la branche n'est pas pertinent.
cb2

1
Il est également intéressant de savoir que git tag -d `git tag`cela supprimera toutes les balises locales. Il en va de même git push --delete origin `git tag`si vous avez tiré les balises distantes localement. C'était pratique dans un environnement de test.
DarkFranX

383

Une manière plus simple est

git push --delete origin YOUR_TAG_NAME

La syntaxe de préfixe IMO du côlon est un peu étrange dans cette situation


4
Je pense que c'est la bonne façon ... d'autres syntaxes ressemblent plus à des hacks pour moi.
Luigi R. Viggiano

11
Oui, c'est simple et ça marche. Bien que je clarifie la réponse en spécifiant quelle est la partie variable git push --delete origin "TAGNAME":, où TAGNAME est le nom de la balise d'origine.
Teemu Leisti

12
Cela marche. Un ajout: si vous avez une branche et une balise du même nom, vous pouvez mettre le mot tagavant le nom de votre balise pour vous assurer d'obtenir la balise, pas la branche.
andypaxo

9
@andypaxo Qu'est - ce que la commande prend est refspecs, la manière correcte serait préfixant les balises avec refs/tags/, comme ceci: refs/tags/v2.3.1.
p3lim

J'ai eu un 'mauvais' nom de balise créé sur le serveur distant d'une manière ou d'une autre, qui avait des caractères spéciaux, donc je ne peux pas me synchroniser avec cela, alors supprimez simplement cela avec votre suggestion: git push --delete origin "service-- <default> - 151 ", ne peut pas le supprimer ni avec intellij, ni avec stash, ni avec sourceTree. Merci !
Dmitri Algazin

215

Si vous avez une balise distante v0.1.0à supprimer, et votre télécommande l'est origin, alors:

git push origin :refs/tags/v0.1.0

Si vous devez également supprimer la balise localement:

git tag -d v0.1.0

Voir la réponse d' Adam Franco pour une explication de la :syntaxe inhabituelle de Git pour la suppression.


2
cela fonctionne également avec jgit. le raccourci: tag ne fonctionne pas avec jgit
rynop

J'ai fatal: remote part of refspec is not a valid name in :/refs/tags/0.0.1...?
Chaim Eliyah

3
@ChaimEliyah vous avez une barre oblique, c'est peut-être votre problème
Joffrey

5
Meilleure réponse, car cela fonctionne également si vous avez une branche et une balise qui s'appellent les mêmes.
Erik A. Brandstadmoen

Devrait juste :tagnamefonctionner pour la suppression à distance.
Acumenus

106

Supprimez toutes les balises locales et obtenez la liste des balises distantes :

git tag -l | xargs git tag -d
git fetch

Supprimer toutes les balises distantes

git tag -l | xargs -n 1 git push --delete origin

Nettoyer les balises locales

git tag -l | xargs git tag -d

2
Comment supprimer toutes les balises des référentiels local et distant. C'est ce que je cherchais, merci!
Jorge Orpinel

git fetch, supprimer la télécommande puis nettoyer les locaux, a fonctionné à merveille!
DiegoRBaquero

lent, mais le plus simple
Lucent Fox

34

Pour supprimer la balise du référentiel distant:

git push --delete origin TAGNAME

Vous pouvez également supprimer la balise localement:

git tag -d TAGNAME

donc une ligne pour faire les deux:git push --delete origin TAGNAME && git tag -d TAGNAME
sakurashinken

25

Depuis votre terminal, procédez comme suit:

git fetch
git tags
git tag -d {tag-name}
git push origin :refs/tags/{tag-name}

Maintenant, allez sur Github.com et rafraîchissez-vous, ils disparaissent.


3
git tag not tags
DSF

23
git tag -d your_tag_name
git push origin :refs/tags/your_tag_name
  1. Première ligne, supprime your_tag_namedu dépôt local .
  2. Deuxième ligne, supprime your_tag_namedu référentiel distant .
  3. Appuyez sur le bouton Supprimer le brouillon dans la section Versions de GitHub .

entrez la description de l'image ici


2
Bien que cette commande puisse répondre à la question, fournir un contexte supplémentaire concernant pourquoi et / ou comment ce code répond à la question améliore sa valeur à long terme. Comment répondre
Popo

20

Supprimer la balise locale '12345'

git tag -d 12345

Supprimer la balise distante '12345' (par exemple, la version GitHub aussi)

git push origin :refs/tags/12345

approche alternative

git push --delete origin tagName
git tag -d tagName

entrez la description de l'image ici


15

Notez juste que, si vous avez une branche distante nommée comme balise distante, ces commandes sont ambiguës:

git push origin :tagname
git push --delete origin tagname

Vous devez donc utiliser cette commande pour supprimer la balise:

git push origin :refs/tags/<tag>

et celui-ci pour supprimer la branche:

git push origin :refs/heads/<branch>

Sinon, vous obtiendrez une erreur comme celle-ci:

error: dst refspec <tagname> matches more than one.
error: failed to push some refs to '<repo>'

Court et concis. Ce message et celui de MeganZhou sont apparus comme étant la réponse à la raison pour laquelle nous avions des problèmes, le nom de la branche et le nom de la balise étaient identiques. J'ai supprimé le tag local et poussé vers: refs / tags et tout allait bien.
rwheadon

12

Méthode jusqu'à 100 fois plus rapide pour des milliers de balises distantes

Après avoir lu ces réponses tout en devant supprimer plus de 11 000 balises, j'ai appris que ces méthodes s'appuient ou xargsprennent beaucoup trop de temps, sauf si vous avez des heures à graver.

En difficulté, j'ai trouvé deux moyens beaucoup plus rapides. Pour les deux, commencez par git tagou git ls-remote --tagspour faire une liste des balises que vous souhaitez supprimer sur la télécommande. Dans les exemples ci-dessous, vous pouvez omettre ou remplacer sorting_proccessing_etcpar tout greping, sorting, tailing ou heading que vous souhaitez ( par exemple, grep -P "my_regex" | sort | head -n -200 etc. ):


Cette première méthode est de loin la plus rapide, peut-être 20 à 100 fois plus rapide que l'utilisation xargs, et fonctionne avec au moins plusieurs milliers de balises à la fois.

git push origin $(< git tag | sorting_processing_etc \
| sed -e 's/^/:/' | paste -sd " ") #note exclude "<" for zsh

Comment cela marche-t-il? La liste normale de balises séparées par des lignes est convertie en une seule ligne de balises séparées par des espaces, chacune étant précédée de :cela. . .

tag1   becomes
tag2   ======>  :tag1 :tag2 :tag3
tag3

L'utilisation git pushde cette balise format ne pousse rien dans chaque référence distante, l'effaçant (le format normal pour pousser de cette façon est local_ref_path:remote_ref_path).

La deuxième méthode est divisée en une réponse distincte ailleurs sur cette même page


Après ces deux méthodes, vous souhaiterez probablement également supprimer vos balises locales. C'est beaucoup plus rapide, nous pouvons donc recommencer à utiliser xargset git tag -d, ce qui est suffisant.

git tag | sorting_processing_etc | xargs -L 1 git tag -d

OU similaire à la suppression à distance:

git tag -d $(< git tag | sorting_processing_etc | paste -sd " ")

Vous devez diviser cela en plusieurs réponses différentes. La réponse avec plusieurs balises sur une ligne est, sans aucun doute, la bonne réponse pour la suppression de balises en bloc. Il est en fait un peu difficile de trouver ces informations presque partout ailleurs. Même en sachant ce que je recherche, j'ai du mal à le trouver dans la page d'aide de git :) Alors bravo à vous et mettez cela en évidence comme bonne réponse, et déplacez l'API GitHub à un endroit différent. Et enfin, la suppression des balises localement, en vrac, fonctionne avec des balises délimitées par des espaces (se débarrasser des deux points)
CubanX

Merci pour les éloges et suggestions. Je vais diviser cela. Je ne comprends pas votre commentaire sur la suppression de balises locales. Je ne pense pas que mon extrait de commande final utilise des deux-points, mais je suis sur mobile, il me manque donc peut-être quelque chose.
TonyH

Désolé, je voulais simplement dire que ce que vous faites pour supprimer des balises distantes fonctionne avec la suppression de balises locales, en fournissant la liste entière en une seule fois. :) Juste au lieu de git push origin: tag1: tag2 etc. vous feriez git tag --delete tag1 tag2 tag3 de cette façon, vous pouvez avoir un nettoyage total. Encore une fois, merci beaucoup!
CubanX

11

Si vous utilisez SourceTree - une excellente interface graphique Git - vous pouvez facilement le faire sans la ligne de commande en procédant comme suit:

  1. Ouvrez votre référentiel dans SourceTree
  2. Sélectionnez et développez l'onglet "Tags" à gauche
  3. Faites un clic droit sur la balise que vous souhaitez supprimer
  4. Sélectionnez "Supprimer YOUR_TAG_NAME"
  5. Dans la fenêtre de vérification, sélectionnez "Supprimer la balise des télécommandes"

YOUR_TAG_NAME sera désormais supprimé de votre référentiel local et de toutes les télécommandes - que ce soit GitHub, BitBucket ou partout ailleurs que vous avez répertorié en tant que télécommande pour ce référentiel.

De plus, si vous avez supprimé une balise localement mais pas sur les origines distantes et que vous souhaitez la supprimer partout, créez simplement une nouvelle balise qui porte le même nom et est attachée au même commit que les origines. Ensuite, répétez les étapes ci-dessus pour supprimer partout.


Fonctionne comme un charme. Merci!
Native_Mobile_Arch_Dev


7

Si vous utilisez PowerShell et que vous souhaitez en supprimer un tas:

# Local tags:
git tag -l | foreach { git tag -d $_ }

# Remote tags:
git tag -l | foreach { git push --delete origin $_ }

Bien sûr, vous pouvez également les filtrer avant de les supprimer:

git tag -l | Where-Object { $_ -like "build-*" } | foreach { git tag -d $_ }

C'était un bon exemple d'expression régulière. Merci bon monsieur
Yunus

7

Comme l'a suggéré @CubanX, j'ai séparé cette réponse de mon original:

Voici une méthode qui est plusieurs fois plus rapide xargset peut évoluer beaucoup plus avec le peaufinage. Il utilise l' API Github , un jeton d'accès personnel, et exploite l'utilitaire parallel.

git tag | sorting_processing_etc | parallel --jobs 2 curl -i -X DELETE \ 
https://api.github.com/repos/My_Account/my_repo/git/refs/tags/{} -H 
\"authorization: token GIT_OAUTH_OR_PERSONAL_KEY_HERE\"  \
-H \"cache-control: no-cache\"`

parallelpossède de nombreux modes de fonctionnement, mais met généralement en parallèle toutes les commandes que vous lui donnez tout en vous permettant de définir des limites sur le nombre de processus. Vous pouvez modifier le --jobs 2paramètre pour permettre un fonctionnement plus rapide, mais j'ai eu des problèmes avec les limites de débit de Github , qui sont actuellement de 5000 / heure, mais semblent également avoir une limite à court terme non documentée.


Après cela, vous voudrez probablement aussi supprimer vos balises locales. C'est beaucoup plus rapide, nous pouvons donc recommencer à utiliser xargset git tag -d, ce qui est suffisant.

git tag | sorting_processing_etc | xargs -L 1 git tag -d

Cela semble beaucoup plus compliqué que l'answe accepté. Quel est l'avantage?
theUtherSide

2
Si vous devez supprimer plusieurs milliers de balises, la vitesse est 10 à 100 fois plus rapide
TonyH

Merci d'avoir clarifié. L'OP a demandé la suppression d'une seule balise. Je ne pouvais pas imaginer pourquoi quelqu'un utiliserait cette approche pour une seule balise. Peut-être que cette réponse est meilleure pour une autre question impliquant la suppression de nombreuses balises
theUtherSide

Je ne pense pas que cela existe. Je pourrais le créer pour me répondre. Voulez-vous penser que c'est approprié?
TonyH

1
Je fais! Je pense que c'est une pratique assez courante ici, en fait.
theUtherSide

6

Les autres réponses indiquent comment y parvenir, mais vous devez garder à l'esprit les conséquences car il s'agit d'un référentiel distant.

La page de manuel git tag, dans la section On Retagging , explique bien comment informer courtoisement les autres utilisateurs du dépôt distant du changement. Ils donnent même un modèle d'annonce pratique pour communiquer comment les autres devraient obtenir vos modifications.


6

Je voulais supprimer toutes les balises à l'exception de celles qui correspondent à un modèle afin de pouvoir supprimer toutes les balises de production, à l'exception des deux derniers mois, voici ce que j'ai utilisé avec beaucoup de succès:

Supprimer toutes les balises distantes et exclure l'expression de la suppression

git tag -l | grep -P '^(?!Production-2017-0[89])' | xargs -n 1 git push --delete origin

Supprimer toutes les balises locales et exclure l'expression de la suppression

git tag -l | grep -P '^(?!Production-2017-0[89])' | xargs git tag -d

5

Script simple pour supprimer la balise donnée des emplacements locaux et d'origine. Avec une vérification si la balise existe vraiment.

if [ $(git tag -l "$1") ]; then
    git tag --delete  $1
    git push --delete origin $1

    echo done.
else
    echo tag named "$1" was not found
fi

Comment utiliser:

  • Créez un fichier de script shell (par exemple git-tag-purge.sh) et collez le contenu.
  • chmodez votre fichier de script pour le rendre exécutable.
  • Rendre le script disponible à l'échelle mondiale
  • cd à votre projet git
  • Script d'appel (par exemple
    $> git-tag-purge.sh nom_tag
    )

4

Il semble que beaucoup de travail soit xargsdéjà accompli. En regardant à travers ce fil, je suppose que la lenteur avec xargslaquelle vous avez vécu est parce que la réponse originale a été utilisée xargs -n 1alors qu'elle n'en avait pas vraiment besoin.

C'est équivalent à votre méthode, sauf qu'elle xargstraite automatiquement la longueur maximale de la ligne de commande:

git tag | sorting_processing_etc | xargs git push --delete origin

xargspeut également exécuter des processus en parallèle. Méthode 2 avec xargs:

git tag | sorting_processing_etc | xargs -P 5 -n 100 git push --delete origin

Ce qui précède utilise un maximum de 5 processus pour gérer un maximum de 100 arguments dans chaque processus. Vous pouvez expérimenter avec les arguments pour trouver ce qui fonctionne le mieux pour vos besoins.


Intéressant. Chaque jour, vous apprenez quelque chose de nouveau sur une commande Unix. Je devrai tester mon cas d'utilisation avec cette alternative.
TonyH

4

Si vous avez créé une balise commençant par le caractère # , par exemple #ST002, vous pourriez constater que vous ne pouvez pas supprimer en utilisant des modèles normaux. c'est à dire

git tag -d #STOO2

Ne supprimera pas la balise, mais l'enveloppera dans un String Literal comme ceci

git tag -d "#ST002" or git tag -d '#ST002'

Cela le supprimera. En espérant que cela aidera quelqu'un qui a fait l'erreur d'utiliser # pour écrire les noms des balises.


2

Voici un testcase local pour le tester localement sans jouer avec une télécommande:

~/p $ mkdir gittest    
~/p/git $ cd gittest/
~/p/gittest $ git init
Initialized empty Git repository in /Users/local_user/p/gittest/.git/
 ~/p/gittest $ touch testfile.txt
 ~/p/gittest $ git add testfile.txt
 ~/p/gittest $ git commit -m "initial commit"
[master (root-commit) 912ce0e] initial commit
 1 file changed, 0 insertions(+), 0 deletions(-)
 create mode 100644 testfile.txt
 ~/p/gittest $ git tag
 ~/p/gittest $ git tag -a testtag
 ~/p/gittest $ git tag
testtag
 ~/p/gittest $ git show-ref
912ce0e40635c90241fdab756dce7ea34938de57 refs/heads/master
b0a6c15cabb990e6d6c46f762891b63608d962f3 refs/tags/testtag
 ~/p/gittest $ cd ..
 ~/p $ mkdir gitbare
 ~/p $ cd gitbare
 ~/p/gitbare $ git init --bare
Initialized empty Git repository in /Users/local_user/p/gitbare/
 ~/p/gitbare $ cd ..
 ~/p $ cd gittest/
 ~/p/gittest $ git remote add origin /Users/local_user/p/gitbare
 ~/p/gittest $ git push -u origin master
Counting objects: 3, done.
Writing objects: 100% (3/3), 215 bytes | 215.00 KiB/s, done.
Total 3 (delta 0), reused 0 (delta 0)
To /Users/local_user/p/gitbare
 * [new branch]      master -> master
Branch 'master' set up to track remote branch 'master' from 'origin'.
 ~/p/gittest $ git push origin testtag
Counting objects: 1, done.
Writing objects: 100% (1/1), 163 bytes | 163.00 KiB/s, done.
Total 1 (delta 0), reused 0 (delta 0)
To /Users/local_user/p/gitbare
 * [new tag]         testtag -> testtag
 ~/p/gittest $ git show-ref
912ce0e40635c90241fdab756dce7ea34938de57 refs/heads/master
912ce0e40635c90241fdab756dce7ea34938de57 refs/remotes/origin/master
b0a6c15cabb990e6d6c46f762891b63608d962f3 refs/tags/testtag
 ~/p/gittest $ git push -d origin testtag
To /Users/local_user/p/gitbare
 - [deleted]         testtag
 ~/p/gittest    git tag -d testtag
Deleted tag 'testtag' (was b0a6c15)
 ~/p/gittest $ git show-ref
912ce0e40635c90241fdab756dce7ea34938de57 refs/heads/master
912ce0e40635c90241fdab756dce7ea34938de57 refs/remotes/origin/master
 ~/p/gittest

1

Salut, je voulais juste partager un alias que j'ai créé qui fait la même chose:

Ajoutez ce qui suit à votre ~ / .gitconfig

[alias]
    delete-tag = "!f() { \
            echo 'deleting tag' $1 'from remote/origin ausing command: git push --delete origin tagName;'; \
            git push --delete origin $1; \
            echo 'deleting tag' $1 'from local using command: git tag -d tagName;'; \
            git tag -d $1; \
        }; f"

L'utilisation ressemble à:

-->git delete-tag v1.0-DeleteMe
deleting tag v1.0-DeleteMe from remote/origin ausing command: git push --delete origin tagName;
To https://github.com/jsticha/pafs
 - [deleted]             v1.0-DeleteMe
deleting tag v1.0-DeleteMe from local using command: git tag -d tagName;
Deleted tag 'v1.0-DeleteMe' (was 300d3ef22)
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.