@@ -575,6 +575,163 @@ async def test_get_artifact_awaits_refresh_when_settings_missing():
575575 )
576576
577577
578+ @pytest .mark .asyncio
579+ async def test_download_artifact_methods_call_store_download_file ():
580+ patch_settings ()
581+ sdk_client = AsyncPolyaxonClientMock ()
582+ sdk_client .config = mock .Mock (host = "http://api" , no_op = None , is_offline = None )
583+ client = make_client (sdk_client )
584+ client ._run_data = make_run ()
585+ client ._store = mock .Mock ()
586+ client ._store .download_file = mock .Mock (side_effect = ["/tmp/file" , "/tmp/archive" ])
587+
588+ file_path = await client .download_artifact (
589+ "outputs/model.pkl" ,
590+ force = True ,
591+ path_to = "/tmp/downloads" ,
592+ )
593+ archive_path = await client .download_artifacts (
594+ "outputs" ,
595+ path_to = "/tmp/downloads" ,
596+ untar = False ,
597+ extract_path = "/tmp/extract" ,
598+ check_path = True ,
599+ )
600+
601+ assert file_path == "/tmp/file"
602+ assert archive_path == "/tmp/archive"
603+ file_kwargs = client ._store .download_file .call_args_list [0 ][1 ]
604+ archive_kwargs = client ._store .download_file .call_args_list [1 ][1 ]
605+ assert file_kwargs ["path" ] == "outputs/model.pkl"
606+ assert file_kwargs ["path_to" ] == "/tmp/downloads"
607+ assert file_kwargs ["params" ] == {"force" : True }
608+ assert file_kwargs ["url" ].endswith (
609+ "/streams/v1/test-namespace/test-owner/test-project/runs/{}/artifact" .format (
610+ RUN_UUID
611+ )
612+ )
613+ assert archive_kwargs ["path" ] == "outputs"
614+ assert archive_kwargs ["path_to" ] == "/tmp/downloads"
615+ assert archive_kwargs ["untar" ] is False
616+ assert archive_kwargs ["delete_tar" ] is False
617+ assert archive_kwargs ["extract_path" ] == "/tmp/extract"
618+ assert archive_kwargs ["params" ] == {"check_path" : True }
619+ assert archive_kwargs ["url" ].endswith (
620+ "/streams/v1/test-namespace/test-owner/test-project/runs/{}/artifacts" .format (
621+ RUN_UUID
622+ )
623+ )
624+
625+
626+ @pytest .mark .asyncio
627+ @pytest .mark .parametrize (
628+ "lineage,expected_method,expected_kwargs" ,
629+ [
630+ (
631+ V1RunArtifact .model_construct (
632+ kind = V1ArtifactKind .METRIC ,
633+ path = f"{ RUN_UUID } /events/metric/loss" ,
634+ ),
635+ "download_artifact" ,
636+ {
637+ "path" : "events/metric/loss" ,
638+ "force" : True ,
639+ "path_to" : "/tmp/downloads" ,
640+ },
641+ ),
642+ (
643+ V1RunArtifact .model_construct (
644+ kind = V1ArtifactKind .MODEL ,
645+ path = "models/model.pkl" ,
646+ ),
647+ "download_artifacts" ,
648+ {
649+ "path" : "models/model.pkl" ,
650+ "path_to" : "/tmp/downloads" ,
651+ "check_path" : True ,
652+ },
653+ ),
654+ (
655+ V1RunArtifact .model_construct (
656+ kind = V1ArtifactKind .DIR ,
657+ path = "outputs" ,
658+ ),
659+ "download_artifacts" ,
660+ {
661+ "path" : "outputs" ,
662+ "path_to" : "/tmp/downloads" ,
663+ },
664+ ),
665+ ],
666+ )
667+ async def test_download_artifact_for_lineage_routes_to_download_helpers (
668+ lineage ,
669+ expected_method ,
670+ expected_kwargs ,
671+ ):
672+ patch_settings ()
673+ sdk_client = AsyncPolyaxonClientMock ()
674+ client = make_client (sdk_client )
675+ client ._run_data = make_run ()
676+ client .download_artifact = AsyncMock (return_value = "file" )
677+ client .download_artifacts = AsyncMock (return_value = "artifacts" )
678+
679+ result = await client .download_artifact_for_lineage (
680+ lineage ,
681+ force = True ,
682+ path_to = "/tmp/downloads" ,
683+ )
684+
685+ if expected_method == "download_artifact" :
686+ assert result == "file"
687+ client .download_artifact .assert_called_once_with (** expected_kwargs )
688+ assert client .download_artifacts .call_count == 0
689+ else :
690+ assert result == "artifacts"
691+ client .download_artifacts .assert_called_once_with (** expected_kwargs )
692+ assert client .download_artifact .call_count == 0
693+
694+
695+ @pytest .mark .asyncio
696+ async def test_download_artifact_for_lineage_downloads_event_package ():
697+ patch_settings ()
698+ sdk_client = AsyncPolyaxonClientMock ()
699+ sdk_client .config = mock .Mock (host = "http://api" , no_op = None , is_offline = None )
700+ client = make_client (sdk_client )
701+ client ._run_data = make_run ()
702+ client ._store = mock .Mock ()
703+ client ._store .download_file = mock .Mock (return_value = "/tmp/events" )
704+ lineage = V1RunArtifact .model_construct (
705+ kind = V1ArtifactKind .MODEL ,
706+ name = "model" ,
707+ path = "events/model" ,
708+ summary = {"is_event" : True },
709+ )
710+
711+ result = await client .download_artifact_for_lineage (
712+ lineage ,
713+ force = True ,
714+ path_to = "/tmp/downloads" ,
715+ )
716+
717+ assert result == "/tmp/events"
718+ kwargs = client ._store .download_file .call_args [1 ]
719+ assert kwargs ["path" ] == RUN_UUID
720+ assert kwargs ["use_filepath" ] is False
721+ assert kwargs ["extract_path" ] == "/tmp/downloads"
722+ assert kwargs ["path_to" ] == "/tmp/downloads"
723+ assert kwargs ["untar" ] is True
724+ assert kwargs ["params" ] == {
725+ "force" : True ,
726+ "names" : "model" ,
727+ "pkg_assets" : True ,
728+ }
729+ assert kwargs ["url" ].endswith (
730+ "/streams/v1/test-namespace/test-owner/test-project/runs/"
731+ "{}/events/model" .format (RUN_UUID )
732+ )
733+
734+
578735@pytest .mark .asyncio
579736async def test_run_action_methods_await_api_without_async_req ():
580737 patch_settings ()
@@ -840,9 +997,6 @@ async def test_promote_methods_use_async_project_client_with_injected_client():
840997 ("upload_artifact" , ("file.txt" ,)),
841998 ("upload_artifacts_dir" , ("outputs" ,)),
842999 ("upload_artifacts" , (["file.txt" ],)),
843- ("download_artifact_for_lineage" , (V1RunArtifact .model_construct (),)),
844- ("download_artifact" , ("file.txt" ,)),
845- ("download_artifacts" , ()),
8461000 ("persist_run" , ("/tmp/run" ,)),
8471001 ("push_offline_run" , ("/tmp/run" ,)),
8481002 ("get_runs_as_hiplot" , ()),
0 commit comments