Skip to content

Renaming a Git Tag

Git does not have a rename command for tags. There is no git tag --move or git tag --rename. Tags are immutable references; once created, you cannot change the name of one without creating a new one and removing the old one.

That leaves developers in an awkward position when a tag carries the wrong name. You tagged v2.1.7 as release-2.1.7. The project switched from a release-X.Y.Z convention to vX.Y.Z. A typo slipped through before the push. Whatever the reason, the tag exists in both local and remote repositories, and it needs to be renamed.

The process takes four commands, and each one does a specific job.

The Four Commands

git tag v2.1.7 release-2.1.7

git tag -d release-2.1.7

git push origin v2.1.7 :release-2.1.7

git pull --prune --tags

1. Create the New Tag

git tag v2.1.7 release-2.1.7

This creates a new lightweight tag, v2.1.7, pointing at the same commit as the existing tag release-2.1.7. The second argument tells Git which commit, tag, or ref to point at. Because tags resolve to commits, this is equivalent to running git tag v2.1.7 <commit-sha>.

At this point, both tags exist locally. Nothing has been pushed or deleted yet.

2. Delete the Old Local Tag

git tag -d release-2.1.7

This removes the local release-2.1.7 tag. The -d flag deletes by name. The tag is now gone from your local repository but still exists on the remote.

3. Push the New Tag and Delete the Remote Tag

git push origin v2.1.7 :release-2.1.7

This command does two things in one step. v2.1.7 pushes the new tag to the remote. :release-2.1.7 deletes the remote tag by pushing an empty reference to it. The colon-prefixed syntax, :<refname>, is Git's way of saying "push nothing to this ref," which instructs the remote to delete it.

The combined form is equivalent to running:

git push origin v2.1.7
git push origin --delete release-2.1.7

Either form works. The combined form makes the intent clear: this is a rename operation, not two unrelated push operations.

4. Sync the Local Repository

git pull --prune --tags

With the remote updated, pulling with --prune --tags removes stale remote-tracking references and fetches the current set of tags from the remote. This keeps your local repository consistent with the state of the remote after the rename and is particularly useful after operations that delete remote refs.

Collaborators who already fetched release-2.1.7 before the rename can run the same command to clean up their local state:

git fetch --prune --prune-tags

--prune-tags explicitly removes any local tags that no longer exist on the remote, which handles the stale release-2.1.7 reference directly.

Lightweight vs. Annotated Tags

The steps above handle lightweight tags, where a tag is simply a named reference to a commit. Annotated tags carry additional metadata: a tagger name, email, date, and message. They are stored as full objects in the Git object database and are the appropriate choice for release tags.

If release-2.1.7 is an annotated tag, git tag v2.1.7 release-2.1.7 creates a lightweight tag pointing at the same commit. The annotation from the old tag is not carried over.

To verify whether an existing tag is annotated or lightweight:

git cat-file -t release-2.1.7

If the output is tag, it is annotated. If the output is commit, it is lightweight.

To create a new annotated tag that points to the same commit as an annotated source tag, dereference the tag to its underlying commit first:

git tag -a v2.1.7 -m "Release 2.1.7" release-2.1.7^{}

The ^{} suffix dereferences the tag object to the commit it points to. This ensures the new annotated tag points directly to the commit rather than to the old tag object.

Signing Release Tags

If your project signs release tags with GPG, sign the new annotated tag using -s instead of -a:

git tag -s v2.1.7 -m "Release 2.1.7" release-2.1.7^{}

For GPG key setup, signing configuration, and verified badges on GitHub and GitLab, see Signing Your Git Commits: From Zero to Verified.

Coordinating With Others

Tag deletion and re-creation rewrites shared history for anyone who already has the old tag. Unlike branch changes, deleted tags do not propagate automatically on git pull. Every collaborator who fetched release-2.1.7 before the change will still have it locally until they explicitly clean up.

Communicate the rename to anyone working in the repository. They can remove the stale tag and pull the replacement:

git fetch --prune --prune-tags

Or step through the full sequence themselves if they also pushed the old tag from their own machine.

Automation and CI/CD Pipelines

If the repository has CI/CD pipelines, release workflows, or tooling that references the old tag name, update those references before or immediately after the rename. A deleted remote tag may trigger unexpected behavior in workflows that poll for new tags, filter by naming convention, or trigger on tag push events.

References