Skip to content
Back to skills

Fpa Backtest Learn

ASecurity

Use when you want the model to learn from how its past forecasts actually turned out - scoring forecasts against the company's real actuals, backtesting assumptions on history, and proposing ratified improvements. Runs at/after monthly close.

  • 6 stars
  • 0 votes
  • 0 copies
  • 2 views
  • Added September 6, 2026
businessrailstestingapiperformance

Works with

  • api

Security analysis

A100/100

Scanned September 6, 2026

npx -y skills add JeffBrines/openfpa --skill fpa-backtest-learn --agent claude-code

Installs into .claude/skills of the current project.

Are you the author of Fpa Backtest Learn?

Add the live security badge to your README. It updates with every re-scan.

Security grade badge for Fpa Backtest Learn
[![Security: A — Skills Directory](https://www.skillsdirectory.com/api/skills/jeffbrines-fpa-backtest-learn/badge)](https://www.skillsdirectory.com/skills/jeffbrines-fpa-backtest-learn)

More formats (shields.io, HTML) on the badges page. Keep it an A: scan every change in CI with Pro.

Download with Pro
SKILL.md
---
name: fpa-backtest-learn
description: Use when you want the model to learn from how its past forecasts actually turned out - scoring forecasts against the company's real actuals, backtesting assumptions on history, and proposing ratified improvements. Runs at/after monthly close.
---

# Backtest & Learn (Operate)

## Overview

The model should get measurably better at this business over time. This skill
scores past forecasts against the company's actuals, surfaces what keeps missing,
and proposes improvements a human ratifies. The objective metric is reconciliation
error against the user's own books (`pyfpa.score_forecast`) - the FP&A analog of a
validation loss.

**Core principle:** self-experimenting, but never self-promoting. The AI may run
and discard bounded challengers autonomously; a human approves replacement of
the champion. Everything learned lives as plain files in `.fpa/`.

## Memory (`.fpa/`)

- `forecasts/<period>.snapshot.yaml` - each forecast's assumptions + predictions, and (after close) its score.
- `scorecard.md` - the running track record (rendered, never hand-edited).
- `experiments/<slug>.experiment.yaml` - each tested model change, its evidence,
  changed files, checks, before/after metrics, and decision.
- `learnings.md` - every accepted change: what, the evidence, the backtest delta, the date.

## Workflow

1. **Snapshot every forecast.** When you produce a forecast, persist it:
   `snapshot_forecast(cfg, forecast_df, label=<period>, created=<today>)` →
   `save_snapshot(..., ".fpa/forecasts/<period>.snapshot.yaml")`.
2. **Score at close.** When a period closes (actuals via **fpa-configure-actuals**),
   load that period's snapshot, `score_forecast(snap.predicted, actuals)`, write the
   score back into the snapshot, and re-render `scorecard.md` with `render_scorecard`.
3. **Attribute** each material per-line miss to a driver (volume / price / cost ratio
   / working-capital timing). **Run the fpa-cfo-judgment one-time-item screen first** -
   never blame the model for a one-off.
   - **Monitor applied corrections:** if a `type: parametric` correction's target line keeps missing, flag it as possibly stale (`applied → superseded`) for the human - never auto-revert.
4. **Create an experiment** before changing the model. State the financial
   hypothesis, CFO question, evidence, fit periods, holdout periods, and files
   expected to change. Save it with `pyfpa.save_experiment`.
5. **Propose**, tagged by type:
   - **Parametric** (an assumption change): re-score it with `holdout_backtest` on the
     company's history. Surface it **only if it lowers holdout fitness** (not in-sample),
     ranked by the delta. Clamp the proposed move with `magnitude_cap` (±25%/cycle).
   - **Structural** (a methodology/skill change, e.g. a revenue-recognition lag): surface
     **only** when `persistent_miss` is true for the line (same-signed across K≥2 closes)
     and it survived the one-time screen. Hand it to **fpa-learn-business** to generate the
     skill *on approval* - propose, don't auto-write.
6. **Evaluate.** Record before/after metrics and explicit checks in the experiment.
   A model change that breaks reconciliation or another accounting invariant is
   failed even if one headline metric improves.
7. **Ratify + log.** Present proposals; the human accepts/rejects. On accept, add
   an `ExperimentDecision`, set `status: accepted`, save with explicit
   `overwrite=True`, update the company model, and append to `learnings.md`.
   Rejected and reverted experiments remain in memory.
8. **Run `fpa-research-loop`** when the miss warrants multiple autonomous
   challenger epochs instead of one manually proposed change.

## Bootstrap (day one)

If the company already has ~12+ months of actuals, you don't have to wait: run
`holdout_backtest` immediately (fit on the earlier months, hold out the recent ones)
to report current accuracy and the first round of parametric proposals.

## Guardrails (always)

- Never score on data the model was fit on (`holdout_backtest` enforces this).
- No proposal off a single period - require a persistent, same-signed miss.
- A parametric change must improve **holdout** fitness, not in-sample fit.
- Cap how far any assumption moves per cycle (`magnitude_cap`).
- Human ratifies champion promotion; autonomous failed epochs are logged and reversible.
- Missing or zero actuals are insufficient evidence, not perfect forecast performance.

## Next

Scored + learned → **fpa-board-briefing** (report the forecast and how it's tracking).

Attribution

Is this your skill, or is something wrong with this listing? Request removal or report an issue. Author removals are honored within 72 hours.

Comments

Loading comments…

Newsletter

Get the weekly list of safe new skills, and the ones we pulled.