| name | releasing-software |
| description | Release prep and tagging with pre-flight verification. Use when user says release, tag, ship it, push to production, create release, or bump version. Not for editing a version string outside a release, a lockfile or a changelog entry by hand, and not for reading what changed in a past release: those are ordinary edits, just do them. |
| compatibility | Requires gh CLI. Optional: goreleaser. |
ABOUTME: Release preparation skill with pre-flight verification, prevents retag-four-times pattern
ABOUTME: Invoked on "release", "tag", "ship it", "push to production"
Releasing Software
Iron Law
NO TAG WITHOUT GREEN CI
Run full verification locally → Fix everything → THEN tag. Never tag before CI passes.
Pre-Release Checklist
| Check | Items | Why |
|---|
| Build Paths | goreleaser.yml main:, workflows, Makefile, Dockerfile | Wrong path = build failure |
| Test Coverage | Every package has ≥1 test file | Go 1.23+ covdata fails without tests |
| Local CI | make test && make lint && make build | Catch failures before push |
| Docs | README.md, CHANGELOG.md, version refs | Professional releases |
| Release Config | goreleaser description, homepage URL, .gitignore | Proper artifact generation |
| Git State | git status, git diff --stat, git log | Clean history |
Release Procedure
Only after ALL checks pass:
- Commit:
git add -A && git commit -m "release: prepare vX.Y.Z"
- Wait for pre-commit hooks
- Push and WAIT:
git push origin main
- Check CI:
gh run list --limit 2
- Only after green:
git tag -a vX.Y.Z -m "vX.Y.Z" && git push origin vX.Y.Z
- Verify release workflow triggered
Red Flags - STOP IMMEDIATELY
- Tagging before CI completes
- "CI will probably pass"
- Deleting/recreating tags
- Force-pushing tags
Common Failures
| Symptom | Root Cause | Fix |
|---|
| "couldn't find main file" | Wrong goreleaser path | Set main: . if main.go at root |
| "no such tool 'covdata'" | Package without tests | Add _test.go with placeholder |
| Had to retag | Tagged before CI passed | WAIT FOR GREEN CI |
| Build fails but tests pass | Wrong build path | Check Makefile/goreleaser match |
Semver Quick Ref
- Patch (0.0.X): Bug fixes only
- Minor (0.X.0): New features, backwards compatible
- Major (X.0.0): Breaking changes
Troubleshooting
goreleaser check
goreleaser release --snapshot --clean
find . -type d -not -path "*/.*" -exec sh -c 'ls {}/*_test.go 2>/dev/null || echo "No tests: {}"' \;
Remember
Every retag erodes trust. Fix problems before tagging, not after.