Git Configuration
Set up Git for a productive workflow — identity, aliases, defaults, and .gitignore patterns for Next.js projects.
Recipe
Quick-reference recipe card — copy-paste ready.
# Set identity
git config --global user.name "Your Name"
git config --global user.email "you@example.com"
# Set default branch name
git config --global init.defaultBranch main
# Use rebase on pull by default
git config pull.rebase true
# Enable rerere (reuse recorded resolution)
git config --global rerere.enabled true
# Set VS Code as editor
git config --global core.editor "code --wait"
# View all config
git config --list --show-originWhen to reach for this: When setting up a new machine, onboarding to a project, or streamlining repetitive Git operations.
Working Example
Recommended .gitignore for Next.js
# Dependencies
node_modules/
.pnp/
.pnp.js
# Build output
.next/
out/
build/
dist/
# Environment files
.env
.env.local
.env.development.local
.env.test.local
.env.production.local
# IDE
.vscode/settings.json
.idea/
*.swp
*.swo
.DS_Store
# Debug
npm-debug.log*
yarn-debug.log*
yarn-error.log*
# TypeScript
*.tsbuildinfo
next-env.d.ts
# Vercel
.vercel
# Testing
coverage/
playwright-report/
test-results/
# Misc
*.pem
.turboWhat this demonstrates:
- Separate sections for dependencies, build output, secrets, IDE files, and tooling
.envfiles are always ignored — secrets should never be committednext-env.d.tsis auto-generated and should be ignored
Deep Dive
Useful Git Aliases
# Short status
git config --global alias.s "status -sb"
# Pretty log
git config --global alias.lg "log --oneline --graph --all --decorate"
# Undo last commit (keep changes staged)
git config --global alias.undo "reset --soft HEAD~1"
# Show what you did today
git config --global alias.today "log --since='midnight' --oneline --author='Your Name'"
# List aliases
git config --global alias.aliases "config --get-regexp ^alias"
# Amend without editing message
git config --global alias.amend "commit --amend --no-edit"
# Quick diff of staged changes
git config --global alias.staged "diff --cached"Usage after setup:
git s # short status
git lg # pretty log graph
git undo # undo last commit
git today # today's commits
git amend # amend last commit silently
git staged # diff of staged changesGlobal vs Local Config
# Global (applies to all repos) — stored in ~/.gitconfig
git config --global user.name "Your Name"
# Local (applies to this repo only) — stored in .git/config
git config user.email "work@company.com"
# System (applies to all users) — rarely used
git config --system core.autocrlf true
# Check where a config value comes from
git config --show-origin user.emailUseful Global Defaults
# Auto-correct typos (runs after 1 second)
git config --global help.autocorrect 10
# Colorize output
git config --global color.ui auto
# Set default merge strategy
git config --global merge.conflictstyle diff3
# Sign commits with GPG
git config --global commit.gpgsign true
git config --global user.signingkey YOUR_GPG_KEY_ID
# Cache credentials for 1 hour
git config --global credential.helper 'cache --timeout=3600'
# macOS keychain
git config --global credential.helper osxkeychainSSH Key Setup for GitHub
# Generate a new SSH key
ssh-keygen -t ed25519 -C "you@example.com"
# Start the SSH agent
eval "$(ssh-agent -s)"
# Add key to agent
ssh-add ~/.ssh/id_ed25519
# Copy public key to clipboard (macOS)
pbcopy < ~/.ssh/id_ed25519.pub
# Then add to GitHub: Settings > SSH and GPG keys > New SSH key
# Test the connection
ssh -T git@github.com
# "Hi username! You've successfully authenticated"Hooks
Git hooks run scripts automatically at key points in the Git workflow.
# Common hooks (in .git/hooks/ or managed by Husky)
pre-commit # Runs before each commit — lint, format, type-check
commit-msg # Validate commit message format
pre-push # Runs before push — run tests
post-merge # Runs after merge — reinstall dependenciesWith Husky (recommended for team projects):
npx husky init
# Add a pre-commit hook
echo "npx lint-staged" > .husky/pre-commitGotchas
Things that will bite you. Each gotcha includes what goes wrong, why it happens, and the fix.
-
Wrong email in commits — Using a personal email on a work repo (or vice versa). Fix: Set local config per repo:
git config user.email "work@company.com". -
.gitignorenot working on tracked files — Adding a file to.gitignoreafter it's already committed doesn't stop tracking it. Fix:git rm --cached .envto untrack it, then commit. -
Line ending issues (CRLF/LF) — Windows and macOS/Linux use different line endings, causing noisy diffs. Fix: Add a
.gitattributesfile:* text=autoand*.tsx text eol=lf. -
Hooks not running — Git hooks need execute permissions. Fix:
chmod +x .husky/pre-commit. With Husky v9+, ensure the.husky/directory is set up correctly.
Alternatives
Other ways to solve the same problem — and when each is the better choice.
| Alternative | Use When | Don't Use When |
|---|---|---|
.gitattributes | Enforcing line endings and diff behavior per file type | Simple single-platform projects |
| Husky + lint-staged | Team projects needing consistent pre-commit checks | Solo projects where you trust your own discipline |
direnv | Per-directory environment config beyond Git | Git-only configuration needs |
FAQs
What is the difference between --global, local, and --system Git config?
--globalapplies to all repos for the current user (~/.gitconfig)- Local (no flag) applies to the current repo only (.git/config)
--systemapplies to all users on the machine (rarely used)- Local settings override global, which overrides system
How do I check where a specific config value comes from?
git config --show-origin user.email- Shows the file path and the value, so you know if it is global or local
Why is my .gitignore not ignoring a file I just added to it?
.gitignoreonly prevents untracked files from being staged- If a file is already tracked (committed), you must untrack it first:
git rm --cached .env
git commit -m "chore: untrack .env"How do I set up Git aliases for common commands?
git config --global alias.s "status -sb"
git config --global alias.lg "log --oneline --graph --all"
git config --global alias.undo "reset --soft HEAD~1"- Then use
git s,git lg,git undoas shortcuts
What does pull.rebase true do, and should I enable it?
- It makes
git pullautomatically rebase instead of merge - This avoids noisy merge commits when pulling updates on a feature branch
- Recommended for most workflows; set with
git config --global pull.rebase true
Gotcha: I am using the wrong email in commits on a work repo. How do I fix it?
git config user.email "work@company.com"- This sets the email for the current repo only (no
--global) - Already-pushed commits with the wrong email cannot be changed without rewriting history
How do I set up SSH keys for GitHub?
- Generate a key:
ssh-keygen -t ed25519 -C "you@example.com" - Add it to the agent:
ssh-add ~/.ssh/id_ed25519 - Copy the public key and add it to GitHub under Settings > SSH and GPG keys
- Test with:
ssh -T git@github.com
What is rerere and when should I enable it?
rererestands for "reuse recorded resolution"- It remembers how you resolved a conflict and auto-applies it next time
- Enable with
git config --global rerere.enabled true - Especially useful when rebasing frequently
How do I set up a pre-commit hook to run lint and type checks?
npx husky init
echo "npx lint-staged" > .husky/pre-commit- Pair with a
lint-stagedconfig inpackage.jsonto run checks only on staged files
Gotcha: My Git hooks are not running. What should I check?
- Ensure the hook file has execute permissions:
chmod +x .husky/pre-commit - With Husky v9+, confirm the
.husky/directory is properly initialized - Check that
preparescript exists inpackage.json:"prepare": "husky"
In a TypeScript project, which files should go in .gitignore?
node_modules/,.next/,out/,dist/,build/(dependencies and build output).env,.env.local,.env.*.local(secrets)*.tsbuildinfo,next-env.d.ts(auto-generated TypeScript files)coverage/,playwright-report/(test output)
How do I handle CRLF vs LF line ending issues across platforms?
- Add a
.gitattributesfile at the repo root:
* text=auto
*.tsx text eol=lf
*.ts text eol=lf
- This normalizes line endings on commit regardless of the developer's OS
Related
- Essential Git Commands — Core Git operations for daily use
- Git Utilities — Stash, bisect, cherry-pick, and other power tools
- GitHub CLI — Manage PRs, issues, and releases from the terminal
- Linting & Formatting — Set up Husky and lint-staged