@@ -1288,6 +1288,59 @@ def teardown_method(self):
12881288 pathlib .Path (self ._local_script_file_name ).unlink ()
12891289 initializer .global_pool .shutdown (wait = True )
12901290
1291+ def test_block_until_complete_logs_symbolic_state_name (
1292+ self , mock_model_service_get
1293+ ):
1294+ """State log must use symbolic enum name, not a bare integer (regression for Python 3.11+)."""
1295+ aiplatform .init (project = _TEST_PROJECT , staging_bucket = _TEST_BUCKET_NAME )
1296+
1297+ logged_messages = []
1298+
1299+ with mock .patch .object (
1300+ pipeline_service_client .PipelineServiceClient , "create_training_pipeline"
1301+ ) as mock_create , mock .patch .object (
1302+ source_utils ._TrainingScriptPythonPackager , "package_and_copy_to_gcs"
1303+ ) as mock_pkg , mock .patch .object (
1304+ pipeline_service_client .PipelineServiceClient , "get_training_pipeline"
1305+ ) as mock_get , mock .patch .object (
1306+ training_jobs , "_LOG_WAIT_TIME" , 0
1307+ ), mock .patch .object (
1308+ training_jobs , "_JOB_WAIT_TIME" , 0
1309+ ), mock .patch .object (
1310+ training_jobs ._LOGGER , "info" , side_effect = lambda msg , * a , ** kw : logged_messages .append (msg )
1311+ ):
1312+ mock_pkg .return_value = _TEST_OUTPUT_PYTHON_PACKAGE_PATH
1313+ mock_create .return_value = gca_training_pipeline .TrainingPipeline (
1314+ name = _TEST_PIPELINE_RESOURCE_NAME ,
1315+ state = gca_pipeline_state .PipelineState .PIPELINE_STATE_SUCCEEDED ,
1316+ model_to_upload = gca_model .Model (name = _TEST_MODEL_NAME ),
1317+ )
1318+ _running = gca_training_pipeline .TrainingPipeline (
1319+ name = _TEST_PIPELINE_RESOURCE_NAME ,
1320+ state = gca_pipeline_state .PipelineState .PIPELINE_STATE_RUNNING ,
1321+ training_task_inputs = {},
1322+ )
1323+ _succeeded = gca_training_pipeline .TrainingPipeline (
1324+ name = _TEST_PIPELINE_RESOURCE_NAME ,
1325+ state = gca_pipeline_state .PipelineState .PIPELINE_STATE_SUCCEEDED ,
1326+ training_task_inputs = {},
1327+ model_to_upload = gca_model .Model (name = _TEST_MODEL_NAME ),
1328+ )
1329+ mock_get .side_effect = [_running , _running ] + [_succeeded ] * 8
1330+ job = training_jobs .CustomTrainingJob (
1331+ display_name = _TEST_DISPLAY_NAME ,
1332+ script_path = self ._local_script_file_name ,
1333+ container_uri = _TEST_TRAINING_CONTAINER_IMAGE ,
1334+ )
1335+ job .run (base_output_dir = _TEST_BASE_OUTPUT_DIR , sync = True )
1336+
1337+ state_log = next (
1338+ (m for m in logged_messages if "current state" in m ), None
1339+ )
1340+ assert state_log is not None , "No 'current state' log message found"
1341+ assert "PIPELINE_STATE_RUNNING" in state_log
1342+ assert "current state:\n 3" not in state_log
1343+
12911344 @mock .patch .object (training_jobs , "_JOB_WAIT_TIME" , 1 )
12921345 @mock .patch .object (training_jobs , "_LOG_WAIT_TIME" , 1 )
12931346 @pytest .mark .parametrize ("sync" , [True , False ])
0 commit comments