Edición, 24 de noviembre de 2016: esta respuesta es aparentemente popular, así que agrego una nota aquí. Si reemplazas una etiqueta en un servidor central, cualquiera que tenga la edad de marcado y cualquier clon de ese repositorio-servidor central que ya tiene la etiqueta-podría retener su antigua etiqueta . Entonces, si bien esto te dice cómo hacerlo, asegúrate de que quieres hacerlo. Deberá hacer que todos los que ya tienen la etiqueta "incorrecta" eliminen su "etiqueta incorrecta" y reemplazarla con la nueva "etiqueta correcta".
Las pruebas en Git 2.10 / 2.11 muestran que retener la etiqueta anterior es el comportamiento predeterminado para los clientes que se ejecutan git fetch
, y la actualización es el comportamiento predeterminado para los clientes que se ejecutan git fetch --tags
.
(La respuesta original sigue.)
Cuando solicita insertar etiquetas, git push --tags
envía (junto con las confirmaciones y otros objetos necesarios y cualquier otra actualización de referencia desde la configuración de inserción) al remoto una solicitud de actualización del formulario . (Bueno, envía muchos: uno para cada etiqueta).new-sha1 refs/tags/name
El control remoto modifica la solicitud de actualización para agregar un old-sha1
(o de nuevo, uno para cada etiqueta), luego se entrega a los ganchos de pre-recepción y / o actualización (los que existan en el control remoto). Esos ganchos pueden decidir si permitir o rechazar la etiqueta crear / eliminar / actualizar.
El old-sha1
valor es SHA-1 "nulo" todo ceros si se está creando la etiqueta. El new-sha1
es el SHA-1 nulo si se elimina la etiqueta. De lo contrario, ambos valores SHA-1 son valores reales y válidos.
Incluso sin ganchos, hay una especie de "gancho incorporado" que también se ejecuta: el control remoto se negará a mover una etiqueta a menos que use la bandera "forzar" (aunque el "gancho incorporado" siempre está bien con ambos "agregar" y "eliminar"). El mensaje de rechazo que estás viendo proviene de este gancho incorporado. (Por cierto, este mismo gancho incorporado también rechaza las actualizaciones de sucursales que no son de avance rápido). 1
Pero, aquí está una de las claves para entender lo que está sucediendo, el git push
paso no tiene idea de si el control remoto tiene esa etiqueta ahora y, de ser así, qué valor tiene SHA-1. Solo dice "aquí está mi lista completa de etiquetas, junto con sus valores SHA-1". El control remoto compara los valores y, si hay adiciones y / o cambios, ejecuta los ganchos en ellos. (Para las etiquetas que son iguales, no hace nada en absoluto. Para las etiquetas que no tienes que tienen, ¡tampoco hace nada!)
Si elimina la etiqueta localmente, entonces push
su inserción simplemente no transfiere la etiqueta. El control remoto supone que no se deben realizar cambios.
Si elimina la etiqueta localmente, créela apuntando a un lugar nuevo, luego push
, su inserción transfiere la etiqueta, y el control remoto ve esto como un cambio de etiqueta y rechaza el cambio, a menos que sea una inserción forzada.
Por lo tanto, tiene dos opciones:
- hacer un empuje forzado, o
- Eliminar la etiqueta en el control remoto.
Esto último es posible a través de git push
2 aunque eliminar la etiqueta localmente e push
ing no tiene ningún efecto. Suponiendo que el nombre del control remoto es origin
, y la etiqueta que desea eliminar es dev
:
git push origin :refs/tags/dev
Esto le pide al control remoto que elimine la etiqueta. La presencia o ausencia de la etiqueta dev
en su repositorio local es irrelevante; Este tipo de push
, con una especificación de referencia, es un push de eliminación pura.:remoteref
El control remoto puede o no permitir la eliminación de etiquetas (dependiendo de los ganchos adicionales agregados). Si permite la eliminación, la etiqueta desaparecerá y, un segundo git push --tags
, cuando tenga una dev
etiqueta local que apunte a algún objeto de confirmación de etiqueta anotada, envíe su nueva dev
etiqueta. En el control remoto, dev
ahora será una etiqueta recién creada, por lo que el control remoto probablemente permitirá el empuje (nuevamente, esto depende de cualquier gancho adicional agregado).
La fuerza de empuje es más simple. Si desea asegurarse de no actualizar nada más que la etiqueta, solo dígale git push
que inserte solo esa especificación de referencia:
git push --force origin refs/tags/dev:refs/tags/dev
(nota: no es necesario --tags
si está empujando explícitamente solo una etiqueta ref-spec).
1 Por supuesto, la razón de este enlace incorporado es ayudar a reforzar el comportamiento que otros usuarios del mismo repositorio remoto esperan: que las ramas no se rebobinan y las etiquetas no se mueven. Si presiona a la fuerza, debe informar a los demás usuarios que está haciendo esto, para que puedan corregirlo. Tenga en cuenta que "las etiquetas no se mueven en absoluto" es una nueva aplicación de Git 1.8.2; versiones anteriores permitirían que la etiqueta "avance" en el gráfico de confirmación, al igual que los nombres de rama. Ver las notas de lanzamiento de git 1.8.2 .
2 Es trivial si puede iniciar sesión en el control remoto. Simplemente vaya al repositorio de Git allí y ejecute git tag -d dev
. Tenga en cuenta que de cualquier manera, eliminando la etiqueta en el control remoto o utilizándola git push
para eliminarla, hay un período de tiempo en el que cualquiera que acceda al control remoto encontrará que dev
falta la etiqueta. (Seguirán teniendo su propia etiqueta anterior, si ya la tienen, e incluso podrían volver a colocar su etiqueta anterior antes de que pueda presionar la nueva).