Spaces:
Sleeping
Sleeping
affu143 commited on
Commit Β·
f18f9f9
1
Parent(s): 3d87f50
cmmit kodthuna
Browse files- server/app.py +34 -14
- server/config_debug_environment.py +7 -1
- server/graders/grader_api.py +79 -32
- test_validator_simulation.py +109 -0
server/app.py
CHANGED
|
@@ -88,6 +88,17 @@ def health():
|
|
| 88 |
def metadata():
|
| 89 |
"""Metadata endpoint with grader paths for validator discovery."""
|
| 90 |
print("[VALIDATOR] GET /metadata called")
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 91 |
return {
|
| 92 |
"name": "ConfigDebugEnvironment",
|
| 93 |
"description": "An environment for training AI agents to debug broken configuration files",
|
|
@@ -96,7 +107,7 @@ def metadata():
|
|
| 96 |
{
|
| 97 |
"id": tid,
|
| 98 |
"has_grader": True,
|
| 99 |
-
"grader": f"server.graders.grader_api:
|
| 100 |
}
|
| 101 |
for tid in TASK_ORDER
|
| 102 |
],
|
|
@@ -137,25 +148,25 @@ async def grader_endpoint(request: Request):
|
|
| 137 |
body.get("action", {}).get("fixed_config", "{}"))
|
| 138 |
|
| 139 |
from server.graders.grader_api import (
|
| 140 |
-
|
| 141 |
-
|
| 142 |
)
|
| 143 |
|
| 144 |
grader_map = {
|
| 145 |
-
"task1_json":
|
| 146 |
-
"task2_yaml":
|
| 147 |
-
"task3_dockerfile":
|
| 148 |
-
"task4_compose":
|
| 149 |
-
"task5_k8s":
|
| 150 |
-
"task6_github_actions":
|
| 151 |
-
"task7_nginx":
|
| 152 |
}
|
| 153 |
|
| 154 |
-
|
| 155 |
-
if
|
| 156 |
return {"error": f"Unknown task_id: {task_id}", "score": 0.01}
|
| 157 |
|
| 158 |
-
score =
|
| 159 |
print(f"[GRADER] task={task_id} score={score}")
|
| 160 |
return {"task_id": task_id, "score": score, "has_grader": True}
|
| 161 |
except Exception as e:
|
|
@@ -165,6 +176,15 @@ async def grader_endpoint(request: Request):
|
|
| 165 |
|
| 166 |
@app.get("/tasks")
|
| 167 |
def tasks():
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 168 |
return {
|
| 169 |
"tasks": [
|
| 170 |
{
|
|
@@ -174,7 +194,7 @@ def tasks():
|
|
| 174 |
"file_type": get_task(tid).file_type,
|
| 175 |
"num_bugs": get_task(tid).num_bugs,
|
| 176 |
"has_grader": True,
|
| 177 |
-
"grader": f"server.graders.grader_api:
|
| 178 |
}
|
| 179 |
for tid in TASK_ORDER
|
| 180 |
],
|
|
|
|
| 88 |
def metadata():
|
| 89 |
"""Metadata endpoint with grader paths for validator discovery."""
|
| 90 |
print("[VALIDATOR] GET /metadata called")
|
| 91 |
+
|
| 92 |
+
task_grader_map = {
|
| 93 |
+
"task1_json": "Task1Grader",
|
| 94 |
+
"task2_yaml": "Task2Grader",
|
| 95 |
+
"task3_dockerfile": "Task3Grader",
|
| 96 |
+
"task4_compose": "Task4Grader",
|
| 97 |
+
"task5_k8s": "Task5Grader",
|
| 98 |
+
"task6_github_actions": "Task6Grader",
|
| 99 |
+
"task7_nginx": "Task7Grader",
|
| 100 |
+
}
|
| 101 |
+
|
| 102 |
return {
|
| 103 |
"name": "ConfigDebugEnvironment",
|
| 104 |
"description": "An environment for training AI agents to debug broken configuration files",
|
|
|
|
| 107 |
{
|
| 108 |
"id": tid,
|
| 109 |
"has_grader": True,
|
| 110 |
+
"grader": f"server.graders.grader_api:{task_grader_map[tid]}",
|
| 111 |
}
|
| 112 |
for tid in TASK_ORDER
|
| 113 |
],
|
|
|
|
| 148 |
body.get("action", {}).get("fixed_config", "{}"))
|
| 149 |
|
| 150 |
from server.graders.grader_api import (
|
| 151 |
+
Task1Grader, Task2Grader, Task3Grader,
|
| 152 |
+
Task4Grader, Task5Grader, Task6Grader, Task7Grader,
|
| 153 |
)
|
| 154 |
|
| 155 |
grader_map = {
|
| 156 |
+
"task1_json": Task1Grader(),
|
| 157 |
+
"task2_yaml": Task2Grader(),
|
| 158 |
+
"task3_dockerfile": Task3Grader(),
|
| 159 |
+
"task4_compose": Task4Grader(),
|
| 160 |
+
"task5_k8s": Task5Grader(),
|
| 161 |
+
"task6_github_actions": Task6Grader(),
|
| 162 |
+
"task7_nginx": Task7Grader(),
|
| 163 |
}
|
| 164 |
|
| 165 |
+
grader = grader_map.get(task_id)
|
| 166 |
+
if grader is None:
|
| 167 |
return {"error": f"Unknown task_id: {task_id}", "score": 0.01}
|
| 168 |
|
| 169 |
+
score = grader.grade(submitted_config)
|
| 170 |
print(f"[GRADER] task={task_id} score={score}")
|
| 171 |
return {"task_id": task_id, "score": score, "has_grader": True}
|
| 172 |
except Exception as e:
|
|
|
|
| 176 |
|
| 177 |
@app.get("/tasks")
|
| 178 |
def tasks():
|
| 179 |
+
task_grader_map = {
|
| 180 |
+
"task1_json": "Task1Grader",
|
| 181 |
+
"task2_yaml": "Task2Grader",
|
| 182 |
+
"task3_dockerfile": "Task3Grader",
|
| 183 |
+
"task4_compose": "Task4Grader",
|
| 184 |
+
"task5_k8s": "Task5Grader",
|
| 185 |
+
"task6_github_actions": "Task6Grader",
|
| 186 |
+
"task7_nginx": "Task7Grader",
|
| 187 |
+
}
|
| 188 |
return {
|
| 189 |
"tasks": [
|
| 190 |
{
|
|
|
|
| 194 |
"file_type": get_task(tid).file_type,
|
| 195 |
"num_bugs": get_task(tid).num_bugs,
|
| 196 |
"has_grader": True,
|
| 197 |
+
"grader": f"server.graders.grader_api:{task_grader_map[tid]}",
|
| 198 |
}
|
| 199 |
for tid in TASK_ORDER
|
| 200 |
],
|
server/config_debug_environment.py
CHANGED
|
@@ -42,10 +42,16 @@ class ConfigDebugEnvironment(Environment):
|
|
| 42 |
# ---- OpenEnv interface methods ----
|
| 43 |
|
| 44 |
def reset(self, seed: Optional[int] = None, episode_id: Optional[str] = None, **kwargs: Any) -> ConfigDebugObservation:
|
| 45 |
-
"""Reset environment
|
| 46 |
self._init_episode()
|
| 47 |
if episode_id:
|
| 48 |
self._episode_id = episode_id
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 49 |
return self._build_observation()
|
| 50 |
|
| 51 |
def step(self, action: ConfigDebugAction, timeout_s: Optional[float] = None, **kwargs: Any) -> ConfigDebugObservation:
|
|
|
|
| 42 |
# ---- OpenEnv interface methods ----
|
| 43 |
|
| 44 |
def reset(self, seed: Optional[int] = None, episode_id: Optional[str] = None, **kwargs: Any) -> ConfigDebugObservation:
|
| 45 |
+
"""Reset environment. Supports task_id kwarg for per-task validation."""
|
| 46 |
self._init_episode()
|
| 47 |
if episode_id:
|
| 48 |
self._episode_id = episode_id
|
| 49 |
+
|
| 50 |
+
# Allow validator to reset to a specific task
|
| 51 |
+
task_id = kwargs.get("task_id")
|
| 52 |
+
if task_id and task_id in self.task_ids:
|
| 53 |
+
self.current_task_index = self.task_ids.index(task_id)
|
| 54 |
+
|
| 55 |
return self._build_observation()
|
| 56 |
|
| 57 |
def step(self, action: ConfigDebugAction, timeout_s: Optional[float] = None, **kwargs: Any) -> ConfigDebugObservation:
|
server/graders/grader_api.py
CHANGED
|
@@ -1,73 +1,120 @@
|
|
| 1 |
"""
|
| 2 |
grader_api.py - Class-based graders for OpenEnv validator.
|
| 3 |
-
Validator expects classes with a grade() method returning float in (0, 1).
|
| 4 |
-
"""
|
| 5 |
|
| 6 |
-
|
| 7 |
-
|
| 8 |
-
from server.graders.dockerfile_grader import grade_task3 as _r3
|
| 9 |
-
from server.graders.compose_grader import grade_task4 as _r4
|
| 10 |
-
from server.graders.k8s_grader import grade_task5 as _r5
|
| 11 |
-
from server.graders.github_actions_grader import grade_task6 as _r6
|
| 12 |
-
from server.graders.nginx_grader import grade_task7 as _r7
|
| 13 |
|
|
|
|
|
|
|
|
|
|
|
|
|
| 14 |
|
| 15 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 16 |
try:
|
| 17 |
-
config =
|
| 18 |
-
|
| 19 |
-
|
| 20 |
-
|
| 21 |
-
|
| 22 |
-
|
| 23 |
-
|
| 24 |
-
|
| 25 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 26 |
if not config:
|
| 27 |
-
config =
|
| 28 |
-
|
|
|
|
| 29 |
if isinstance(result, (tuple, list)):
|
| 30 |
-
|
| 31 |
else:
|
| 32 |
-
|
| 33 |
-
|
| 34 |
-
|
|
|
|
|
|
|
| 35 |
return 0.5
|
| 36 |
|
| 37 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 38 |
class Task1Grader:
|
| 39 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 40 |
-
return
|
| 41 |
|
| 42 |
|
| 43 |
class Task2Grader:
|
| 44 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 45 |
-
return
|
| 46 |
|
| 47 |
|
| 48 |
class Task3Grader:
|
| 49 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 50 |
-
return
|
| 51 |
|
| 52 |
|
| 53 |
class Task4Grader:
|
| 54 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 55 |
-
return
|
| 56 |
|
| 57 |
|
| 58 |
class Task5Grader:
|
| 59 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 60 |
-
return
|
| 61 |
|
| 62 |
|
| 63 |
class Task6Grader:
|
| 64 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 65 |
-
return
|
| 66 |
|
| 67 |
|
| 68 |
class Task7Grader:
|
| 69 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 70 |
-
return
|
| 71 |
|
| 72 |
|
| 73 |
# Function aliases so app.py /grader endpoint and task_registry still work
|
|
|
|
| 1 |
"""
|
| 2 |
grader_api.py - Class-based graders for OpenEnv validator.
|
|
|
|
|
|
|
| 3 |
|
| 4 |
+
The validator imports these classes from openenv.yaml, instantiates them,
|
| 5 |
+
and calls .grade(env, *args, **kwargs) -> float.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 6 |
|
| 7 |
+
The validator passes the Environment object as `env`. We extract
|
| 8 |
+
the ground_truth from the current task and grade it.
|
| 9 |
+
Scores are strictly in (0.01, 0.99).
|
| 10 |
+
"""
|
| 11 |
|
| 12 |
+
from server.graders.json_grader import grade_task1 as _grade_json
|
| 13 |
+
from server.graders.yaml_grader import grade_task2 as _grade_yaml
|
| 14 |
+
from server.graders.dockerfile_grader import grade_task3 as _grade_dockerfile
|
| 15 |
+
from server.graders.compose_grader import grade_task4 as _grade_compose
|
| 16 |
+
from server.graders.k8s_grader import grade_task5 as _grade_k8s
|
| 17 |
+
from server.graders.github_actions_grader import grade_task6 as _grade_github_actions
|
| 18 |
+
from server.graders.nginx_grader import grade_task7 as _grade_nginx
|
| 19 |
+
|
| 20 |
+
|
| 21 |
+
def _run_grader(grader_fn, env, *args, **kwargs) -> float:
|
| 22 |
+
"""Run a grader function, extracting config from env if available.
|
| 23 |
+
|
| 24 |
+
The validator may call grade(env) where env is the Environment instance.
|
| 25 |
+
We try to get the ground_truth config to grade, falling back to sensible defaults.
|
| 26 |
+
"""
|
| 27 |
try:
|
| 28 |
+
config = None
|
| 29 |
+
|
| 30 |
+
# Try to get ground_truth from the environment's current task
|
| 31 |
+
if env is not None:
|
| 32 |
+
# If env is the Environment object
|
| 33 |
+
if hasattr(env, '_current_task_id'):
|
| 34 |
+
from server.tasks.task_registry import get_task
|
| 35 |
+
task_id = env._current_task_id()
|
| 36 |
+
task = get_task(task_id)
|
| 37 |
+
config = task.ground_truth
|
| 38 |
+
# If env has a state property with task info
|
| 39 |
+
elif hasattr(env, 'state'):
|
| 40 |
+
state = env.state
|
| 41 |
+
if hasattr(state, 'current_task_id') and state.current_task_id:
|
| 42 |
+
from server.tasks.task_registry import get_task
|
| 43 |
+
task = get_task(state.current_task_id)
|
| 44 |
+
config = task.ground_truth
|
| 45 |
+
# If env is already a string (config directly)
|
| 46 |
+
elif isinstance(env, str):
|
| 47 |
+
config = env
|
| 48 |
+
|
| 49 |
+
# If we still don't have config, use ground_truth of the matching task
|
| 50 |
if not config:
|
| 51 |
+
config = _get_default_ground_truth(grader_fn)
|
| 52 |
+
|
| 53 |
+
result = grader_fn(config)
|
| 54 |
if isinstance(result, (tuple, list)):
|
| 55 |
+
score = float(result[0])
|
| 56 |
else:
|
| 57 |
+
score = float(result)
|
| 58 |
+
|
| 59 |
+
return max(0.01, min(0.99, score))
|
| 60 |
+
except Exception as e:
|
| 61 |
+
print(f"[GRADER] Error in _run_grader: {e}")
|
| 62 |
return 0.5
|
| 63 |
|
| 64 |
|
| 65 |
+
def _get_default_ground_truth(grader_fn):
|
| 66 |
+
"""Get the ground_truth for the task matching this grader function."""
|
| 67 |
+
from server.tasks.task_registry import TASK_REGISTRY
|
| 68 |
+
|
| 69 |
+
grader_map = {
|
| 70 |
+
_grade_json: "task1_json",
|
| 71 |
+
_grade_yaml: "task2_yaml",
|
| 72 |
+
_grade_dockerfile: "task3_dockerfile",
|
| 73 |
+
_grade_compose: "task4_compose",
|
| 74 |
+
_grade_k8s: "task5_k8s",
|
| 75 |
+
_grade_github_actions: "task6_github_actions",
|
| 76 |
+
_grade_nginx: "task7_nginx",
|
| 77 |
+
}
|
| 78 |
+
|
| 79 |
+
task_id = grader_map.get(grader_fn)
|
| 80 |
+
if task_id and task_id in TASK_REGISTRY:
|
| 81 |
+
return TASK_REGISTRY[task_id].ground_truth
|
| 82 |
+
return "{}"
|
| 83 |
+
|
| 84 |
+
|
| 85 |
class Task1Grader:
|
| 86 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 87 |
+
return _run_grader(_grade_json, env, *args, **kwargs)
|
| 88 |
|
| 89 |
|
| 90 |
class Task2Grader:
|
| 91 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 92 |
+
return _run_grader(_grade_yaml, env, *args, **kwargs)
|
| 93 |
|
| 94 |
|
| 95 |
class Task3Grader:
|
| 96 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 97 |
+
return _run_grader(_grade_dockerfile, env, *args, **kwargs)
|
| 98 |
|
| 99 |
|
| 100 |
class Task4Grader:
|
| 101 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 102 |
+
return _run_grader(_grade_compose, env, *args, **kwargs)
|
| 103 |
|
| 104 |
|
| 105 |
class Task5Grader:
|
| 106 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 107 |
+
return _run_grader(_grade_k8s, env, *args, **kwargs)
|
| 108 |
|
| 109 |
|
| 110 |
class Task6Grader:
|
| 111 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 112 |
+
return _run_grader(_grade_github_actions, env, *args, **kwargs)
|
| 113 |
|
| 114 |
|
| 115 |
class Task7Grader:
|
| 116 |
def grade(self, env=None, *args, **kwargs) -> float:
|
| 117 |
+
return _run_grader(_grade_nginx, env, *args, **kwargs)
|
| 118 |
|
| 119 |
|
| 120 |
# Function aliases so app.py /grader endpoint and task_registry still work
|
test_validator_simulation.py
ADDED
|
@@ -0,0 +1,109 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
"""
|
| 2 |
+
Simulates EXACTLY what the Scaler validator does:
|
| 3 |
+
1. Import grader classes from openenv.yaml paths
|
| 4 |
+
2. Instantiate each class
|
| 5 |
+
3. Call .grade(env) or .grade(None)
|
| 6 |
+
4. Check score is strictly in (0.01, 0.99)
|
| 7 |
+
|
| 8 |
+
Run: python test_validator_simulation.py
|
| 9 |
+
"""
|
| 10 |
+
import sys
|
| 11 |
+
import os
|
| 12 |
+
|
| 13 |
+
# Add project root to path
|
| 14 |
+
sys.path.insert(0, os.path.dirname(os.path.abspath(__file__)))
|
| 15 |
+
|
| 16 |
+
def test_grader_classes():
|
| 17 |
+
print("=" * 60)
|
| 18 |
+
print("VALIDATOR SIMULATION: Testing grader classes")
|
| 19 |
+
print("=" * 60)
|
| 20 |
+
|
| 21 |
+
from server.graders.grader_api import (
|
| 22 |
+
Task1Grader, Task2Grader, Task3Grader,
|
| 23 |
+
Task4Grader, Task5Grader, Task6Grader, Task7Grader,
|
| 24 |
+
)
|
| 25 |
+
|
| 26 |
+
graders = {
|
| 27 |
+
"task1_json": Task1Grader(),
|
| 28 |
+
"task2_yaml": Task2Grader(),
|
| 29 |
+
"task3_dockerfile": Task3Grader(),
|
| 30 |
+
"task4_compose": Task4Grader(),
|
| 31 |
+
"task5_k8s": Task5Grader(),
|
| 32 |
+
"task6_github_actions": Task6Grader(),
|
| 33 |
+
"task7_nginx": Task7Grader(),
|
| 34 |
+
}
|
| 35 |
+
|
| 36 |
+
all_pass = True
|
| 37 |
+
|
| 38 |
+
for task_id, grader in graders.items():
|
| 39 |
+
# Test 1: .grade(None) β validator may call with None
|
| 40 |
+
score_none = grader.grade(None)
|
| 41 |
+
ok_none = 0.0 < score_none < 1.0
|
| 42 |
+
|
| 43 |
+
# Test 2: .grade(env) β validator passes environment
|
| 44 |
+
from server.config_debug_environment import ConfigDebugEnvironment
|
| 45 |
+
env = ConfigDebugEnvironment()
|
| 46 |
+
env.reset(task_id=task_id)
|
| 47 |
+
score_env = grader.grade(env)
|
| 48 |
+
ok_env = 0.0 < score_env < 1.0
|
| 49 |
+
|
| 50 |
+
# Test 3: .grade(ground_truth_string) β direct string
|
| 51 |
+
from server.tasks.task_registry import get_task
|
| 52 |
+
task = get_task(task_id)
|
| 53 |
+
score_gt = grader.grade(task.ground_truth)
|
| 54 |
+
ok_gt = 0.0 < score_gt < 1.0
|
| 55 |
+
|
| 56 |
+
status = "PASS" if (ok_none and ok_env and ok_gt) else "FAIL"
|
| 57 |
+
if not (ok_none and ok_env and ok_gt):
|
| 58 |
+
all_pass = False
|
| 59 |
+
|
| 60 |
+
print(f"\n[{status}] {task_id}")
|
| 61 |
+
print(f" .grade(None) = {score_none:.4f} {'OK' if ok_none else 'OUT OF RANGE!'}")
|
| 62 |
+
print(f" .grade(env) = {score_env:.4f} {'OK' if ok_env else 'OUT OF RANGE!'}")
|
| 63 |
+
print(f" .grade(ground_truth) = {score_gt:.4f} {'OK' if ok_gt else 'OUT OF RANGE!'}")
|
| 64 |
+
|
| 65 |
+
# Strict check
|
| 66 |
+
if score_none == 0.0 or score_none == 1.0:
|
| 67 |
+
print(f" FATAL: score is exactly {score_none} β validator rejects 0.0 and 1.0!")
|
| 68 |
+
all_pass = False
|
| 69 |
+
if score_env == 0.0 or score_env == 1.0:
|
| 70 |
+
print(f" FATAL: score is exactly {score_env} β validator rejects 0.0 and 1.0!")
|
| 71 |
+
all_pass = False
|
| 72 |
+
if score_gt == 0.0 or score_gt == 1.0:
|
| 73 |
+
print(f" FATAL: score is exactly {score_gt} β validator rejects 0.0 and 1.0!")
|
| 74 |
+
all_pass = False
|
| 75 |
+
|
| 76 |
+
print("\n" + "=" * 60)
|
| 77 |
+
if all_pass:
|
| 78 |
+
print("ALL TASKS PASSED β safe to push and submit!")
|
| 79 |
+
else:
|
| 80 |
+
print("SOME TASKS FAILED β fix before pushing!")
|
| 81 |
+
print("=" * 60)
|
| 82 |
+
|
| 83 |
+
|
| 84 |
+
def test_docker_verification():
|
| 85 |
+
"""The exact Docker test command from the Meta AI email."""
|
| 86 |
+
print("\n\nDOCKER VERIFICATION EQUIVALENT:")
|
| 87 |
+
print("-" * 40)
|
| 88 |
+
|
| 89 |
+
from server.graders.grader_api import (
|
| 90 |
+
Task1Grader, Task2Grader, Task3Grader,
|
| 91 |
+
Task4Grader, Task5Grader, Task6Grader, Task7Grader,
|
| 92 |
+
)
|
| 93 |
+
|
| 94 |
+
for name, cls in [
|
| 95 |
+
("Task1Grader", Task1Grader),
|
| 96 |
+
("Task2Grader", Task2Grader),
|
| 97 |
+
("Task3Grader", Task3Grader),
|
| 98 |
+
("Task4Grader", Task4Grader),
|
| 99 |
+
("Task5Grader", Task5Grader),
|
| 100 |
+
("Task6Grader", Task6Grader),
|
| 101 |
+
("Task7Grader", Task7Grader),
|
| 102 |
+
]:
|
| 103 |
+
score = cls().grade(None)
|
| 104 |
+
print(f"{name}().grade(None) = {score}")
|
| 105 |
+
|
| 106 |
+
|
| 107 |
+
if __name__ == "__main__":
|
| 108 |
+
test_grader_classes()
|
| 109 |
+
test_docker_verification()
|