claude-git-hooks
v2.35.0
Published
Git hooks with Claude CLI for code analysis and automatic commit messages
Downloads
888
Maintainers
Readme
Claude Git Hooks
AI-powered git hooks for automatic commit messages, code analysis, and PR creation.
Requirements
- Node.js >=16.9.0
- Git
- Claude CLI (authenticated)
Quick Start
npm install -g claude-git-hooks
cd your-project
claude-hooks installUsage
Auto Commit Message
git commit -m "auto"
# Claude generates message from branch name + changes
# Format: [TASK-ID] type: description
# Example: branch feature/IX-123-auth → [IX-123] feat: add authenticationCreate PR
claude-hooks create-pr develop
# Automatically pushes branch if unpublished (with confirmation)
# Analyzes diff, generates title/description, creates PR on GitHubAuto-push feature (v2.11.0):
- Detects unpublished branches or unpushed commits
- Shows commit preview before pushing
- Prompts for confirmation (configurable)
- Handles diverged branches gracefully
Merge strategy awareness (v2.25.0):
- Auto-detects required strategy from branch naming:
feature/*/release-fix/*→ squash,release-candidate/*/hotfix/*/→ main→ merge commit - Displays strategy in PR preview; adds
merge-strategy:squashormerge-strategy:merge-commitlabel - Prepends body reminder for merge-commit PRs; unknown patterns prompt user to select manually
Automatic label resolution (v2.31.0):
- Resolves labels from 5 rule types: preset, size, quality, strategy, and defaults
- Remote config priority (
mscope-S-L/git-hooks-config/labels.json) with local fallback - Size labels:
size:S(<10 files),size:M(10-50),size:L(50-100),size:XL(>100) — thresholds configurable remotely - Quality labels:
breaking-change,security,performancefrom analysis result - Each rule type independently enabled/disabled via remote config
Team Configuration
Label rules, PR categories, and role-based permissions are managed centrally in mscope-S-L/git-hooks-config. Changes there take effect immediately across all governed repositories — no tool update or deploy required.
Token Setup
claude-hooks setup-github # Configure GitHub token for PR creation
claude-hooks setup-linear # Configure Linear token for ticket enrichmentOption 1 - Settings file (recommended):
// .claude/settings.local.json (gitignored)
{ "githubToken": "ghp_..." }Option 2 - Environment variable:
export GITHUB_TOKEN="ghp_..."Create token at https://github.com/settings/tokens with scopes: repo, read:org
Linting & Formatting
Runs formatters and linters on staged files automatically during pre-commit, or on demand:
# Lint staged files (default)
claude-hooks lint
# Lint all files in a directory
claude-hooks lint src/
# Lint specific files
claude-hooks lint file1.js file2.java
# Mix of directories and files
claude-hooks lint src/ lib/utils/ file.jsTools per preset (configured via remote config):
| Preset | Tools |
| ----------- | ----------------------------- |
| frontend | Prettier, ESLint |
| backend | Spotless |
| fullstack | Prettier, ESLint, Spotless |
| database | sqlfluff |
| ai | Prettier, ESLint |
| default | Prettier, ESLint |
Behavior:
- Formatters run first (Prettier), then linters (ESLint) — format before lint
- Auto-fix enabled by default — fixes and re-stages files automatically
- Missing tools are skipped with install instructions (never blocks)
- Unfixable issues are forwarded to the Claude judge for semantic resolution
- Tool-to-preset mapping is fetched from remote config (team-controlled, no release needed)
Analyze Code (Interactive Review)
Run interactive code analysis before committing:
# Analyze staged changes (default)
claude-hooks analyze
# Analyze unstaged changes
claude-hooks analyze --unstaged
# Analyze all tracked files
claude-hooks analyze --allWhat it does:
- Analyzes selected file scope (staged, unstaged, or all)
- Shows all issues (INFO, MINOR, MAJOR, CRITICAL, BLOCKER)
- Interactive prompt with options:
- Continue: Creates commit automatically with auto-generated message
- Abort: Generate resolution prompt and fix issues
- View: Show detailed issue list
- Executes
git commit -m "auto" --no-verifyon confirmation - Works outside git hooks (no stdin limitations)
Use case: Complete analysis-to-commit workflow in one command.
Analyze Diff (without creating PR)
claude-hooks analyze-diff develop
# Generates PR metadata without creatingAnalyze PR from GitHub URL
claude-hooks analyze-pr https://github.com/owner/repo/pull/123
# Fetches PR, applies preset guidelines, posts review comments
claude-hooks analyze-pr https://github.com/owner/repo/pull/123 --dry-run
# Analyze without posting comments
claude-hooks analyze-pr https://github.com/owner/repo/pull/123 --preset backend --model opus
# Override preset and model- Auto-detects preset from PR labels, Linear ticket labels, or file extensions
- Enriches with Linear ticket context when
[AUT-1234]found in PR title - Interactive comment workflow: confirm/skip each finding before posting
- Classifies into inline (file:line) and general (review-level) categories
Bump Version
Automatic version management with CHANGELOG generation and Git tagging:
# Bump patch version (1.0.0 → 1.0.1)
claude-hooks bump-version patch
# Bump with suffix
claude-hooks bump-version minor --suffix SNAPSHOT # → 1.1.0-SNAPSHOT
# Bump and generate CHANGELOG
claude-hooks bump-version major --update-changelog
# Preview without applying
claude-hooks bump-version patch --dry-run
# Push tag immediately (otherwise pushed by create-pr)
claude-hooks bump-version patch --push
# Manual workflow (skip automatic commit)
claude-hooks bump-version patch --no-commitWhat it does:
- Detects project type (Node.js, Maven, or monorepo with both)
- Updates
package.jsonand/orpom.xml - Generates CHANGELOG entry with Claude (analyzes commits)
- Commits changes automatically with conventional commit format
- Creates annotated Git tag with
vprefix (e.g.,v2.7.0) - Tags stay local by default (use
--pushto push immediately, or letcreate-prhandle it)
Version workflow:
2.7.0 → 2.8.0-SNAPSHOT # Start development
2.8.0-SNAPSHOT → 2.8.0-RC # Release candidate
2.8.0-RC → 2.8.0 # Final releaseIntegration with create-pr:
- Validates version alignment (package.json, pom.xml, CHANGELOG, tags)
- Detects and prompts to push unpushed tags
- Warns if local version ≤ remote version
Generate CHANGELOG
Standalone CHANGELOG generation (without version bump):
# Auto-detect version from package.json/pom.xml
claude-hooks generate-changelog
# Specific version with release marking
claude-hooks generate-changelog 2.7.0 --release
# Compare against different base branch
claude-hooks generate-changelog --base-branch developWhat it does:
- Analyzes commits since last tag using Claude
- Categorizes by Conventional Commits types (feat, fix, refactor, etc.)
- Generates Keep a Changelog format entries
- Discovers all CHANGELOG.md files (monorepo aware); prompts to select when multiple found
- Updates the selected CHANGELOG.md automatically
- Useful when
bump-version --update-changelogfails
Disable/Enable Hooks
claude-hooks disable [pre-commit|prepare-commit-msg]
claude-hooks enable [pre-commit|prepare-commit-msg]Uninstall
claude-hooks uninstallPresets
claude-hooks presets # List available
claude-hooks --set-preset backend # Set preset
claude-hooks preset current # Show current| Preset | Extensions | Focus | | --------- | ---------------------------------------- | ------------------------ | | backend | .java, .xml, .yml, .yaml | Spring Boot, JPA, OWASP | | frontend | .js, .jsx, .ts, .tsx, .css, .scss, .html | React, XSS, a11y | | fullstack | all above | API contract consistency | | database | .sql | SQL injection, indexes | | ai | .js, .json, .md, .sh | Node.js, Claude API | | default | multiple | General quality |
Skip Analysis
git commit --no-verify -m "message"Debug Mode
claude-hooks --debug true|false|statusTelemetry
claude-hooks telemetry show # View statistics
claude-hooks telemetry clear # Clear dataHelp & Issue Reporting
claude-hooks help "how do presets work?" # AI-powered help (uses CLAUDE.md)
claude-hooks help --report-issue # Interactive GitHub issue creation
claude-hooks --help # Static command referenceBatch Info
claude-hooks batch-info
# Shows: orchestration model, threshold, default analysis model
# Shows: per-model average analysis time and orchestration overhead (from telemetry)Other Commands
claude-hooks status # Show hook status
claude-hooks update # Update to latest versionArchitecture Reference (AI Context)
Design Philosophy
Modular, decoupled, reusable code. Each component has a single responsibility and can be tested/modified independently.
Directory Map
| Path | Purpose | Key Exports |
| ------------------ | -------------------------------------------------------- | ---------------------------------------- |
| bin/claude-hooks | Thin CLI router - argument parsing, command dispatch | - |
| lib/commands/ | Command modules - one file per CLI command | See table below |
| lib/config.js | Config system - load/merge configuration | getConfig() |
| lib/hooks/ | Git hook logic - Node.js implementations | pre-commit.js, prepare-commit-msg.js |
| lib/utils/ | Reusable utilities - shared across commands | See table below |
| templates/ | Static assets - bash wrappers, prompts, presets | Copied during install |
Command Modules (lib/commands/)
| Module | Purpose | Key Exports |
| ----------------------- | ----------------------------------------------------------------- | ----------------------------------------------------------------------------- |
| helpers.js | Shared CLI utilities - colors, output, platform detection | colors, error(), success(), info(), checkGitRepo(), Entertainment |
| install.js | Installation logic - dependencies, hooks, templates | runInstall(), extractLegacySettings() |
| hooks.js | Hook management - enable, disable, status, uninstall | runEnable(), runDisable(), runStatus(), runUninstall() |
| analyze.js | Interactive code analysis - analyze before committing | runAnalyze() |
| analyze-diff.js | Diff analysis - generate PR metadata from git diff | runAnalyzeDiff() |
| analyze-pr.js | PR analysis - analyze GitHub PR with team guidelines | runAnalyzePr() |
| create-pr.js | PR creation - full workflow via Octokit | runCreatePr() |
| bump-version.js | Version management - bump with CHANGELOG and Git tag | runBumpVersion() |
| generate-changelog.js | CHANGELOG generation - standalone command | runGenerateChangelog() |
| setup-github.js | Token setup - interactive GitHub configuration | runSetupGitHub() |
| setup-linear.js | Token setup - interactive Linear configuration | runSetupLinear() |
| presets.js | Preset management - list, set, show current | runShowPresets(), runSetPreset(), runCurrentPreset() |
| update.js | Self-update - check and install latest version | runUpdate() |
| migrate-config.js | Config migration - legacy to v2.8.0 format | runMigrateConfig() |
| debug.js | Debug toggle - enable/disable verbose logging | runSetDebug() |
| telemetry-cmd.js | Telemetry commands - show/clear statistics | runShowTelemetry(), runClearTelemetry() |
| diff-batch-info.js | Batch info - orchestration config + per-model speed telemetry | runDiffBatchInfo() |
| help.js | Help, AI help, report-issue | runShowHelp(), showStaticHelp(), runShowVersion() |
Utility Modules (lib/utils/)
| Module | Purpose | Key Exports |
| ------------------------------- | -------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| analysis-engine.js | Shared analysis logic - file data, orchestration, results (v2.13.0) | buildFilesData(), runAnalysis(), consolidateResults(), displayResults() |
| diff-analysis-orchestrator.js | Intelligent orchestration - semantic batch grouping via Opus (v2.20.0) | orchestrateBatches(), buildFileOverview(), detectDependencies() |
| claude-client.js | Claude CLI wrapper - spawn, retry, model override | analyzeCode(), executeClaudeWithRetry(), extractJSON() |
| prompt-builder.js | Prompt construction - load templates, replace variables, inject commit context | buildAnalysisPrompt(), loadPrompt() |
| git-operations.js | Git abstractions - staged files, diff, branch comparison | getStagedFiles(), getDiff(), getRepoRoot(), resolveBaseBranch(), getDiffBetweenRefs() |
| pr-metadata-engine.js | PR metadata generation - branch context, diff reduction (v2.14.0) | getBranchContext(), buildDiffPayload(), generatePRMetadata(), analyzeBranchForPR() |
| github-api.js | Octokit integration - PR creation, PR analysis, token validation, content fetching | createPullRequest(), fetchPullRequest(), fetchPullRequestFiles(), createPullRequestReview(), parseGitHubPRUrl(), validateToken(), saveGitHubToken(), fetchFileContent(), fetchDirectoryListing(), createIssue() |
| token-store.js | Token persistence - centralized settings.local.json read/write | loadToken(), saveToken(), hasToken(), loadLocalSettings() |
| linear-connector.js | Linear integration - ticket context fetching with retry | fetchTicket(), extractLinearTicketFromTitle(), testConnection(), loadLinearToken() |
| pr-statistics.js | PR statistics - write-only JSONL analytics | recordPRAnalysis() |
| github-client.js | GitHub helpers - repo parsing, config-based reviewers | getReviewersForFiles(), parseGitHubRepo() |
| reviewer-selector.js | Team-based reviewer selection - GitHub Teams API resolution (v2.32.0) | selectReviewers() |
| preset-loader.js | Preset system - load tech-stack configurations | loadPreset(), listPresets() |
| task-id.js | Task ID extraction - Jira, GitHub, Linear patterns | getOrPromptTaskId(), formatWithTaskId() |
| judge.js | Auto-fix judge - LLM verdict + search/replace fixes (v2.20.0) | judgeAndFix(), applyFix() |
| resolution-prompt.js | Issue resolution - AI-friendly fix prompts | generateResolutionPrompt() |
| logger.js | Logging system - centralized output with debug mode | info(), warning(), error(), debug() |
| interactive-ui.js | CLI UI components - previews, prompts, spinners | showPRPreview(), promptConfirmation(), promptMenu() |
| telemetry.js | Local telemetry - track JSON parsing, retries | recordEvent(), displayStatistics() |
Execution Flow
Pre-commit Hook
git commit → templates/pre-commit (bash wrapper)
→ lib/hooks/pre-commit.js
→ getStagedFiles() → filterFiles() by preset extensions + size
→ buildFilesData() → runAnalysis() (via analysis-engine.js)
→ displayResults() → show quality gate status
→ judge evaluates ALL issues (any severity):
→ TRUE_ISSUE: auto-fix via search/replace + git add
→ FALSE_POSITIVE: dismissed
→ ALL resolved: exit 0 (pass)
→ ANY unresolved: generates resolution prompt → exit 1 (block)
→ judge failure: user warned → exit 1 (block)
→ judge disabled: original quality gate (blocks on critical/blocker only)Note: For interactive review of non-blocking issues, use claude-hooks analyze before committing.
Commit Message Generation
git commit -m "auto" → templates/prepare-commit-msg (bash wrapper)
→ lib/hooks/prepare-commit-msg.js
→ extract task-id from branch name
→ generate message via Claude
→ write to COMMIT_EDITMSGPR Metadata Generation (analyze-diff / create-pr)
claude-hooks analyze-diff|create-pr → bin/claude-hooks (router)
→ lib/commands/analyze-diff.js or create-pr.js (thin wrapper)
→ analyzeBranchForPR() (pr-metadata-engine.js)
→ resolveBaseBranch() (git-operations.js)
→ getDiffBetweenRefs() + getCommitsBetweenRefs()
→ buildDiffPayload() with tiered reduction (context → proportional → stat-only)
→ executeClaudeWithRetry() → PRMetadata
→ analyze-diff: formats to console + saves JSON
→ create-pr: additionally creates PR via Octokit APIPR Analysis (analyze-pr)
claude-hooks analyze-pr <url> → bin/claude-hooks (router)
→ lib/commands/analyze-pr.js
→ parseGitHubPRUrl() → fetchPullRequest() + fetchPullRequestFiles()
→ extractLinearTicketFromTitle() → fetchTicket() (optional enrichment)
→ resolvePreset() (labels → ticket → auto-detect → default)
→ loadPrompt('ANALYZE_PR.md') with preset guidelines + categories
→ executeClaudeWithRetry() → extractJSON() → normalizeCategory()
→ interactive comment workflow (confirm/skip)
→ createPullRequestReview() → inline + general comments
→ recordPRAnalysis() (JSONL statistics)Config Priority
defaults (lib/config.js)
< user config (.claude/config.json)
< preset config (.claude/presets/{name}/)Preset always wins - tech-stack specific has priority over user preferences.
Config Format (v2.8.0)
{
"version": "2.8.0",
"preset": "backend",
"overrides": {
"github": {
"pr": {
"defaultBase": "develop",
"reviewers": ["user"],
"autoPush": true, // Auto-push unpublished branches (v2.11.0)
"pushConfirm": true, // Prompt before push (v2.11.0)
"showCommits": true, // Show commit preview (v2.11.0)
"verifyRemote": true // Verify remote exists (v2.11.0)
}
}
}
}Key Patterns
- Factory:
preset-loader.js- dynamic config per tech-stack - Template Method:
prompt-builder.js- prompts from .md templates - Strategy:
analysis-engine.js- sequential vs orchestrated analysis - Adapter:
git-operations.js- git commands to JS functions - Command:
lib/commands/*.js- one module per CLI command
Modification Guide
| To change... | Edit... |
| ------------------------- | ------------------------------------------------- |
| CLI argument parsing | bin/claude-hooks |
| Install workflow | lib/commands/install.js |
| PR creation flow | lib/commands/create-pr.js |
| PR analysis from URL | lib/commands/analyze-pr.js |
| Analysis logic | lib/hooks/pre-commit.js |
| Message generation | lib/hooks/prepare-commit-msg.js |
| Prompt templates | templates/*.md or .claude/prompts/*.md |
| Preset definitions | templates/presets/{name}/ |
| Config defaults | lib/config.js |
| GitHub integration | lib/utils/github-api.js |
| Claude CLI calls | lib/utils/claude-client.js |
| Batch orchestration logic | lib/utils/diff-analysis-orchestrator.js |
| Orchestration prompt | templates/DIFF_ANALYSIS_ORCHESTRATION_PROMPT.md |
| Auto-fix judge logic | lib/utils/judge.js |
File Structure
claude-git-hooks/
├── bin/claude-hooks # Thin CLI router - dispatch to commands
├── lib/
│ ├── config.js # Config system - load and merge
│ ├── commands/ # Command modules - one per CLI command
│ │ ├── helpers.js # Shared utilities - colors, output
│ │ ├── install.js # Install command - hooks, templates
│ │ ├── hooks.js # Hook management - enable/disable
│ │ ├── analyze-diff.js # Diff analysis - PR metadata
│ │ ├── analyze-pr.js # PR analysis - GitHub PR review
│ │ ├── create-pr.js # PR creation - Octokit workflow
│ │ ├── setup-github.js # Token setup - interactive GitHub config
│ │ ├── setup-linear.js # Token setup - interactive Linear config
│ │ ├── presets.js # Preset commands - list/set
│ │ ├── update.js # Self-update - npm latest
│ │ ├── migrate-config.js # Migration - legacy to v2.8.0
│ │ ├── debug.js # Debug mode - toggle verbose
│ │ ├── telemetry-cmd.js # Telemetry - show/clear stats
│ │ ├── diff-batch-info.js # Batch info - orchestration config
│ │ └── help.js # Help display - usage info
│ ├── hooks/ # Git hooks - Node.js logic
│ │ ├── pre-commit.js # Pre-commit analysis
│ │ └── prepare-commit-msg.js # Message generation
│ └── utils/ # Reusable modules - shared logic
│ ├── diff-analysis-orchestrator.js # Intelligent batch orchestration
│ ├── judge.js # Auto-fix judge (v2.20.0)
│ └── token-store.js # Token persistence - settings.local.json
├── templates/
│ ├── pre-commit # Bash wrapper - invokes Node.js
│ ├── prepare-commit-msg # Bash wrapper - invokes Node.js
│ ├── DIFF_ANALYSIS_ORCHESTRATION_PROMPT.md # Opus orchestration prompt
│ ├── *.md # Other prompt templates
│ └── presets/ # Preset configurations
└── test/unit/ # Jest testsAnalysis Routing (v2.20.0)
Two-tier strategy based on file count:
| Files | Strategy | Details | | ----- | ----------------------------- | ------------------------------------------------------------------------------ | | 1–2 | Sequential | Single Claude call, full context | | 3+ | Intelligent orchestration | Opus groups files semantically, assigns model per batch, shared commit context |
Orchestration flow (3+ files):
- Opus reads a lightweight file overview + detected cross-file dependencies
- Groups related files into semantically coherent batches
- Assigns model per batch:
haiku(config/docs),sonnet(business logic),opus(security-critical) - All batches run in parallel; each receives a shared commit overview header
- Falls back to one-file-per-batch if orchestration fails
Inspect orchestration settings:
claude-hooks batch-info # Shows config + per-model avg speed from telemetryHardcoded Defaults (v2.8.0+)
- Max file size: 1MB
- Max files per commit: 30
- Orchestrator threshold: 3 files
- Orchestrator model: opus (internal, not configurable)
More information: https://github.com/mscope-S-L/git-hooks
