Show HN: Gh-dep – TUI to batch review/merge Dependabot/Renovate PRs across repos

1 month ago 2

Test Go Report Card

A GitHub CLI extension that streamlines the review and merge workflow for automated dependency update PRs.

gh-dep demo

  • 🖥️ Interactive TUI: Full-featured terminal UI with keyboard navigation and live settings adjustment
  • 📋 List dependency PRs by label/author with clean table output
  • 📦 Group PRs by package@version for easier batched review
  • Bulk approve all PRs for a chosen group
  • 🚀 Bulk merge per group via:
    • Dependabot mode: Post @dependabot merge comments (respects CI checks)
    • API mode: Direct GitHub Merge API calls (with optional CI validation)
  • 🏢 Multi-repo support: Target specific repos or entire organizations
  • 🔄 Works out-of-the-box with Dependabot and Renovate
  • 🎨 Multiple output formats: Human-readable tables or JSON
  • ⚙️ Configuration support: Save default repos and custom patterns via gh config
  • 🎯 Custom patterns: Define your own PR title patterns for grouping
  • GitHub CLI (gh) version 2.x or later
  • Go 1.21 or later (for building from source)
gh extension install jackchuka/gh-dep
# Clone the repository git clone https://github.com/jackchuka/gh-dep.git cd gh-dep # Build the extension go build -o gh-dep # Install as a gh extension gh extension install .

Interactive Mode (Recommended)

# Launch interactive TUI for a single repo gh dep --repo owner/app # Or for an entire organization gh dep --owner myorg

In the TUI, you can:

  • Navigate with ↑/↓ or j/k
  • Select PRs with space or a (select all)
  • Toggle action mode with m (Approve → Merge → Approve & Merge)
  • Adjust merge settings on-the-fly:
    • M - Toggle merge method (squash → merge → rebase)
    • D - Toggle merge mode (dependabot → api)
    • c - Toggle CI checks requirement
  • Search PRs with /
  • Open current PR in browser with o
  • Execute selected actions with x
  • View help with ?
# List and group dependency PRs in a single repo gh dep list --repo owner/app --group # Output: # GROUP REPO PR URL # [email protected] app #123 https://github.com/owner/app/pull/123 # api #129 https://github.com/owner/api/pull/129 # web #131 https://github.com/owner/web/pull/131 # [email protected] app #118 https://github.com/owner/app/pull/118 # api #122 https://github.com/owner/api/pull/122 # View cached groups gh dep groups # Approve all PRs in a group (dry-run first) gh dep approve --group [email protected] --dry-run # Approve for real gh dep approve --group [email protected] # Merge via Dependabot comments (recommended - respects branch protections) gh dep merge --group [email protected] --mode dependabot --method squash # Or merge directly via API with CI check validation gh dep merge --group [email protected] --mode api --method squash --require-checks

Main Command - Interactive TUI (Recommended)

Launch an interactive terminal UI for managing dependency PRs with:

  • Multi-select: Use space to toggle, a to select all, d to deselect all
  • Navigation: ↑/↓ or j/k to move, o to open PR in browser
  • Search: Press / to filter PRs by title, repo, or number
  • Live Settings: Toggle execution mode and merge settings without restarting
    • m - Action mode (Approve → Merge → Approve & Merge)
    • M - Merge method (squash → merge → rebase)
    • D - Merge mode (dependabot → api)
    • c - CI checks requirement
  • Execute: Press x to run selected actions with real-time feedback
  • Help: Press ? to view all keyboard shortcuts

Flags:

  • --author - PR author to filter (default: dependabot[bot], use any for all)
  • --label - PR label to filter
  • --limit - Max PRs to fetch per repo (default: 200)
  • --repo / -R - Target repo(s), comma-separated
  • --owner - Target all repos in an organization
  • --merge-method - Initial merge method (default: squash)
  • --merge-mode - Initial merge mode (default: dependabot)
  • --require-checks - Initial CI checks setting

Examples:

# Launch TUI for a single repo gh dep --repo owner/app # Launch for entire organization with custom initial settings gh dep --owner myorg --merge-method rebase --merge-mode api # Filter by label gh dep --repo owner/app --label dependencies

list - List dependency PRs

Flags:

  • --label - PR label to filter
  • --author - PR author to filter (default: dependabot[bot], use any for all)
  • --group - Group PRs by package@version and cache results
  • --json - Output as JSON
  • --limit - Max PRs to fetch per repo (default: 200)
  • --repo / -R - Target repo(s), comma-separated (e.g., owner/repo1,owner/repo2)
  • --owner - Target all repos in an organization

groups - Show cached groups

Flags:

  • --json - Output as JSON

Shows the groups from the last list --group command without fetching from GitHub.

approve - Bulk approve PRs

gh dep approve --group GROUP_KEY [flags]

Flags:

  • --group - Required. Group key (e.g., [email protected])
  • --dry-run - Print actions without executing
  • --repo / -R - Target repo(s) (uses cache if omitted)
  • --org / -O - Target organization (uses cache if omitted)
gh dep merge --group GROUP_KEY [flags]

Flags:

  • --group - Required. Group key (e.g., [email protected])
  • --mode - Merge mode: dependabot or api (default: dependabot)
  • --method - Merge method: merge, squash, or rebase (default: squash)
  • --require-checks - Require CI checks to pass before merging (API mode only)
  • --dry-run - Print actions without executing

Examples:

# Merge via Dependabot comments (recommended) gh dep merge --group [email protected] --mode dependabot --method squash # Merge via API with CI validation gh dep merge --group [email protected] --mode api --method rebase --require-checks # Dry-run merge gh dep merge --group [email protected] --dry-run

Save default configuration to avoid passing flags every time:

# Set default repos gh config set dep.repo "myorg/app,myorg/api,myorg/web" # Set custom PR title patterns (comma-separated regexes with 2 capture groups: package, version) gh config set dep.patterns "bump\s+([^\s]+)\s+from\s+[^\s]+\s+to\s+v?(\d+(?:\.\d+)?(?:\.\d+)?)" # View current config gh config get dep.repo

When flags are not provided, gh dep will use these defaults.

Multi-Repo & Organization Support

# Group across multiple repos gh dep list --group --repo myorg/app,myorg/api,myorg/web # Output: # GROUP REPO PR URL # [email protected] app #123 https://github.com/myorg/app/pull/123 # app #129 https://github.com/myorg/app/pull/129 # app #131 https://github.com/myorg/app/pull/131 # api #45 https://github.com/myorg/api/pull/45 # [email protected] app #118 https://github.com/myorg/app/pull/118 # app #122 https://github.com/myorg/app/pull/122 # Approve across all repos gh dep approve --group [email protected]
# List all dependency PRs across entire org gh dep list --group --owner myorg # Approve/merge org-wide gh dep approve --group [email protected] gh dep merge --group [email protected] --mode dependabot

Dependabot Mode (Recommended)

Posts @dependabot merge comments. Dependabot handles:

  • Waiting for CI checks
  • Respecting branch protections
  • Auto-rebasing if needed

Use when: You want Dependabot to control the merge process.

gh dep merge --group [email protected] --mode dependabot --method squash

Calls GitHub's Merge API directly.

Use when: You want immediate merges and have permissions to bypass protections.

Tip: Use --require-checks to validate CI status before merging:

gh dep merge --group [email protected] --mode api --method squash --require-checks

Supported PR Title Patterns

The tool automatically parses titles from:

  • Bump <pkg> from X to Y
  • chore(deps): bump <pkg> from X to Y
  • Update <pkg> to vY
  • Update dependency <pkg> to vY
  • chore(deps): update <pkg> to vY

Define your own patterns via gh config:

gh config set dep.patterns "your-pattern-here,another-pattern"

Pattern requirements:

  • Must be valid regex
  • Must have exactly 2 capture groups: (package) and (version)
  • Multiple patterns can be comma-separated

Example custom patterns:

# Match "deps: upgrade foo to 1.2.3" gh config set dep.patterns "deps:\s+upgrade\s+([^\s]+)\s+to\s+(\d+(?:\.\d+)?(?:\.\d+)?)" # Match single-digit versions like "bump actions/setup-go from 5 to 6" gh config set dep.patterns "bump\s+([^\s]+)\s+from\s+[^\s]+\s+to\s+(\d+(?:\.\d+)?(?:\.\d+)?)"

Unknown titles are grouped as unknown@unknown for manual review.

Groups are cached at:

${XDG_CACHE_HOME:-$HOME/.cache}/gh-dep/groups.json

Cache is overwritten on each list --group execution.

Default output uses GitHub CLI's table formatter for clean, aligned columns:

# Flat list gh dep list # Output: # REPO PR TITLE # tailor-platform/app-shell #112 chore(deps-dev): bump tw-animate-css from 1.2.5 to 1.4.0 # tailor-platform/app-shell #111 chore(deps-dev): bump typescript-eslint from 8.28.0 to 8.44.1 # Grouped (single table) gh dep list --group # Output: # GROUP REPO PR URL # [email protected] app-shell #112 https://github.com/tailor-platform/app-shell/pull/112 # [email protected] app-shell #111 https://github.com/tailor-platform/app-shell/pull/111

Use --json for machine-readable output:

# Flat list as JSON array gh dep list --json # Grouped as JSON object gh dep list --group --json # Output: # { # "[email protected]": [ # { # "number": 112, # "title": "chore(deps-dev): bump tw-animate-css from 1.2.5 to 1.4.0", # "author": "dependabot[bot]", # "repo": "tailor-platform/app-shell", # "url": "https://github.com/tailor-platform/app-shell/pull/112" # } # ] # }

Contributions welcome! Please:

  1. Fork the repository
  2. Create a feature branch
  3. Add tests for new functionality
  4. Ensure go test ./... passes
  5. Submit a pull request

MIT License - see LICENSE for details.

Built with:


Made with ❤️ for dependency management automation

Read Entire Article