This walks the whole lifecycle with real commands — from the authorization letter you send the client to the report you hand them, and the retest you bill later. The trick throughout: one scope file and one finding format flow between the tools, so nothing gets retyped.
This guide uses Forge Line Complete — every tool in one install. Get it → · new to the tools? Start with the quickstart.
Unzip forge-line-complete.zip, then from that folder:
$ python3 -m venv .venv && source .venv/bin/activate $ pip install -r requirements.txt $ pip install ./swage ./forgekit # adds swage / forge / ore / quench / … commands $ $EDITOR brand.yaml # your company, accent, contact — set once, every tool reads it
Windows: use py and .venv\Scripts\activate. One brand.yaml puts your identity on every scan, report, and legal document from here on.
forge ui to open a local console in your browser (127.0.0.1, nothing leaves your machine) that drives every step below — pick an engagement, run each stage with a button, watch findings accumulate, open the report. The terminal commands here and the console do exactly the same work.A short interview becomes your client paperwork and the machine-readable scope every later tool reads. Answer the questions (client, targets, window, techniques):
$ swage new acme # interview → acme.engagement.yaml $ swage render acme.engagement.yaml --brand brand.yaml ✓ acme-roe.docx · acme-authorization.docx · acme-sow.docx # + Markdown copies
Send the client the Authorization to Test letter and get it signed. Now you're clear to work — and acme.engagement.yaml carries the scope, window and your details into every step below.
produces → acme.engagement.yaml (forge-engagement/1.0) + RoE / Authorization / SoW documents
Ore enumerates what's in scope — the engagement file is its authorization, so it refuses targets outside your scope and window.
$ forge ore --engagement acme.engagement.yaml --forge acme.findings.yaml --brand brand.yaml
Add --active --i-have-authorization to probe ports (sends packets) — only when your signed scope covers it.
produces → an inventory report + appends any findings to acme.findings.yaml
Append external-posture and email-authentication findings to the same findings file. Every tool speaks one format, so they stack:
$ python3 -m anvil acme.example --brand brand.yaml --forge acme.findings.yaml $ python3 -m anvil acme.example --deep --forge acme.findings.yaml # adds exposed-file + method checks $ python3 hearth/hearth.py ./dmarc-reports/ --brand brand.yaml --forge acme.findings.yaml
produces → more findings in acme.findings.yaml (forge-finding/1.0)
If the engagement goes inside the perimeter, Ingot runs a read-only CIS-style baseline against a host or config and turns gaps into findings.
$ forge ingot linux --engagement acme.engagement.yaml --forge acme.findings.yaml --brand brand.yaml
Baselines: linux, windows, or a path to your own. Read-only — it inspects, it doesn't change anything.
The findings you get by hand — the ones no scanner catches — live in Redline, a pentester's Obsidian vault. Then export them into the same pipeline:
# Obsidian → "Open folder as vault" → pick the redline/ folder, enable Dataview $ python3 redline/scripts/export-to-hammer.py --engagement "Acme" --out manual.findings.yaml
CVSS scores auto-calculate from the vector you put on each finding note.
This is where the line pays off. Hand Hammer the findings from any tool plus your scope file, and it pulls the client name, window and your name straight from the scope — no retyping the header:
$ python3 hammer/hammer.py acme.findings.yaml \ --engagement acme.engagement.yaml --brand brand.yaml --out acme-report ✓ Scored 14 findings. acme-report.docx · acme-report.html — worst-first, CVSS-scored, in your branding
Merge several files (hammer.py a.yaml b.yaml …) or import raw output from 45+ scanners with --import — Nessus, Burp, ZAP, Nuclei, Trivy, Grype, Semgrep, Prowler, gitleaks and more, plus any tool that emits SARIF and generic CSV/JSON. Open the .html and print to PDF, or edit the .docx.
produces → acme-report.docx + acme-report.html, client-ready
Weeks later, re-run the engagement and diff it. Quench marks each finding fixed, open, or regressed — the second visit you can charge for:
$ forge quench acme.findings.yaml --engagement acme.engagement.yaml --auto --brand brand.yaml $ python3 hammer/hammer.py acme.findings.yaml --engagement acme.engagement.yaml --open-only --out retest ✓ a clean retest report showing only what's still open
Close the engagement by turning it into the client's deliverable. Temper generates a cyber-insurance readiness pack (WISP, IR plan, AUP, gap checklist) — and it answers the controls it can verify straight from your findings, citing the evidence:
$ python3 temper/temper.py --engagement acme.engagement.yaml \ --findings acme.findings.yaml --brand brand.yaml ✓ readiness pack — patching/encryption/email controls marked Gap from the actual findings, cited
The controls a scan can't see (MFA, backups, training…) stay interview-driven — run temper.py --interview --findings … to combine self-report with observed evidence. A client who self-reports "all good" but has TLS 1.0 or a spoofable domain gets a Gap with proof, not a rubber stamp.
You never converted a file by hand in any step above. That's the point of a line: two shared, versioned formats do the plumbing.
| Scope | forge-engagement/1.0 — written by Swage, read by Ore, Ingot, Hammer and Quench so scope and identity flow through once. |
| Findings | forge-finding/1.0 — emitted by Ore, Anvil, Hearth, Ingot and Redline; read by Hammer and Quench. |
| Brand | brand.yaml — one file, every tool. Set your identity once. |
Both formats are openly published: forge-engagement-1.0.json · forge-finding-1.0.json. Governance docs (WISP, IR plan, AUP) come from Temper; always-on drift monitoring from Anvil Watch.