Do equal-budget teams actually get fair fights? This project is a headless, deterministic combat simulator and batch-screening balance pipeline for an idle RPG — built to answer that question with data instead of intuition.
This simulation took shape from wanting a comprehensive way to collect and analyze data from the idle RPG's battles — which formulas worked, which stat weights worked, how stats affected battle outcomes, and how each hero's abilities shaped those outcomes and where they needed tuning. I wanted real, verifiable data to base balance and longevity decisions on. The build came with plenty of challenges I learned from and overcame — the biggest being how massive the data gets, and how quickly, which drove the need for different versions of the sim producing different amounts of data for different sizes of tests to narrow down results. The sim has already shown real merit, finding several problems in hero designs and formulas. It has been a genuinely valuable build.
Highlights:
• ~52× measured speedup after compiling the battle loop with Numba (~200 → ~10,400 battles/sec, same packet, both serial)
• 151 million battles screened in ~20 minutes on consumer laptop hardware
• A dominance problem found by screening (one module in 25/25 top risk teams) and fixed through controlled A/B packets: 66 → 36 → 27 dominant teams
• Every result gated by written GREEN/YELLOW/RED verdicts, 129 automated tests, and exact-parity proofs between the two battle loops
Implementation was executed by AI coding agents under my direction — I supplied the design, the architecture calls, and every accept/reject decision; the governance system that made that trustworthy (written operating rules, gate verdicts, logged approvals, evidence records) is my design.
Note: the current module pool is placeholder test kits, not shipped heroes — real hero kits and full stat interactions are future scope.
Post-mortem — what I'd do differently:
• Start the record keeping on day one. The sim's earliest real finds — the stat weight and formula problems — came before I set the repo up, so I have no hard evidence to point at for them. Learned that one the hard way.
• Commit every experiment, even the throwaway variants. One of my A/B test configs never got committed and only survives through its output files.
• Lock design targets in before grading against them. I audited combat length against a 200-tick target that was never made official, and had to walk that verdict back.
• Plan for the data blowing up sooner. CSV writing became the bottleneck — around 60% of runtime — before I moved to binary output.

Systems-design case study: a headless deterministic combat engine + batch-screening balance pipeline.
Check the claims yourself — code, gate records, and evidence: https://github.com/cody220022-jpg/idle-rpg-combat-sim-showcase