oracle-ads 2.13.9rc0__py3-none-any.whl → 2.13.10rc0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- ads/aqua/__init__.py +40 -0
- ads/aqua/app.py +507 -0
- ads/aqua/cli.py +96 -0
- ads/aqua/client/__init__.py +3 -0
- ads/aqua/client/client.py +836 -0
- ads/aqua/client/openai_client.py +305 -0
- ads/aqua/common/__init__.py +5 -0
- ads/aqua/common/decorator.py +125 -0
- ads/aqua/common/entities.py +274 -0
- ads/aqua/common/enums.py +134 -0
- ads/aqua/common/errors.py +109 -0
- ads/aqua/common/utils.py +1295 -0
- ads/aqua/config/__init__.py +4 -0
- ads/aqua/config/container_config.py +247 -0
- ads/aqua/config/evaluation/__init__.py +4 -0
- ads/aqua/config/evaluation/evaluation_service_config.py +147 -0
- ads/aqua/config/utils/__init__.py +4 -0
- ads/aqua/config/utils/serializer.py +339 -0
- ads/aqua/constants.py +116 -0
- ads/aqua/data.py +14 -0
- ads/aqua/dummy_data/icon.txt +1 -0
- ads/aqua/dummy_data/oci_model_deployments.json +56 -0
- ads/aqua/dummy_data/oci_models.json +1 -0
- ads/aqua/dummy_data/readme.md +26 -0
- ads/aqua/evaluation/__init__.py +8 -0
- ads/aqua/evaluation/constants.py +53 -0
- ads/aqua/evaluation/entities.py +186 -0
- ads/aqua/evaluation/errors.py +70 -0
- ads/aqua/evaluation/evaluation.py +1814 -0
- ads/aqua/extension/__init__.py +42 -0
- ads/aqua/extension/aqua_ws_msg_handler.py +76 -0
- ads/aqua/extension/base_handler.py +90 -0
- ads/aqua/extension/common_handler.py +121 -0
- ads/aqua/extension/common_ws_msg_handler.py +36 -0
- ads/aqua/extension/deployment_handler.py +381 -0
- ads/aqua/extension/deployment_ws_msg_handler.py +54 -0
- ads/aqua/extension/errors.py +30 -0
- ads/aqua/extension/evaluation_handler.py +129 -0
- ads/aqua/extension/evaluation_ws_msg_handler.py +61 -0
- ads/aqua/extension/finetune_handler.py +96 -0
- ads/aqua/extension/model_handler.py +390 -0
- ads/aqua/extension/models/__init__.py +0 -0
- ads/aqua/extension/models/ws_models.py +145 -0
- ads/aqua/extension/models_ws_msg_handler.py +50 -0
- ads/aqua/extension/ui_handler.py +300 -0
- ads/aqua/extension/ui_websocket_handler.py +130 -0
- ads/aqua/extension/utils.py +133 -0
- ads/aqua/finetuning/__init__.py +7 -0
- ads/aqua/finetuning/constants.py +23 -0
- ads/aqua/finetuning/entities.py +181 -0
- ads/aqua/finetuning/finetuning.py +749 -0
- ads/aqua/model/__init__.py +8 -0
- ads/aqua/model/constants.py +60 -0
- ads/aqua/model/entities.py +385 -0
- ads/aqua/model/enums.py +32 -0
- ads/aqua/model/model.py +2134 -0
- ads/aqua/model/utils.py +52 -0
- ads/aqua/modeldeployment/__init__.py +6 -0
- ads/aqua/modeldeployment/constants.py +10 -0
- ads/aqua/modeldeployment/deployment.py +1315 -0
- ads/aqua/modeldeployment/entities.py +653 -0
- ads/aqua/modeldeployment/utils.py +543 -0
- ads/aqua/resources/gpu_shapes_index.json +94 -0
- ads/aqua/server/__init__.py +4 -0
- ads/aqua/server/__main__.py +24 -0
- ads/aqua/server/app.py +47 -0
- ads/aqua/server/aqua_spec.yml +1291 -0
- ads/aqua/training/__init__.py +4 -0
- ads/aqua/training/exceptions.py +476 -0
- ads/aqua/ui.py +519 -0
- ads/automl/__init__.py +9 -0
- ads/automl/driver.py +330 -0
- ads/automl/provider.py +975 -0
- ads/bds/__init__.py +5 -0
- ads/bds/auth.py +127 -0
- ads/bds/big_data_service.py +255 -0
- ads/catalog/__init__.py +19 -0
- ads/catalog/model.py +1576 -0
- ads/catalog/notebook.py +461 -0
- ads/catalog/project.py +468 -0
- ads/catalog/summary.py +178 -0
- ads/common/__init__.py +11 -0
- ads/common/analyzer.py +65 -0
- ads/common/artifact/.model-ignore +63 -0
- ads/common/artifact/__init__.py +10 -0
- ads/common/auth.py +1122 -0
- ads/common/card_identifier.py +83 -0
- ads/common/config.py +647 -0
- ads/common/data.py +165 -0
- ads/common/decorator/__init__.py +9 -0
- ads/common/decorator/argument_to_case.py +88 -0
- ads/common/decorator/deprecate.py +69 -0
- ads/common/decorator/require_nonempty_arg.py +65 -0
- ads/common/decorator/runtime_dependency.py +178 -0
- ads/common/decorator/threaded.py +97 -0
- ads/common/decorator/utils.py +35 -0
- ads/common/dsc_file_system.py +303 -0
- ads/common/error.py +14 -0
- ads/common/extended_enum.py +81 -0
- ads/common/function/__init__.py +5 -0
- ads/common/function/fn_util.py +142 -0
- ads/common/function/func_conf.yaml +25 -0
- ads/common/ipython.py +76 -0
- ads/common/model.py +679 -0
- ads/common/model_artifact.py +1759 -0
- ads/common/model_artifact_schema.json +107 -0
- ads/common/model_export_util.py +664 -0
- ads/common/model_metadata.py +24 -0
- ads/common/object_storage_details.py +296 -0
- ads/common/oci_client.py +179 -0
- ads/common/oci_datascience.py +46 -0
- ads/common/oci_logging.py +1144 -0
- ads/common/oci_mixin.py +957 -0
- ads/common/oci_resource.py +136 -0
- ads/common/serializer.py +559 -0
- ads/common/utils.py +1852 -0
- ads/common/word_lists.py +1491 -0
- ads/common/work_request.py +189 -0
- ads/config.py +1 -0
- ads/data_labeling/__init__.py +13 -0
- ads/data_labeling/boundingbox.py +253 -0
- ads/data_labeling/constants.py +47 -0
- ads/data_labeling/data_labeling_service.py +244 -0
- ads/data_labeling/interface/__init__.py +5 -0
- ads/data_labeling/interface/loader.py +16 -0
- ads/data_labeling/interface/parser.py +16 -0
- ads/data_labeling/interface/reader.py +23 -0
- ads/data_labeling/loader/__init__.py +5 -0
- ads/data_labeling/loader/file_loader.py +241 -0
- ads/data_labeling/metadata.py +110 -0
- ads/data_labeling/mixin/__init__.py +5 -0
- ads/data_labeling/mixin/data_labeling.py +232 -0
- ads/data_labeling/ner.py +129 -0
- ads/data_labeling/parser/__init__.py +5 -0
- ads/data_labeling/parser/dls_record_parser.py +388 -0
- ads/data_labeling/parser/export_metadata_parser.py +94 -0
- ads/data_labeling/parser/export_record_parser.py +473 -0
- ads/data_labeling/reader/__init__.py +5 -0
- ads/data_labeling/reader/dataset_reader.py +574 -0
- ads/data_labeling/reader/dls_record_reader.py +121 -0
- ads/data_labeling/reader/export_record_reader.py +62 -0
- ads/data_labeling/reader/jsonl_reader.py +75 -0
- ads/data_labeling/reader/metadata_reader.py +203 -0
- ads/data_labeling/reader/record_reader.py +263 -0
- ads/data_labeling/record.py +52 -0
- ads/data_labeling/visualizer/__init__.py +5 -0
- ads/data_labeling/visualizer/image_visualizer.py +525 -0
- ads/data_labeling/visualizer/text_visualizer.py +357 -0
- ads/database/__init__.py +5 -0
- ads/database/connection.py +338 -0
- ads/dataset/__init__.py +10 -0
- ads/dataset/capabilities.md +51 -0
- ads/dataset/classification_dataset.py +339 -0
- ads/dataset/correlation.py +226 -0
- ads/dataset/correlation_plot.py +563 -0
- ads/dataset/dask_series.py +173 -0
- ads/dataset/dataframe_transformer.py +110 -0
- ads/dataset/dataset.py +1979 -0
- ads/dataset/dataset_browser.py +360 -0
- ads/dataset/dataset_with_target.py +995 -0
- ads/dataset/exception.py +25 -0
- ads/dataset/factory.py +987 -0
- ads/dataset/feature_engineering_transformer.py +35 -0
- ads/dataset/feature_selection.py +107 -0
- ads/dataset/forecasting_dataset.py +26 -0
- ads/dataset/helper.py +1450 -0
- ads/dataset/label_encoder.py +99 -0
- ads/dataset/mixin/__init__.py +5 -0
- ads/dataset/mixin/dataset_accessor.py +134 -0
- ads/dataset/pipeline.py +58 -0
- ads/dataset/plot.py +710 -0
- ads/dataset/progress.py +86 -0
- ads/dataset/recommendation.py +297 -0
- ads/dataset/recommendation_transformer.py +502 -0
- ads/dataset/regression_dataset.py +14 -0
- ads/dataset/sampled_dataset.py +1050 -0
- ads/dataset/target.py +98 -0
- ads/dataset/timeseries.py +18 -0
- ads/dbmixin/__init__.py +5 -0
- ads/dbmixin/db_pandas_accessor.py +153 -0
- ads/environment/__init__.py +9 -0
- ads/environment/ml_runtime.py +66 -0
- ads/evaluations/README.md +14 -0
- ads/evaluations/__init__.py +109 -0
- ads/evaluations/evaluation_plot.py +983 -0
- ads/evaluations/evaluator.py +1334 -0
- ads/evaluations/statistical_metrics.py +543 -0
- ads/experiments/__init__.py +9 -0
- ads/experiments/capabilities.md +0 -0
- ads/explanations/__init__.py +21 -0
- ads/explanations/base_explainer.py +142 -0
- ads/explanations/capabilities.md +83 -0
- ads/explanations/explainer.py +190 -0
- ads/explanations/mlx_global_explainer.py +1050 -0
- ads/explanations/mlx_interface.py +386 -0
- ads/explanations/mlx_local_explainer.py +287 -0
- ads/explanations/mlx_whatif_explainer.py +201 -0
- ads/feature_engineering/__init__.py +20 -0
- ads/feature_engineering/accessor/__init__.py +5 -0
- ads/feature_engineering/accessor/dataframe_accessor.py +535 -0
- ads/feature_engineering/accessor/mixin/__init__.py +5 -0
- ads/feature_engineering/accessor/mixin/correlation.py +166 -0
- ads/feature_engineering/accessor/mixin/eda_mixin.py +266 -0
- ads/feature_engineering/accessor/mixin/eda_mixin_series.py +85 -0
- ads/feature_engineering/accessor/mixin/feature_types_mixin.py +211 -0
- ads/feature_engineering/accessor/mixin/utils.py +65 -0
- ads/feature_engineering/accessor/series_accessor.py +431 -0
- ads/feature_engineering/adsimage/__init__.py +5 -0
- ads/feature_engineering/adsimage/image.py +192 -0
- ads/feature_engineering/adsimage/image_reader.py +170 -0
- ads/feature_engineering/adsimage/interface/__init__.py +5 -0
- ads/feature_engineering/adsimage/interface/reader.py +19 -0
- ads/feature_engineering/adsstring/__init__.py +7 -0
- ads/feature_engineering/adsstring/oci_language/__init__.py +8 -0
- ads/feature_engineering/adsstring/string/__init__.py +8 -0
- ads/feature_engineering/data_schema.json +57 -0
- ads/feature_engineering/dataset/__init__.py +5 -0
- ads/feature_engineering/dataset/zip_code_data.py +42062 -0
- ads/feature_engineering/exceptions.py +40 -0
- ads/feature_engineering/feature_type/__init__.py +133 -0
- ads/feature_engineering/feature_type/address.py +184 -0
- ads/feature_engineering/feature_type/adsstring/__init__.py +5 -0
- ads/feature_engineering/feature_type/adsstring/common_regex_mixin.py +164 -0
- ads/feature_engineering/feature_type/adsstring/oci_language.py +93 -0
- ads/feature_engineering/feature_type/adsstring/parsers/__init__.py +5 -0
- ads/feature_engineering/feature_type/adsstring/parsers/base.py +47 -0
- ads/feature_engineering/feature_type/adsstring/parsers/nltk_parser.py +96 -0
- ads/feature_engineering/feature_type/adsstring/parsers/spacy_parser.py +221 -0
- ads/feature_engineering/feature_type/adsstring/string.py +258 -0
- ads/feature_engineering/feature_type/base.py +58 -0
- ads/feature_engineering/feature_type/boolean.py +183 -0
- ads/feature_engineering/feature_type/category.py +146 -0
- ads/feature_engineering/feature_type/constant.py +137 -0
- ads/feature_engineering/feature_type/continuous.py +151 -0
- ads/feature_engineering/feature_type/creditcard.py +314 -0
- ads/feature_engineering/feature_type/datetime.py +190 -0
- ads/feature_engineering/feature_type/discrete.py +134 -0
- ads/feature_engineering/feature_type/document.py +43 -0
- ads/feature_engineering/feature_type/gis.py +251 -0
- ads/feature_engineering/feature_type/handler/__init__.py +5 -0
- ads/feature_engineering/feature_type/handler/feature_validator.py +524 -0
- ads/feature_engineering/feature_type/handler/feature_warning.py +319 -0
- ads/feature_engineering/feature_type/handler/warnings.py +128 -0
- ads/feature_engineering/feature_type/integer.py +142 -0
- ads/feature_engineering/feature_type/ip_address.py +144 -0
- ads/feature_engineering/feature_type/ip_address_v4.py +138 -0
- ads/feature_engineering/feature_type/ip_address_v6.py +138 -0
- ads/feature_engineering/feature_type/lat_long.py +256 -0
- ads/feature_engineering/feature_type/object.py +43 -0
- ads/feature_engineering/feature_type/ordinal.py +132 -0
- ads/feature_engineering/feature_type/phone_number.py +135 -0
- ads/feature_engineering/feature_type/string.py +171 -0
- ads/feature_engineering/feature_type/text.py +93 -0
- ads/feature_engineering/feature_type/unknown.py +43 -0
- ads/feature_engineering/feature_type/zip_code.py +164 -0
- ads/feature_engineering/feature_type_manager.py +406 -0
- ads/feature_engineering/schema.py +795 -0
- ads/feature_engineering/utils.py +245 -0
- ads/feature_store/.readthedocs.yaml +19 -0
- ads/feature_store/README.md +65 -0
- ads/feature_store/__init__.py +9 -0
- ads/feature_store/common/__init__.py +0 -0
- ads/feature_store/common/enums.py +339 -0
- ads/feature_store/common/exceptions.py +18 -0
- ads/feature_store/common/spark_session_singleton.py +125 -0
- ads/feature_store/common/utils/__init__.py +0 -0
- ads/feature_store/common/utils/base64_encoder_decoder.py +72 -0
- ads/feature_store/common/utils/feature_schema_mapper.py +283 -0
- ads/feature_store/common/utils/transformation_utils.py +82 -0
- ads/feature_store/common/utils/utility.py +403 -0
- ads/feature_store/data_validation/__init__.py +0 -0
- ads/feature_store/data_validation/great_expectation.py +129 -0
- ads/feature_store/dataset.py +1230 -0
- ads/feature_store/dataset_job.py +530 -0
- ads/feature_store/docs/Dockerfile +7 -0
- ads/feature_store/docs/Makefile +44 -0
- ads/feature_store/docs/conf.py +28 -0
- ads/feature_store/docs/requirements.txt +14 -0
- ads/feature_store/docs/source/ads.feature_store.query.rst +20 -0
- ads/feature_store/docs/source/cicd.rst +137 -0
- ads/feature_store/docs/source/conf.py +86 -0
- ads/feature_store/docs/source/data_versioning.rst +33 -0
- ads/feature_store/docs/source/dataset.rst +388 -0
- ads/feature_store/docs/source/dataset_job.rst +27 -0
- ads/feature_store/docs/source/demo.rst +70 -0
- ads/feature_store/docs/source/entity.rst +78 -0
- ads/feature_store/docs/source/feature_group.rst +624 -0
- ads/feature_store/docs/source/feature_group_job.rst +29 -0
- ads/feature_store/docs/source/feature_store.rst +122 -0
- ads/feature_store/docs/source/feature_store_class.rst +123 -0
- ads/feature_store/docs/source/feature_validation.rst +66 -0
- ads/feature_store/docs/source/figures/cicd.png +0 -0
- ads/feature_store/docs/source/figures/data_validation.png +0 -0
- ads/feature_store/docs/source/figures/data_versioning.png +0 -0
- ads/feature_store/docs/source/figures/dataset.gif +0 -0
- ads/feature_store/docs/source/figures/dataset.png +0 -0
- ads/feature_store/docs/source/figures/dataset_lineage.png +0 -0
- ads/feature_store/docs/source/figures/dataset_statistics.png +0 -0
- ads/feature_store/docs/source/figures/dataset_statistics_viz.png +0 -0
- ads/feature_store/docs/source/figures/dataset_validation_results.png +0 -0
- ads/feature_store/docs/source/figures/dataset_validation_summary.png +0 -0
- ads/feature_store/docs/source/figures/drift_monitoring.png +0 -0
- ads/feature_store/docs/source/figures/entity.png +0 -0
- ads/feature_store/docs/source/figures/feature_group.png +0 -0
- ads/feature_store/docs/source/figures/feature_group_lineage.png +0 -0
- ads/feature_store/docs/source/figures/feature_group_statistics_viz.png +0 -0
- ads/feature_store/docs/source/figures/feature_store_deployment.png +0 -0
- ads/feature_store/docs/source/figures/feature_store_overview.png +0 -0
- ads/feature_store/docs/source/figures/featuregroup.gif +0 -0
- ads/feature_store/docs/source/figures/lineage_d1.png +0 -0
- ads/feature_store/docs/source/figures/lineage_d2.png +0 -0
- ads/feature_store/docs/source/figures/lineage_fg.png +0 -0
- ads/feature_store/docs/source/figures/logo-dark-mode.png +0 -0
- ads/feature_store/docs/source/figures/logo-light-mode.png +0 -0
- ads/feature_store/docs/source/figures/overview.png +0 -0
- ads/feature_store/docs/source/figures/resource_manager.png +0 -0
- ads/feature_store/docs/source/figures/resource_manager_feature_store_stack.png +0 -0
- ads/feature_store/docs/source/figures/resource_manager_home.png +0 -0
- ads/feature_store/docs/source/figures/stats_1.png +0 -0
- ads/feature_store/docs/source/figures/stats_2.png +0 -0
- ads/feature_store/docs/source/figures/stats_d.png +0 -0
- ads/feature_store/docs/source/figures/stats_fg.png +0 -0
- ads/feature_store/docs/source/figures/transformation.png +0 -0
- ads/feature_store/docs/source/figures/transformations.gif +0 -0
- ads/feature_store/docs/source/figures/validation.png +0 -0
- ads/feature_store/docs/source/figures/validation_fg.png +0 -0
- ads/feature_store/docs/source/figures/validation_results.png +0 -0
- ads/feature_store/docs/source/figures/validation_summary.png +0 -0
- ads/feature_store/docs/source/index.rst +81 -0
- ads/feature_store/docs/source/module.rst +8 -0
- ads/feature_store/docs/source/notebook.rst +94 -0
- ads/feature_store/docs/source/overview.rst +47 -0
- ads/feature_store/docs/source/quickstart.rst +176 -0
- ads/feature_store/docs/source/release_notes.rst +194 -0
- ads/feature_store/docs/source/setup_feature_store.rst +81 -0
- ads/feature_store/docs/source/statistics.rst +58 -0
- ads/feature_store/docs/source/transformation.rst +199 -0
- ads/feature_store/docs/source/ui.rst +65 -0
- ads/feature_store/docs/source/user_guides.setup.feature_store_operator.rst +66 -0
- ads/feature_store/docs/source/user_guides.setup.helm_chart.rst +192 -0
- ads/feature_store/docs/source/user_guides.setup.terraform.rst +338 -0
- ads/feature_store/entity.py +718 -0
- ads/feature_store/execution_strategy/__init__.py +0 -0
- ads/feature_store/execution_strategy/delta_lake/__init__.py +0 -0
- ads/feature_store/execution_strategy/delta_lake/delta_lake_service.py +375 -0
- ads/feature_store/execution_strategy/engine/__init__.py +0 -0
- ads/feature_store/execution_strategy/engine/spark_engine.py +316 -0
- ads/feature_store/execution_strategy/execution_strategy.py +113 -0
- ads/feature_store/execution_strategy/execution_strategy_provider.py +47 -0
- ads/feature_store/execution_strategy/spark/__init__.py +0 -0
- ads/feature_store/execution_strategy/spark/spark_execution.py +618 -0
- ads/feature_store/feature.py +192 -0
- ads/feature_store/feature_group.py +1494 -0
- ads/feature_store/feature_group_expectation.py +346 -0
- ads/feature_store/feature_group_job.py +602 -0
- ads/feature_store/feature_lineage/__init__.py +0 -0
- ads/feature_store/feature_lineage/graphviz_service.py +180 -0
- ads/feature_store/feature_option_details.py +50 -0
- ads/feature_store/feature_statistics/__init__.py +0 -0
- ads/feature_store/feature_statistics/statistics_service.py +99 -0
- ads/feature_store/feature_store.py +699 -0
- ads/feature_store/feature_store_registrar.py +518 -0
- ads/feature_store/input_feature_detail.py +149 -0
- ads/feature_store/mixin/__init__.py +4 -0
- ads/feature_store/mixin/oci_feature_store.py +145 -0
- ads/feature_store/model_details.py +73 -0
- ads/feature_store/query/__init__.py +0 -0
- ads/feature_store/query/filter.py +266 -0
- ads/feature_store/query/generator/__init__.py +0 -0
- ads/feature_store/query/generator/query_generator.py +298 -0
- ads/feature_store/query/join.py +161 -0
- ads/feature_store/query/query.py +403 -0
- ads/feature_store/query/validator/__init__.py +0 -0
- ads/feature_store/query/validator/query_validator.py +57 -0
- ads/feature_store/response/__init__.py +0 -0
- ads/feature_store/response/response_builder.py +68 -0
- ads/feature_store/service/__init__.py +0 -0
- ads/feature_store/service/oci_dataset.py +139 -0
- ads/feature_store/service/oci_dataset_job.py +199 -0
- ads/feature_store/service/oci_entity.py +125 -0
- ads/feature_store/service/oci_feature_group.py +164 -0
- ads/feature_store/service/oci_feature_group_job.py +214 -0
- ads/feature_store/service/oci_feature_store.py +182 -0
- ads/feature_store/service/oci_lineage.py +87 -0
- ads/feature_store/service/oci_transformation.py +104 -0
- ads/feature_store/statistics/__init__.py +0 -0
- ads/feature_store/statistics/abs_feature_value.py +49 -0
- ads/feature_store/statistics/charts/__init__.py +0 -0
- ads/feature_store/statistics/charts/abstract_feature_plot.py +37 -0
- ads/feature_store/statistics/charts/box_plot.py +148 -0
- ads/feature_store/statistics/charts/frequency_distribution.py +65 -0
- ads/feature_store/statistics/charts/probability_distribution.py +68 -0
- ads/feature_store/statistics/charts/top_k_frequent_elements.py +98 -0
- ads/feature_store/statistics/feature_stat.py +126 -0
- ads/feature_store/statistics/generic_feature_value.py +33 -0
- ads/feature_store/statistics/statistics.py +41 -0
- ads/feature_store/statistics_config.py +101 -0
- ads/feature_store/templates/feature_store_template.yaml +45 -0
- ads/feature_store/transformation.py +499 -0
- ads/feature_store/validation_output.py +57 -0
- ads/hpo/__init__.py +9 -0
- ads/hpo/_imports.py +91 -0
- ads/hpo/ads_search_space.py +439 -0
- ads/hpo/distributions.py +325 -0
- ads/hpo/objective.py +280 -0
- ads/hpo/search_cv.py +1657 -0
- ads/hpo/stopping_criterion.py +75 -0
- ads/hpo/tuner_artifact.py +413 -0
- ads/hpo/utils.py +91 -0
- ads/hpo/validation.py +140 -0
- ads/hpo/visualization/__init__.py +5 -0
- ads/hpo/visualization/_contour.py +23 -0
- ads/hpo/visualization/_edf.py +20 -0
- ads/hpo/visualization/_intermediate_values.py +21 -0
- ads/hpo/visualization/_optimization_history.py +25 -0
- ads/hpo/visualization/_parallel_coordinate.py +169 -0
- ads/hpo/visualization/_param_importances.py +26 -0
- ads/jobs/__init__.py +53 -0
- ads/jobs/ads_job.py +663 -0
- ads/jobs/builders/__init__.py +5 -0
- ads/jobs/builders/base.py +156 -0
- ads/jobs/builders/infrastructure/__init__.py +6 -0
- ads/jobs/builders/infrastructure/base.py +165 -0
- ads/jobs/builders/infrastructure/dataflow.py +1252 -0
- ads/jobs/builders/infrastructure/dsc_job.py +1894 -0
- ads/jobs/builders/infrastructure/dsc_job_runtime.py +1233 -0
- ads/jobs/builders/infrastructure/utils.py +65 -0
- ads/jobs/builders/runtimes/__init__.py +5 -0
- ads/jobs/builders/runtimes/artifact.py +338 -0
- ads/jobs/builders/runtimes/base.py +325 -0
- ads/jobs/builders/runtimes/container_runtime.py +242 -0
- ads/jobs/builders/runtimes/python_runtime.py +1016 -0
- ads/jobs/builders/runtimes/pytorch_runtime.py +204 -0
- ads/jobs/cli.py +104 -0
- ads/jobs/env_var_parser.py +131 -0
- ads/jobs/extension.py +160 -0
- ads/jobs/schema/__init__.py +5 -0
- ads/jobs/schema/infrastructure_schema.json +116 -0
- ads/jobs/schema/job_schema.json +42 -0
- ads/jobs/schema/runtime_schema.json +183 -0
- ads/jobs/schema/validator.py +141 -0
- ads/jobs/serializer.py +296 -0
- ads/jobs/templates/__init__.py +5 -0
- ads/jobs/templates/container.py +6 -0
- ads/jobs/templates/driver_notebook.py +177 -0
- ads/jobs/templates/driver_oci.py +500 -0
- ads/jobs/templates/driver_python.py +48 -0
- ads/jobs/templates/driver_pytorch.py +852 -0
- ads/jobs/templates/driver_utils.py +615 -0
- ads/jobs/templates/hostname_from_env.c +55 -0
- ads/jobs/templates/oci_metrics.py +181 -0
- ads/jobs/utils.py +104 -0
- ads/llm/__init__.py +28 -0
- ads/llm/autogen/__init__.py +2 -0
- ads/llm/autogen/constants.py +15 -0
- ads/llm/autogen/reports/__init__.py +2 -0
- ads/llm/autogen/reports/base.py +67 -0
- ads/llm/autogen/reports/data.py +103 -0
- ads/llm/autogen/reports/session.py +526 -0
- ads/llm/autogen/reports/templates/chat_box.html +13 -0
- ads/llm/autogen/reports/templates/chat_box_lt.html +5 -0
- ads/llm/autogen/reports/templates/chat_box_rt.html +6 -0
- ads/llm/autogen/reports/utils.py +56 -0
- ads/llm/autogen/v02/__init__.py +4 -0
- ads/llm/autogen/v02/client.py +295 -0
- ads/llm/autogen/v02/log_handlers/__init__.py +2 -0
- ads/llm/autogen/v02/log_handlers/oci_file_handler.py +83 -0
- ads/llm/autogen/v02/loggers/__init__.py +6 -0
- ads/llm/autogen/v02/loggers/metric_logger.py +320 -0
- ads/llm/autogen/v02/loggers/session_logger.py +580 -0
- ads/llm/autogen/v02/loggers/utils.py +86 -0
- ads/llm/autogen/v02/runtime_logging.py +163 -0
- ads/llm/chain.py +268 -0
- ads/llm/chat_template.py +31 -0
- ads/llm/deploy.py +63 -0
- ads/llm/guardrails/__init__.py +5 -0
- ads/llm/guardrails/base.py +442 -0
- ads/llm/guardrails/huggingface.py +44 -0
- ads/llm/langchain/__init__.py +5 -0
- ads/llm/langchain/plugins/__init__.py +5 -0
- ads/llm/langchain/plugins/chat_models/__init__.py +5 -0
- ads/llm/langchain/plugins/chat_models/oci_data_science.py +1027 -0
- ads/llm/langchain/plugins/embeddings/__init__.py +4 -0
- ads/llm/langchain/plugins/embeddings/oci_data_science_model_deployment_endpoint.py +184 -0
- ads/llm/langchain/plugins/llms/__init__.py +5 -0
- ads/llm/langchain/plugins/llms/oci_data_science_model_deployment_endpoint.py +979 -0
- ads/llm/requirements.txt +3 -0
- ads/llm/serialize.py +219 -0
- ads/llm/serializers/__init__.py +0 -0
- ads/llm/serializers/retrieval_qa.py +153 -0
- ads/llm/serializers/runnable_parallel.py +27 -0
- ads/llm/templates/score_chain.jinja2 +155 -0
- ads/llm/templates/tool_chat_template_hermes.jinja +130 -0
- ads/llm/templates/tool_chat_template_mistral_parallel.jinja +94 -0
- ads/model/__init__.py +52 -0
- ads/model/artifact.py +573 -0
- ads/model/artifact_downloader.py +254 -0
- ads/model/artifact_uploader.py +267 -0
- ads/model/base_properties.py +238 -0
- ads/model/common/.model-ignore +66 -0
- ads/model/common/__init__.py +5 -0
- ads/model/common/utils.py +142 -0
- ads/model/datascience_model.py +2635 -0
- ads/model/deployment/__init__.py +20 -0
- ads/model/deployment/common/__init__.py +5 -0
- ads/model/deployment/common/utils.py +308 -0
- ads/model/deployment/model_deployer.py +466 -0
- ads/model/deployment/model_deployment.py +1846 -0
- ads/model/deployment/model_deployment_infrastructure.py +671 -0
- ads/model/deployment/model_deployment_properties.py +493 -0
- ads/model/deployment/model_deployment_runtime.py +838 -0
- ads/model/extractor/__init__.py +5 -0
- ads/model/extractor/automl_extractor.py +74 -0
- ads/model/extractor/embedding_onnx_extractor.py +80 -0
- ads/model/extractor/huggingface_extractor.py +88 -0
- ads/model/extractor/keras_extractor.py +84 -0
- ads/model/extractor/lightgbm_extractor.py +93 -0
- ads/model/extractor/model_info_extractor.py +114 -0
- ads/model/extractor/model_info_extractor_factory.py +105 -0
- ads/model/extractor/pytorch_extractor.py +87 -0
- ads/model/extractor/sklearn_extractor.py +112 -0
- ads/model/extractor/spark_extractor.py +89 -0
- ads/model/extractor/tensorflow_extractor.py +85 -0
- ads/model/extractor/xgboost_extractor.py +94 -0
- ads/model/framework/__init__.py +5 -0
- ads/model/framework/automl_model.py +178 -0
- ads/model/framework/embedding_onnx_model.py +438 -0
- ads/model/framework/huggingface_model.py +399 -0
- ads/model/framework/lightgbm_model.py +266 -0
- ads/model/framework/pytorch_model.py +266 -0
- ads/model/framework/sklearn_model.py +250 -0
- ads/model/framework/spark_model.py +326 -0
- ads/model/framework/tensorflow_model.py +254 -0
- ads/model/framework/xgboost_model.py +258 -0
- ads/model/generic_model.py +3518 -0
- ads/model/model_artifact_boilerplate/README.md +381 -0
- ads/model/model_artifact_boilerplate/__init__.py +5 -0
- ads/model/model_artifact_boilerplate/artifact_introspection_test/__init__.py +5 -0
- ads/model/model_artifact_boilerplate/artifact_introspection_test/model_artifact_validate.py +427 -0
- ads/model/model_artifact_boilerplate/artifact_introspection_test/requirements.txt +2 -0
- ads/model/model_artifact_boilerplate/runtime.yaml +7 -0
- ads/model/model_artifact_boilerplate/score.py +61 -0
- ads/model/model_file_description_schema.json +68 -0
- ads/model/model_introspect.py +331 -0
- ads/model/model_metadata.py +1810 -0
- ads/model/model_metadata_mixin.py +460 -0
- ads/model/model_properties.py +63 -0
- ads/model/model_version_set.py +739 -0
- ads/model/runtime/__init__.py +5 -0
- ads/model/runtime/env_info.py +306 -0
- ads/model/runtime/model_deployment_details.py +37 -0
- ads/model/runtime/model_provenance_details.py +58 -0
- ads/model/runtime/runtime_info.py +81 -0
- ads/model/runtime/schemas/inference_env_info_schema.yaml +16 -0
- ads/model/runtime/schemas/model_provenance_schema.yaml +36 -0
- ads/model/runtime/schemas/training_env_info_schema.yaml +16 -0
- ads/model/runtime/utils.py +201 -0
- ads/model/serde/__init__.py +5 -0
- ads/model/serde/common.py +40 -0
- ads/model/serde/model_input.py +547 -0
- ads/model/serde/model_serializer.py +1184 -0
- ads/model/service/__init__.py +5 -0
- ads/model/service/oci_datascience_model.py +1076 -0
- ads/model/service/oci_datascience_model_deployment.py +500 -0
- ads/model/service/oci_datascience_model_version_set.py +176 -0
- ads/model/transformer/__init__.py +5 -0
- ads/model/transformer/onnx_transformer.py +324 -0
- ads/mysqldb/__init__.py +5 -0
- ads/mysqldb/mysql_db.py +227 -0
- ads/opctl/__init__.py +18 -0
- ads/opctl/anomaly_detection.py +11 -0
- ads/opctl/backend/__init__.py +5 -0
- ads/opctl/backend/ads_dataflow.py +353 -0
- ads/opctl/backend/ads_ml_job.py +710 -0
- ads/opctl/backend/ads_ml_pipeline.py +164 -0
- ads/opctl/backend/ads_model_deployment.py +209 -0
- ads/opctl/backend/base.py +146 -0
- ads/opctl/backend/local.py +1053 -0
- ads/opctl/backend/marketplace/__init__.py +9 -0
- ads/opctl/backend/marketplace/helm_helper.py +173 -0
- ads/opctl/backend/marketplace/local_marketplace.py +271 -0
- ads/opctl/backend/marketplace/marketplace_backend_runner.py +71 -0
- ads/opctl/backend/marketplace/marketplace_operator_interface.py +44 -0
- ads/opctl/backend/marketplace/marketplace_operator_runner.py +24 -0
- ads/opctl/backend/marketplace/marketplace_utils.py +212 -0
- ads/opctl/backend/marketplace/models/__init__.py +5 -0
- ads/opctl/backend/marketplace/models/bearer_token.py +94 -0
- ads/opctl/backend/marketplace/models/marketplace_type.py +70 -0
- ads/opctl/backend/marketplace/models/ocir_details.py +56 -0
- ads/opctl/backend/marketplace/prerequisite_checker.py +238 -0
- ads/opctl/cli.py +707 -0
- ads/opctl/cmds.py +869 -0
- ads/opctl/conda/__init__.py +5 -0
- ads/opctl/conda/cli.py +193 -0
- ads/opctl/conda/cmds.py +749 -0
- ads/opctl/conda/config.yaml +34 -0
- ads/opctl/conda/manifest_template.yaml +13 -0
- ads/opctl/conda/multipart_uploader.py +188 -0
- ads/opctl/conda/pack.py +89 -0
- ads/opctl/config/__init__.py +5 -0
- ads/opctl/config/base.py +57 -0
- ads/opctl/config/diagnostics/__init__.py +5 -0
- ads/opctl/config/diagnostics/distributed/default_requirements_config.yaml +62 -0
- ads/opctl/config/merger.py +255 -0
- ads/opctl/config/resolver.py +297 -0
- ads/opctl/config/utils.py +79 -0
- ads/opctl/config/validator.py +17 -0
- ads/opctl/config/versioner.py +68 -0
- ads/opctl/config/yaml_parsers/__init__.py +7 -0
- ads/opctl/config/yaml_parsers/base.py +58 -0
- ads/opctl/config/yaml_parsers/distributed/__init__.py +7 -0
- ads/opctl/config/yaml_parsers/distributed/yaml_parser.py +201 -0
- ads/opctl/constants.py +66 -0
- ads/opctl/decorator/__init__.py +5 -0
- ads/opctl/decorator/common.py +129 -0
- ads/opctl/diagnostics/__init__.py +5 -0
- ads/opctl/diagnostics/__main__.py +25 -0
- ads/opctl/diagnostics/check_distributed_job_requirements.py +212 -0
- ads/opctl/diagnostics/check_requirements.py +144 -0
- ads/opctl/diagnostics/requirement_exception.py +9 -0
- ads/opctl/distributed/README.md +109 -0
- ads/opctl/distributed/__init__.py +5 -0
- ads/opctl/distributed/certificates.py +32 -0
- ads/opctl/distributed/cli.py +207 -0
- ads/opctl/distributed/cmds.py +731 -0
- ads/opctl/distributed/common/__init__.py +5 -0
- ads/opctl/distributed/common/abstract_cluster_provider.py +449 -0
- ads/opctl/distributed/common/abstract_framework_spec_builder.py +88 -0
- ads/opctl/distributed/common/cluster_config_helper.py +103 -0
- ads/opctl/distributed/common/cluster_provider_factory.py +21 -0
- ads/opctl/distributed/common/cluster_runner.py +54 -0
- ads/opctl/distributed/common/framework_factory.py +29 -0
- ads/opctl/docker/Dockerfile.job +103 -0
- ads/opctl/docker/Dockerfile.job.arm +107 -0
- ads/opctl/docker/Dockerfile.job.gpu +175 -0
- ads/opctl/docker/base-env.yaml +13 -0
- ads/opctl/docker/cuda.repo +6 -0
- ads/opctl/docker/operator/.dockerignore +0 -0
- ads/opctl/docker/operator/Dockerfile +41 -0
- ads/opctl/docker/operator/Dockerfile.gpu +85 -0
- ads/opctl/docker/operator/cuda.repo +6 -0
- ads/opctl/docker/operator/environment.yaml +8 -0
- ads/opctl/forecast.py +11 -0
- ads/opctl/index.yaml +3 -0
- ads/opctl/model/__init__.py +5 -0
- ads/opctl/model/cli.py +65 -0
- ads/opctl/model/cmds.py +73 -0
- ads/opctl/operator/README.md +4 -0
- ads/opctl/operator/__init__.py +31 -0
- ads/opctl/operator/cli.py +344 -0
- ads/opctl/operator/cmd.py +596 -0
- ads/opctl/operator/common/__init__.py +5 -0
- ads/opctl/operator/common/backend_factory.py +460 -0
- ads/opctl/operator/common/const.py +27 -0
- ads/opctl/operator/common/data/synthetic.csv +16001 -0
- ads/opctl/operator/common/dictionary_merger.py +148 -0
- ads/opctl/operator/common/errors.py +42 -0
- ads/opctl/operator/common/operator_config.py +99 -0
- ads/opctl/operator/common/operator_loader.py +811 -0
- ads/opctl/operator/common/operator_schema.yaml +130 -0
- ads/opctl/operator/common/operator_yaml_generator.py +152 -0
- ads/opctl/operator/common/utils.py +208 -0
- ads/opctl/operator/lowcode/__init__.py +5 -0
- ads/opctl/operator/lowcode/anomaly/MLoperator +16 -0
- ads/opctl/operator/lowcode/anomaly/README.md +207 -0
- ads/opctl/operator/lowcode/anomaly/__init__.py +5 -0
- ads/opctl/operator/lowcode/anomaly/__main__.py +103 -0
- ads/opctl/operator/lowcode/anomaly/cmd.py +35 -0
- ads/opctl/operator/lowcode/anomaly/const.py +167 -0
- ads/opctl/operator/lowcode/anomaly/environment.yaml +10 -0
- ads/opctl/operator/lowcode/anomaly/model/__init__.py +5 -0
- ads/opctl/operator/lowcode/anomaly/model/anomaly_dataset.py +146 -0
- ads/opctl/operator/lowcode/anomaly/model/anomaly_merlion.py +162 -0
- ads/opctl/operator/lowcode/anomaly/model/automlx.py +99 -0
- ads/opctl/operator/lowcode/anomaly/model/autots.py +115 -0
- ads/opctl/operator/lowcode/anomaly/model/base_model.py +404 -0
- ads/opctl/operator/lowcode/anomaly/model/factory.py +110 -0
- ads/opctl/operator/lowcode/anomaly/model/isolationforest.py +78 -0
- ads/opctl/operator/lowcode/anomaly/model/oneclasssvm.py +78 -0
- ads/opctl/operator/lowcode/anomaly/model/randomcutforest.py +120 -0
- ads/opctl/operator/lowcode/anomaly/model/tods.py +119 -0
- ads/opctl/operator/lowcode/anomaly/operator_config.py +127 -0
- ads/opctl/operator/lowcode/anomaly/schema.yaml +401 -0
- ads/opctl/operator/lowcode/anomaly/utils.py +88 -0
- ads/opctl/operator/lowcode/common/__init__.py +5 -0
- ads/opctl/operator/lowcode/common/const.py +10 -0
- ads/opctl/operator/lowcode/common/data.py +116 -0
- ads/opctl/operator/lowcode/common/errors.py +47 -0
- ads/opctl/operator/lowcode/common/transformations.py +296 -0
- ads/opctl/operator/lowcode/common/utils.py +384 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/MLoperator +13 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/README.md +30 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/__init__.py +5 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/__main__.py +116 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/cmd.py +85 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/const.py +15 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/environment.yaml +0 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/models/__init__.py +4 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/models/apigw_config.py +32 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/models/db_config.py +43 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/models/mysql_config.py +120 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/models/serializable_yaml_model.py +34 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/operator_utils.py +386 -0
- ads/opctl/operator/lowcode/feature_store_marketplace/schema.yaml +160 -0
- ads/opctl/operator/lowcode/forecast/MLoperator +25 -0
- ads/opctl/operator/lowcode/forecast/README.md +209 -0
- ads/opctl/operator/lowcode/forecast/__init__.py +5 -0
- ads/opctl/operator/lowcode/forecast/__main__.py +89 -0
- ads/opctl/operator/lowcode/forecast/cmd.py +40 -0
- ads/opctl/operator/lowcode/forecast/const.py +92 -0
- ads/opctl/operator/lowcode/forecast/environment.yaml +20 -0
- ads/opctl/operator/lowcode/forecast/errors.py +26 -0
- ads/opctl/operator/lowcode/forecast/model/__init__.py +5 -0
- ads/opctl/operator/lowcode/forecast/model/arima.py +279 -0
- ads/opctl/operator/lowcode/forecast/model/automlx.py +553 -0
- ads/opctl/operator/lowcode/forecast/model/autots.py +312 -0
- ads/opctl/operator/lowcode/forecast/model/base_model.py +875 -0
- ads/opctl/operator/lowcode/forecast/model/factory.py +106 -0
- ads/opctl/operator/lowcode/forecast/model/forecast_datasets.py +492 -0
- ads/opctl/operator/lowcode/forecast/model/ml_forecast.py +243 -0
- ads/opctl/operator/lowcode/forecast/model/neuralprophet.py +482 -0
- ads/opctl/operator/lowcode/forecast/model/prophet.py +450 -0
- ads/opctl/operator/lowcode/forecast/model_evaluator.py +244 -0
- ads/opctl/operator/lowcode/forecast/operator_config.py +234 -0
- ads/opctl/operator/lowcode/forecast/schema.yaml +506 -0
- ads/opctl/operator/lowcode/forecast/utils.py +397 -0
- ads/opctl/operator/lowcode/forecast/whatifserve/__init__.py +7 -0
- ads/opctl/operator/lowcode/forecast/whatifserve/deployment_manager.py +285 -0
- ads/opctl/operator/lowcode/forecast/whatifserve/score.py +246 -0
- ads/opctl/operator/lowcode/pii/MLoperator +17 -0
- ads/opctl/operator/lowcode/pii/README.md +208 -0
- ads/opctl/operator/lowcode/pii/__init__.py +5 -0
- ads/opctl/operator/lowcode/pii/__main__.py +78 -0
- ads/opctl/operator/lowcode/pii/cmd.py +39 -0
- ads/opctl/operator/lowcode/pii/constant.py +84 -0
- ads/opctl/operator/lowcode/pii/environment.yaml +17 -0
- ads/opctl/operator/lowcode/pii/errors.py +27 -0
- ads/opctl/operator/lowcode/pii/model/__init__.py +5 -0
- ads/opctl/operator/lowcode/pii/model/factory.py +82 -0
- ads/opctl/operator/lowcode/pii/model/guardrails.py +167 -0
- ads/opctl/operator/lowcode/pii/model/pii.py +145 -0
- ads/opctl/operator/lowcode/pii/model/processor/__init__.py +34 -0
- ads/opctl/operator/lowcode/pii/model/processor/email_replacer.py +34 -0
- ads/opctl/operator/lowcode/pii/model/processor/mbi_replacer.py +35 -0
- ads/opctl/operator/lowcode/pii/model/processor/name_replacer.py +225 -0
- ads/opctl/operator/lowcode/pii/model/processor/number_replacer.py +73 -0
- ads/opctl/operator/lowcode/pii/model/processor/remover.py +26 -0
- ads/opctl/operator/lowcode/pii/model/report.py +487 -0
- ads/opctl/operator/lowcode/pii/operator_config.py +95 -0
- ads/opctl/operator/lowcode/pii/schema.yaml +108 -0
- ads/opctl/operator/lowcode/pii/utils.py +43 -0
- ads/opctl/operator/lowcode/recommender/MLoperator +16 -0
- ads/opctl/operator/lowcode/recommender/README.md +206 -0
- ads/opctl/operator/lowcode/recommender/__init__.py +5 -0
- ads/opctl/operator/lowcode/recommender/__main__.py +82 -0
- ads/opctl/operator/lowcode/recommender/cmd.py +33 -0
- ads/opctl/operator/lowcode/recommender/constant.py +30 -0
- ads/opctl/operator/lowcode/recommender/environment.yaml +11 -0
- ads/opctl/operator/lowcode/recommender/model/base_model.py +212 -0
- ads/opctl/operator/lowcode/recommender/model/factory.py +56 -0
- ads/opctl/operator/lowcode/recommender/model/recommender_dataset.py +25 -0
- ads/opctl/operator/lowcode/recommender/model/svd.py +106 -0
- ads/opctl/operator/lowcode/recommender/operator_config.py +81 -0
- ads/opctl/operator/lowcode/recommender/schema.yaml +265 -0
- ads/opctl/operator/lowcode/recommender/utils.py +13 -0
- ads/opctl/operator/runtime/__init__.py +5 -0
- ads/opctl/operator/runtime/const.py +17 -0
- ads/opctl/operator/runtime/container_runtime_schema.yaml +50 -0
- ads/opctl/operator/runtime/marketplace_runtime.py +50 -0
- ads/opctl/operator/runtime/python_marketplace_runtime_schema.yaml +21 -0
- ads/opctl/operator/runtime/python_runtime_schema.yaml +21 -0
- ads/opctl/operator/runtime/runtime.py +115 -0
- ads/opctl/schema.yaml.yml +36 -0
- ads/opctl/script.py +40 -0
- ads/opctl/spark/__init__.py +5 -0
- ads/opctl/spark/cli.py +43 -0
- ads/opctl/spark/cmds.py +147 -0
- ads/opctl/templates/diagnostic_report_template.jinja2 +102 -0
- ads/opctl/utils.py +344 -0
- ads/oracledb/__init__.py +5 -0
- ads/oracledb/oracle_db.py +346 -0
- ads/pipeline/__init__.py +39 -0
- ads/pipeline/ads_pipeline.py +2279 -0
- ads/pipeline/ads_pipeline_run.py +772 -0
- ads/pipeline/ads_pipeline_step.py +605 -0
- ads/pipeline/builders/__init__.py +5 -0
- ads/pipeline/builders/infrastructure/__init__.py +5 -0
- ads/pipeline/builders/infrastructure/custom_script.py +32 -0
- ads/pipeline/cli.py +119 -0
- ads/pipeline/extension.py +291 -0
- ads/pipeline/schema/__init__.py +5 -0
- ads/pipeline/schema/cs_step_schema.json +35 -0
- ads/pipeline/schema/ml_step_schema.json +31 -0
- ads/pipeline/schema/pipeline_schema.json +71 -0
- ads/pipeline/visualizer/__init__.py +5 -0
- ads/pipeline/visualizer/base.py +570 -0
- ads/pipeline/visualizer/graph_renderer.py +272 -0
- ads/pipeline/visualizer/text_renderer.py +84 -0
- ads/secrets/__init__.py +11 -0
- ads/secrets/adb.py +386 -0
- ads/secrets/auth_token.py +86 -0
- ads/secrets/big_data_service.py +365 -0
- ads/secrets/mysqldb.py +149 -0
- ads/secrets/oracledb.py +160 -0
- ads/secrets/secrets.py +407 -0
- ads/telemetry/__init__.py +7 -0
- ads/telemetry/base.py +69 -0
- ads/telemetry/client.py +122 -0
- ads/telemetry/telemetry.py +257 -0
- ads/templates/dataflow_pyspark.jinja2 +13 -0
- ads/templates/dataflow_sparksql.jinja2 +22 -0
- ads/templates/func.jinja2 +20 -0
- ads/templates/schemas/openapi.json +1740 -0
- ads/templates/score-pkl.jinja2 +173 -0
- ads/templates/score.jinja2 +322 -0
- ads/templates/score_embedding_onnx.jinja2 +202 -0
- ads/templates/score_generic.jinja2 +165 -0
- ads/templates/score_huggingface_pipeline.jinja2 +217 -0
- ads/templates/score_lightgbm.jinja2 +185 -0
- ads/templates/score_onnx.jinja2 +407 -0
- ads/templates/score_onnx_new.jinja2 +473 -0
- ads/templates/score_oracle_automl.jinja2 +185 -0
- ads/templates/score_pyspark.jinja2 +154 -0
- ads/templates/score_pytorch.jinja2 +219 -0
- ads/templates/score_scikit-learn.jinja2 +184 -0
- ads/templates/score_tensorflow.jinja2 +184 -0
- ads/templates/score_xgboost.jinja2 +178 -0
- ads/text_dataset/__init__.py +5 -0
- ads/text_dataset/backends.py +211 -0
- ads/text_dataset/dataset.py +445 -0
- ads/text_dataset/extractor.py +207 -0
- ads/text_dataset/options.py +53 -0
- ads/text_dataset/udfs.py +22 -0
- ads/text_dataset/utils.py +49 -0
- ads/type_discovery/__init__.py +9 -0
- ads/type_discovery/abstract_detector.py +21 -0
- ads/type_discovery/constant_detector.py +41 -0
- ads/type_discovery/continuous_detector.py +54 -0
- ads/type_discovery/credit_card_detector.py +99 -0
- ads/type_discovery/datetime_detector.py +92 -0
- ads/type_discovery/discrete_detector.py +118 -0
- ads/type_discovery/document_detector.py +146 -0
- ads/type_discovery/ip_detector.py +68 -0
- ads/type_discovery/latlon_detector.py +90 -0
- ads/type_discovery/phone_number_detector.py +63 -0
- ads/type_discovery/type_discovery_driver.py +87 -0
- ads/type_discovery/typed_feature.py +594 -0
- ads/type_discovery/unknown_detector.py +41 -0
- ads/type_discovery/zipcode_detector.py +48 -0
- ads/vault/__init__.py +7 -0
- ads/vault/vault.py +237 -0
- {oracle_ads-2.13.9rc0.dist-info → oracle_ads-2.13.10rc0.dist-info}/METADATA +150 -149
- oracle_ads-2.13.10rc0.dist-info/RECORD +858 -0
- {oracle_ads-2.13.9rc0.dist-info → oracle_ads-2.13.10rc0.dist-info}/WHEEL +1 -2
- {oracle_ads-2.13.9rc0.dist-info → oracle_ads-2.13.10rc0.dist-info}/entry_points.txt +2 -1
- oracle_ads-2.13.9rc0.dist-info/RECORD +0 -9
- oracle_ads-2.13.9rc0.dist-info/top_level.txt +0 -1
- {oracle_ads-2.13.9rc0.dist-info → oracle_ads-2.13.10rc0.dist-info}/licenses/LICENSE.txt +0 -0
@@ -0,0 +1,1315 @@
|
|
1
|
+
#!/usr/bin/env python
|
2
|
+
# Copyright (c) 2024, 2025 Oracle and/or its affiliates.
|
3
|
+
# Licensed under the Universal Permissive License v 1.0 as shown at https://oss.oracle.com/licenses/upl/
|
4
|
+
|
5
|
+
import json
|
6
|
+
import shlex
|
7
|
+
from datetime import datetime, timedelta
|
8
|
+
from typing import Dict, List, Optional, Union
|
9
|
+
|
10
|
+
from cachetools import TTLCache, cached
|
11
|
+
from oci.data_science.models import ModelDeploymentShapeSummary
|
12
|
+
from pydantic import ValidationError
|
13
|
+
|
14
|
+
from ads.aqua.app import AquaApp, logger
|
15
|
+
from ads.aqua.common.entities import (
|
16
|
+
AquaMultiModelRef,
|
17
|
+
ComputeShapeSummary,
|
18
|
+
ContainerPath,
|
19
|
+
)
|
20
|
+
from ads.aqua.common.enums import (
|
21
|
+
InferenceContainerTypeFamily,
|
22
|
+
ModelFormat,
|
23
|
+
Tags,
|
24
|
+
)
|
25
|
+
from ads.aqua.common.errors import AquaRuntimeError, AquaValueError
|
26
|
+
from ads.aqua.common.utils import (
|
27
|
+
DEFINED_METADATA_TO_FILE_MAP,
|
28
|
+
build_params_string,
|
29
|
+
build_pydantic_error_message,
|
30
|
+
get_combined_params,
|
31
|
+
get_container_params_type,
|
32
|
+
get_ocid_substring,
|
33
|
+
get_params_dict,
|
34
|
+
get_params_list,
|
35
|
+
get_resource_name,
|
36
|
+
get_restricted_params_by_container,
|
37
|
+
load_gpu_shapes_index,
|
38
|
+
validate_cmd_var,
|
39
|
+
)
|
40
|
+
from ads.aqua.config.container_config import AquaContainerConfig, Usage
|
41
|
+
from ads.aqua.constants import (
|
42
|
+
AQUA_MODEL_ARTIFACT_FILE,
|
43
|
+
AQUA_MODEL_TYPE_CUSTOM,
|
44
|
+
AQUA_MODEL_TYPE_MULTI,
|
45
|
+
AQUA_MODEL_TYPE_SERVICE,
|
46
|
+
AQUA_MULTI_MODEL_CONFIG,
|
47
|
+
MODEL_BY_REFERENCE_OSS_PATH_KEY,
|
48
|
+
MODEL_NAME_DELIMITER,
|
49
|
+
UNKNOWN_DICT,
|
50
|
+
)
|
51
|
+
from ads.aqua.data import AquaResourceIdentifier
|
52
|
+
from ads.aqua.model import AquaModelApp
|
53
|
+
from ads.aqua.model.constants import AquaModelMetadataKeys, ModelCustomMetadataFields
|
54
|
+
from ads.aqua.model.utils import (
|
55
|
+
extract_base_model_from_ft,
|
56
|
+
extract_fine_tune_artifacts_path,
|
57
|
+
)
|
58
|
+
from ads.aqua.modeldeployment.entities import (
|
59
|
+
AquaDeployment,
|
60
|
+
AquaDeploymentConfig,
|
61
|
+
AquaDeploymentDetail,
|
62
|
+
ConfigurationItem,
|
63
|
+
ConfigValidationError,
|
64
|
+
CreateModelDeploymentDetails,
|
65
|
+
ModelDeploymentConfigSummary,
|
66
|
+
)
|
67
|
+
from ads.aqua.modeldeployment.utils import MultiModelDeploymentConfigLoader
|
68
|
+
from ads.common.object_storage_details import ObjectStorageDetails
|
69
|
+
from ads.common.utils import UNKNOWN, get_log_links
|
70
|
+
from ads.config import (
|
71
|
+
AQUA_DEPLOYMENT_CONTAINER_CMD_VAR_METADATA_NAME,
|
72
|
+
AQUA_DEPLOYMENT_CONTAINER_METADATA_NAME,
|
73
|
+
AQUA_DEPLOYMENT_CONTAINER_URI_METADATA_NAME,
|
74
|
+
COMPARTMENT_OCID,
|
75
|
+
PROJECT_OCID,
|
76
|
+
)
|
77
|
+
from ads.model.datascience_model import DataScienceModel
|
78
|
+
from ads.model.deployment import (
|
79
|
+
ModelDeployment,
|
80
|
+
ModelDeploymentContainerRuntime,
|
81
|
+
ModelDeploymentInfrastructure,
|
82
|
+
ModelDeploymentMode,
|
83
|
+
)
|
84
|
+
from ads.model.model_metadata import ModelCustomMetadataItem
|
85
|
+
from ads.telemetry import telemetry
|
86
|
+
|
87
|
+
|
88
|
+
class AquaDeploymentApp(AquaApp):
|
89
|
+
"""Provides a suite of APIs to interact with Aqua model deployments within the Oracle
|
90
|
+
Cloud Infrastructure Data Science service, serving as an interface for deploying
|
91
|
+
machine learning models.
|
92
|
+
|
93
|
+
|
94
|
+
Methods
|
95
|
+
-------
|
96
|
+
create(model_id: str, instance_shape: str, display_name: str,...) -> AquaDeployment
|
97
|
+
Creates a model deployment for Aqua Model.
|
98
|
+
get(model_deployment_id: str) -> AquaDeployment:
|
99
|
+
Retrieves details of an Aqua model deployment by its unique identifier.
|
100
|
+
list(**kwargs) -> List[AquaModelSummary]:
|
101
|
+
Lists all Aqua deployments within a specified compartment and/or project.
|
102
|
+
get_deployment_config(self, model_id: str) -> AquaDeploymentConfig:
|
103
|
+
Gets the deployment config of given Aqua model.
|
104
|
+
get_multimodel_deployment_config(self, model_ids: List[str],...) -> ModelDeploymentConfigSummary:
|
105
|
+
Retrieves the deployment configuration for multiple Aqua models and calculates
|
106
|
+
the GPU allocations for all compatible shapes.
|
107
|
+
list_shapes(self, **kwargs) -> List[Dict]:
|
108
|
+
Lists the valid model deployment shapes.
|
109
|
+
|
110
|
+
Note:
|
111
|
+
Use `ads aqua deployment <method_name> --help` to get more details on the parameters available.
|
112
|
+
This class is designed to work within the Oracle Cloud Infrastructure
|
113
|
+
and requires proper configuration and authentication set up to interact
|
114
|
+
with OCI services.
|
115
|
+
"""
|
116
|
+
|
117
|
+
@telemetry(entry_point="plugin=deployment&action=create", name="aqua")
|
118
|
+
def create(
|
119
|
+
self,
|
120
|
+
create_deployment_details: Optional[CreateModelDeploymentDetails] = None,
|
121
|
+
**kwargs,
|
122
|
+
) -> "AquaDeployment":
|
123
|
+
"""
|
124
|
+
Creates a new Aqua model deployment.\n
|
125
|
+
For detailed information about CLI flags see: https://github.com/oracle-samples/oci-data-science-ai-samples/blob/main/ai-quick-actions/cli-tips.md#create-model-deployment
|
126
|
+
|
127
|
+
Args:
|
128
|
+
create_deployment_details : CreateModelDeploymentDetails, optional
|
129
|
+
An instance of CreateModelDeploymentDetails containing all required and optional
|
130
|
+
fields for creating a model deployment via Aqua.
|
131
|
+
kwargs:
|
132
|
+
instance_shape (str): The instance shape used for deployment.
|
133
|
+
display_name (str): The name of the model deployment.
|
134
|
+
compartment_id (Optional[str]): The compartment OCID.
|
135
|
+
project_id (Optional[str]): The project OCID.
|
136
|
+
description (Optional[str]): The description of the deployment.
|
137
|
+
model_id (Optional[str]): The model OCID to deploy.
|
138
|
+
models (Optional[List[AquaMultiModelRef]]): List of models for multimodel deployment.
|
139
|
+
instance_count (int): Number of instances used for deployment.
|
140
|
+
log_group_id (Optional[str]): OCI logging group ID for logs.
|
141
|
+
access_log_id (Optional[str]): OCID for access logs.
|
142
|
+
predict_log_id (Optional[str]): OCID for prediction logs.
|
143
|
+
bandwidth_mbps (Optional[int]): Bandwidth limit on the load balancer in Mbps.
|
144
|
+
web_concurrency (Optional[int]): Number of worker processes/threads for handling requests.
|
145
|
+
server_port (Optional[int]): Server port for the Docker container image.
|
146
|
+
health_check_port (Optional[int]): Health check port for the Docker container image.
|
147
|
+
env_var (Optional[Dict[str, str]]): Environment variables for deployment.
|
148
|
+
container_family (Optional[str]): Image family of the model deployment container runtime.
|
149
|
+
memory_in_gbs (Optional[float]): Memory (in GB) for the selected shape.
|
150
|
+
ocpus (Optional[float]): OCPU count for the selected shape.
|
151
|
+
model_file (Optional[str]): File used for model deployment.
|
152
|
+
private_endpoint_id (Optional[str]): Private endpoint ID for model deployment.
|
153
|
+
container_image_uri (Optional[str]): Image URI for model deployment container runtime.
|
154
|
+
cmd_var (Optional[List[str]]): Command variables for the container runtime.
|
155
|
+
freeform_tags (Optional[Dict]): Freeform tags for model deployment.
|
156
|
+
defined_tags (Optional[Dict]): Defined tags for model deployment.
|
157
|
+
|
158
|
+
Returns
|
159
|
+
-------
|
160
|
+
AquaDeployment
|
161
|
+
An Aqua deployment instance.
|
162
|
+
"""
|
163
|
+
# Build deployment details from kwargs if not explicitly provided.
|
164
|
+
if create_deployment_details is None:
|
165
|
+
try:
|
166
|
+
create_deployment_details = CreateModelDeploymentDetails(**kwargs)
|
167
|
+
except ValidationError as ex:
|
168
|
+
custom_errors = build_pydantic_error_message(ex)
|
169
|
+
raise AquaValueError(
|
170
|
+
f"Invalid parameters for creating a model deployment. Error details: {custom_errors}."
|
171
|
+
) from ex
|
172
|
+
|
173
|
+
if not (create_deployment_details.model_id or create_deployment_details.models):
|
174
|
+
raise AquaValueError(
|
175
|
+
"Invalid parameters for creating a model deployment. Either `model_id` or `models` must be provided."
|
176
|
+
)
|
177
|
+
|
178
|
+
# Set defaults for compartment and project if not provided.
|
179
|
+
compartment_id = create_deployment_details.compartment_id or COMPARTMENT_OCID
|
180
|
+
project_id = create_deployment_details.project_id or PROJECT_OCID
|
181
|
+
freeform_tags = create_deployment_details.freeform_tags
|
182
|
+
defined_tags = create_deployment_details.defined_tags
|
183
|
+
|
184
|
+
# validate instance shape availability in compartment
|
185
|
+
available_shapes = [
|
186
|
+
shape.name.lower()
|
187
|
+
for shape in self.list_shapes(compartment_id=compartment_id)
|
188
|
+
]
|
189
|
+
|
190
|
+
if create_deployment_details.instance_shape.lower() not in available_shapes:
|
191
|
+
raise AquaValueError(
|
192
|
+
f"Invalid Instance Shape. The selected shape '{create_deployment_details.instance_shape}' "
|
193
|
+
f"is not available in the {self.region} region. Please choose another shape to deploy the model."
|
194
|
+
)
|
195
|
+
|
196
|
+
# Get container config
|
197
|
+
container_config = self.get_container_config()
|
198
|
+
|
199
|
+
# Create an AquaModelApp instance once to perform the deployment creation.
|
200
|
+
model_app = AquaModelApp()
|
201
|
+
if create_deployment_details.model_id:
|
202
|
+
logger.debug(
|
203
|
+
f"Single model ({create_deployment_details.model_id}) provided. "
|
204
|
+
"Delegating to single model creation method."
|
205
|
+
)
|
206
|
+
aqua_model = model_app.create(
|
207
|
+
model_id=create_deployment_details.model_id,
|
208
|
+
compartment_id=compartment_id,
|
209
|
+
project_id=project_id,
|
210
|
+
freeform_tags=freeform_tags,
|
211
|
+
defined_tags=defined_tags,
|
212
|
+
)
|
213
|
+
return self._create(
|
214
|
+
aqua_model=aqua_model,
|
215
|
+
create_deployment_details=create_deployment_details,
|
216
|
+
container_config=container_config,
|
217
|
+
)
|
218
|
+
else:
|
219
|
+
model_ids = [model.model_id for model in create_deployment_details.models]
|
220
|
+
|
221
|
+
try:
|
222
|
+
model_config_summary = self.get_multimodel_deployment_config(
|
223
|
+
model_ids=model_ids, compartment_id=compartment_id
|
224
|
+
)
|
225
|
+
if not model_config_summary.gpu_allocation:
|
226
|
+
raise AquaValueError(model_config_summary.error_message)
|
227
|
+
create_deployment_details.validate_multimodel_deployment_feasibility(
|
228
|
+
models_config_summary=model_config_summary
|
229
|
+
)
|
230
|
+
except ConfigValidationError as err:
|
231
|
+
raise AquaValueError(f"{err}") from err
|
232
|
+
|
233
|
+
service_inference_containers = container_config.inference.values()
|
234
|
+
|
235
|
+
supported_container_families = [
|
236
|
+
container_config_item.family
|
237
|
+
for container_config_item in service_inference_containers
|
238
|
+
if any(
|
239
|
+
usage.upper() in container_config_item.usages
|
240
|
+
for usage in [Usage.MULTI_MODEL, Usage.OTHER]
|
241
|
+
)
|
242
|
+
]
|
243
|
+
|
244
|
+
if not supported_container_families:
|
245
|
+
raise AquaValueError(
|
246
|
+
"Currently, there are no containers that support multi-model deployment."
|
247
|
+
)
|
248
|
+
|
249
|
+
# Check if provided container family supports multi-model deployment
|
250
|
+
if (
|
251
|
+
create_deployment_details.container_family
|
252
|
+
and create_deployment_details.container_family
|
253
|
+
not in supported_container_families
|
254
|
+
):
|
255
|
+
raise AquaValueError(
|
256
|
+
f"Unsupported deployment container '{create_deployment_details.container_family}'. "
|
257
|
+
f"Only {supported_container_families} families are supported for multi-model deployments."
|
258
|
+
)
|
259
|
+
|
260
|
+
# Verify if it matches one of the registered containers and attempt to
|
261
|
+
# extract the container family from there.
|
262
|
+
# If the container is not recognized, we can only issue a warning that
|
263
|
+
# the provided container may not support multi-model deployment.
|
264
|
+
if create_deployment_details.container_image_uri:
|
265
|
+
selected_container_name = ContainerPath(
|
266
|
+
full_path=create_deployment_details.container_image_uri
|
267
|
+
).name
|
268
|
+
|
269
|
+
container_config_item = next(
|
270
|
+
(
|
271
|
+
container_config_item
|
272
|
+
for container_config_item in service_inference_containers
|
273
|
+
if ContainerPath(
|
274
|
+
full_path=f"{container_config_item.name}:{container_config_item.version}"
|
275
|
+
).name.upper()
|
276
|
+
== selected_container_name.upper()
|
277
|
+
),
|
278
|
+
None,
|
279
|
+
)
|
280
|
+
|
281
|
+
if (
|
282
|
+
container_config_item
|
283
|
+
and container_config_item.family not in supported_container_families
|
284
|
+
):
|
285
|
+
raise AquaValueError(
|
286
|
+
f"Unsupported deployment container '{create_deployment_details.container_image_uri}'. "
|
287
|
+
f"Only {supported_container_families} families are supported for multi-model deployments."
|
288
|
+
)
|
289
|
+
|
290
|
+
if not container_config_item:
|
291
|
+
logger.warning(
|
292
|
+
f"The provided container `{create_deployment_details.container_image_uri}` may not support multi-model deployment. "
|
293
|
+
f"Only the following container families are supported: {supported_container_families}."
|
294
|
+
)
|
295
|
+
|
296
|
+
logger.debug(
|
297
|
+
f"Multi models ({model_ids}) provided. Delegating to multi model creation method."
|
298
|
+
)
|
299
|
+
|
300
|
+
aqua_model = model_app.create_multi(
|
301
|
+
models=create_deployment_details.models,
|
302
|
+
compartment_id=compartment_id,
|
303
|
+
project_id=project_id,
|
304
|
+
freeform_tags=freeform_tags,
|
305
|
+
defined_tags=defined_tags,
|
306
|
+
)
|
307
|
+
return self._create_multi(
|
308
|
+
aqua_model=aqua_model,
|
309
|
+
model_config_summary=model_config_summary,
|
310
|
+
create_deployment_details=create_deployment_details,
|
311
|
+
container_config=container_config,
|
312
|
+
)
|
313
|
+
|
314
|
+
def _create(
|
315
|
+
self,
|
316
|
+
aqua_model: DataScienceModel,
|
317
|
+
create_deployment_details: CreateModelDeploymentDetails,
|
318
|
+
container_config: Dict,
|
319
|
+
) -> AquaDeployment:
|
320
|
+
"""Builds the configurations required by single model deployment and creates the deployment.
|
321
|
+
|
322
|
+
Parameters
|
323
|
+
----------
|
324
|
+
aqua_model : DataScienceModel
|
325
|
+
An instance of Aqua data science model.
|
326
|
+
create_deployment_details : CreateModelDeploymentDetails
|
327
|
+
An instance of CreateModelDeploymentDetails containing all required and optional
|
328
|
+
fields for creating a model deployment via Aqua.
|
329
|
+
container_config: Dict
|
330
|
+
Container config dictionary.
|
331
|
+
|
332
|
+
Returns
|
333
|
+
-------
|
334
|
+
AquaDeployment
|
335
|
+
An Aqua deployment instance.
|
336
|
+
"""
|
337
|
+
tags = {}
|
338
|
+
for tag in [
|
339
|
+
Tags.AQUA_SERVICE_MODEL_TAG,
|
340
|
+
Tags.AQUA_FINE_TUNED_MODEL_TAG,
|
341
|
+
Tags.AQUA_TAG,
|
342
|
+
]:
|
343
|
+
if tag in aqua_model.freeform_tags:
|
344
|
+
tags[tag] = aqua_model.freeform_tags[tag]
|
345
|
+
|
346
|
+
tags.update({Tags.AQUA_MODEL_NAME_TAG: aqua_model.display_name})
|
347
|
+
tags.update({Tags.TASK: aqua_model.freeform_tags.get(Tags.TASK, UNKNOWN)})
|
348
|
+
|
349
|
+
# Set up info to get deployment config
|
350
|
+
config_source_id = create_deployment_details.model_id
|
351
|
+
model_name = aqua_model.display_name
|
352
|
+
|
353
|
+
# set up env and cmd var
|
354
|
+
env_var = create_deployment_details.env_var or {}
|
355
|
+
cmd_var = create_deployment_details.cmd_var or []
|
356
|
+
|
357
|
+
try:
|
358
|
+
model_path_prefix = aqua_model.custom_metadata_list.get(
|
359
|
+
MODEL_BY_REFERENCE_OSS_PATH_KEY
|
360
|
+
).value.rstrip("/")
|
361
|
+
except ValueError as err:
|
362
|
+
raise AquaValueError(
|
363
|
+
f"{MODEL_BY_REFERENCE_OSS_PATH_KEY} key is not available in the custom metadata field."
|
364
|
+
) from err
|
365
|
+
|
366
|
+
if ObjectStorageDetails.is_oci_path(model_path_prefix):
|
367
|
+
os_path = ObjectStorageDetails.from_path(model_path_prefix)
|
368
|
+
model_path_prefix = os_path.filepath.rstrip("/")
|
369
|
+
|
370
|
+
env_var.update({"BASE_MODEL": f"{model_path_prefix}"})
|
371
|
+
|
372
|
+
is_fine_tuned_model = Tags.AQUA_FINE_TUNED_MODEL_TAG in aqua_model.freeform_tags
|
373
|
+
|
374
|
+
if is_fine_tuned_model:
|
375
|
+
config_source_id, model_name = extract_base_model_from_ft(aqua_model)
|
376
|
+
_, fine_tune_output_path = extract_fine_tune_artifacts_path(aqua_model)
|
377
|
+
env_var.update({"FT_MODEL": f"{fine_tune_output_path}"})
|
378
|
+
|
379
|
+
container_type_key = self._get_container_type_key(
|
380
|
+
model=aqua_model,
|
381
|
+
container_family=create_deployment_details.container_family,
|
382
|
+
)
|
383
|
+
|
384
|
+
container_image_uri = (
|
385
|
+
create_deployment_details.container_image_uri
|
386
|
+
or self.get_container_image(container_type=container_type_key)
|
387
|
+
)
|
388
|
+
if not container_image_uri:
|
389
|
+
try:
|
390
|
+
container_image_uri = aqua_model.custom_metadata_list.get(
|
391
|
+
AQUA_DEPLOYMENT_CONTAINER_URI_METADATA_NAME
|
392
|
+
).value
|
393
|
+
except ValueError as err:
|
394
|
+
raise AquaValueError(
|
395
|
+
f"{AQUA_DEPLOYMENT_CONTAINER_URI_METADATA_NAME} key is not available in the custom metadata "
|
396
|
+
f"field. Either re-register the model with custom container URI, or set container_image_uri "
|
397
|
+
f"parameter when creating this deployment."
|
398
|
+
) from err
|
399
|
+
logger.info(
|
400
|
+
f"Aqua Image used for deploying {aqua_model.id} : {container_image_uri}"
|
401
|
+
)
|
402
|
+
|
403
|
+
try:
|
404
|
+
cmd_var_string = aqua_model.custom_metadata_list.get(
|
405
|
+
AQUA_DEPLOYMENT_CONTAINER_CMD_VAR_METADATA_NAME
|
406
|
+
).value
|
407
|
+
default_cmd_var = shlex.split(cmd_var_string)
|
408
|
+
if default_cmd_var:
|
409
|
+
cmd_var = validate_cmd_var(default_cmd_var, cmd_var)
|
410
|
+
logger.info(f"CMD used for deploying {aqua_model.id} :{cmd_var}")
|
411
|
+
except ValueError:
|
412
|
+
logger.debug(
|
413
|
+
f"CMD will be ignored for this deployment as {AQUA_DEPLOYMENT_CONTAINER_CMD_VAR_METADATA_NAME} "
|
414
|
+
f"key is not available in the custom metadata field for this model."
|
415
|
+
)
|
416
|
+
except Exception as e:
|
417
|
+
logger.error(
|
418
|
+
f"There was an issue processing CMD arguments. Error: {str(e)}"
|
419
|
+
)
|
420
|
+
|
421
|
+
model_formats_str = aqua_model.freeform_tags.get(
|
422
|
+
Tags.MODEL_FORMAT, ModelFormat.SAFETENSORS
|
423
|
+
).upper()
|
424
|
+
model_format = model_formats_str.split(",")
|
425
|
+
|
426
|
+
# Figure out a better way to handle this in future release
|
427
|
+
if (
|
428
|
+
ModelFormat.GGUF in model_format
|
429
|
+
and container_type_key.lower()
|
430
|
+
== InferenceContainerTypeFamily.AQUA_LLAMA_CPP_CONTAINER_FAMILY
|
431
|
+
):
|
432
|
+
model_file = create_deployment_details.model_file
|
433
|
+
if model_file is not None:
|
434
|
+
logger.info(
|
435
|
+
f"Overriding {model_file} as model_file for model {aqua_model.id}."
|
436
|
+
)
|
437
|
+
else:
|
438
|
+
try:
|
439
|
+
model_file = aqua_model.custom_metadata_list.get(
|
440
|
+
AQUA_MODEL_ARTIFACT_FILE
|
441
|
+
).value
|
442
|
+
except ValueError as err:
|
443
|
+
raise AquaValueError(
|
444
|
+
f"{AQUA_MODEL_ARTIFACT_FILE} key is not available in the custom metadata field "
|
445
|
+
f"for model {aqua_model.id}. Either register the model with a default model_file or pass "
|
446
|
+
f"as a parameter when creating a deployment."
|
447
|
+
) from err
|
448
|
+
|
449
|
+
env_var.update({"BASE_MODEL_FILE": f"{model_file}"})
|
450
|
+
tags.update({Tags.MODEL_ARTIFACT_FILE: model_file})
|
451
|
+
|
452
|
+
# Fetch the startup cli command for the container
|
453
|
+
# container_index.json will have "containerSpec" section which will provide the cli params for
|
454
|
+
# a given container family
|
455
|
+
container_config = self.get_container_config_item(container_type_key)
|
456
|
+
|
457
|
+
container_spec = container_config.spec if container_config else UNKNOWN
|
458
|
+
# these params cannot be overridden for Aqua deployments
|
459
|
+
params = container_spec.cli_param if container_spec else UNKNOWN
|
460
|
+
server_port = create_deployment_details.server_port or (
|
461
|
+
container_spec.server_port if container_spec else None
|
462
|
+
)
|
463
|
+
# Give precendece to the input parameter
|
464
|
+
health_check_port = create_deployment_details.health_check_port or (
|
465
|
+
container_spec.health_check_port if container_spec else None
|
466
|
+
)
|
467
|
+
|
468
|
+
deployment_config = self.get_deployment_config(model_id=config_source_id)
|
469
|
+
|
470
|
+
config_params = deployment_config.configuration.get(
|
471
|
+
create_deployment_details.instance_shape, ConfigurationItem()
|
472
|
+
).parameters.get(get_container_params_type(container_type_key), UNKNOWN)
|
473
|
+
|
474
|
+
# validate user provided params
|
475
|
+
user_params = env_var.get("PARAMS", UNKNOWN)
|
476
|
+
if user_params:
|
477
|
+
# todo: remove this check in the future version, logic to be moved to container_index
|
478
|
+
if (
|
479
|
+
container_type_key.lower()
|
480
|
+
== InferenceContainerTypeFamily.AQUA_LLAMA_CPP_CONTAINER_FAMILY
|
481
|
+
):
|
482
|
+
# AQUA_LLAMA_CPP_CONTAINER_FAMILY container uses uvicorn that required model/server params
|
483
|
+
# to be set as env vars
|
484
|
+
raise AquaValueError(
|
485
|
+
f"Currently, parameters cannot be overridden for the container: {container_image_uri}. Please proceed "
|
486
|
+
f"with deployment without parameter overrides."
|
487
|
+
)
|
488
|
+
|
489
|
+
restricted_params = self._find_restricted_params(
|
490
|
+
params, user_params, container_type_key
|
491
|
+
)
|
492
|
+
if restricted_params:
|
493
|
+
raise AquaValueError(
|
494
|
+
f"Parameters {restricted_params} are set by Aqua "
|
495
|
+
f"and cannot be overridden or are invalid."
|
496
|
+
)
|
497
|
+
|
498
|
+
deployment_params = get_combined_params(config_params, user_params)
|
499
|
+
|
500
|
+
params = f"{params} {deployment_params}".strip()
|
501
|
+
if params:
|
502
|
+
env_var.update({"PARAMS": params})
|
503
|
+
env_vars = container_spec.env_vars if container_spec else []
|
504
|
+
for env in env_vars:
|
505
|
+
if isinstance(env, dict):
|
506
|
+
env = {k: v for k, v in env.items() if v}
|
507
|
+
for key, _ in env.items():
|
508
|
+
if key not in env_var:
|
509
|
+
env_var.update(env)
|
510
|
+
|
511
|
+
logger.info(f"Env vars used for deploying {aqua_model.id} :{env_var}")
|
512
|
+
|
513
|
+
tags = {**tags, **(create_deployment_details.freeform_tags or {})}
|
514
|
+
model_type = (
|
515
|
+
AQUA_MODEL_TYPE_CUSTOM if is_fine_tuned_model else AQUA_MODEL_TYPE_SERVICE
|
516
|
+
)
|
517
|
+
|
518
|
+
return self._create_deployment(
|
519
|
+
create_deployment_details=create_deployment_details,
|
520
|
+
aqua_model_id=aqua_model.id,
|
521
|
+
model_name=model_name,
|
522
|
+
model_type=model_type,
|
523
|
+
container_image_uri=container_image_uri,
|
524
|
+
server_port=server_port,
|
525
|
+
health_check_port=health_check_port,
|
526
|
+
env_var=env_var,
|
527
|
+
tags=tags,
|
528
|
+
cmd_var=cmd_var,
|
529
|
+
)
|
530
|
+
|
531
|
+
def _create_multi(
|
532
|
+
self,
|
533
|
+
aqua_model: DataScienceModel,
|
534
|
+
model_config_summary: ModelDeploymentConfigSummary,
|
535
|
+
create_deployment_details: CreateModelDeploymentDetails,
|
536
|
+
container_config: AquaContainerConfig,
|
537
|
+
) -> AquaDeployment:
|
538
|
+
"""Builds the environment variables required by multi deployment container and creates the deployment.
|
539
|
+
|
540
|
+
Parameters
|
541
|
+
----------
|
542
|
+
model_config_summary : model_config_summary
|
543
|
+
Summary Model Deployment configuration for the group of models.
|
544
|
+
aqua_model : DataScienceModel
|
545
|
+
An instance of Aqua data science model.
|
546
|
+
create_deployment_details : CreateModelDeploymentDetails
|
547
|
+
An instance of CreateModelDeploymentDetails containing all required and optional
|
548
|
+
fields for creating a model deployment via Aqua.
|
549
|
+
container_config: Dict
|
550
|
+
Container config dictionary.
|
551
|
+
Returns
|
552
|
+
-------
|
553
|
+
AquaDeployment
|
554
|
+
An Aqua deployment instance.
|
555
|
+
"""
|
556
|
+
model_config = []
|
557
|
+
model_name_list = []
|
558
|
+
env_var = {**(create_deployment_details.env_var or UNKNOWN_DICT)}
|
559
|
+
|
560
|
+
container_type_key = self._get_container_type_key(
|
561
|
+
model=aqua_model,
|
562
|
+
container_family=create_deployment_details.container_family,
|
563
|
+
)
|
564
|
+
container_config = self.get_container_config_item(container_type_key)
|
565
|
+
container_spec = container_config.spec if container_config else UNKNOWN
|
566
|
+
|
567
|
+
container_params = container_spec.cli_param if container_spec else UNKNOWN
|
568
|
+
|
569
|
+
for model in create_deployment_details.models:
|
570
|
+
user_params = build_params_string(model.env_var)
|
571
|
+
if user_params:
|
572
|
+
restricted_params = self._find_restricted_params(
|
573
|
+
container_params, user_params, container_type_key
|
574
|
+
)
|
575
|
+
if restricted_params:
|
576
|
+
selected_model = model.model_name or model.model_id
|
577
|
+
raise AquaValueError(
|
578
|
+
f"Parameters {restricted_params} are set by Aqua "
|
579
|
+
f"and cannot be overridden or are invalid."
|
580
|
+
f"Select other parameters for model {selected_model}."
|
581
|
+
)
|
582
|
+
|
583
|
+
# replaces `--served-model-name`` with user's model name
|
584
|
+
container_params_dict = get_params_dict(container_params)
|
585
|
+
container_params_dict.update({"--served-model-name": model.model_name})
|
586
|
+
# replaces `--tensor-parallel-size` with model gpu count
|
587
|
+
container_params_dict.update({"--tensor-parallel-size": model.gpu_count})
|
588
|
+
params = build_params_string(container_params_dict)
|
589
|
+
|
590
|
+
deployment_config = model_config_summary.deployment_config.get(
|
591
|
+
model.model_id, AquaDeploymentConfig()
|
592
|
+
).configuration.get(
|
593
|
+
create_deployment_details.instance_shape, ConfigurationItem()
|
594
|
+
)
|
595
|
+
|
596
|
+
# finds the corresponding deployment parameters based on the gpu count
|
597
|
+
# and combines them with user's parameters. Existing deployment parameters
|
598
|
+
# will be overriden by user's parameters.
|
599
|
+
params_found = False
|
600
|
+
for item in deployment_config.multi_model_deployment:
|
601
|
+
if (
|
602
|
+
model.gpu_count
|
603
|
+
and item.gpu_count
|
604
|
+
and item.gpu_count == model.gpu_count
|
605
|
+
):
|
606
|
+
config_parameters = item.parameters.get(
|
607
|
+
get_container_params_type(container_type_key), UNKNOWN
|
608
|
+
)
|
609
|
+
params = f"{params} {get_combined_params(config_parameters, user_params)}".strip()
|
610
|
+
params_found = True
|
611
|
+
break
|
612
|
+
|
613
|
+
if not params_found and deployment_config.parameters:
|
614
|
+
config_parameters = deployment_config.parameters.get(
|
615
|
+
get_container_params_type(container_type_key), UNKNOWN
|
616
|
+
)
|
617
|
+
params = f"{params} {get_combined_params(config_parameters, user_params)}".strip()
|
618
|
+
params_found = True
|
619
|
+
|
620
|
+
# if no config parameters found, append user parameters directly.
|
621
|
+
if not params_found:
|
622
|
+
params = f"{params} {user_params}".strip()
|
623
|
+
|
624
|
+
artifact_path_prefix = model.artifact_location.rstrip("/")
|
625
|
+
if ObjectStorageDetails.is_oci_path(artifact_path_prefix):
|
626
|
+
os_path = ObjectStorageDetails.from_path(artifact_path_prefix)
|
627
|
+
artifact_path_prefix = os_path.filepath.rstrip("/")
|
628
|
+
|
629
|
+
# override by-default completion/ chat endpoint with other endpoint (embedding)
|
630
|
+
config_data = {"params": params, "model_path": artifact_path_prefix}
|
631
|
+
if model.model_task:
|
632
|
+
config_data["model_task"] = model.model_task
|
633
|
+
|
634
|
+
if model.fine_tune_weights_location:
|
635
|
+
config_data["fine_tune_weights_location"] = (
|
636
|
+
model.fine_tune_weights_location
|
637
|
+
)
|
638
|
+
|
639
|
+
model_config.append(config_data)
|
640
|
+
model_name_list.append(model.model_name)
|
641
|
+
|
642
|
+
env_var.update({AQUA_MULTI_MODEL_CONFIG: json.dumps({"models": model_config})})
|
643
|
+
|
644
|
+
env_vars = container_spec.env_vars if container_spec else []
|
645
|
+
for env in env_vars:
|
646
|
+
if isinstance(env, dict):
|
647
|
+
env = {k: v for k, v in env.items() if v}
|
648
|
+
for key, _ in env.items():
|
649
|
+
if key not in env_var:
|
650
|
+
env_var.update(env)
|
651
|
+
|
652
|
+
logger.info(f"Env vars used for deploying {aqua_model.id} : {env_var}.")
|
653
|
+
|
654
|
+
container_image_uri = (
|
655
|
+
create_deployment_details.container_image_uri
|
656
|
+
or self.get_container_image(container_type=container_type_key)
|
657
|
+
)
|
658
|
+
server_port = create_deployment_details.server_port or (
|
659
|
+
container_spec.server_port if container_spec else None
|
660
|
+
)
|
661
|
+
health_check_port = create_deployment_details.health_check_port or (
|
662
|
+
container_spec.health_check_port if container_spec else None
|
663
|
+
)
|
664
|
+
tags = {
|
665
|
+
Tags.AQUA_MODEL_ID_TAG: aqua_model.id,
|
666
|
+
Tags.MULTIMODEL_TYPE_TAG: "true",
|
667
|
+
Tags.AQUA_TAG: "active",
|
668
|
+
**(create_deployment_details.freeform_tags or UNKNOWN_DICT),
|
669
|
+
}
|
670
|
+
|
671
|
+
model_name = f"{MODEL_NAME_DELIMITER} ".join(model_name_list)
|
672
|
+
|
673
|
+
aqua_deployment = self._create_deployment(
|
674
|
+
create_deployment_details=create_deployment_details,
|
675
|
+
aqua_model_id=aqua_model.id,
|
676
|
+
model_name=model_name,
|
677
|
+
model_type=AQUA_MODEL_TYPE_MULTI,
|
678
|
+
container_image_uri=container_image_uri,
|
679
|
+
server_port=server_port,
|
680
|
+
health_check_port=health_check_port,
|
681
|
+
env_var=env_var,
|
682
|
+
tags=tags,
|
683
|
+
)
|
684
|
+
aqua_deployment.models = create_deployment_details.models
|
685
|
+
return aqua_deployment
|
686
|
+
|
687
|
+
def _create_deployment(
|
688
|
+
self,
|
689
|
+
create_deployment_details: CreateModelDeploymentDetails,
|
690
|
+
aqua_model_id: str,
|
691
|
+
model_name: str,
|
692
|
+
model_type: str,
|
693
|
+
container_image_uri: str,
|
694
|
+
server_port: str,
|
695
|
+
health_check_port: str,
|
696
|
+
env_var: dict,
|
697
|
+
tags: dict,
|
698
|
+
cmd_var: Optional[dict] = None,
|
699
|
+
):
|
700
|
+
"""Creates data science model deployment.
|
701
|
+
|
702
|
+
Parameters
|
703
|
+
----------
|
704
|
+
create_deployment_details : CreateModelDeploymentDetails
|
705
|
+
An instance of CreateModelDeploymentDetails containing all required and optional
|
706
|
+
fields for creating a model deployment via Aqua.
|
707
|
+
aqua_model_id: str
|
708
|
+
The id of the aqua model to be deployed.
|
709
|
+
model_name: str
|
710
|
+
The name of the aqua model to be deployed. If it's multi model deployment, it is a list of model names.
|
711
|
+
model_type: str
|
712
|
+
The type of aqua model to be deployed. Allowed values are: `custom`, `service` and `multi_model`.
|
713
|
+
container_image_uri: str
|
714
|
+
The container image uri to deploy the model.
|
715
|
+
server_port: str
|
716
|
+
The service port of the container image.
|
717
|
+
health_check_port: str
|
718
|
+
The health check port of the container image.
|
719
|
+
env_var: dict
|
720
|
+
The environment variables input for the deployment.
|
721
|
+
tags: dict
|
722
|
+
The tags input for the deployment.
|
723
|
+
cmd_var: dict, optional
|
724
|
+
The cmd arguments input for the deployment.
|
725
|
+
|
726
|
+
Returns
|
727
|
+
-------
|
728
|
+
AquaDeployment
|
729
|
+
An Aqua deployment instance.
|
730
|
+
"""
|
731
|
+
# Start model deployment
|
732
|
+
# configure model deployment infrastructure
|
733
|
+
infrastructure = (
|
734
|
+
ModelDeploymentInfrastructure()
|
735
|
+
.with_project_id(create_deployment_details.project_id or PROJECT_OCID)
|
736
|
+
.with_compartment_id(
|
737
|
+
create_deployment_details.compartment_id or COMPARTMENT_OCID
|
738
|
+
)
|
739
|
+
.with_shape_name(create_deployment_details.instance_shape)
|
740
|
+
.with_bandwidth_mbps(create_deployment_details.bandwidth_mbps)
|
741
|
+
.with_replica(create_deployment_details.instance_count)
|
742
|
+
.with_web_concurrency(create_deployment_details.web_concurrency)
|
743
|
+
.with_private_endpoint_id(create_deployment_details.private_endpoint_id)
|
744
|
+
.with_access_log(
|
745
|
+
log_group_id=create_deployment_details.log_group_id,
|
746
|
+
log_id=create_deployment_details.access_log_id,
|
747
|
+
)
|
748
|
+
.with_predict_log(
|
749
|
+
log_group_id=create_deployment_details.log_group_id,
|
750
|
+
log_id=create_deployment_details.predict_log_id,
|
751
|
+
)
|
752
|
+
)
|
753
|
+
if (
|
754
|
+
create_deployment_details.memory_in_gbs
|
755
|
+
and create_deployment_details.ocpus
|
756
|
+
and infrastructure.shape_name.endswith("Flex")
|
757
|
+
):
|
758
|
+
infrastructure.with_shape_config_details(
|
759
|
+
ocpus=create_deployment_details.ocpus,
|
760
|
+
memory_in_gbs=create_deployment_details.memory_in_gbs,
|
761
|
+
)
|
762
|
+
# configure model deployment runtime
|
763
|
+
container_runtime = (
|
764
|
+
ModelDeploymentContainerRuntime()
|
765
|
+
.with_image(container_image_uri)
|
766
|
+
.with_server_port(server_port)
|
767
|
+
.with_health_check_port(health_check_port)
|
768
|
+
.with_env(env_var)
|
769
|
+
.with_deployment_mode(ModelDeploymentMode.HTTPS)
|
770
|
+
.with_model_uri(aqua_model_id)
|
771
|
+
.with_region(self.region)
|
772
|
+
.with_overwrite_existing_artifact(True)
|
773
|
+
.with_remove_existing_artifact(True)
|
774
|
+
)
|
775
|
+
if cmd_var:
|
776
|
+
container_runtime.with_cmd(cmd_var)
|
777
|
+
|
778
|
+
# configure model deployment and deploy model on container runtime
|
779
|
+
deployment = (
|
780
|
+
ModelDeployment()
|
781
|
+
.with_display_name(create_deployment_details.display_name)
|
782
|
+
.with_description(create_deployment_details.description)
|
783
|
+
.with_freeform_tags(**tags)
|
784
|
+
.with_defined_tags(**(create_deployment_details.defined_tags or {}))
|
785
|
+
.with_infrastructure(infrastructure)
|
786
|
+
.with_runtime(container_runtime)
|
787
|
+
).deploy(wait_for_completion=False)
|
788
|
+
|
789
|
+
deployment_id = deployment.id
|
790
|
+
logger.info(
|
791
|
+
f"Aqua model deployment {deployment_id} created for model {aqua_model_id}."
|
792
|
+
)
|
793
|
+
|
794
|
+
# we arbitrarily choose last 8 characters of OCID to identify MD in telemetry
|
795
|
+
telemetry_kwargs = {"ocid": get_ocid_substring(deployment_id, key_len=8)}
|
796
|
+
|
797
|
+
if Tags.BASE_MODEL_CUSTOM in tags:
|
798
|
+
telemetry_kwargs["custom_base_model"] = True
|
799
|
+
|
800
|
+
# tracks unique deployments that were created in the user compartment
|
801
|
+
self.telemetry.record_event_async(
|
802
|
+
category=f"aqua/{model_type}/deployment",
|
803
|
+
action="create",
|
804
|
+
detail=model_name,
|
805
|
+
**telemetry_kwargs,
|
806
|
+
)
|
807
|
+
# tracks the shape used for deploying the custom or service models by name
|
808
|
+
self.telemetry.record_event_async(
|
809
|
+
category=f"aqua/{model_type}/deployment/create",
|
810
|
+
action="shape",
|
811
|
+
detail=create_deployment_details.instance_shape,
|
812
|
+
value=model_name,
|
813
|
+
)
|
814
|
+
|
815
|
+
return AquaDeployment.from_oci_model_deployment(
|
816
|
+
deployment.dsc_model_deployment, self.region
|
817
|
+
)
|
818
|
+
|
819
|
+
@staticmethod
|
820
|
+
def _get_container_type_key(model: DataScienceModel, container_family: str) -> str:
|
821
|
+
container_type_key = UNKNOWN
|
822
|
+
if container_family:
|
823
|
+
container_type_key = container_family
|
824
|
+
else:
|
825
|
+
try:
|
826
|
+
container_type_key = model.custom_metadata_list.get(
|
827
|
+
AQUA_DEPLOYMENT_CONTAINER_METADATA_NAME
|
828
|
+
).value
|
829
|
+
except ValueError as err:
|
830
|
+
raise AquaValueError(
|
831
|
+
f"{AQUA_DEPLOYMENT_CONTAINER_METADATA_NAME} key is not available in the custom metadata field "
|
832
|
+
f"for model {model.id}. For unverified Aqua models, {AQUA_DEPLOYMENT_CONTAINER_METADATA_NAME} should be"
|
833
|
+
f"set and value can be one of {', '.join(InferenceContainerTypeFamily.values())}."
|
834
|
+
) from err
|
835
|
+
|
836
|
+
return container_type_key
|
837
|
+
|
838
|
+
@telemetry(entry_point="plugin=deployment&action=list", name="aqua")
|
839
|
+
def list(self, **kwargs) -> List["AquaDeployment"]:
|
840
|
+
"""List Aqua model deployments in a given compartment and under certain project.
|
841
|
+
|
842
|
+
Parameters
|
843
|
+
----------
|
844
|
+
kwargs
|
845
|
+
Keyword arguments, such as compartment_id and project_id,
|
846
|
+
for `list_call_get_all_results <https://docs.oracle.com/en-us/iaas/tools/python/2.118.1/api/pagination.html#oci.pagination.list_call_get_all_results>`_
|
847
|
+
|
848
|
+
Returns
|
849
|
+
-------
|
850
|
+
List[AquaDeployment]:
|
851
|
+
The list of the Aqua model deployments.
|
852
|
+
"""
|
853
|
+
compartment_id = kwargs.pop("compartment_id", COMPARTMENT_OCID)
|
854
|
+
|
855
|
+
model_deployments = self.list_resource(
|
856
|
+
self.ds_client.list_model_deployments,
|
857
|
+
compartment_id=compartment_id,
|
858
|
+
**kwargs,
|
859
|
+
)
|
860
|
+
|
861
|
+
results = []
|
862
|
+
for model_deployment in model_deployments:
|
863
|
+
oci_aqua = (
|
864
|
+
(
|
865
|
+
Tags.AQUA_TAG in model_deployment.freeform_tags
|
866
|
+
or Tags.AQUA_TAG.lower() in model_deployment.freeform_tags
|
867
|
+
)
|
868
|
+
if model_deployment.freeform_tags
|
869
|
+
else False
|
870
|
+
)
|
871
|
+
|
872
|
+
if oci_aqua:
|
873
|
+
results.append(
|
874
|
+
AquaDeployment.from_oci_model_deployment(
|
875
|
+
model_deployment, self.region
|
876
|
+
)
|
877
|
+
)
|
878
|
+
|
879
|
+
# log telemetry if MD is in active or failed state
|
880
|
+
deployment_id = model_deployment.id
|
881
|
+
state = model_deployment.lifecycle_state.upper()
|
882
|
+
if state in ["ACTIVE", "FAILED"]:
|
883
|
+
# tracks unique deployments that were listed in the user compartment
|
884
|
+
# we arbitrarily choose last 8 characters of OCID to identify MD in telemetry
|
885
|
+
self.telemetry.record_event_async(
|
886
|
+
category="aqua/deployment",
|
887
|
+
action="list",
|
888
|
+
detail=get_ocid_substring(deployment_id, key_len=8),
|
889
|
+
value=state,
|
890
|
+
)
|
891
|
+
|
892
|
+
logger.info(
|
893
|
+
f"Fetched {len(results)} model deployments from compartment_id={compartment_id}."
|
894
|
+
)
|
895
|
+
# tracks number of times deployment listing was called
|
896
|
+
self.telemetry.record_event_async(category="aqua/deployment", action="list")
|
897
|
+
|
898
|
+
return results
|
899
|
+
|
900
|
+
@telemetry(entry_point="plugin=deployment&action=delete", name="aqua")
|
901
|
+
def delete(self, model_deployment_id: str):
|
902
|
+
logger.info(f"Deleting model deployment {model_deployment_id}.")
|
903
|
+
return self.ds_client.delete_model_deployment(
|
904
|
+
model_deployment_id=model_deployment_id
|
905
|
+
).data
|
906
|
+
|
907
|
+
@telemetry(entry_point="plugin=deployment&action=deactivate", name="aqua")
|
908
|
+
def deactivate(self, model_deployment_id: str):
|
909
|
+
logger.info(f"Deactivating model deployment {model_deployment_id}.")
|
910
|
+
return self.ds_client.deactivate_model_deployment(
|
911
|
+
model_deployment_id=model_deployment_id
|
912
|
+
).data
|
913
|
+
|
914
|
+
@telemetry(entry_point="plugin=deployment&action=activate", name="aqua")
|
915
|
+
def activate(self, model_deployment_id: str):
|
916
|
+
logger.info(f"Activating model deployment {model_deployment_id}.")
|
917
|
+
return self.ds_client.activate_model_deployment(
|
918
|
+
model_deployment_id=model_deployment_id
|
919
|
+
).data
|
920
|
+
|
921
|
+
@telemetry(entry_point="plugin=deployment&action=get", name="aqua")
|
922
|
+
def get(self, model_deployment_id: str, **kwargs) -> "AquaDeploymentDetail":
|
923
|
+
"""Gets the information of Aqua model deployment.
|
924
|
+
|
925
|
+
Parameters
|
926
|
+
----------
|
927
|
+
model_deployment_id: str
|
928
|
+
The OCID of the Aqua model deployment.
|
929
|
+
kwargs
|
930
|
+
Keyword arguments, for `get_model_deployment
|
931
|
+
<https://docs.oracle.com/en-us/iaas/tools/python/2.119.1/api/data_science/client/oci.data_science.DataScienceClient.html#oci.data_science.DataScienceClient.get_model_deployment>`_
|
932
|
+
|
933
|
+
Returns
|
934
|
+
-------
|
935
|
+
AquaDeploymentDetail:
|
936
|
+
The instance of the Aqua model deployment details.
|
937
|
+
"""
|
938
|
+
logger.info(f"Fetching model deployment details for {model_deployment_id}.")
|
939
|
+
|
940
|
+
model_deployment = self.ds_client.get_model_deployment(
|
941
|
+
model_deployment_id=model_deployment_id, **kwargs
|
942
|
+
).data
|
943
|
+
oci_aqua = (
|
944
|
+
(
|
945
|
+
Tags.AQUA_TAG in model_deployment.freeform_tags
|
946
|
+
or Tags.AQUA_TAG.lower() in model_deployment.freeform_tags
|
947
|
+
)
|
948
|
+
if model_deployment.freeform_tags
|
949
|
+
else False
|
950
|
+
)
|
951
|
+
|
952
|
+
if not oci_aqua:
|
953
|
+
raise AquaRuntimeError(
|
954
|
+
f"Target deployment {model_deployment_id} is not Aqua deployment as it does not contain "
|
955
|
+
f"{Tags.AQUA_TAG} tag."
|
956
|
+
)
|
957
|
+
|
958
|
+
log_id = ""
|
959
|
+
log_group_id = ""
|
960
|
+
log_name = ""
|
961
|
+
log_group_name = ""
|
962
|
+
|
963
|
+
logs = (
|
964
|
+
model_deployment.category_log_details.access
|
965
|
+
or model_deployment.category_log_details.predict
|
966
|
+
)
|
967
|
+
if logs:
|
968
|
+
log_id = logs.log_id
|
969
|
+
log_group_id = logs.log_group_id
|
970
|
+
if log_id:
|
971
|
+
log_name = get_resource_name(log_id)
|
972
|
+
if log_group_id:
|
973
|
+
log_group_name = get_resource_name(log_group_id)
|
974
|
+
|
975
|
+
log_group_url = get_log_links(region=self.region, log_group_id=log_group_id)
|
976
|
+
log_url = get_log_links(
|
977
|
+
region=self.region,
|
978
|
+
log_group_id=log_group_id,
|
979
|
+
log_id=log_id,
|
980
|
+
compartment_id=model_deployment.compartment_id,
|
981
|
+
source_id=model_deployment.id,
|
982
|
+
)
|
983
|
+
|
984
|
+
aqua_deployment = AquaDeployment.from_oci_model_deployment(
|
985
|
+
model_deployment, self.region
|
986
|
+
)
|
987
|
+
if Tags.MULTIMODEL_TYPE_TAG in model_deployment.freeform_tags:
|
988
|
+
aqua_model_id = model_deployment.freeform_tags.get(
|
989
|
+
Tags.AQUA_MODEL_ID_TAG, UNKNOWN
|
990
|
+
)
|
991
|
+
if not aqua_model_id:
|
992
|
+
raise AquaRuntimeError(
|
993
|
+
f"Invalid multi model deployment {model_deployment_id}."
|
994
|
+
f"Make sure the {Tags.AQUA_MODEL_ID_TAG} tag is added to the deployment."
|
995
|
+
)
|
996
|
+
aqua_model = DataScienceModel.from_id(aqua_model_id)
|
997
|
+
custom_metadata_list = aqua_model.custom_metadata_list
|
998
|
+
multi_model_metadata_value = custom_metadata_list.get(
|
999
|
+
ModelCustomMetadataFields.MULTIMODEL_METADATA,
|
1000
|
+
ModelCustomMetadataItem(
|
1001
|
+
key=ModelCustomMetadataFields.MULTIMODEL_METADATA
|
1002
|
+
),
|
1003
|
+
).value
|
1004
|
+
if not multi_model_metadata_value:
|
1005
|
+
raise AquaRuntimeError(
|
1006
|
+
f"Invalid multi-model deployment: {model_deployment_id}. "
|
1007
|
+
f"Ensure that the required custom metadata `{ModelCustomMetadataFields.MULTIMODEL_METADATA}` is added to the AQUA multi-model `{aqua_model.display_name}` ({aqua_model.id})."
|
1008
|
+
)
|
1009
|
+
multi_model_metadata = json.loads(
|
1010
|
+
aqua_model.dsc_model.get_custom_metadata_artifact(
|
1011
|
+
metadata_key_name=ModelCustomMetadataFields.MULTIMODEL_METADATA
|
1012
|
+
).decode("utf-8")
|
1013
|
+
)
|
1014
|
+
aqua_deployment.models = [
|
1015
|
+
AquaMultiModelRef(**metadata) for metadata in multi_model_metadata
|
1016
|
+
]
|
1017
|
+
return AquaDeploymentDetail(
|
1018
|
+
**vars(aqua_deployment),
|
1019
|
+
log_group=AquaResourceIdentifier(
|
1020
|
+
log_group_id, log_group_name, log_group_url
|
1021
|
+
),
|
1022
|
+
log=AquaResourceIdentifier(log_id, log_name, log_url),
|
1023
|
+
)
|
1024
|
+
|
1025
|
+
@telemetry(
|
1026
|
+
entry_point="plugin=deployment&action=get_deployment_config", name="aqua"
|
1027
|
+
)
|
1028
|
+
def get_deployment_config(self, model_id: str) -> AquaDeploymentConfig:
|
1029
|
+
"""Gets the deployment config of given Aqua model.
|
1030
|
+
|
1031
|
+
Parameters
|
1032
|
+
----------
|
1033
|
+
model_id: str
|
1034
|
+
The OCID of the Aqua model.
|
1035
|
+
|
1036
|
+
Returns
|
1037
|
+
-------
|
1038
|
+
AquaDeploymentConfig:
|
1039
|
+
An instance of AquaDeploymentConfig.
|
1040
|
+
"""
|
1041
|
+
config = self.get_config_from_metadata(
|
1042
|
+
model_id, AquaModelMetadataKeys.DEPLOYMENT_CONFIGURATION
|
1043
|
+
).config
|
1044
|
+
if config:
|
1045
|
+
logger.info(
|
1046
|
+
f"Fetched {AquaModelMetadataKeys.DEPLOYMENT_CONFIGURATION} from defined metadata for model: {model_id}."
|
1047
|
+
)
|
1048
|
+
return AquaDeploymentConfig(**(config or UNKNOWN_DICT))
|
1049
|
+
config = self.get_config(
|
1050
|
+
model_id,
|
1051
|
+
DEFINED_METADATA_TO_FILE_MAP.get(
|
1052
|
+
AquaModelMetadataKeys.DEPLOYMENT_CONFIGURATION.lower()
|
1053
|
+
),
|
1054
|
+
).config
|
1055
|
+
if not config:
|
1056
|
+
logger.debug(
|
1057
|
+
f"Deployment config for custom model: {model_id} is not available. Use defaults."
|
1058
|
+
)
|
1059
|
+
return AquaDeploymentConfig(**(config or UNKNOWN_DICT))
|
1060
|
+
|
1061
|
+
@telemetry(
|
1062
|
+
entry_point="plugin=deployment&action=get_multimodel_deployment_config",
|
1063
|
+
name="aqua",
|
1064
|
+
)
|
1065
|
+
def get_multimodel_deployment_config(
|
1066
|
+
self,
|
1067
|
+
model_ids: List[str],
|
1068
|
+
primary_model_id: Optional[str] = None,
|
1069
|
+
**kwargs: Dict,
|
1070
|
+
) -> ModelDeploymentConfigSummary:
|
1071
|
+
"""
|
1072
|
+
Retrieves the deployment configuration for multiple models and calculates
|
1073
|
+
GPU allocations across all compatible shapes.
|
1074
|
+
|
1075
|
+
More details:
|
1076
|
+
https://github.com/oracle-samples/oci-data-science-ai-samples/blob/main/ai-quick-actions/multimodel-deployment-tips.md#get_multimodel_deployment_config
|
1077
|
+
|
1078
|
+
CLI example:
|
1079
|
+
ads aqua deployment get_multimodel_deployment_config --model_ids '["md_ocid1","md_ocid2"]'
|
1080
|
+
|
1081
|
+
If a primary model ID is provided, GPU allocation will prioritize that model
|
1082
|
+
when selecting compatible shapes.
|
1083
|
+
|
1084
|
+
Example:
|
1085
|
+
Assume all three models: A, B, and C, support the same shape: "BM.GPU.H100.8" and each supports the following GPU counts for that shape: 1, 2, 4, 8.
|
1086
|
+
If `no` primary model is specified, valid allocations could be: [2, 4, 2], [2, 2, 4], or [4, 2, 2]
|
1087
|
+
If `B` is set as the primary model, the allocation will be: [2, 4, 2], where B receives the maximum available GPU count
|
1088
|
+
|
1089
|
+
Parameters
|
1090
|
+
----------
|
1091
|
+
model_ids : List[str]
|
1092
|
+
A list of OCIDs for the Aqua models.
|
1093
|
+
primary_model_id : Optional[str]
|
1094
|
+
The OCID of the primary Aqua model. If provided, GPU allocation will prioritize
|
1095
|
+
this model. Otherwise, GPUs will be evenly allocated.
|
1096
|
+
**kwargs: Dict
|
1097
|
+
- compartment_id: str
|
1098
|
+
The compartment OCID to retrieve the model deployment shapes.
|
1099
|
+
|
1100
|
+
Returns
|
1101
|
+
-------
|
1102
|
+
ModelDeploymentConfigSummary
|
1103
|
+
A summary of the model deployment configurations and GPU allocations.
|
1104
|
+
"""
|
1105
|
+
if not model_ids:
|
1106
|
+
raise AquaValueError(
|
1107
|
+
"Model IDs were not provided. Please provide a valid list of model IDs to retrieve the multi-model deployment configuration."
|
1108
|
+
)
|
1109
|
+
|
1110
|
+
compartment_id = kwargs.pop("compartment_id", COMPARTMENT_OCID)
|
1111
|
+
|
1112
|
+
# Get the all model deployment available shapes in a given compartment
|
1113
|
+
available_shapes = self.list_shapes(compartment_id=compartment_id)
|
1114
|
+
|
1115
|
+
return MultiModelDeploymentConfigLoader(
|
1116
|
+
deployment_app=self,
|
1117
|
+
).load(
|
1118
|
+
shapes=available_shapes,
|
1119
|
+
model_ids=model_ids,
|
1120
|
+
primary_model_id=primary_model_id,
|
1121
|
+
)
|
1122
|
+
|
1123
|
+
def get_deployment_default_params(
|
1124
|
+
self,
|
1125
|
+
model_id: str,
|
1126
|
+
instance_shape: str,
|
1127
|
+
gpu_count: int = None,
|
1128
|
+
) -> List[str]:
|
1129
|
+
"""Gets the default params set in the deployment configs for the given model and instance shape.
|
1130
|
+
|
1131
|
+
Parameters
|
1132
|
+
----------
|
1133
|
+
model_id: str
|
1134
|
+
The OCID of the Aqua model.
|
1135
|
+
|
1136
|
+
instance_shape: (str).
|
1137
|
+
The shape of the instance used for deployment.
|
1138
|
+
|
1139
|
+
gpu_count: (int, optional).
|
1140
|
+
The number of GPUs used by the Aqua model. Defaults to None.
|
1141
|
+
|
1142
|
+
Returns
|
1143
|
+
-------
|
1144
|
+
List[str]:
|
1145
|
+
List of parameters from the loaded from deployment config json file. If not available, then an empty list
|
1146
|
+
is returned.
|
1147
|
+
|
1148
|
+
"""
|
1149
|
+
default_params = []
|
1150
|
+
config_params = {}
|
1151
|
+
model = DataScienceModel.from_id(model_id)
|
1152
|
+
try:
|
1153
|
+
container_type_key = model.custom_metadata_list.get(
|
1154
|
+
AQUA_DEPLOYMENT_CONTAINER_METADATA_NAME
|
1155
|
+
).value
|
1156
|
+
except ValueError:
|
1157
|
+
container_type_key = UNKNOWN
|
1158
|
+
logger.debug(
|
1159
|
+
f"{AQUA_DEPLOYMENT_CONTAINER_METADATA_NAME} key is not available in the custom metadata field for model {model_id}."
|
1160
|
+
)
|
1161
|
+
|
1162
|
+
if (
|
1163
|
+
container_type_key
|
1164
|
+
and container_type_key in InferenceContainerTypeFamily.values()
|
1165
|
+
):
|
1166
|
+
deployment_config = self.get_deployment_config(model_id)
|
1167
|
+
|
1168
|
+
instance_shape_config = deployment_config.configuration.get(
|
1169
|
+
instance_shape, ConfigurationItem()
|
1170
|
+
)
|
1171
|
+
|
1172
|
+
if instance_shape_config.multi_model_deployment and gpu_count:
|
1173
|
+
gpu_params = instance_shape_config.multi_model_deployment
|
1174
|
+
|
1175
|
+
for gpu_config in gpu_params:
|
1176
|
+
if gpu_config.gpu_count == gpu_count:
|
1177
|
+
config_params = gpu_config.parameters.get(
|
1178
|
+
get_container_params_type(container_type_key), UNKNOWN
|
1179
|
+
)
|
1180
|
+
break
|
1181
|
+
|
1182
|
+
else:
|
1183
|
+
config_params = instance_shape_config.parameters.get(
|
1184
|
+
get_container_params_type(container_type_key), UNKNOWN
|
1185
|
+
)
|
1186
|
+
|
1187
|
+
if config_params:
|
1188
|
+
params_list = get_params_list(config_params)
|
1189
|
+
restricted_params_set = get_restricted_params_by_container(
|
1190
|
+
container_type_key
|
1191
|
+
)
|
1192
|
+
|
1193
|
+
# remove restricted params from the list as user cannot override them during deployment
|
1194
|
+
for params in params_list:
|
1195
|
+
if params.split()[0] not in restricted_params_set:
|
1196
|
+
default_params.append(params)
|
1197
|
+
|
1198
|
+
return default_params
|
1199
|
+
|
1200
|
+
def validate_deployment_params(
|
1201
|
+
self,
|
1202
|
+
model_id: str,
|
1203
|
+
params: List[str] = None,
|
1204
|
+
container_family: str = None,
|
1205
|
+
) -> Dict:
|
1206
|
+
"""Validate if the deployment parameters passed by the user can be overridden. Parameter values are not
|
1207
|
+
validated, only param keys are validated.
|
1208
|
+
|
1209
|
+
Parameters
|
1210
|
+
----------
|
1211
|
+
model_id: str
|
1212
|
+
The OCID of the Aqua model.
|
1213
|
+
params : List[str], optional
|
1214
|
+
Params passed by the user.
|
1215
|
+
container_family: str
|
1216
|
+
The image family of model deployment container runtime. Required for unverified Aqua models.
|
1217
|
+
|
1218
|
+
Returns
|
1219
|
+
-------
|
1220
|
+
Return a list of restricted params.
|
1221
|
+
|
1222
|
+
"""
|
1223
|
+
restricted_params = []
|
1224
|
+
if params:
|
1225
|
+
model = DataScienceModel.from_id(model_id)
|
1226
|
+
container_type_key = self._get_container_type_key(
|
1227
|
+
model=model, container_family=container_family
|
1228
|
+
)
|
1229
|
+
|
1230
|
+
container_config = self.get_container_config_item(container_type_key)
|
1231
|
+
container_spec = container_config.spec if container_config else UNKNOWN
|
1232
|
+
cli_params = container_spec.cli_param if container_spec else UNKNOWN
|
1233
|
+
|
1234
|
+
restricted_params = self._find_restricted_params(
|
1235
|
+
cli_params, params, container_type_key
|
1236
|
+
)
|
1237
|
+
|
1238
|
+
if restricted_params:
|
1239
|
+
raise AquaValueError(
|
1240
|
+
f"Parameters {restricted_params} are set by Aqua "
|
1241
|
+
f"and cannot be overridden or are invalid."
|
1242
|
+
)
|
1243
|
+
return {"valid": True}
|
1244
|
+
|
1245
|
+
@staticmethod
|
1246
|
+
def _find_restricted_params(
|
1247
|
+
default_params: Union[str, List[str]],
|
1248
|
+
user_params: Union[str, List[str]],
|
1249
|
+
container_family: str,
|
1250
|
+
) -> List[str]:
|
1251
|
+
"""Returns a list of restricted params that user chooses to override when creating an Aqua deployment.
|
1252
|
+
The default parameters coming from the container index json file cannot be overridden.
|
1253
|
+
|
1254
|
+
Parameters
|
1255
|
+
----------
|
1256
|
+
default_params:
|
1257
|
+
Inference container parameter string with default values.
|
1258
|
+
user_params:
|
1259
|
+
Inference container parameter string with user provided values.
|
1260
|
+
container_family: str
|
1261
|
+
The image family of model deployment container runtime.
|
1262
|
+
|
1263
|
+
Returns
|
1264
|
+
-------
|
1265
|
+
A list with params keys common between params1 and params2.
|
1266
|
+
|
1267
|
+
"""
|
1268
|
+
restricted_params = []
|
1269
|
+
if default_params and user_params:
|
1270
|
+
default_params_dict = get_params_dict(default_params)
|
1271
|
+
user_params_dict = get_params_dict(user_params)
|
1272
|
+
|
1273
|
+
restricted_params_set = get_restricted_params_by_container(container_family)
|
1274
|
+
for key, _items in user_params_dict.items():
|
1275
|
+
if key in default_params_dict or key in restricted_params_set:
|
1276
|
+
restricted_params.append(key.lstrip("-"))
|
1277
|
+
|
1278
|
+
return restricted_params
|
1279
|
+
|
1280
|
+
@telemetry(entry_point="plugin=deployment&action=list_shapes", name="aqua")
|
1281
|
+
@cached(cache=TTLCache(maxsize=1, ttl=timedelta(minutes=5), timer=datetime.now))
|
1282
|
+
def list_shapes(self, **kwargs) -> List[ComputeShapeSummary]:
|
1283
|
+
"""Lists the valid model deployment shapes.
|
1284
|
+
|
1285
|
+
Parameters
|
1286
|
+
----------
|
1287
|
+
kwargs
|
1288
|
+
Keyword arguments, such as compartment_id
|
1289
|
+
for `list_call_get_all_results <https://docs.oracle.com/en-us/iaas/tools/python/2.118.1/api/pagination.html#oci.pagination.list_call_get_all_results>`_
|
1290
|
+
|
1291
|
+
Returns
|
1292
|
+
-------
|
1293
|
+
List[ComputeShapeSummary]:
|
1294
|
+
The list of the model deployment shapes.
|
1295
|
+
"""
|
1296
|
+
compartment_id = kwargs.pop("compartment_id", COMPARTMENT_OCID)
|
1297
|
+
oci_shapes: list[ModelDeploymentShapeSummary] = self.list_resource(
|
1298
|
+
self.ds_client.list_model_deployment_shapes,
|
1299
|
+
compartment_id=compartment_id,
|
1300
|
+
**kwargs,
|
1301
|
+
)
|
1302
|
+
|
1303
|
+
gpu_specs = load_gpu_shapes_index()
|
1304
|
+
|
1305
|
+
return [
|
1306
|
+
ComputeShapeSummary(
|
1307
|
+
core_count=oci_shape.core_count,
|
1308
|
+
memory_in_gbs=oci_shape.memory_in_gbs,
|
1309
|
+
shape_series=oci_shape.shape_series,
|
1310
|
+
name=oci_shape.name,
|
1311
|
+
gpu_specs=gpu_specs.shapes.get(oci_shape.name)
|
1312
|
+
or gpu_specs.shapes.get(oci_shape.name.upper()),
|
1313
|
+
)
|
1314
|
+
for oci_shape in oci_shapes
|
1315
|
+
]
|