yxc20098 commited on
Commit
40d2f25
·
1 Parent(s): 7e9ddc9

fix-forward: repair merged PR#5/#6 (unblocked by own-unit actor_type fix)

Browse files

The collaborator merged PR#5 (tech-production-planning) and PR#6
(economy-investment/rush-hour fail_conditions + longhorizon pack) raw
— main was RED (3 failures). With the engine own-unit actor_type fix:

- tech-production-planning: now WINNABLE (scripted chain wins easy
~tick 2883). Un-quarantined; realigned the inert within_ticks to the
tick reachable at max_turns (5403/7203/8103) + added timeout fails;
classified NOT_APPLICABLE (non-spatial build-order); added 'mine'
glossary entry; fixed the PR's test (res.signals.units_summary
AttributeError -> a win already proves the 3tnk; hard-fail test
updated to the any_of shape).
- economy-investment / rush-hour / longhorizon-opening-to-assault:
realigned the inert after_ticks fails to R=93+90·(max_turns-1) so a
non-finisher LOSES instead of drawing (turn budget unchanged ->
solvency-safe); classified longhorizon NOT_APPLICABLE.

Suite 380 passed, 1 skipped; catalog regenerated.

docs/scenarios.html CHANGED
The diff for this file is too large to render. See raw diff
 
openra_bench/game_knowledge.py CHANGED
@@ -52,6 +52,7 @@ ACTOR_GLOSSARY: dict[str, str] = {
52
  "fix": "service depot (repairs vehicles)",
53
  "dome": "radar dome (reveals map / tech prerequisite)",
54
  "silo": "ore silo (stores surplus ore)",
 
55
  "gun": "gun turret (anti-vehicle base defence)",
56
  "pbox": "pillbox (anti-infantry base defence)",
57
  "tsla": "Tesla coil (powerful anti-everything defence)",
 
52
  "fix": "service depot (repairs vehicles)",
53
  "dome": "radar dome (reveals map / tech prerequisite)",
54
  "silo": "ore silo (stores surplus ore)",
55
+ "mine": "ore mine (resource node harvesters gather from)",
56
  "gun": "gun turret (anti-vehicle base defence)",
57
  "pbox": "pillbox (anti-infantry base defence)",
58
  "tsla": "Tesla coil (powerful anti-everything defence)",
openra_bench/scenarios/packs/economy-investment.yaml CHANGED
@@ -73,9 +73,11 @@ levels:
73
  all_of:
74
  - building_count_gte: {type: proc, n: 2}
75
  - building_count_gte: {type: powr, n: 2}
76
- - within_ticks: 22000
 
 
77
  fail_condition:
78
- after_ticks: 22001
79
  max_turns: 70
80
  medium:
81
  description: >
@@ -89,9 +91,9 @@ levels:
89
  - building_count_gte: {type: proc, n: 2}
90
  - building_count_gte: {type: powr, n: 2}
91
  - own_units_gte: 3
92
- - within_ticks: 16000
93
  fail_condition:
94
- after_ticks: 16001
95
  max_turns: 80
96
  hard:
97
  description: >
@@ -105,9 +107,9 @@ levels:
105
  - own_units_gte: 6
106
  - building_count_gte: {type: proc, n: 1}
107
  - units_lost_lte: 0
108
- - within_ticks: 14000
109
  fail_condition:
110
  any_of:
111
- - after_ticks: 14001
112
  - not: {units_lost_lte: 0}
113
  max_turns: 90
 
73
  all_of:
74
  - building_count_gte: {type: proc, n: 2}
75
  - building_count_gte: {type: powr, n: 2}
76
+ - within_ticks: 6303
77
+ # aligned to tick reachable at max_turns (~90/turn): non-finisher
78
+ # LOSES not draws; turn budget unchanged (solvency-safe).
79
  fail_condition:
80
+ after_ticks: 6303
81
  max_turns: 70
82
  medium:
83
  description: >
 
91
  - building_count_gte: {type: proc, n: 2}
92
  - building_count_gte: {type: powr, n: 2}
93
  - own_units_gte: 3
94
+ - within_ticks: 7203
95
  fail_condition:
96
+ after_ticks: 7203
97
  max_turns: 80
98
  hard:
99
  description: >
 
107
  - own_units_gte: 6
108
  - building_count_gte: {type: proc, n: 1}
109
  - units_lost_lte: 0
110
+ - within_ticks: 8103
111
  fail_condition:
112
  any_of:
113
+ - after_ticks: 8103
114
  - not: {units_lost_lte: 0}
115
  max_turns: 90
openra_bench/scenarios/packs/longhorizon-opening-to-assault.yaml CHANGED
@@ -103,9 +103,9 @@ levels:
103
  - has_building: proc
104
  - own_units_gte: 4
105
  - reach_region: {x: 115, y: 32, radius: 8}
106
- - within_ticks: 40000
107
  fail_condition:
108
- after_ticks: 40001
109
  max_turns: 120
110
 
111
  medium:
@@ -119,9 +119,9 @@ levels:
119
  - has_building: proc
120
  - own_units_gte: 5
121
  - reach_region: {x: 115, y: 32, radius: 7}
122
- - within_ticks: 32000
123
  fail_condition:
124
- after_ticks: 32001
125
  max_turns: 140
126
 
127
  hard:
@@ -140,10 +140,10 @@ levels:
140
  - has_building: proc
141
  - own_units_gte: 6
142
  - reach_region: {x: 115, y: 32, radius: 6}
143
- - within_ticks: 24000
144
  - units_lost_lte: 4
145
  fail_condition:
146
  any_of:
147
- - after_ticks: 24001
148
  - not: {own_units_gte: 1}
149
  max_turns: 160
 
103
  - has_building: proc
104
  - own_units_gte: 4
105
  - reach_region: {x: 115, y: 32, radius: 8}
106
+ - within_ticks: 10803
107
  fail_condition:
108
+ after_ticks: 10803
109
  max_turns: 120
110
 
111
  medium:
 
119
  - has_building: proc
120
  - own_units_gte: 5
121
  - reach_region: {x: 115, y: 32, radius: 7}
122
+ - within_ticks: 12603
123
  fail_condition:
124
+ after_ticks: 12603
125
  max_turns: 140
126
 
127
  hard:
 
140
  - has_building: proc
141
  - own_units_gte: 6
142
  - reach_region: {x: 115, y: 32, radius: 6}
143
+ - within_ticks: 14403
144
  - units_lost_lte: 4
145
  fail_condition:
146
  any_of:
147
+ - after_ticks: 14403
148
  - not: {own_units_gte: 1}
149
  max_turns: 160
openra_bench/scenarios/packs/rush-hour.yaml CHANGED
@@ -523,12 +523,12 @@ levels:
523
  win_condition:
524
  all_of:
525
  - units_killed_gte: 5
526
- - within_ticks: 16000
527
  - units_lost_lte: 6
528
  fail_condition:
529
  any_of:
530
  - not: {own_units_gte: 1}
531
- - after_ticks: 16001
532
  medium:
533
  description: >
534
  Rush Hour Sweep \u2014 medium. Tighter clock and attrition cap:
@@ -537,12 +537,12 @@ levels:
537
  win_condition:
538
  all_of:
539
  - units_killed_gte: 7
540
- - within_ticks: 13000
541
  - units_lost_lte: 4
542
  fail_condition:
543
  any_of:
544
  - not: {own_units_gte: 1}
545
- - after_ticks: 13001
546
  hard:
547
  description: >
548
  Rush Hour Sweep \u2014 hard. The agent force already round-robins
@@ -552,9 +552,9 @@ levels:
552
  win_condition:
553
  all_of:
554
  - units_killed_gte: 9
555
- - within_ticks: 10000
556
  - units_lost_lte: 3
557
  fail_condition:
558
  any_of:
559
  - not: {own_units_gte: 1}
560
- - after_ticks: 10001
 
523
  win_condition:
524
  all_of:
525
  - units_killed_gte: 5
526
+ - within_ticks: 3603
527
  - units_lost_lte: 6
528
  fail_condition:
529
  any_of:
530
  - not: {own_units_gte: 1}
531
+ - after_ticks: 3603
532
  medium:
533
  description: >
534
  Rush Hour Sweep \u2014 medium. Tighter clock and attrition cap:
 
537
  win_condition:
538
  all_of:
539
  - units_killed_gte: 7
540
+ - within_ticks: 3603
541
  - units_lost_lte: 4
542
  fail_condition:
543
  any_of:
544
  - not: {own_units_gte: 1}
545
+ - after_ticks: 3603
546
  hard:
547
  description: >
548
  Rush Hour Sweep \u2014 hard. The agent force already round-robins
 
552
  win_condition:
553
  all_of:
554
  - units_killed_gte: 9
555
+ - within_ticks: 3603
556
  - units_lost_lte: 3
557
  fail_condition:
558
  any_of:
559
  - not: {own_units_gte: 1}
560
+ - after_ticks: 3603
openra_bench/scenarios/packs/tech-production-planning.yaml CHANGED
@@ -67,7 +67,11 @@ levels:
67
  all_of:
68
  - unit_type_count_gte: {type: 3tnk, n: 1}
69
  - building_count_gte: {type: fix, n: 1}
70
- - within_ticks: 18000
 
 
 
 
71
  max_turns: 60
72
 
73
  medium:
@@ -93,7 +97,9 @@ levels:
93
  - unit_type_count_gte: {type: e3, n: 1}
94
  - unit_type_count_gte: {type: e1, n: 3}
95
  - power_surplus_gte: 0
96
- - within_ticks: 22000
 
 
97
  max_turns: 80
98
 
99
  hard:
@@ -121,7 +127,9 @@ levels:
121
  all_of:
122
  - enemies_discovered_gte: 2
123
  - unit_type_count_gte: {type: e3, n: 5}
124
- - within_ticks: 14000
125
  fail_condition:
126
- unit_type_count_gte: {type: e1, n: 10}
 
 
127
  max_turns: 90
 
67
  all_of:
68
  - unit_type_count_gte: {type: 3tnk, n: 1}
69
  - building_count_gte: {type: fix, n: 1}
70
+ - within_ticks: 5403
71
+ # aligned to tick reachable at max_turns (~90/turn); scripted
72
+ # chain wins easy by ~tick 2883 so this stays solvable.
73
+ fail_condition:
74
+ after_ticks: 5403
75
  max_turns: 60
76
 
77
  medium:
 
97
  - unit_type_count_gte: {type: e3, n: 1}
98
  - unit_type_count_gte: {type: e1, n: 3}
99
  - power_surplus_gte: 0
100
+ - within_ticks: 7203
101
+ fail_condition:
102
+ after_ticks: 7203
103
  max_turns: 80
104
 
105
  hard:
 
127
  all_of:
128
  - enemies_discovered_gte: 2
129
  - unit_type_count_gte: {type: e3, n: 5}
130
+ - within_ticks: 8103
131
  fail_condition:
132
+ any_of:
133
+ - after_ticks: 8103
134
+ - unit_type_count_gte: {type: e1, n: 10}
135
  max_turns: 90
tests/test_hard_tier.py CHANGED
@@ -48,6 +48,11 @@ NOT_APPLICABLE = {
48
  "economy-force-buildup": "non-spatial: production economy",
49
  "building-and-planning": "non-spatial: build-order/tech, fixed base",
50
  "strict-production-bom": "non-spatial: exact bill-of-materials spec",
 
 
 
 
 
51
  "reasoning-risk-route": "rigor 5/5 from one tuned safe seam — varying "
52
  "the start would break the single-solution tuning / seed parity",
53
  "strategy-dilemma": "win redesigned to destroy fact+proc (faithful "
 
48
  "economy-force-buildup": "non-spatial: production economy",
49
  "building-and-planning": "non-spatial: build-order/tech, fixed base",
50
  "strict-production-bom": "non-spatial: exact bill-of-materials spec",
51
+ "tech-production-planning": "non-spatial: build-order dependency "
52
+ "planning (precedence + power + budget); start position irrelevant",
53
+ "longhorizon-opening-to-assault": "fixed pre-seeded base; the test "
54
+ "is the scout→tech→army→strike phase chain within one budget, not "
55
+ "start-position generalization (single base by design)",
56
  "reasoning-risk-route": "rigor 5/5 from one tuned safe seam — varying "
57
  "the start would break the single-solution tuning / seed parity",
58
  "strategy-dilemma": "win redesigned to destroy fact+proc (faithful "
tests/test_tech_production_planning.py CHANGED
@@ -75,11 +75,12 @@ def test_easy_tech_chain_wins_and_scores():
75
  assert "weap" in btypes and "fix" in btypes, (
76
  f"chain incomplete; own_building_types={btypes}"
77
  )
78
- # The agent actually trained a Heavy Tank.
79
- unit_types = [u["type"] for u in res.signals.units_summary]
80
- assert "3tnk" in unit_types, f"no 3tnk produced; units={unit_types}"
81
  # Production debited the budget.
82
  assert res.signals.cash < 5000, "construction must debit the budget"
 
 
 
 
83
  assert res.outcome == "win", f"easy should be winnable, got {res.outcome}"
84
 
85
  sc = score_episode(c, res)
@@ -126,6 +127,10 @@ def test_hard_fail_predicate_set():
126
  it). Schema-level check, no episode run required."""
127
  c = compile_level(load_pack(PACK), "hard")
128
  assert c.fail_condition is not None
129
- # The fail leaf is unit_type_count_gte on e1 at n=10.
 
 
130
  fc = c.fail_condition.model_dump(exclude_none=True)
131
- assert fc == {"unit_type_count_gte": {"type": "e1", "n": 10}}, fc
 
 
 
75
  assert "weap" in btypes and "fix" in btypes, (
76
  f"chain incomplete; own_building_types={btypes}"
77
  )
 
 
 
78
  # Production debited the budget.
79
  assert res.signals.cash < 5000, "construction must debit the budget"
80
+ # A win implies a Heavy Tank was trained: the win condition
81
+ # includes `unit_type_count_gte {type: 3tnk, n: 1}`, so outcome ==
82
+ # "win" is itself proof the 3tnk was produced (and observed — this
83
+ # also exercises the own-unit actor_type fix).
84
  assert res.outcome == "win", f"easy should be winnable, got {res.outcome}"
85
 
86
  sc = score_episode(c, res)
 
127
  it). Schema-level check, no episode run required."""
128
  c = compile_level(load_pack(PACK), "hard")
129
  assert c.fail_condition is not None
130
+ # Hard loses on EITHER the timeout (deadline aligned to the tick
131
+ # reachable at max_turns — no draw degeneracy) OR overproducing
132
+ # infantry past 10.
133
  fc = c.fail_condition.model_dump(exclude_none=True)
134
+ clauses = fc.get("any_of", [fc])
135
+ assert {"unit_type_count_gte": {"type": "e1", "n": 10}} in clauses, fc
136
+ assert any("after_ticks" in cl for cl in clauses), fc