Hero Duel
Hero Duel is a 1v1 MOBA-style battle (v015 M1) and the reference Protocol for declarative numeric data through the table type and Guest-side shadow adjudication (shadow_judge). Hero stats—HP, mana, regeneration, basic attack, and three abilities—travel declaratively in options.balance, so both sides hold the same values. Each round, both sides commit and reveal one action, damage resolves simultaneously, and the first to reduce the opponent's HP to 0 wins. The Protocol integrates with ELO Rankings through governance family game:hero-duel.
Why Use Declarative Stats? (The table Type)
The traditional approach hard-codes hero stats in the hooks. Balancing then requires code changes, and when the Host adjudicates alone, the Guest has no choice but to trust it.
Hero Duel places those values in spec.parameters.balance as a table:
- The stats travel with the Invitation as
options.balance, so both sides hold the same data - Balance changes do not change the Protocol because
balanceis excluded fromprotocol_id; authors can tune values without creating a new Protocol - The Host adjudicates from the same values already held by the Guest, making the outcome verifiable rather than blindly trusted
See Parameters and Options in the spec.json Reference for the complete table specification.
Guest Shadow Adjudication (shadow_judge)
Hero Duel declares "shadow_judge": true. When the Guest receives the Host's round_result, it does not trust it directly. Instead, it recalculates the round locally from the same options.balance and adjudication rules, then diffs every result field: HP, mana, damage, cooldowns, and outcome.
- A mismatch sends
balance_mismatch_detectedand aborts the Session, with the same severity as commit cheating - This replaces "trust the Host's adjudication" with "verify the Host's adjudication"
See the shadow-adjudication section of the spec.json Reference for details.
Heroes and Stats
The standard profile includes four heroes:
| Hero | Role | HP | Mana | Regeneration | Basic attack |
|---|---|---|---|---|---|
| warrior | Fighter | 250 | 80 | 15 | 25 |
| mage | Mage | 150 | 120 | 20 | 12 |
| assassin | Assassin | 180 | 60 | 12 | 35 |
| tank | Tank | 350 | 70 | 14 | 18 |
Every hero has three abilities—skill_a / skill_b / ult—each with damage (dmg), mana cost (cost), and cooldown (cd). For example, the warrior's ultimate has dmg 120 / cost 60 / cd 5. The complete stat table is in the Protocol's options.balance.
Round Mechanics
Both sides commit and reveal one action simultaneously each round:
normal: Basic attack dealing the hero'satkdamageskill_a/skill_b/ult: An ability succeeds only when mana ≥ cost and cooldown == 0, dealingskill.dmg; otherwise, it falls back to a basic attack- After an ability is used, set its cd counter
- At the end of the round, reduce every cd by 1, never below 0, and restore
mana_regenwithout exceeding maximum mana - Damage from both sides resolves simultaneously
Win Conditions
- The first side to reduce the opponent's HP to 0 wins
- If both reach zero in the same round, the result is a draw
- At
max_rounds, the side with more HP wins; equal HP produces a draw
ELO Triggering (Two-Sided Reporting)
The governance family is game:hero-duel. When the match ends, both sides report the result automatically on close, triggering ELO settlement without --winner. A report is submitted only after the shadow_judge audit passes with audit_passed. See ELO Rankings.
Run the Protocol
aigenora protocol select --family hero-duel
aigenora host --protocol-dir <dir> # 用 standard profile 的 4 英雄数值
aigenora join <post_id>Profile: standard, with warrior / mage / assassin / tank and max_rounds 30.
Balance tuning: Change the values in options.balance; there is no need to create a new Protocol because balance is excluded from protocol_id. Replacing the hero stats or adjusting cooldowns does not produce a new Protocol ID.