99import requests
1010import subprocess
1111import sys
12+ import time
1213
1314import dotenv
1415from amaranth import *
1516
1617from .. import ChipFlowError
1718from ..platforms import SiliconPlatform , top_interfaces
18- from urllib .parse import urlparse
1919
2020
2121logger = logging .getLogger (__name__ )
@@ -74,6 +74,9 @@ def build_cli_parser(self, parser):
7474 submit_subparser .add_argument (
7575 "--dry-run" , help = argparse .SUPPRESS ,
7676 default = False , action = "store_true" )
77+ submit_subparser .add_argument (
78+ "--wait" , help = argparse .SUPPRESS ,
79+ default = False , action = "store_true" )
7780
7881 def run_cli (self , args ):
7982 if args .action == "submit" and not args .dry_run :
@@ -90,7 +93,7 @@ def run_cli(self, args):
9093
9194 rtlil_path = self .prepare () # always prepare before submission
9295 if args .action == "submit" :
93- self .submit (rtlil_path , dry_run = args .dry_run )
96+ self .submit (rtlil_path , dry_run = args .dry_run , wait = args . wait )
9497
9598 def prepare (self ):
9699 """Elaborate the design and convert it to RTLIL.
@@ -99,7 +102,7 @@ def prepare(self):
99102 """
100103 return self .platform .build (SiliconTop (self .config ), name = self .config_model .chipflow .project_name )
101104
102- def submit (self , rtlil_path , * , dry_run = False ):
105+ def submit (self , rtlil_path , * , dry_run = False , wait = False ):
103106 """Submit the design to the ChipFlow cloud builder.
104107 """
105108 git_head = subprocess .check_output (
@@ -174,11 +177,13 @@ def submit(self, rtlil_path, *, dry_run=False):
174177 return
175178
176179 logger .info (f"Submitting { submission_name } for project { self .project_name } " )
177- endpoint = os .environ .get ("CHIPFLOW_API_ENDPOINT " , "https://build.chipflow.org/api/builds " )
178- host = urlparse ( endpoint ). netloc
180+ chipflow_api_origin = os .environ .get ("CHIPFLOW_API_ORIGIN " , "https://build.chipflow.org" )
181+ build_submit_url = f" { chipflow_api_origin } /build/submit"
179182
180183 resp = requests .post (
181- os .environ .get ("CHIPFLOW_API_ENDPOINT" , "https://build.chipflow.org/api/builds" ),
184+ build_submit_url ,
185+ # TODO: This needs to be reworked to accept only one key, auth accepts user and pass
186+ # TODO: but we want to submit a single key
182187 auth = (os .environ ["CHIPFLOW_API_KEY_ID" ], os .environ ["CHIPFLOW_API_KEY_SECRET" ]),
183188 data = data ,
184189 files = {
@@ -197,7 +202,36 @@ def submit(self, rtlil_path, *, dry_run=False):
197202 # Handle response based on status code
198203 if resp .status_code == 200 :
199204 logger .info (f"Submitted design: { resp_data } " )
200- print (f"https://{ host } /build/{ resp_data ['build_id' ]} " )
205+ build_url = f"{ chipflow_api_origin } /build/{ resp_data ['build_id' ]} "
206+ build_status_url = f"{ chipflow_api_origin } /build/{ resp_data ['build_id' ]} /status"
207+
208+ print (f"Design submitted successfully! Build URL: { build_url } " )
209+
210+ # Poll the status API until the build is completed or failed
211+ if wait :
212+ while True :
213+ status_resp = requests .get (
214+ build_status_url ,
215+ auth = (os .environ ["CHIPFLOW_API_KEY_ID" ], os .environ ["CHIPFLOW_API_KEY_SECRET" ])
216+ )
217+ if status_resp .status_code != 200 :
218+ logger .error (f"Failed to fetch build status: { status_resp .text } " )
219+ raise ChipFlowError ("Error while checking build status." )
220+
221+ status_data = status_resp .json ()
222+ build_status = status_data .get ("status" )
223+ logger .info (f"Build status: { build_status } " )
224+
225+ if build_status == "completed" :
226+ print ("Build completed successfully!" )
227+ exit (0 )
228+ elif build_status == "failed" :
229+ print ("Build failed." )
230+ exit (1 )
231+
232+ # Wait before polling again
233+ time .sleep (10 )
234+
201235 else :
202236 # Log detailed information about the failed request
203237 logger .error (f"Request failed with status code { resp .status_code } " )
0 commit comments