{
  "name": "Corpus-bound calculation receipt — Topstep $50k reference",
  "description": "Versioned, hash-addressed analytical calculation receipt binding a firm rules corpus id to trader inputs and honest public outputs (dollar levels + after-cost expectancy). Public face is free and citable; first sale opens the worksheet and portfolio-replay kit under the same hash so a visitor can re-mint with their own portfolio.",
  "url": "https://propsurvival.com/articles/calc-receipt-data.json",
  "license": "https://creativecommons.org/licenses/by/4.0/",
  "citation": "PropSurvival calc receipt 566d4961 · calc-receipt-1 · topstep@40ecf3b35a8ccb90",
  "datePublished": "2026-08-16",
  "dateModified": "2026-08-16",
  "_generated_by": "tools/build-calc-receipt.js",
  "_reproduce": "node tools/build-calc-receipt.js",
  "_subject_is_synthetic": true,
  "method": {
    "engine": "src/lib/calc-receipt.js — rule dollar levels + same expectancy arithmetic as coreMetrics / net-return-proof",
    "formulaId": "corpus-rule-levels+expectancy-after-cost-1",
    "version": "calc-receipt-1",
    "formula": "levels: $ = size×pct; E_net = p_w*(W-c) - p_l*(L+c) - p_be*c; floor0 = size - maxDD$",
    "evidenceClass": "Model-derived analytical result bound to a disclosed rules corpus id. Not an empirical claim about any named market outcome or pass rate.",
    "assumptions": [
      "Firm rule percentages are taken from the stated corpus id (rulesHash when present) and applied as fixed fractions of the stated account size.",
      "Daily loss pct 100 is the engine sentinel for 'no daily loss limit' — public.dailyLossUsd is null in that case.",
      "At t = 0 (fresh account, equity = balance = high-water mark) the drawdown floor is balance − maxDrawdownUsd for every ddMode the shipping engine models.",
      "Trade outcomes are i.i.d. at the stated win and break-even rates (no streak or Markov clustering).",
      "Average win R and average loss R are fixed constants; per-trade cost is a constant R deduction on every trade.",
      "This receipt is analytical arithmetic, not a Monte Carlo path sample of pass probability."
    ],
    "rulesHashAlgorithm": "sha256(canonical firm rules JSON paths)[:16] — same family as tools/corpus-sync.js"
  },
  "reference": {
    "corpusId": {
      "firmId": "topstep",
      "firmName": "Topstep",
      "accountSize": 50000,
      "source": "rules/topstep",
      "rulesHash": "40ecf3b35a8ccb90"
    },
    "rules": {
      "targetPct": 6,
      "dailyDdPct": 2,
      "totalDdPct": 4,
      "ddMode": "trail_eod",
      "freezeAtInitial": true,
      "consistencyPct": 50,
      "minDays": 2,
      "maxDays": 60,
      "onDailyBasis": "initial"
    },
    "trader": {
      "winRatePct": 50,
      "breakEvenRatePct": 0,
      "avgWinR": 1.2,
      "avgLossR": 1,
      "tradeCostR": 0.05
    }
  },
  "proof": {
    "kind": "calc-receipt",
    "version": "calc-receipt-1",
    "hash": "566d4961",
    "engine": {
      "formulaId": "corpus-rule-levels+expectancy-after-cost-1",
      "matches": "rule dollar levels + coreMetrics.e / grossE / costDrag",
      "formula": "levels: $ = size×pct; E_net = p_w*(W-c) - p_l*(L+c) - p_be*c; floor0 = size - maxDD$"
    },
    "assumptions": [
      "Firm rule percentages are taken from the stated corpus id (rulesHash when present) and applied as fixed fractions of the stated account size.",
      "Daily loss pct 100 is the engine sentinel for 'no daily loss limit' — public.dailyLossUsd is null in that case.",
      "At t = 0 (fresh account, equity = balance = high-water mark) the drawdown floor is balance − maxDrawdownUsd for every ddMode the shipping engine models.",
      "Trade outcomes are i.i.d. at the stated win and break-even rates (no streak or Markov clustering).",
      "Average win R and average loss R are fixed constants; per-trade cost is a constant R deduction on every trade.",
      "This receipt is analytical arithmetic, not a Monte Carlo path sample of pass probability."
    ],
    "corpusId": {
      "firmId": "topstep",
      "firmName": "Topstep",
      "rulesHash": "40ecf3b35a8ccb90",
      "accountSize": 50000,
      "source": "rules/topstep"
    },
    "rules": {
      "targetPct": 6,
      "dailyDdPct": 2,
      "totalDdPct": 4,
      "ddMode": "trail_eod",
      "freezeAtInitial": true,
      "consistencyPct": 50,
      "minDays": 2,
      "maxDays": 60,
      "onDailyBasis": "initial"
    },
    "trader": {
      "winRatePct": 50,
      "breakEvenRatePct": 0,
      "avgWinR": 1.2,
      "avgLossR": 1,
      "tradeCostR": 0.05
    },
    "inputs": {
      "corpusId": {
        "firmId": "topstep",
        "firmName": "Topstep",
        "rulesHash": "40ecf3b35a8ccb90",
        "accountSize": 50000,
        "source": "rules/topstep"
      },
      "rules": {
        "targetPct": 6,
        "dailyDdPct": 2,
        "totalDdPct": 4,
        "ddMode": "trail_eod",
        "freezeAtInitial": true,
        "consistencyPct": 50,
        "minDays": 2,
        "maxDays": 60,
        "onDailyBasis": "initial"
      },
      "trader": {
        "winRatePct": 50,
        "breakEvenRatePct": 0,
        "avgWinR": 1.2,
        "avgLossR": 1,
        "tradeCostR": 0.05
      }
    },
    "public": {
      "targetUsd": 3000,
      "dailyLossUsd": 1000,
      "maxDrawdownUsd": 2000,
      "floorUsd": 48000,
      "headroomUsd": 2000,
      "bindsAtStart": "daily",
      "targetVsDrawdown": 1.5,
      "consistencyPct": 50,
      "netExpectancyR": 0.05,
      "grossExpectancyR": 0.1,
      "costDrag": 0.5,
      "formula": "levels: $ = size×pct; E_net = p_w*(W-c) - p_l*(L+c) - p_be*c; floor0 = size - maxDD$"
    },
    "full": null,
    "unlock": {
      "requires": "sale",
      "opens": "full",
      "open": false,
      "note": "Public face only. First sale opens the worksheet and portfolio-replay kit under the same hash; re-mint with your trader inputs under the same corpus id."
    },
    "citation": "PropSurvival calc receipt 566d4961 · calc-receipt-1 · topstep@40ecf3b35a8ccb90",
    "evidenceClass": "Model-derived analytical result bound to a disclosed rules corpus id. Not an empirical claim about any named market outcome or pass rate."
  },
  "unlock": {
    "requires": "sale",
    "opens": "full worksheet + portfolioReplay under the same hash",
    "recompute": "node -e \"const CR=require('./src/lib/calc-receipt.js');const r=require('./articles/calc-receipt-data.json');console.log(JSON.stringify(CR.mint({corpusId:r.reference.corpusId,rules:r.reference.rules,trader:r.reference.trader},{unlocked:true}),null,2))\""
  }
}
