# gh-auto-agent — How It Works
> A deep-dive into the architecture, design philosophy, and the problems this tool solves.
---
## Table of Contents
1. [What Is It?](#1-what-is-it)
2. [The Problems It Solves](#2-the-problems-it-solves)
3. [Benefits](#3-benefits)
4. [How It Works — The Core Loop](#4-how-it-works--the-core-loop)
5. [Static vs AI: The Deliberate Split](#5-static-vs-ai-the-deliberate-split)
6. [Architecture Diagram](#6-architecture-diagram)
7. [Module Responsibilities](#7-module-responsibilities)
8. [Execution Flow Examples](#8-execution-flow-examples)
9. [Design Decisions](#9-design-decisions)
---
## 1. What Is It?
**gh-auto-agent** is an autonomous command-line agent that automates GitHub
workflows end-to-end. It wraps the GitHub CLI (`gh`) and Git, but unlike a plain
wrapper or shell alias, it:
- **Understands the context** of your project (language, framework, repo state)
- **Reasons about failures** it has never seen before (when AI is enabled)
- **Self-heals** — detects errors, applies fixes, and retries autonomously
- **Knows when *not* to add complexity** — uses a single native `gh` command
where one already does the job
The guiding principle:
```
Detect → Think → Fix → Ship (no manual intervention)
```
---
## 2. The Problems It Solves
### Problem 1 — GitHub workflows are multi-step and repetitive
Shipping a change normally means:
```bash
git checkout -b feature/x
git add .
git commit -m "..."
git push --set-upstream origin feature/x
gh pr create --fill
gh pr checks # wait...
gh pr merge --squash
git checkout main && git pull
```
Eight commands, lots of waiting, easy to get wrong.
**→ `agent ship "message"` does all of it.**
### Problem 2 — CI failures require manual diagnosis
When a workflow fails, you open the logs, read through them, figure out the root
cause, fix it, commit, and re-run. Repeatedly.
**→ `agent fix` / `agent heal` parse the logs, diagnose the cause (AI for unknown
errors), apply a safe fix, and re-run automatically.**
### Problem 3 — Project setup is boilerplate
A new repo needs: the repo itself, a README, a `.gitignore`, a license, and a CI
workflow.
**→ `agent init` uses native `gh` flags for the first four and adds a
language-aware CI workflow (the part `gh` can't do).**
### Problem 4 — Failures happen while you're not looking
CI breaks after a merge, and nobody notices until later.
**→ `agent watch` continuously monitors runs and auto-fixes failures in real time.**
### Problem 5 — Tooling bloat
Most automation tools pull in dozens of npm packages.
**→ Zero dependencies. Everything (YAML parser, glob matcher, LLM client,
`.env` loader) is built in.**
---
## 3. Benefits
| Benefit | Why it matters |
|---|---|
| **One-command workflows** | `ship`, `init`, `deploy` replace long command chains |
| **Self-healing** | Failures are fixed automatically, not just reported |
| **Context-aware** | Detects language/framework → correct CI, commit messages |
| **AI only where useful** | Reasoning for unknown errors; static speed everywhere else |
| **Safe by design** | Destructive commands are blocked; force-push uses `--force-with-lease` |
| **Zero dependencies** | Nothing to audit, fast install, no supply-chain risk |
| **Works offline** | Static mode handles all *known* errors with no network/AI |
| **Portable config** | `.env` file or shell exports — your choice |
---
## 4. How It Works — The Core Loop
Every operation runs through a **self-healing loop** (`modules/workflow.js →
executeWithHealing`):
```
┌─────────────┐
│ EXECUTE │ run the task (gh/git command)
└──────┬──────┘
│
success? ──── yes ──→ ✅ DONE
│ no
▼
┌─────────────┐
│ PARSE LOGS │ match output against known error patterns
└──────┬──────┘
│
known pattern? ── no ──→ 🧠 AI ANALYSIS (if enabled)
│ yes │
▼ ▼
┌─────────────┐ ┌─────────────────┐
│ APPLY FIX │ ◄────────│ root-cause + cmd │
└──────┬──────┘ └─────────────────┘
│
retry < 5? ── yes ──→ (back to EXECUTE)
│ no
▼
❌ STOP (report unrecoverable)
```
- **Max retries:** 5
- **Stops when:** success, or all fixes exhausted, or an unrecoverable error
- **State** (retry count, last task, history) is persisted in
`.gh-auto-agent-state.json`
---
## 5. Static vs AI: The Deliberate Split
AI is **optional and additive**. It is used *only* where genuine reasoning is
needed. Deterministic tasks stay static — faster, predictable, and offline.
| Task | Engine | Why |
|---|---|---|
| Auth, push, merge, labels, branch protection | **Static** | Deterministic — AI adds latency/risk, no benefit |
| Known errors (auth failed, push rejected, conflict…) | **Static** regex → fixed command | Fast, predictable, works offline |
| **Unknown** CI failures | **AI** root-cause → safe fix | Patterns can't cover every error |
| `workflow failed` | **AI** diagnoses *why*, fixes cause | Beats blindly re-running the same failure |
| Commit messages | **AI** reads the diff | Meaningful, not "update 3 files" |
| PR descriptions | **AI** summarizes real changes | Real context for reviewers |
If no AI provider is configured, the agent runs in **static mode** and still
handles every *known* error. AI never blocks a workflow.
**Safety filter:** AI-suggested commands are sanitized — `rm -rf`, force-push to
`main`, `git reset --hard`, `sudo`, fork bombs, etc. are blocked and never run.
A command only executes when the model's confidence is ≥ 0.5.
---
## 6. Architecture Diagram
### High-level component view
```mermaid
flowchart TD
User([User]) -->|agent command| CLI[index.js
CLI entry point]
CLI -->|loads first| ENV[core/env.js
.env loader]
CLI --> ORCH[modules/orchestrator.js
🧠 The Brain]
ORCH --> INTEL[intelligence.js
context analysis]
ORCH --> WF[workflow.js
self-healing loop]
ORCH --> PIPE[pipeline.js
YAML pipelines]
ORCH --> TEAM[team.js
reviewers & labels]
WF --> PARSER[parser.js
error detection]
WF --> AUTOFIX[autofix.js
fix engine]
AUTOFIX -->|known error| STATIC[Static fixes
regex → command]
AUTOFIX -->|unknown error| AI[core/ai.js
🧠 LLM client]
AUTOFIX --> GH[github.js
gh/git wrappers]
WF --> GH
ORCH --> GH
GH --> EXEC[core/executor.js
shell execution]
AUTOFIX --> EXEC
EXEC --> SHELL[(gh CLI / git)]
AI -.optional.-> LLM[(OpenAI / GitHub Models
Azure / Ollama)]
ORCH --> STATE[core/stateManager.js
state persistence]
ORCH --> LOG[core/logger.js
console + file logs]
```
### Layered view
```
┌──────────────────────────────────────────────────────────┐
│ CLI LAYER index.js (parse args, route command) │
├──────────────────────────────────────────────────────────┤
│ ORCHESTRATION orchestrator.js (init/ship/fix/heal/ │
│ watch/deploy) + intelligence.js │
├──────────────────────────────────────────────────────────┤
│ AUTOMATION workflow.js (healing loop) │
│ pipeline.js · team.js │
├──────────────────────────────────────────────────────────┤
│ REASONING parser.js (static) + autofix.js │
│ ─ falls back to ─ core/ai.js (LLM) │
├──────────────────────────────────────────────────────────┤
│ EXECUTION github.js → core/executor.js │
├──────────────────────────────────────────────────────────┤
│ FOUNDATION logger.js · stateManager.js · env.js │
│ yaml-lite.js │
└──────────────────────────────────────────────────────────┘
│
▼
gh CLI · git · (optional) LLM API
```
---
## 7. Module Responsibilities
### `core/` — Foundation (no GitHub knowledge)
| File | Responsibility |
|---|---|
| `executor.js` | Runs shell commands (sync, streaming, retry). Returns `{success, output, error}` |
| `logger.js` | Colored console output + per-run file logs in `logs/github/` |
| `stateManager.js` | Persists execution state, retry counters, task history |
| `env.js` | Loads `.env` into `process.env` (never overwrites real env) |
| `ai.js` | OpenAI-compatible LLM client; failure analysis, commit/PR generation; command safety filter |
### `modules/` — Domain logic
| File | Responsibility |
|---|---|
| `orchestrator.js` | The brain — implements `init`, `ship`, `fix`, `heal`, `watch`, `deploy` |
| `intelligence.js` | Project analysis (language, framework, tests) + health dashboard |
| `workflow.js` | The self-healing `executeWithHealing` loop + workflow monitoring |
| `autofix.js` | Maps error IDs → fix actions; AI fallback for unknown errors; CI templates |
| `parser.js` | Matches command output against ~13 known error patterns |
| `github.js` | Thin, typed wrappers over `gh`/`git` commands |
| `pipeline.js` | Runs YAML-defined multi-step pipelines with auto-healing |
| `team.js` | Auto-assigns reviewers, labels PRs, generates CODEOWNERS |
| `yaml-lite.js` | Zero-dependency YAML parser for pipeline files |
---
## 8. Execution Flow Examples
### Example A — `agent ship "feat: add login"`
```mermaid
sequenceDiagram
participant U as User
participant O as orchestrator
participant AI as core/ai.js
participant G as github.js
participant GH as gh / git
U->>O: agent ship "feat: add login"
O->>G: getCurrentBranch()
G->>GH: git rev-parse --abbrev-ref HEAD
Note over O: on main → create feature branch
O->>G: branchCreate(feature/...)
O->>AI: generateCommitMessage(diff) (if AI on)
AI-->>O: "feat: add login flow"
O->>G: add → commit → push (self-healing)
O->>AI: generatePRDescription(changes)
O->>G: prCreate(title, body)
O->>G: prChecks() (wait for CI)
O->>G: prMerge(--squash)
O-->>U: 🎉 Shipped to main
```
### Example B — `agent fix` on a failing CI
```mermaid
sequenceDiagram
participant U as User
participant O as orchestrator
participant P as parser
participant A as autofix
participant AI as core/ai.js
U->>O: agent fix
O->>O: scan runs, PRs, configs, git state
O->>A: applyFix(workflow_failed, {runId, logs})
A->>P: parse(logs)
alt known pattern
P-->>A: matched → static fix
else unknown
A->>AI: analyzeFailure(logs)
AI-->>A: {rootCause, safe command, confidence}
A->>A: run command if confidence ≥ 0.5
end
A-->>O: fixed → rerun workflow
O-->>U: Fixed N/M issues
```
---
## 9. Design Decisions
1. **Zero dependencies** — easier to audit, no supply-chain risk, instant install.
The YAML parser, glob matcher, LLM client, and `.env` loader are all hand-written.
2. **Static-first, AI-second** — AI is powerful but slow, non-deterministic, and
needs a key. Known problems are solved statically; AI handles only the long tail.
3. **Native `gh` over re-implementation** — where a single `gh` flag does the job
(e.g. `gh repo create --add-readme --gitignore --license`), we use it instead
of chaining commands.
4. **Safety over autonomy** — the agent is autonomous, but destructive commands
are blocked, force-push uses `--force-with-lease`, and AI commands need a
confidence threshold.
5. **Graceful degradation** — no AI key? Static mode. No `gh`? Clear error. The
tool never hard-fails on optional features.
---
*See [USAGE.md](./USAGE.md) for installation, commands, and testing.*