← Back to Home

How to Write Clean Git Commit Messages

Updated January 14, 2026
gitcommit messagesconventional commitshygiene

Writing Clean Git Commit Messages

Good commit messages help teams understand code changes and project history.

Conventional Commits Format

<type>(<scope>): <subject>

<body>

<footer>

Types

Type Description Example
feat New feature feat(auth): add OAuth2 support
fix Bug fix fix(player): prevent audio overlap
docs Documentation docs(readme): update installation steps
style Formatting style(components): format with prettier
refactor Code change refactor(services): extract validation logic
test Adding tests test(audio): add duration calculation tests
chore Maintenance chore(deps): update dependencies

Subject Line

✅ Good: feat(auth): add OAuth2 support
❌ Bad: Added OAuth2 support
❌ Bad: feat(Auth): Add OAuth2 Support.

Body

Add support for YouTube OAuth2 authentication to enable video
uploads. This replaces the previous API key approach with a more
secure token-based system.

The new flow:
1. User initiates OAuth flow
2. Browser opens for consent
3. Access token stored locally
4. Token refreshed automatically

Footer

Closes #456
Co-Authored-By: Claude <noreply@anthropic.com>

Complete Example

feat(services): add cost tracking for Gemini API calls

Implement cost estimation and tracking for all AI operations to help
manage budget effectively. This includes:

- Token counting for input/output
- Per-model pricing calculations
- Cumulative cost tracking by operation
- Budget alerts when approaching limits

This allows users to monitor and optimize their API usage.

Closes #123
Co-Authored-By: Claude <noreply@anthropic.com>

Multi-Commit Changes

For larger changes, organize into logical commits:

1. refactor(audio): extract AudioService from pipeline
2. test(audio): add 21 unit tests for AudioService
3. refactor(pipeline): use new AudioService
4. docs(readme): document audio service extraction

Commit Message Template

#!/bin/bash
# Save as .git/hooks/prepare-commit-msg

commit_msg=$(cat "$1")

# Check for conventional commit format
if ! echo "$commit_msg" | grep -qE '^(feat|fix|docs|style|refactor|test|chore)(\(.+\))?: '; then
  echo "Invalid commit message format!"
  echo "Use: type(scope): subject"
  echo ""
  echo "Types: feat, fix, docs, style, refactor, test, chore"
  exit 1
fi

# Check subject length
subject=$(echo "$commit_msg" | head -n1)
if [ ${#subject} -gt 50 ]; then
  echo "Subject line too long (max 50 characters)"
  exit 1
fi

Interactive Rebase for Cleanup

# Rebase last 5 commits
git rebase -i HEAD~5

# Commands:
# pick = use commit
# reword = edit message
# edit = pause for changes
# squash = merge into previous
# drop = remove commit

Co-Authored-By Attribution

For AI-assisted development:

fix(video): correct frame calculation for cross-fades

The previous calculation didn't account for the 30-frame overlap
between consecutive scenes, causing timing issues.

Co-Authored-By: Claude <noreply@anthropic.com>

Common Mistakes to Avoid

❌ Bad ✅ Good
update stuff feat(api): add rate limiting
fix bug fix(player): prevent audio overlap
wip refactor(ui): extract header component
finished feature feat(auth): add OAuth2 support
fixed it fix(api): handle timeout errors

Branch Naming

feat/add-oauth2-support
fix/player-timing
docs/update-readme
refactor/extract-services

Summary Checklist