99from dotenv import load_dotenv
1010from openai import OpenAI
1111
12- # ----------------------------
13- # PATH SETUP
14- # ----------------------------
1512ROOT = Path (__file__ ).resolve ().parent
1613REPO_ROOT = ROOT .parent
1714
2017
2118load_dotenv ()
2219
23- # ----------------------------
24- # CONFIG
25- # ----------------------------
2620TASK_DIR = ROOT / "tasks"
2721SYSTEM_PROMPT = (ROOT / "system_prompt.txt" ).read_text ().strip ()
2822
3125
3226BASE_URL = "https://vishvam10-cloudenv.hf.space"
3327
34- TASK_ORDER = ["easy-task" ]
28+ TASK_ORDER = ["easy-task" , "medium-task" , "hard-task" ]
3529
3630MAX_PARSE_RETRIES = 3
3731MAX_STEPS = 5
@@ -46,7 +40,6 @@ def log_start(task: str, env: str, model: str) -> None:
4640def log_step (
4741 step : int , action : str , reward : float , done : bool , error : Optional [str ]
4842) -> None :
49-
5043 error_val = error if error else "null"
5144 done_val = str (done ).lower ()
5245 action_safe = action .replace ("\n " , " " ).replace ("\r " , "" )[:120 ]
@@ -68,32 +61,38 @@ def log_end(
6861 )
6962
7063
71- # ----------------------------
72- # LOAD TASK
73- # ----------------------------
7464def load_task (name : str ):
7565 return json .loads ((TASK_DIR / f"{ name } .json" ).read_text ())
7666
7767
78- # ----------------------------
79- # RESET
80- # ----------------------------
81- async def env_reset (task_id : str , episode_id : str ):
68+ async def register_pipeline (task : dict ):
8269 async with httpx .AsyncClient (timeout = 30 ) as http :
8370 r = await http .post (
84- f"{ BASE_URL } /reset " ,
71+ f"{ BASE_URL } /api/pipelines " ,
8572 json = {
86- "task_id" : task_id ,
87- "episode_id" : episode_id ,
73+ "pipeline_id" : task ["pipeline_id" ],
74+ "broken_pipeline" : task ["broken_pipeline" ],
75+ "ideal_pipeline" : task ["ideal_pipeline" ],
8876 },
8977 )
78+
79+ if r .status_code not in (200 , 201 , 400 ):
80+ print (
81+ f"[PIPELINE REGISTER ERROR] { r .status_code } { r .text } " ,
82+ flush = True ,
83+ )
84+
85+
86+ async def env_reset (task_id : str , episode_id : str ):
87+ async with httpx .AsyncClient (timeout = 30 ) as http :
88+ r = await http .post (
89+ f"{ BASE_URL } /reset" ,
90+ json = {"task_id" : task_id , "episode_id" : episode_id },
91+ )
9092 r .raise_for_status ()
9193 return r .json ()
9294
9395
94- # ----------------------------
95- # STEP
96- # ----------------------------
9796async def env_step (action : dict ):
9897 async with httpx .AsyncClient (timeout = 30 ) as http :
9998 r = await http .post (
@@ -104,9 +103,6 @@ async def env_step(action: dict):
104103 return r .json ()
105104
106105
107- # ----------------------------
108- # SAFE JSON CLEANING
109- # ----------------------------
110106def clean_json (raw : str ) -> str :
111107 raw = raw .strip ()
112108 raw = re .sub (r"^```(?:json)?\s*" , "" , raw )
@@ -119,9 +115,6 @@ def clean_json(raw: str) -> str:
119115 return raw
120116
121117
122- # ----------------------------
123- # BUILD ACTION (DICT ONLY)
124- # ----------------------------
125118def build_action (raw : str , task_id : str , episode_id : str ):
126119 try :
127120 raw = clean_json (raw )
@@ -162,9 +155,6 @@ def build_action(raw: str, task_id: str, episode_id: str):
162155 return None
163156
164157
165- # ----------------------------
166- # LLM CALL
167- # ----------------------------
168158def call_model (step , state , broken , ideal , history ):
169159 prompt = f"""
170160Return ONLY valid JSON.
@@ -189,15 +179,14 @@ def call_model(step, state, broken, ideal, history):
189179 return (res .choices [0 ].message .content or "" ).strip ()
190180
191181
192- # ----------------------------
193- # EPISODE LOOP
194- # ----------------------------
195182async def run_episode (task ):
196183 task_id = task ["pipeline_id" ]
197184 episode_id = f"{ task_id } -episode-1"
198185
199186 log_start (task = task_id , env = "http" , model = MODEL_NAME )
200187
188+ result = await env_reset (task_id , episode_id )
189+
201190 await env_step (
202191 {
203192 "task_id" : task_id ,
@@ -208,15 +197,14 @@ async def run_episode(task):
208197 "payload" : {},
209198 }
210199 )
211- result = await env_reset (task_id , episode_id )
212-
213- obs = result ["observation" ]
214200
201+ await register_pipeline (task )
202+
203+ obs = {}
215204 history = []
216205 rewards = []
217206 step_count = 0
218207
219-
220208 for step in range (MAX_STEPS ):
221209 if obs .get ("done" ):
222210 break
@@ -226,7 +214,7 @@ async def run_episode(task):
226214 try :
227215 raw = call_model (
228216 step ,
229- obs [ "current_pipeline_state" ] ,
217+ obs ,
230218 task ["broken_pipeline" ],
231219 task ["ideal_pipeline" ],
232220 history ,
@@ -260,36 +248,18 @@ async def run_episode(task):
260248 except Exception as e :
261249 error = str (e )
262250
263- log_step (
264- step = step ,
265- action = "ERROR" ,
266- reward = 0.0 ,
267- done = False ,
268- error = error ,
269- )
270-
251+ log_step (step , "ERROR" , 0.0 , False , error )
271252 break
272253
273254 if obs .get ("done" ):
274255 break
275256
276- # ----------------------------
277- # END LOG
278- # ----------------------------
279257 success = obs .get ("done" , False )
280258 score = sum (rewards ) / (len (rewards ) or 1 )
281259
282- log_end (
283- success = success ,
284- steps = step_count ,
285- score = score ,
286- rewards = rewards ,
287- )
260+ log_end (success = success , steps = step_count , score = score , rewards = rewards )
288261
289262
290- # ----------------------------
291- # MAIN
292- # ----------------------------
293263async def main ():
294264 for name in TASK_ORDER :
295265 task = load_task (name )
0 commit comments