faf-taf-git

May 3, 2026 Β· View on GitHub

TAF Claude Code

Q: What does TAF do? A: It prints Receipts. Q: What sort of Receipts? A: Test Receipts. Q: Why do I need Test Receipts? A: Proof over time.

Bonus: Cannot be gamed.

TAF is a Receipt Printer for git. Every CI run prints a receipt to .taf. The receipts accumulate on a git branch. The history is append-only. The proof is permanent.

Works on any git repo. No FAF required. TAF is a standalone product β€” install the action, get receipts. FAF integration is one of TAF's use cases (see below), not a precondition.

npm: faf-taf-git Β· action: Wolfe-Jam/faf-taf-git


🎯 WHAT

A Test Receipt Printer for git. Every CI run produces one receipt β€” timestamp, counts, result, trigger β€” appended to .taf on the taf-receipts branch. The timeline is the proof.

Example Test Receipt:

- timestamp: 2026-02-17T19:12:14.810Z
  result: PASSED
  tests:
    total: 808
    passed: 799
    failed: 0
    skipped: 9
  trigger: github-actions

Every field maps to a real receipt: timestamp = receipt date, tests = itemized lines, result = total, trigger = cashier/register, run_id = receipt number, project = vendor, format_version = receipt template.

What you get:

  • Proof over time β€” longitudinal evidence, not snapshots
  • Pattern detection β€” pass-rate trends, regression vs new failure
  • Platform-agnostic β€” works in ANY CI/CD (GitHub Actions, GitLab, Jenkins, CircleCI, Bitbucket, Azure, local, pre-commit)
  • Git-native β€” no external services, no SaaS lock-in
  • Cannot be gamed β€” git SHA detects edits, append-only history detects deletions, CI sandbox prevents output forgery

πŸ‘₯ WHO

For development teams who need:

  • Proof of testing over time (not just current state)
  • Git-tracked test accountability (visible in PRs, commits, history)
  • AI-readable test context (feeds into .faf project DNA)
  • Platform-agnostic testing receipts (works in ANY CI/CD)

Use cases:

  • Open source projects (prove your tests pass)
  • Regulated industries (auditable test history)
  • AI-augmented development (give AI your test timeline)
  • Championship engineering (F1-grade accountability)

πŸ€” WHY

The Problem

Tests run, results disappear. No permanent record. No accountability.

Before:

βœ… Tests passing (right now)
❓ Were they passing yesterday?
❓ When did that flaky test start failing?
❓ What's the trend over time?

After (with .taf):

βœ… Tests passing (tracked in git)
βœ… History shows: 99% pass rate over 30 days
βœ… Flaky test identified: started failing Feb 10
βœ… Trend: improving (was 85%, now 99%)

The Solution

Git-native receipts. Every test run becomes a permanent, auditable record.

.taf is software accountability - proof that your code works, tracked over time, visible to everyone.


πŸ“ WHERE

Works in ANY CI/CD environment that runs Node.js:

PlatformStatusExample
GitHub Actionsβœ… TestedSee Quick Start
GitLab CIβœ… Testednpx faf-taf-git --commit
Jenkinsβœ… Compatiblesh 'npx faf-taf-git --commit'
CircleCIβœ… Compatiblerun: npx faf-taf-git --commit
Bitbucket Pipelinesβœ… Compatiblenpx faf-taf-git --commit
Travis CIβœ… Compatiblenpx faf-taf-git --commit
Azure Pipelinesβœ… Compatiblenpx faf-taf-git --commit
Local developmentβœ… Worksnpm test && npx faf-taf-git
Pre-commit hooksβœ… WorksSee Examples

Architecture: Platform-agnostic core. No CI-specific dependencies. Pure functions.


⏰ WHEN

Use faf-taf-git when you need:

  1. Proof of testing over time

    • Regulated industries (SOC 2, ISO, HIPAA)
    • Open source credibility (show your tests pass)
    • Client deliverables (prove quality)
  2. AI-augmented development

    • Give AI your test history (feeds .faf format)
    • AI can see: "Tests were 85% passing, now 99%"
    • Better context = better AI assistance
  3. Debugging flaky tests

    • Timeline shows when tests started failing
    • Pattern detection (fails on Windows only, etc.)
    • Root cause analysis with historical data
  4. Team accountability

    • PRs show test impact (IMPROVED, DEGRADED, etc.)
    • No hiding broken tests
    • Git history = test history

Don't use when:

  • You only need current test status (use a test reporter)
  • You don't commit to git (TAF is git-native)
  • You're not ready for accountability πŸ˜‰

🧩 Use Cases

TAF works on any git repo. Adoption requires zero ecosystem buy-in β€” install the action, you get receipts. Below are the use cases TAF serves today and tomorrow:

Standalone (no FAF required)

Use CaseWhat TAF gives you
Plain JS/TS projectsReceipt for every Jest or Vitest run, on every CI execution
Pytest projectsReceipt for every Python test run (pending pytest parser β€” v2.2 roadmap)
Open source maintainers"This repo has 1,847 receipts going back 14 months, none missing"
Regulated industries (SOC 2, ISO, HIPAA)Append-only longitudinal evidence β€” auditors get a tamper-evident timeline, not a snapshot
Supply-chain trust"Prove these tests ran before this artifact shipped"
AI-agent verification"Prove this agent's code passed tests consistently over the last 90 days"

With FAF (optional integration)

Use CaseWhat TAF gives you
FAF-aware projectsReceipts include faf_score, faf_associated, faf_location β€” the receipt tells you not just did the tests pass, but what was the project's AI-readiness when they ran. Score trends over time become visible.
Full CAR FrameworkTAF (Receipt) + WJTTC (Audit) + FAF (Claim) β€” closed-loop attestation: project DNA β†’ testing audit β†’ permanent receipt

FAF is one tenant among many. TAF is the platform. The receipt printer doesn't care what kind of project prints to it.


πŸš€ HOW

Quick Start (GitHub Actions)

Step 1: Create .taf file

npm install -g faf-cli
faf taf init

Step 2: Add to CI workflow

name: Tests

on:
  push:
    branches: [main]

jobs:
  test:
    runs-on: ubuntu-latest
    permissions:
      contents: write  # Required for auto-commit

    steps:
      - uses: actions/checkout@v6

      - name: Setup Node.js
        uses: actions/setup-node@v6
        with:
          node-version: '20.x'

      - name: Install dependencies
        run: npm ci

      - name: Build
        run: npm run build

      - name: Run Tests and Capture Output
        run: npm test 2>&1 | tee test-output.txt

      - name: Generate TAF Receipt
        uses: Wolfe-Jam/faf-taf-git@v2.0.4
        with:
          test-output-file: test-output.txt
          auto-commit: 'true'
          commit-message: 'chore(taf): update .taf receipt [skip ci]'

Step 3: Push and watch

  • Tests run automatically
  • .taf file updates with new entry
  • Changes committed back to repo
  • History tracked in git

Standalone CLI (Any Platform)

# Run tests and update .taf
npm test 2>&1 | tee test-output.txt
npx faf-taf-git --file test-output.txt --commit

# Or in one command (legacy v1.x CLI)
npx faf-taf-git --command "npm test" --commit

GitLab CI

test:
  script:
    - npm ci
    - npm test 2>&1 | tee test-output.txt
    - npx faf-taf-git --file test-output.txt --commit --message "ci: update .taf [skip ci]"

Jenkins

stage('Test') {
  steps {
    sh 'npm ci'
    sh 'npm test 2>&1 | tee test-output.txt'
    sh 'npx faf-taf-git --file test-output.txt --commit'
  }
}

Local Development

# Run tests and update .taf (no commit)
npm test 2>&1 | tee test-output.txt
npx faf-taf-git --file test-output.txt --verbose

# Pre-commit hook
#!/bin/bash
npm test 2>&1 | tee test-output.txt && npx faf-taf-git --file test-output.txt

🎨 HOW IT WORKS

v2.0.0+ Architecture (Pre-Capture Pattern)

Step 1: Run Tests              Step 2: Generate Receipt
β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”        β”Œβ”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”
β”‚ npm test 2>&1 |     β”‚        β”‚ faf-taf-git reads    β”‚
β”‚ tee test-output.txt │───────▢│ test-output.txt and  β”‚
β”‚                     β”‚        β”‚ updates .taf file    β”‚
β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜        β””β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”€β”˜

Why separate steps?

  • Avoids GitHub Actions execution context corruption
  • More reliable (tested 19 methods before this breakthrough)
  • Platform-agnostic (works in ANY CI/CD)
  • Simpler architecture (400+ lines removed)

Process:

  1. Capture output - npm test 2>&1 | tee test-output.txt
  2. Parse results - Extracts test counts from Jest output
  3. Update .taf - Appends new test run to timeline
  4. Commit - Optionally commits changes to git

πŸ“‹ API

GitHub Action Inputs

InputDescriptionDefaultRequired
test-output-filePath to file containing test output-βœ… Yes
auto-commitAutomatically commit .taf updatestrueNo
commit-messageCustom commit messagechore(taf): update .taf receipt [skip ci]No

GitHub Action Outputs

OutputDescriptionExample
resultTest resultPASSED, FAILED, IMPROVED, DEGRADED
passedNumber of tests passed799
failedNumber of tests failed0
totalTotal number of tests808
skippedNumber of skipped tests9
taf-updatedWhether .taf was updatedtrue or false

CLI Options

npx faf-taf-git [options]

Options:
  --file <path>       Path to test output file (v2.0.0+)
  --command <cmd>     Test command to run (legacy v1.x)
  --commit            Auto-commit .taf changes
  --message <msg>     Custom commit message
  --cwd <dir>         Working directory
  --verbose, -v       Verbose output
  --help, -h          Show help

πŸ§ͺ Test Framework Support

FrameworkStatusNotes
Jestβœ… Fully supportedAll output formats
Vitestβœ… Fully supportedIncluding todo counts
Mocha⏳ Planned-
Pytest⏳ Planned-
Go test⏳ Planned-
Rust cargo test⏳ Planned-

πŸŽ“ Examples

Using Outputs

- name: Generate TAF Receipt
  id: taf
  uses: Wolfe-Jam/faf-taf-git@v2.0.4
  with:
    test-output-file: test-output.txt

- name: Check Results
  run: |
    echo "Result: ${{ steps.taf.outputs.result }}"
    echo "Tests: ${{ steps.taf.outputs.passed }}/${{ steps.taf.outputs.total }} passing"
    if [ "${{ steps.taf.outputs.result }}" == "DEGRADED" ]; then
      echo "⚠️ Test quality degraded!"
      exit 1
    fi

CircleCI

version: 2.1

jobs:
  test:
    docker:
      - image: node:20
    steps:
      - checkout
      - run: npm ci
      - run: npm test 2>&1 | tee test-output.txt
      - run: npx faf-taf-git --file test-output.txt --commit

Pre-commit Hook

#!/bin/bash
# .git/hooks/pre-commit

# Run tests and capture output
npm test 2>&1 | tee test-output.txt
TEST_EXIT=$?

# Update .taf (don't commit yet - that's what the commit is for!)
npx faf-taf-git --file test-output.txt

# Exit with test status
exit $TEST_EXIT

πŸ† The Golden Triangle

Projects with .faf + repo + .taf are engineered to succeed:

       .faf
     (WHAT IT IS)
         /    \
        /      \
       /        \
    repo    ←→   .taf
(IMPLEMENTATION) (PROOF IT WORKS)
  • .faf - Tells AI what the repo is (better than prose)
  • repo - The implementation (code doesn't lie)
  • .taf - Proves it works (receipts don't negotiate)

Why this matters:

  • AI reads .faf to understand your project
  • AI reads .taf to understand test quality
  • Better context = better AI assistance
  • Accountability built in

πŸ”§ Development

Build

npm run build

Test

npm test

Package (GitHub Action)

npm run package  # Creates bundled dist/index.js

Test Locally

npm run build
node dist/cli.js --help

πŸ“– Migration from v1.x

v2.0.0 is a breaking change - the architecture was redesigned for reliability.

What Changed

v1.x (test-command):

- uses: Wolfe-Jam/faf-taf-git@v1
  with:
    test-command: npm test

v2.x (test-output-file):

- run: npm test 2>&1 | tee test-output.txt

- uses: Wolfe-Jam/faf-taf-git@v2.0.4
  with:
    test-output-file: test-output.txt

Why the Change

v1.x ran tests inside the action using @actions/exec. This caused:

  • GitHub Actions execution context corruption
  • Logging failures (tested 19 different methods)
  • Filesystem operations failing silently
  • Unreliable receipt generation

v2.0.0 uses pre-capture pattern - separate test execution from receipt generation. This is:

  • βœ… More reliable (no execution context issues)
  • βœ… Platform-agnostic (works everywhere)
  • βœ… Simpler (400+ lines removed, 11KB smaller)
  • βœ… Production-ready (tested thoroughly)

Migration Steps

  1. Update workflow to use test-output-file instead of test-command
  2. Add test output capture step: npm test 2>&1 | tee test-output.txt
  3. Update version to @v2.0.4

See CHANGELOG.md for complete version history.


🀝 Contributing

See CONTRIBUTING.md for development guidelines.


πŸ“š Learn More


πŸ›£οΈ Standards Roadmap

FormatIANA Status
application/vnd.faf+yaml (FAF)βœ… Registered
application/vnd.fafm+yaml (VML)🟑 Under review
application/vnd.taf+yaml (TAF)⏳ Queued

.taf is filed entirely on its own merits β€” append-only test provenance, git-tracked, tamper-evident β€” independent of .faf's registration.


If faf-taf-git has been useful, consider starring the repo β€” it helps others find it.

πŸ“„ License

MIT - FREE FOREVER


πŸ’Ž Philosophy

Software Accountability

This tool implements a paradigm shift:

Before: Tests run β†’ results disappear β†’ no permanent record

After: Tests run β†’ .taf updated β†’ git-tracked forever

.taf is about accountability. Proof that your code works. Tracked over time. Visible to everyone.

Built with championship standards. F1-inspired engineering. Methodically tested.

Platform-agnostic core. Works everywhere. Trust the format.