mixed-tags
history
lightweight tag (v0.1.0), annotated tag (v1.0.0), and a tag pointing at a tree object (tree-snapshot)
Description
Three commits carry three tag shapes:
v0.1.0 lightweight tag — a named ref pointing directly at the
first commit; no tag object is created.
v1.0.0 annotated tag — a full tag object that stores the tagger
identity, timestamp, and release message. This is what
`git describe` resolves and what release tooling signs.
tree-snapshot lightweight tag — points at the tree object of HEAD rather
than a commit. Uncommon but valid; some tag-parsing tools
handle this case incorrectly.
Detecting the tag type:
git cat-file -t v0.1.0 → commit (lightweight: resolves to commit)
git cat-file -t v1.0.0 → tag (annotated: is a tag object)
git cat-file -t tree-snapshot → tree (unusual: points at a tree)
Useful for testing:
- Distinguishing annotated vs lightweight tags (`git cat-file -t`)
- `git describe` behaviour (only annotated tags by default)
- Tag-listing and sorting (by date, semver, name)
- Edge-case handling for tags that point at non-commit objects Contracts
- main is checked out
- main has 3 commits
- v0.1.0 is a lightweight tag pointing at HEAD~2 (git cat-file -t → commit)
- v1.0.0 is an annotated tag object pointing at HEAD (git cat-file -t → tag)
- tree-snapshot is a lightweight tag pointing at a tree object (git cat-file -t → tree)
- worktree is clean
Tags
Branches
main Use it
import { spinUpScenario } from '@gfargo/git-scenarios'
const repo = await spinUpScenario('mixed-tags') npx git-scenarios create mixed-tags import { describeWithScenario } from '@gfargo/git-scenarios/jest'
describeWithScenario('mixed-tags', (getRepo) => {
it('should have the expected state', async () => {
const repo = getRepo()
// your assertions here
})
}) Commit graph
* bbd015e (HEAD -> main, tag: v1.0.0) feat: stable release
* f207e93 feat: v0.1.0 content
* 7520170 (tag: v0.1.0) chore: initial