genesis-flow 1.0.0__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.
- genesis_flow-1.0.0.dist-info/METADATA +822 -0
- genesis_flow-1.0.0.dist-info/RECORD +645 -0
- genesis_flow-1.0.0.dist-info/WHEEL +5 -0
- genesis_flow-1.0.0.dist-info/entry_points.txt +19 -0
- genesis_flow-1.0.0.dist-info/licenses/LICENSE.txt +202 -0
- genesis_flow-1.0.0.dist-info/top_level.txt +1 -0
- mlflow/__init__.py +367 -0
- mlflow/__main__.py +3 -0
- mlflow/ag2/__init__.py +56 -0
- mlflow/ag2/ag2_logger.py +294 -0
- mlflow/anthropic/__init__.py +40 -0
- mlflow/anthropic/autolog.py +129 -0
- mlflow/anthropic/chat.py +144 -0
- mlflow/artifacts/__init__.py +268 -0
- mlflow/autogen/__init__.py +144 -0
- mlflow/autogen/chat.py +142 -0
- mlflow/azure/__init__.py +26 -0
- mlflow/azure/auth_handler.py +257 -0
- mlflow/azure/client.py +319 -0
- mlflow/azure/config.py +120 -0
- mlflow/azure/connection_factory.py +340 -0
- mlflow/azure/exceptions.py +27 -0
- mlflow/azure/stores.py +327 -0
- mlflow/azure/utils.py +183 -0
- mlflow/bedrock/__init__.py +45 -0
- mlflow/bedrock/_autolog.py +202 -0
- mlflow/bedrock/chat.py +122 -0
- mlflow/bedrock/stream.py +160 -0
- mlflow/bedrock/utils.py +43 -0
- mlflow/cli.py +707 -0
- mlflow/client.py +12 -0
- mlflow/config/__init__.py +56 -0
- mlflow/crewai/__init__.py +79 -0
- mlflow/crewai/autolog.py +253 -0
- mlflow/crewai/chat.py +29 -0
- mlflow/data/__init__.py +75 -0
- mlflow/data/artifact_dataset_sources.py +170 -0
- mlflow/data/code_dataset_source.py +40 -0
- mlflow/data/dataset.py +123 -0
- mlflow/data/dataset_registry.py +168 -0
- mlflow/data/dataset_source.py +110 -0
- mlflow/data/dataset_source_registry.py +219 -0
- mlflow/data/delta_dataset_source.py +167 -0
- mlflow/data/digest_utils.py +108 -0
- mlflow/data/evaluation_dataset.py +562 -0
- mlflow/data/filesystem_dataset_source.py +81 -0
- mlflow/data/http_dataset_source.py +145 -0
- mlflow/data/huggingface_dataset.py +258 -0
- mlflow/data/huggingface_dataset_source.py +118 -0
- mlflow/data/meta_dataset.py +104 -0
- mlflow/data/numpy_dataset.py +223 -0
- mlflow/data/pandas_dataset.py +231 -0
- mlflow/data/polars_dataset.py +352 -0
- mlflow/data/pyfunc_dataset_mixin.py +31 -0
- mlflow/data/schema.py +76 -0
- mlflow/data/sources.py +1 -0
- mlflow/data/spark_dataset.py +406 -0
- mlflow/data/spark_dataset_source.py +74 -0
- mlflow/data/spark_delta_utils.py +118 -0
- mlflow/data/tensorflow_dataset.py +350 -0
- mlflow/data/uc_volume_dataset_source.py +81 -0
- mlflow/db.py +27 -0
- mlflow/dspy/__init__.py +17 -0
- mlflow/dspy/autolog.py +197 -0
- mlflow/dspy/callback.py +398 -0
- mlflow/dspy/constant.py +1 -0
- mlflow/dspy/load.py +93 -0
- mlflow/dspy/save.py +393 -0
- mlflow/dspy/util.py +109 -0
- mlflow/dspy/wrapper.py +226 -0
- mlflow/entities/__init__.py +104 -0
- mlflow/entities/_mlflow_object.py +52 -0
- mlflow/entities/assessment.py +545 -0
- mlflow/entities/assessment_error.py +80 -0
- mlflow/entities/assessment_source.py +141 -0
- mlflow/entities/dataset.py +92 -0
- mlflow/entities/dataset_input.py +51 -0
- mlflow/entities/dataset_summary.py +62 -0
- mlflow/entities/document.py +48 -0
- mlflow/entities/experiment.py +109 -0
- mlflow/entities/experiment_tag.py +35 -0
- mlflow/entities/file_info.py +45 -0
- mlflow/entities/input_tag.py +35 -0
- mlflow/entities/lifecycle_stage.py +35 -0
- mlflow/entities/logged_model.py +228 -0
- mlflow/entities/logged_model_input.py +26 -0
- mlflow/entities/logged_model_output.py +32 -0
- mlflow/entities/logged_model_parameter.py +46 -0
- mlflow/entities/logged_model_status.py +74 -0
- mlflow/entities/logged_model_tag.py +33 -0
- mlflow/entities/metric.py +200 -0
- mlflow/entities/model_registry/__init__.py +29 -0
- mlflow/entities/model_registry/_model_registry_entity.py +13 -0
- mlflow/entities/model_registry/model_version.py +243 -0
- mlflow/entities/model_registry/model_version_deployment_job_run_state.py +44 -0
- mlflow/entities/model_registry/model_version_deployment_job_state.py +70 -0
- mlflow/entities/model_registry/model_version_search.py +25 -0
- mlflow/entities/model_registry/model_version_stages.py +25 -0
- mlflow/entities/model_registry/model_version_status.py +35 -0
- mlflow/entities/model_registry/model_version_tag.py +35 -0
- mlflow/entities/model_registry/prompt.py +73 -0
- mlflow/entities/model_registry/prompt_version.py +244 -0
- mlflow/entities/model_registry/registered_model.py +175 -0
- mlflow/entities/model_registry/registered_model_alias.py +35 -0
- mlflow/entities/model_registry/registered_model_deployment_job_state.py +39 -0
- mlflow/entities/model_registry/registered_model_search.py +25 -0
- mlflow/entities/model_registry/registered_model_tag.py +35 -0
- mlflow/entities/multipart_upload.py +74 -0
- mlflow/entities/param.py +49 -0
- mlflow/entities/run.py +97 -0
- mlflow/entities/run_data.py +84 -0
- mlflow/entities/run_info.py +188 -0
- mlflow/entities/run_inputs.py +59 -0
- mlflow/entities/run_outputs.py +43 -0
- mlflow/entities/run_status.py +41 -0
- mlflow/entities/run_tag.py +36 -0
- mlflow/entities/source_type.py +31 -0
- mlflow/entities/span.py +774 -0
- mlflow/entities/span_event.py +96 -0
- mlflow/entities/span_status.py +102 -0
- mlflow/entities/trace.py +317 -0
- mlflow/entities/trace_data.py +71 -0
- mlflow/entities/trace_info.py +220 -0
- mlflow/entities/trace_info_v2.py +162 -0
- mlflow/entities/trace_location.py +173 -0
- mlflow/entities/trace_state.py +39 -0
- mlflow/entities/trace_status.py +68 -0
- mlflow/entities/view_type.py +51 -0
- mlflow/environment_variables.py +866 -0
- mlflow/evaluation/__init__.py +16 -0
- mlflow/evaluation/assessment.py +369 -0
- mlflow/evaluation/evaluation.py +411 -0
- mlflow/evaluation/evaluation_tag.py +61 -0
- mlflow/evaluation/fluent.py +48 -0
- mlflow/evaluation/utils.py +201 -0
- mlflow/exceptions.py +213 -0
- mlflow/experiments.py +140 -0
- mlflow/gemini/__init__.py +81 -0
- mlflow/gemini/autolog.py +186 -0
- mlflow/gemini/chat.py +261 -0
- mlflow/genai/__init__.py +71 -0
- mlflow/genai/datasets/__init__.py +67 -0
- mlflow/genai/datasets/evaluation_dataset.py +131 -0
- mlflow/genai/evaluation/__init__.py +3 -0
- mlflow/genai/evaluation/base.py +411 -0
- mlflow/genai/evaluation/constant.py +23 -0
- mlflow/genai/evaluation/utils.py +244 -0
- mlflow/genai/judges/__init__.py +21 -0
- mlflow/genai/judges/databricks.py +404 -0
- mlflow/genai/label_schemas/__init__.py +153 -0
- mlflow/genai/label_schemas/label_schemas.py +209 -0
- mlflow/genai/labeling/__init__.py +159 -0
- mlflow/genai/labeling/labeling.py +250 -0
- mlflow/genai/optimize/__init__.py +13 -0
- mlflow/genai/optimize/base.py +198 -0
- mlflow/genai/optimize/optimizers/__init__.py +4 -0
- mlflow/genai/optimize/optimizers/base_optimizer.py +38 -0
- mlflow/genai/optimize/optimizers/dspy_mipro_optimizer.py +221 -0
- mlflow/genai/optimize/optimizers/dspy_optimizer.py +91 -0
- mlflow/genai/optimize/optimizers/utils/dspy_mipro_callback.py +76 -0
- mlflow/genai/optimize/optimizers/utils/dspy_mipro_utils.py +18 -0
- mlflow/genai/optimize/types.py +75 -0
- mlflow/genai/optimize/util.py +30 -0
- mlflow/genai/prompts/__init__.py +206 -0
- mlflow/genai/scheduled_scorers.py +431 -0
- mlflow/genai/scorers/__init__.py +26 -0
- mlflow/genai/scorers/base.py +492 -0
- mlflow/genai/scorers/builtin_scorers.py +765 -0
- mlflow/genai/scorers/scorer_utils.py +138 -0
- mlflow/genai/scorers/validation.py +165 -0
- mlflow/genai/utils/data_validation.py +146 -0
- mlflow/genai/utils/enum_utils.py +23 -0
- mlflow/genai/utils/trace_utils.py +211 -0
- mlflow/groq/__init__.py +42 -0
- mlflow/groq/_groq_autolog.py +74 -0
- mlflow/johnsnowlabs/__init__.py +888 -0
- mlflow/langchain/__init__.py +24 -0
- mlflow/langchain/api_request_parallel_processor.py +330 -0
- mlflow/langchain/autolog.py +147 -0
- mlflow/langchain/chat_agent_langgraph.py +340 -0
- mlflow/langchain/constant.py +1 -0
- mlflow/langchain/constants.py +1 -0
- mlflow/langchain/databricks_dependencies.py +444 -0
- mlflow/langchain/langchain_tracer.py +597 -0
- mlflow/langchain/model.py +919 -0
- mlflow/langchain/output_parsers.py +142 -0
- mlflow/langchain/retriever_chain.py +153 -0
- mlflow/langchain/runnables.py +527 -0
- mlflow/langchain/utils/chat.py +402 -0
- mlflow/langchain/utils/logging.py +671 -0
- mlflow/langchain/utils/serialization.py +36 -0
- mlflow/legacy_databricks_cli/__init__.py +0 -0
- mlflow/legacy_databricks_cli/configure/__init__.py +0 -0
- mlflow/legacy_databricks_cli/configure/provider.py +482 -0
- mlflow/litellm/__init__.py +175 -0
- mlflow/llama_index/__init__.py +22 -0
- mlflow/llama_index/autolog.py +55 -0
- mlflow/llama_index/chat.py +43 -0
- mlflow/llama_index/constant.py +1 -0
- mlflow/llama_index/model.py +577 -0
- mlflow/llama_index/pyfunc_wrapper.py +332 -0
- mlflow/llama_index/serialize_objects.py +188 -0
- mlflow/llama_index/tracer.py +561 -0
- mlflow/metrics/__init__.py +479 -0
- mlflow/metrics/base.py +39 -0
- mlflow/metrics/genai/__init__.py +25 -0
- mlflow/metrics/genai/base.py +101 -0
- mlflow/metrics/genai/genai_metric.py +771 -0
- mlflow/metrics/genai/metric_definitions.py +450 -0
- mlflow/metrics/genai/model_utils.py +371 -0
- mlflow/metrics/genai/prompt_template.py +68 -0
- mlflow/metrics/genai/prompts/__init__.py +0 -0
- mlflow/metrics/genai/prompts/v1.py +422 -0
- mlflow/metrics/genai/utils.py +6 -0
- mlflow/metrics/metric_definitions.py +619 -0
- mlflow/mismatch.py +34 -0
- mlflow/mistral/__init__.py +34 -0
- mlflow/mistral/autolog.py +71 -0
- mlflow/mistral/chat.py +135 -0
- mlflow/ml_package_versions.py +452 -0
- mlflow/models/__init__.py +97 -0
- mlflow/models/auth_policy.py +83 -0
- mlflow/models/cli.py +354 -0
- mlflow/models/container/__init__.py +294 -0
- mlflow/models/container/scoring_server/__init__.py +0 -0
- mlflow/models/container/scoring_server/nginx.conf +39 -0
- mlflow/models/dependencies_schemas.py +287 -0
- mlflow/models/display_utils.py +158 -0
- mlflow/models/docker_utils.py +211 -0
- mlflow/models/evaluation/__init__.py +23 -0
- mlflow/models/evaluation/_shap_patch.py +64 -0
- mlflow/models/evaluation/artifacts.py +194 -0
- mlflow/models/evaluation/base.py +1811 -0
- mlflow/models/evaluation/calibration_curve.py +109 -0
- mlflow/models/evaluation/default_evaluator.py +996 -0
- mlflow/models/evaluation/deprecated.py +23 -0
- mlflow/models/evaluation/evaluator_registry.py +80 -0
- mlflow/models/evaluation/evaluators/classifier.py +704 -0
- mlflow/models/evaluation/evaluators/default.py +233 -0
- mlflow/models/evaluation/evaluators/regressor.py +96 -0
- mlflow/models/evaluation/evaluators/shap.py +296 -0
- mlflow/models/evaluation/lift_curve.py +178 -0
- mlflow/models/evaluation/utils/metric.py +123 -0
- mlflow/models/evaluation/utils/trace.py +179 -0
- mlflow/models/evaluation/validation.py +434 -0
- mlflow/models/flavor_backend.py +93 -0
- mlflow/models/flavor_backend_registry.py +53 -0
- mlflow/models/model.py +1639 -0
- mlflow/models/model_config.py +150 -0
- mlflow/models/notebook_resources/agent_evaluation_template.html +235 -0
- mlflow/models/notebook_resources/eval_with_dataset_example.py +22 -0
- mlflow/models/notebook_resources/eval_with_synthetic_example.py +22 -0
- mlflow/models/python_api.py +369 -0
- mlflow/models/rag_signatures.py +128 -0
- mlflow/models/resources.py +321 -0
- mlflow/models/signature.py +662 -0
- mlflow/models/utils.py +2054 -0
- mlflow/models/wheeled_model.py +280 -0
- mlflow/openai/__init__.py +57 -0
- mlflow/openai/_agent_tracer.py +364 -0
- mlflow/openai/api_request_parallel_processor.py +131 -0
- mlflow/openai/autolog.py +509 -0
- mlflow/openai/constant.py +1 -0
- mlflow/openai/model.py +824 -0
- mlflow/openai/utils/chat_schema.py +367 -0
- mlflow/optuna/__init__.py +3 -0
- mlflow/optuna/storage.py +646 -0
- mlflow/plugins/__init__.py +72 -0
- mlflow/plugins/base.py +358 -0
- mlflow/plugins/builtin/__init__.py +24 -0
- mlflow/plugins/builtin/pytorch_plugin.py +150 -0
- mlflow/plugins/builtin/sklearn_plugin.py +158 -0
- mlflow/plugins/builtin/transformers_plugin.py +187 -0
- mlflow/plugins/cli.py +321 -0
- mlflow/plugins/discovery.py +340 -0
- mlflow/plugins/manager.py +465 -0
- mlflow/plugins/registry.py +316 -0
- mlflow/plugins/templates/framework_plugin_template.py +329 -0
- mlflow/prompt/constants.py +20 -0
- mlflow/prompt/promptlab_model.py +197 -0
- mlflow/prompt/registry_utils.py +248 -0
- mlflow/promptflow/__init__.py +495 -0
- mlflow/protos/__init__.py +0 -0
- mlflow/protos/assessments_pb2.py +174 -0
- mlflow/protos/databricks_artifacts_pb2.py +489 -0
- mlflow/protos/databricks_filesystem_service_pb2.py +196 -0
- mlflow/protos/databricks_managed_catalog_messages_pb2.py +95 -0
- mlflow/protos/databricks_managed_catalog_service_pb2.py +86 -0
- mlflow/protos/databricks_pb2.py +267 -0
- mlflow/protos/databricks_trace_server_pb2.py +374 -0
- mlflow/protos/databricks_uc_registry_messages_pb2.py +1249 -0
- mlflow/protos/databricks_uc_registry_service_pb2.py +170 -0
- mlflow/protos/facet_feature_statistics_pb2.py +296 -0
- mlflow/protos/internal_pb2.py +77 -0
- mlflow/protos/mlflow_artifacts_pb2.py +336 -0
- mlflow/protos/model_registry_pb2.py +1073 -0
- mlflow/protos/scalapb/__init__.py +0 -0
- mlflow/protos/scalapb/scalapb_pb2.py +104 -0
- mlflow/protos/service_pb2.py +2600 -0
- mlflow/protos/unity_catalog_oss_messages_pb2.py +457 -0
- mlflow/protos/unity_catalog_oss_service_pb2.py +130 -0
- mlflow/protos/unity_catalog_prompt_messages_pb2.py +447 -0
- mlflow/protos/unity_catalog_prompt_messages_pb2_grpc.py +24 -0
- mlflow/protos/unity_catalog_prompt_service_pb2.py +164 -0
- mlflow/protos/unity_catalog_prompt_service_pb2_grpc.py +785 -0
- mlflow/py.typed +0 -0
- mlflow/pydantic_ai/__init__.py +57 -0
- mlflow/pydantic_ai/autolog.py +173 -0
- mlflow/pyfunc/__init__.py +3844 -0
- mlflow/pyfunc/_mlflow_pyfunc_backend_predict.py +61 -0
- mlflow/pyfunc/backend.py +523 -0
- mlflow/pyfunc/context.py +78 -0
- mlflow/pyfunc/dbconnect_artifact_cache.py +144 -0
- mlflow/pyfunc/loaders/__init__.py +7 -0
- mlflow/pyfunc/loaders/chat_agent.py +117 -0
- mlflow/pyfunc/loaders/chat_model.py +125 -0
- mlflow/pyfunc/loaders/code_model.py +31 -0
- mlflow/pyfunc/loaders/responses_agent.py +112 -0
- mlflow/pyfunc/mlserver.py +46 -0
- mlflow/pyfunc/model.py +1473 -0
- mlflow/pyfunc/scoring_server/__init__.py +604 -0
- mlflow/pyfunc/scoring_server/app.py +7 -0
- mlflow/pyfunc/scoring_server/client.py +146 -0
- mlflow/pyfunc/spark_model_cache.py +48 -0
- mlflow/pyfunc/stdin_server.py +44 -0
- mlflow/pyfunc/utils/__init__.py +3 -0
- mlflow/pyfunc/utils/data_validation.py +224 -0
- mlflow/pyfunc/utils/environment.py +22 -0
- mlflow/pyfunc/utils/input_converter.py +47 -0
- mlflow/pyfunc/utils/serving_data_parser.py +11 -0
- mlflow/pytorch/__init__.py +1171 -0
- mlflow/pytorch/_lightning_autolog.py +580 -0
- mlflow/pytorch/_pytorch_autolog.py +50 -0
- mlflow/pytorch/pickle_module.py +35 -0
- mlflow/rfunc/__init__.py +42 -0
- mlflow/rfunc/backend.py +134 -0
- mlflow/runs.py +89 -0
- mlflow/server/__init__.py +302 -0
- mlflow/server/auth/__init__.py +1224 -0
- mlflow/server/auth/__main__.py +4 -0
- mlflow/server/auth/basic_auth.ini +6 -0
- mlflow/server/auth/cli.py +11 -0
- mlflow/server/auth/client.py +537 -0
- mlflow/server/auth/config.py +34 -0
- mlflow/server/auth/db/__init__.py +0 -0
- mlflow/server/auth/db/cli.py +18 -0
- mlflow/server/auth/db/migrations/__init__.py +0 -0
- mlflow/server/auth/db/migrations/alembic.ini +110 -0
- mlflow/server/auth/db/migrations/env.py +76 -0
- mlflow/server/auth/db/migrations/versions/8606fa83a998_initial_migration.py +51 -0
- mlflow/server/auth/db/migrations/versions/__init__.py +0 -0
- mlflow/server/auth/db/models.py +67 -0
- mlflow/server/auth/db/utils.py +37 -0
- mlflow/server/auth/entities.py +165 -0
- mlflow/server/auth/logo.py +14 -0
- mlflow/server/auth/permissions.py +65 -0
- mlflow/server/auth/routes.py +18 -0
- mlflow/server/auth/sqlalchemy_store.py +263 -0
- mlflow/server/graphql/__init__.py +0 -0
- mlflow/server/graphql/autogenerated_graphql_schema.py +353 -0
- mlflow/server/graphql/graphql_custom_scalars.py +24 -0
- mlflow/server/graphql/graphql_errors.py +15 -0
- mlflow/server/graphql/graphql_no_batching.py +89 -0
- mlflow/server/graphql/graphql_schema_extensions.py +74 -0
- mlflow/server/handlers.py +3217 -0
- mlflow/server/prometheus_exporter.py +17 -0
- mlflow/server/validation.py +30 -0
- mlflow/shap/__init__.py +691 -0
- mlflow/sklearn/__init__.py +1994 -0
- mlflow/sklearn/utils.py +1041 -0
- mlflow/smolagents/__init__.py +66 -0
- mlflow/smolagents/autolog.py +139 -0
- mlflow/smolagents/chat.py +29 -0
- mlflow/store/__init__.py +10 -0
- mlflow/store/_unity_catalog/__init__.py +1 -0
- mlflow/store/_unity_catalog/lineage/__init__.py +1 -0
- mlflow/store/_unity_catalog/lineage/constants.py +2 -0
- mlflow/store/_unity_catalog/registry/__init__.py +6 -0
- mlflow/store/_unity_catalog/registry/prompt_info.py +75 -0
- mlflow/store/_unity_catalog/registry/rest_store.py +1740 -0
- mlflow/store/_unity_catalog/registry/uc_oss_rest_store.py +507 -0
- mlflow/store/_unity_catalog/registry/utils.py +121 -0
- mlflow/store/artifact/__init__.py +0 -0
- mlflow/store/artifact/artifact_repo.py +472 -0
- mlflow/store/artifact/artifact_repository_registry.py +154 -0
- mlflow/store/artifact/azure_blob_artifact_repo.py +275 -0
- mlflow/store/artifact/azure_data_lake_artifact_repo.py +295 -0
- mlflow/store/artifact/cli.py +141 -0
- mlflow/store/artifact/cloud_artifact_repo.py +332 -0
- mlflow/store/artifact/databricks_artifact_repo.py +729 -0
- mlflow/store/artifact/databricks_artifact_repo_resources.py +301 -0
- mlflow/store/artifact/databricks_logged_model_artifact_repo.py +93 -0
- mlflow/store/artifact/databricks_models_artifact_repo.py +216 -0
- mlflow/store/artifact/databricks_sdk_artifact_repo.py +134 -0
- mlflow/store/artifact/databricks_sdk_models_artifact_repo.py +97 -0
- mlflow/store/artifact/dbfs_artifact_repo.py +240 -0
- mlflow/store/artifact/ftp_artifact_repo.py +132 -0
- mlflow/store/artifact/gcs_artifact_repo.py +296 -0
- mlflow/store/artifact/hdfs_artifact_repo.py +209 -0
- mlflow/store/artifact/http_artifact_repo.py +218 -0
- mlflow/store/artifact/local_artifact_repo.py +142 -0
- mlflow/store/artifact/mlflow_artifacts_repo.py +94 -0
- mlflow/store/artifact/models_artifact_repo.py +259 -0
- mlflow/store/artifact/optimized_s3_artifact_repo.py +356 -0
- mlflow/store/artifact/presigned_url_artifact_repo.py +173 -0
- mlflow/store/artifact/r2_artifact_repo.py +70 -0
- mlflow/store/artifact/runs_artifact_repo.py +265 -0
- mlflow/store/artifact/s3_artifact_repo.py +330 -0
- mlflow/store/artifact/sftp_artifact_repo.py +141 -0
- mlflow/store/artifact/uc_volume_artifact_repo.py +76 -0
- mlflow/store/artifact/unity_catalog_models_artifact_repo.py +168 -0
- mlflow/store/artifact/unity_catalog_oss_models_artifact_repo.py +168 -0
- mlflow/store/artifact/utils/__init__.py +0 -0
- mlflow/store/artifact/utils/models.py +148 -0
- mlflow/store/db/__init__.py +0 -0
- mlflow/store/db/base_sql_model.py +3 -0
- mlflow/store/db/db_types.py +10 -0
- mlflow/store/db/utils.py +314 -0
- mlflow/store/db_migrations/__init__.py +0 -0
- mlflow/store/db_migrations/alembic.ini +74 -0
- mlflow/store/db_migrations/env.py +84 -0
- mlflow/store/db_migrations/versions/0584bdc529eb_add_cascading_deletion_to_datasets_from_experiments.py +88 -0
- mlflow/store/db_migrations/versions/0a8213491aaa_drop_duplicate_killed_constraint.py +49 -0
- mlflow/store/db_migrations/versions/0c779009ac13_add_deleted_time_field_to_runs_table.py +24 -0
- mlflow/store/db_migrations/versions/181f10493468_allow_nulls_for_metric_values.py +35 -0
- mlflow/store/db_migrations/versions/27a6a02d2cf1_add_model_version_tags_table.py +38 -0
- mlflow/store/db_migrations/versions/2b4d017a5e9b_add_model_registry_tables_to_db.py +77 -0
- mlflow/store/db_migrations/versions/2d6e25af4d3e_increase_max_param_val_length.py +33 -0
- mlflow/store/db_migrations/versions/3500859a5d39_add_model_aliases_table.py +50 -0
- mlflow/store/db_migrations/versions/39d1c3be5f05_add_is_nan_constraint_for_metrics_tables_if_necessary.py +41 -0
- mlflow/store/db_migrations/versions/400f98739977_add_logged_model_tables.py +123 -0
- mlflow/store/db_migrations/versions/4465047574b1_increase_max_dataset_schema_size.py +38 -0
- mlflow/store/db_migrations/versions/451aebb31d03_add_metric_step.py +35 -0
- mlflow/store/db_migrations/versions/5b0e9adcef9c_add_cascade_deletion_to_trace_tables_fk.py +40 -0
- mlflow/store/db_migrations/versions/6953534de441_add_step_to_inputs_table.py +25 -0
- mlflow/store/db_migrations/versions/728d730b5ebd_add_registered_model_tags_table.py +38 -0
- mlflow/store/db_migrations/versions/7ac759974ad8_update_run_tags_with_larger_limit.py +36 -0
- mlflow/store/db_migrations/versions/7f2a7d5fae7d_add_datasets_inputs_input_tags_tables.py +82 -0
- mlflow/store/db_migrations/versions/84291f40a231_add_run_link_to_model_version.py +26 -0
- mlflow/store/db_migrations/versions/867495a8f9d4_add_trace_tables.py +90 -0
- mlflow/store/db_migrations/versions/89d4b8295536_create_latest_metrics_table.py +169 -0
- mlflow/store/db_migrations/versions/90e64c465722_migrate_user_column_to_tags.py +64 -0
- mlflow/store/db_migrations/versions/97727af70f4d_creation_time_last_update_time_experiments.py +25 -0
- mlflow/store/db_migrations/versions/__init__.py +0 -0
- mlflow/store/db_migrations/versions/a8c4a736bde6_allow_nulls_for_run_id.py +27 -0
- mlflow/store/db_migrations/versions/acf3f17fdcc7_add_storage_location_field_to_model_.py +29 -0
- mlflow/store/db_migrations/versions/bd07f7e963c5_create_index_on_run_uuid.py +26 -0
- mlflow/store/db_migrations/versions/bda7b8c39065_increase_model_version_tag_value_limit.py +38 -0
- mlflow/store/db_migrations/versions/c48cb773bb87_reset_default_value_for_is_nan_in_metrics_table_for_mysql.py +41 -0
- mlflow/store/db_migrations/versions/cbc13b556ace_add_v3_trace_schema_columns.py +31 -0
- mlflow/store/db_migrations/versions/cc1f77228345_change_param_value_length_to_500.py +34 -0
- mlflow/store/db_migrations/versions/cfd24bdc0731_update_run_status_constraint_with_killed.py +78 -0
- mlflow/store/db_migrations/versions/df50e92ffc5e_add_experiment_tags_table.py +38 -0
- mlflow/store/db_migrations/versions/f5a4f2784254_increase_run_tag_value_limit.py +36 -0
- mlflow/store/entities/__init__.py +3 -0
- mlflow/store/entities/paged_list.py +18 -0
- mlflow/store/model_registry/__init__.py +10 -0
- mlflow/store/model_registry/abstract_store.py +1081 -0
- mlflow/store/model_registry/base_rest_store.py +44 -0
- mlflow/store/model_registry/databricks_workspace_model_registry_rest_store.py +37 -0
- mlflow/store/model_registry/dbmodels/__init__.py +0 -0
- mlflow/store/model_registry/dbmodels/models.py +206 -0
- mlflow/store/model_registry/file_store.py +1091 -0
- mlflow/store/model_registry/rest_store.py +481 -0
- mlflow/store/model_registry/sqlalchemy_store.py +1286 -0
- mlflow/store/tracking/__init__.py +23 -0
- mlflow/store/tracking/abstract_store.py +816 -0
- mlflow/store/tracking/dbmodels/__init__.py +0 -0
- mlflow/store/tracking/dbmodels/initial_models.py +243 -0
- mlflow/store/tracking/dbmodels/models.py +1073 -0
- mlflow/store/tracking/file_store.py +2438 -0
- mlflow/store/tracking/postgres_managed_identity.py +146 -0
- mlflow/store/tracking/rest_store.py +1131 -0
- mlflow/store/tracking/sqlalchemy_store.py +2785 -0
- mlflow/system_metrics/__init__.py +61 -0
- mlflow/system_metrics/metrics/__init__.py +0 -0
- mlflow/system_metrics/metrics/base_metrics_monitor.py +32 -0
- mlflow/system_metrics/metrics/cpu_monitor.py +23 -0
- mlflow/system_metrics/metrics/disk_monitor.py +21 -0
- mlflow/system_metrics/metrics/gpu_monitor.py +71 -0
- mlflow/system_metrics/metrics/network_monitor.py +34 -0
- mlflow/system_metrics/metrics/rocm_monitor.py +123 -0
- mlflow/system_metrics/system_metrics_monitor.py +198 -0
- mlflow/tracing/__init__.py +16 -0
- mlflow/tracing/assessment.py +356 -0
- mlflow/tracing/client.py +531 -0
- mlflow/tracing/config.py +125 -0
- mlflow/tracing/constant.py +105 -0
- mlflow/tracing/destination.py +81 -0
- mlflow/tracing/display/__init__.py +40 -0
- mlflow/tracing/display/display_handler.py +196 -0
- mlflow/tracing/export/async_export_queue.py +186 -0
- mlflow/tracing/export/inference_table.py +138 -0
- mlflow/tracing/export/mlflow_v3.py +137 -0
- mlflow/tracing/export/utils.py +70 -0
- mlflow/tracing/fluent.py +1417 -0
- mlflow/tracing/processor/base_mlflow.py +199 -0
- mlflow/tracing/processor/inference_table.py +175 -0
- mlflow/tracing/processor/mlflow_v3.py +47 -0
- mlflow/tracing/processor/otel.py +73 -0
- mlflow/tracing/provider.py +487 -0
- mlflow/tracing/trace_manager.py +200 -0
- mlflow/tracing/utils/__init__.py +616 -0
- mlflow/tracing/utils/artifact_utils.py +28 -0
- mlflow/tracing/utils/copy.py +55 -0
- mlflow/tracing/utils/environment.py +55 -0
- mlflow/tracing/utils/exception.py +21 -0
- mlflow/tracing/utils/once.py +35 -0
- mlflow/tracing/utils/otlp.py +63 -0
- mlflow/tracing/utils/processor.py +54 -0
- mlflow/tracing/utils/search.py +292 -0
- mlflow/tracing/utils/timeout.py +250 -0
- mlflow/tracing/utils/token.py +19 -0
- mlflow/tracing/utils/truncation.py +124 -0
- mlflow/tracing/utils/warning.py +76 -0
- mlflow/tracking/__init__.py +39 -0
- mlflow/tracking/_model_registry/__init__.py +1 -0
- mlflow/tracking/_model_registry/client.py +764 -0
- mlflow/tracking/_model_registry/fluent.py +853 -0
- mlflow/tracking/_model_registry/registry.py +67 -0
- mlflow/tracking/_model_registry/utils.py +251 -0
- mlflow/tracking/_tracking_service/__init__.py +0 -0
- mlflow/tracking/_tracking_service/client.py +883 -0
- mlflow/tracking/_tracking_service/registry.py +56 -0
- mlflow/tracking/_tracking_service/utils.py +275 -0
- mlflow/tracking/artifact_utils.py +179 -0
- mlflow/tracking/client.py +5900 -0
- mlflow/tracking/context/__init__.py +0 -0
- mlflow/tracking/context/abstract_context.py +35 -0
- mlflow/tracking/context/databricks_cluster_context.py +15 -0
- mlflow/tracking/context/databricks_command_context.py +15 -0
- mlflow/tracking/context/databricks_job_context.py +49 -0
- mlflow/tracking/context/databricks_notebook_context.py +41 -0
- mlflow/tracking/context/databricks_repo_context.py +43 -0
- mlflow/tracking/context/default_context.py +51 -0
- mlflow/tracking/context/git_context.py +32 -0
- mlflow/tracking/context/registry.py +98 -0
- mlflow/tracking/context/system_environment_context.py +15 -0
- mlflow/tracking/default_experiment/__init__.py +1 -0
- mlflow/tracking/default_experiment/abstract_context.py +43 -0
- mlflow/tracking/default_experiment/databricks_notebook_experiment_provider.py +44 -0
- mlflow/tracking/default_experiment/registry.py +75 -0
- mlflow/tracking/fluent.py +3595 -0
- mlflow/tracking/metric_value_conversion_utils.py +93 -0
- mlflow/tracking/multimedia.py +206 -0
- mlflow/tracking/registry.py +86 -0
- mlflow/tracking/request_auth/__init__.py +0 -0
- mlflow/tracking/request_auth/abstract_request_auth_provider.py +34 -0
- mlflow/tracking/request_auth/registry.py +60 -0
- mlflow/tracking/request_header/__init__.py +0 -0
- mlflow/tracking/request_header/abstract_request_header_provider.py +36 -0
- mlflow/tracking/request_header/databricks_request_header_provider.py +38 -0
- mlflow/tracking/request_header/default_request_header_provider.py +17 -0
- mlflow/tracking/request_header/registry.py +79 -0
- mlflow/transformers/__init__.py +2982 -0
- mlflow/transformers/flavor_config.py +258 -0
- mlflow/transformers/hub_utils.py +83 -0
- mlflow/transformers/llm_inference_utils.py +468 -0
- mlflow/transformers/model_io.py +301 -0
- mlflow/transformers/peft.py +51 -0
- mlflow/transformers/signature.py +183 -0
- mlflow/transformers/torch_utils.py +55 -0
- mlflow/types/__init__.py +21 -0
- mlflow/types/agent.py +270 -0
- mlflow/types/chat.py +240 -0
- mlflow/types/llm.py +935 -0
- mlflow/types/responses.py +139 -0
- mlflow/types/responses_helpers.py +416 -0
- mlflow/types/schema.py +1505 -0
- mlflow/types/type_hints.py +647 -0
- mlflow/types/utils.py +753 -0
- mlflow/utils/__init__.py +283 -0
- mlflow/utils/_capture_modules.py +256 -0
- mlflow/utils/_capture_transformers_modules.py +75 -0
- mlflow/utils/_spark_utils.py +201 -0
- mlflow/utils/_unity_catalog_oss_utils.py +97 -0
- mlflow/utils/_unity_catalog_utils.py +479 -0
- mlflow/utils/annotations.py +218 -0
- mlflow/utils/arguments_utils.py +16 -0
- mlflow/utils/async_logging/__init__.py +1 -0
- mlflow/utils/async_logging/async_artifacts_logging_queue.py +258 -0
- mlflow/utils/async_logging/async_logging_queue.py +366 -0
- mlflow/utils/async_logging/run_artifact.py +38 -0
- mlflow/utils/async_logging/run_batch.py +58 -0
- mlflow/utils/async_logging/run_operations.py +49 -0
- mlflow/utils/autologging_utils/__init__.py +737 -0
- mlflow/utils/autologging_utils/client.py +432 -0
- mlflow/utils/autologging_utils/config.py +33 -0
- mlflow/utils/autologging_utils/events.py +294 -0
- mlflow/utils/autologging_utils/logging_and_warnings.py +328 -0
- mlflow/utils/autologging_utils/metrics_queue.py +71 -0
- mlflow/utils/autologging_utils/safety.py +1104 -0
- mlflow/utils/autologging_utils/versioning.py +95 -0
- mlflow/utils/checkpoint_utils.py +206 -0
- mlflow/utils/class_utils.py +6 -0
- mlflow/utils/cli_args.py +257 -0
- mlflow/utils/conda.py +354 -0
- mlflow/utils/credentials.py +231 -0
- mlflow/utils/data_utils.py +17 -0
- mlflow/utils/databricks_utils.py +1436 -0
- mlflow/utils/docstring_utils.py +477 -0
- mlflow/utils/doctor.py +133 -0
- mlflow/utils/download_cloud_file_chunk.py +43 -0
- mlflow/utils/env_manager.py +16 -0
- mlflow/utils/env_pack.py +131 -0
- mlflow/utils/environment.py +1009 -0
- mlflow/utils/exception_utils.py +14 -0
- mlflow/utils/file_utils.py +978 -0
- mlflow/utils/git_utils.py +77 -0
- mlflow/utils/gorilla.py +797 -0
- mlflow/utils/import_hooks/__init__.py +363 -0
- mlflow/utils/lazy_load.py +51 -0
- mlflow/utils/logging_utils.py +168 -0
- mlflow/utils/mime_type_utils.py +58 -0
- mlflow/utils/mlflow_tags.py +103 -0
- mlflow/utils/model_utils.py +486 -0
- mlflow/utils/name_utils.py +346 -0
- mlflow/utils/nfs_on_spark.py +62 -0
- mlflow/utils/openai_utils.py +164 -0
- mlflow/utils/os.py +12 -0
- mlflow/utils/oss_registry_utils.py +29 -0
- mlflow/utils/plugins.py +17 -0
- mlflow/utils/process.py +182 -0
- mlflow/utils/promptlab_utils.py +146 -0
- mlflow/utils/proto_json_utils.py +743 -0
- mlflow/utils/pydantic_utils.py +54 -0
- mlflow/utils/request_utils.py +279 -0
- mlflow/utils/requirements_utils.py +704 -0
- mlflow/utils/rest_utils.py +673 -0
- mlflow/utils/search_logged_model_utils.py +127 -0
- mlflow/utils/search_utils.py +2111 -0
- mlflow/utils/secure_loading.py +221 -0
- mlflow/utils/security_validation.py +384 -0
- mlflow/utils/server_cli_utils.py +61 -0
- mlflow/utils/spark_utils.py +15 -0
- mlflow/utils/string_utils.py +138 -0
- mlflow/utils/thread_utils.py +63 -0
- mlflow/utils/time.py +54 -0
- mlflow/utils/timeout.py +42 -0
- mlflow/utils/uri.py +572 -0
- mlflow/utils/validation.py +662 -0
- mlflow/utils/virtualenv.py +458 -0
- mlflow/utils/warnings_utils.py +25 -0
- mlflow/utils/yaml_utils.py +179 -0
- mlflow/version.py +24 -0
@@ -0,0 +1,221 @@
|
|
1
|
+
import contextlib
|
2
|
+
import io
|
3
|
+
import logging
|
4
|
+
import math
|
5
|
+
import os
|
6
|
+
from typing import TYPE_CHECKING, Optional
|
7
|
+
|
8
|
+
from mlflow.entities.model_registry import Prompt
|
9
|
+
from mlflow.exceptions import MlflowException
|
10
|
+
from mlflow.genai.optimize.optimizers.dspy_optimizer import _DSPyOptimizer
|
11
|
+
from mlflow.genai.optimize.types import OBJECTIVE_FN, LLMParams
|
12
|
+
from mlflow.genai.prompts import register_prompt
|
13
|
+
from mlflow.genai.scorers import Scorer
|
14
|
+
from mlflow.tracking._model_registry.fluent import active_run
|
15
|
+
from mlflow.tracking.fluent import log_metric, log_param
|
16
|
+
|
17
|
+
if TYPE_CHECKING:
|
18
|
+
import dspy
|
19
|
+
import pandas as pd
|
20
|
+
|
21
|
+
|
22
|
+
_logger = logging.getLogger(__name__)
|
23
|
+
|
24
|
+
|
25
|
+
class _DSPyMIPROv2Optimizer(_DSPyOptimizer):
|
26
|
+
def optimize(
|
27
|
+
self,
|
28
|
+
prompt: Prompt,
|
29
|
+
target_llm_params: LLMParams,
|
30
|
+
train_data: "pd.DataFrame",
|
31
|
+
scorers: list[Scorer],
|
32
|
+
objective: Optional[OBJECTIVE_FN] = None,
|
33
|
+
eval_data: Optional["pd.DataFrame"] = None,
|
34
|
+
) -> Prompt:
|
35
|
+
import dspy
|
36
|
+
|
37
|
+
from mlflow.genai.optimize.optimizers.utils.dspy_mipro_callback import _DSPyMIPROv2Callback
|
38
|
+
from mlflow.genai.optimize.optimizers.utils.dspy_mipro_utils import format_optimized_prompt
|
39
|
+
|
40
|
+
_logger.info(
|
41
|
+
f"🎯 Starting prompt optimization for: {prompt.uri}\n"
|
42
|
+
f"⏱️ This may take several minutes or longer depending on dataset size...\n"
|
43
|
+
f"📊 Training with {len(train_data)} examples."
|
44
|
+
)
|
45
|
+
|
46
|
+
input_fields = self._get_input_fields(train_data)
|
47
|
+
self._validate_input_fields(input_fields, prompt)
|
48
|
+
output_fields = self._get_output_fields(train_data)
|
49
|
+
|
50
|
+
teacher_settings = {}
|
51
|
+
if self.optimizer_config.optimizer_llm:
|
52
|
+
teacher_lm = dspy.LM(
|
53
|
+
model=self.optimizer_config.optimizer_llm.model_name,
|
54
|
+
temperature=self.optimizer_config.optimizer_llm.temperature,
|
55
|
+
api_base=self.optimizer_config.optimizer_llm.base_uri,
|
56
|
+
)
|
57
|
+
teacher_settings["lm"] = teacher_lm
|
58
|
+
|
59
|
+
lm = dspy.LM(
|
60
|
+
model=target_llm_params.model_name,
|
61
|
+
temperature=target_llm_params.temperature,
|
62
|
+
api_base=target_llm_params.base_uri,
|
63
|
+
)
|
64
|
+
|
65
|
+
instructions = self._extract_instructions(prompt.template, teacher_settings.get("lm", lm))
|
66
|
+
|
67
|
+
signature = dspy.make_signature(
|
68
|
+
{
|
69
|
+
**{key: (_type, dspy.InputField()) for key, _type in input_fields.items()},
|
70
|
+
**{key: (_type, dspy.OutputField()) for key, _type in output_fields.items()},
|
71
|
+
},
|
72
|
+
instructions,
|
73
|
+
)
|
74
|
+
|
75
|
+
# Define main student program
|
76
|
+
program = dspy.Predict(signature)
|
77
|
+
|
78
|
+
train_data = self._convert_to_dspy_dataset(train_data)
|
79
|
+
eval_data = self._convert_to_dspy_dataset(eval_data) if eval_data is not None else None
|
80
|
+
|
81
|
+
num_candidates = self.optimizer_config.num_instruction_candidates
|
82
|
+
optimizer = dspy.MIPROv2(
|
83
|
+
metric=self._convert_to_dspy_metric(input_fields, output_fields, scorers, objective),
|
84
|
+
max_bootstrapped_demos=self.optimizer_config.max_few_show_examples,
|
85
|
+
num_candidates=num_candidates,
|
86
|
+
num_threads=self.optimizer_config.num_threads,
|
87
|
+
teacher_settings=teacher_settings,
|
88
|
+
auto=None,
|
89
|
+
)
|
90
|
+
|
91
|
+
adapter = dspy.JSONAdapter()
|
92
|
+
callbacks = (
|
93
|
+
[
|
94
|
+
_DSPyMIPROv2Callback(prompt.name, input_fields),
|
95
|
+
]
|
96
|
+
if self.optimizer_config.autolog
|
97
|
+
else []
|
98
|
+
)
|
99
|
+
with dspy.context(lm=lm, adapter=adapter, callbacks=callbacks):
|
100
|
+
with self._maybe_suppress_stdout_stderr():
|
101
|
+
optimized_program = optimizer.compile(
|
102
|
+
program,
|
103
|
+
trainset=train_data,
|
104
|
+
valset=eval_data,
|
105
|
+
num_trials=self._get_num_trials(num_candidates),
|
106
|
+
minibatch_size=self._get_minibatch_size(train_data, eval_data),
|
107
|
+
requires_permission_to_run=False,
|
108
|
+
)
|
109
|
+
|
110
|
+
template = format_optimized_prompt(
|
111
|
+
program=optimized_program,
|
112
|
+
input_fields=input_fields,
|
113
|
+
)
|
114
|
+
|
115
|
+
self._display_optimization_result(optimized_program)
|
116
|
+
final_score = getattr(optimized_program, "score", None)
|
117
|
+
optimized_prompt = register_prompt(
|
118
|
+
name=prompt.name,
|
119
|
+
template=template,
|
120
|
+
tags={
|
121
|
+
"overall_eval_score": str(final_score),
|
122
|
+
},
|
123
|
+
)
|
124
|
+
|
125
|
+
if self.optimizer_config.autolog:
|
126
|
+
self._log_optimization_result(final_score, optimized_prompt)
|
127
|
+
|
128
|
+
return optimized_prompt
|
129
|
+
|
130
|
+
def _get_num_trials(self, num_candidates: int) -> int:
|
131
|
+
# MAX(2*log(num_candidates), 3/2*num_candidates)
|
132
|
+
return int(max(2 * math.log2(num_candidates), 1.5 * num_candidates))
|
133
|
+
|
134
|
+
def _get_minibatch_size(
|
135
|
+
self,
|
136
|
+
train_data: "pd.DataFrame",
|
137
|
+
eval_data: Optional["pd.DataFrame"] = None,
|
138
|
+
) -> int:
|
139
|
+
# The default minibatch size is 35 in MIPROv2.
|
140
|
+
if eval_data is not None:
|
141
|
+
return min(35, len(eval_data) // 2)
|
142
|
+
return min(35, len(train_data) // 2)
|
143
|
+
|
144
|
+
def _validate_input_fields(self, input_fields: dict[str, type], prompt: Prompt) -> None:
|
145
|
+
if missing_fields := set(prompt.variables) - set(input_fields.keys()):
|
146
|
+
raise MlflowException(
|
147
|
+
f"Validation failed. Missing prompt variables in dataset: {missing_fields}. "
|
148
|
+
"Please ensure your dataset contains columns for all prompt variables."
|
149
|
+
)
|
150
|
+
|
151
|
+
def _extract_instructions(self, template: str, lm: "dspy.LM") -> str:
|
152
|
+
import dspy
|
153
|
+
|
154
|
+
extractor = dspy.Predict(
|
155
|
+
dspy.make_signature(
|
156
|
+
{
|
157
|
+
"prompt": (str, dspy.InputField()),
|
158
|
+
"instruction": (str, dspy.OutputField()),
|
159
|
+
},
|
160
|
+
"Extract the core instructions from the prompt "
|
161
|
+
"to use as the system message for the LLM.",
|
162
|
+
)
|
163
|
+
)
|
164
|
+
|
165
|
+
with dspy.context(lm=lm):
|
166
|
+
return extractor(prompt=template).instruction
|
167
|
+
|
168
|
+
@contextlib.contextmanager
|
169
|
+
def _maybe_suppress_stdout_stderr(self):
|
170
|
+
"""Context manager for redirecting stdout/stderr based on verbose setting.
|
171
|
+
If verbose is False, redirects output to devnull or StringIO.
|
172
|
+
If verbose is True, doesn't redirect output.
|
173
|
+
"""
|
174
|
+
if not self.optimizer_config.verbose:
|
175
|
+
try:
|
176
|
+
output_sink = open(os.devnull, "w") # noqa: SIM115
|
177
|
+
except (OSError, IOError):
|
178
|
+
output_sink = io.StringIO()
|
179
|
+
|
180
|
+
with output_sink:
|
181
|
+
with (
|
182
|
+
contextlib.redirect_stdout(output_sink),
|
183
|
+
contextlib.redirect_stderr(output_sink),
|
184
|
+
):
|
185
|
+
yield
|
186
|
+
else:
|
187
|
+
yield
|
188
|
+
|
189
|
+
def _display_optimization_result(self, program: "dspy.Predict"):
|
190
|
+
score = getattr(program, "score", None)
|
191
|
+
if score is None:
|
192
|
+
return
|
193
|
+
# In DSPy < 2.6.17, trial_logs contains initial score in key=-1.
|
194
|
+
trial_logs = getattr(program, "trial_logs", {})
|
195
|
+
if 1 in trial_logs:
|
196
|
+
initial_score = trial_logs[1].get("full_eval_score")
|
197
|
+
elif -1 in trial_logs:
|
198
|
+
initial_score = trial_logs[-1].get("full_eval_score")
|
199
|
+
else:
|
200
|
+
initial_score = None
|
201
|
+
if initial_score is not None:
|
202
|
+
if initial_score == score:
|
203
|
+
_logger.info(f"Optimization complete! Score remained stable at: {score}.")
|
204
|
+
return
|
205
|
+
else:
|
206
|
+
_logger.info(
|
207
|
+
f"🎉 Optimization complete! "
|
208
|
+
f"Initial score: {initial_score}. "
|
209
|
+
f"Final score: {score}."
|
210
|
+
)
|
211
|
+
|
212
|
+
def _log_optimization_result(self, final_score: Optional[float], optimized_prompt: Prompt):
|
213
|
+
if not active_run():
|
214
|
+
return
|
215
|
+
|
216
|
+
if final_score:
|
217
|
+
log_metric(
|
218
|
+
"final_eval_score",
|
219
|
+
final_score,
|
220
|
+
)
|
221
|
+
log_param("optimized_prompt_uri", optimized_prompt.uri)
|
@@ -0,0 +1,91 @@
|
|
1
|
+
import importlib.metadata
|
2
|
+
import importlib.util
|
3
|
+
import inspect
|
4
|
+
from typing import TYPE_CHECKING, Callable, Optional
|
5
|
+
|
6
|
+
from packaging.version import Version
|
7
|
+
|
8
|
+
from mlflow.exceptions import MlflowException
|
9
|
+
from mlflow.genai.optimize.optimizers import _BaseOptimizer
|
10
|
+
from mlflow.genai.optimize.types import OBJECTIVE_FN, OptimizerConfig
|
11
|
+
from mlflow.genai.optimize.util import infer_type_from_value
|
12
|
+
from mlflow.genai.scorers import Scorer
|
13
|
+
|
14
|
+
if TYPE_CHECKING:
|
15
|
+
import dspy
|
16
|
+
import pandas as pd
|
17
|
+
|
18
|
+
|
19
|
+
class _DSPyOptimizer(_BaseOptimizer):
|
20
|
+
def __init__(self, optimizer_config: OptimizerConfig):
|
21
|
+
super().__init__(optimizer_config)
|
22
|
+
|
23
|
+
if not importlib.util.find_spec("dspy"):
|
24
|
+
raise ImportError("dspy is not installed. Please install it with `pip install dspy`.")
|
25
|
+
|
26
|
+
dspy_version = importlib.metadata.version("dspy")
|
27
|
+
if Version(dspy_version) < Version("2.6.0"):
|
28
|
+
raise MlflowException(
|
29
|
+
f"Current dspy version {dspy_version} is unsupported. "
|
30
|
+
"Please upgrade to version >= 2.6.0"
|
31
|
+
)
|
32
|
+
|
33
|
+
def _get_input_fields(self, train_data: "pd.DataFrame") -> dict[str, type]:
|
34
|
+
if "inputs" in train_data.columns:
|
35
|
+
sample_input = train_data["inputs"].values[0]
|
36
|
+
return {k: infer_type_from_value(v) for k, v in sample_input.items()}
|
37
|
+
return {}
|
38
|
+
|
39
|
+
def _get_output_fields(self, train_data: "pd.DataFrame") -> dict[str, type]:
|
40
|
+
if "expectations" in train_data.columns:
|
41
|
+
sample_output = train_data["expectations"].values[0]
|
42
|
+
return {k: infer_type_from_value(v) for k, v in sample_output.items()}
|
43
|
+
return {}
|
44
|
+
|
45
|
+
def _convert_to_dspy_dataset(self, data: "pd.DataFrame") -> list["dspy.Example"]:
|
46
|
+
import dspy
|
47
|
+
|
48
|
+
examples = []
|
49
|
+
for _, row in data.iterrows():
|
50
|
+
expectations = row["expectations"] if "expectations" in row else {}
|
51
|
+
examples.append(
|
52
|
+
dspy.Example(**row["inputs"], **expectations).with_inputs(*row["inputs"].keys())
|
53
|
+
)
|
54
|
+
return examples
|
55
|
+
|
56
|
+
def _convert_to_dspy_metric(
|
57
|
+
self,
|
58
|
+
input_fields: dict[str, type],
|
59
|
+
output_fields: dict[str, type],
|
60
|
+
scorers: list[Scorer],
|
61
|
+
objective: Optional[OBJECTIVE_FN] = None,
|
62
|
+
) -> Callable[["dspy.Example"], float]:
|
63
|
+
def metric(example: "dspy.Example", pred: "dspy.Example", trace=None) -> float:
|
64
|
+
scores = {}
|
65
|
+
inputs = {key: example.get(key) for key in input_fields.keys()}
|
66
|
+
expectations = {key: example.get(key) for key in output_fields.keys()}
|
67
|
+
outputs = {key: pred.get(key) for key in output_fields.keys()}
|
68
|
+
|
69
|
+
for scorer in scorers:
|
70
|
+
kwargs = {"inputs": inputs, "outputs": outputs, "expectations": expectations}
|
71
|
+
signature = inspect.signature(scorer)
|
72
|
+
kwargs = {
|
73
|
+
key: value for key, value in kwargs.items() if key in signature.parameters
|
74
|
+
}
|
75
|
+
scores[scorer.name] = scorer(**kwargs)
|
76
|
+
if objective is not None:
|
77
|
+
return objective(scores)
|
78
|
+
elif all(isinstance(score, (int, float, bool)) for score in scores.values()):
|
79
|
+
# Use total score by default if no objective is provided
|
80
|
+
return sum(scores.values())
|
81
|
+
else:
|
82
|
+
non_numerical_scorers = [
|
83
|
+
k for k, v in scores.items() if not isinstance(v, (int, float, bool))
|
84
|
+
]
|
85
|
+
raise MlflowException(
|
86
|
+
f"Scorer [{','.join(non_numerical_scorers)}] return a string, Assessment or a "
|
87
|
+
"list of Assessment. Please provide `objective` function to aggregate "
|
88
|
+
"non-numerical values into a single value for optimization."
|
89
|
+
)
|
90
|
+
|
91
|
+
return metric
|
@@ -0,0 +1,76 @@
|
|
1
|
+
from collections import defaultdict
|
2
|
+
from typing import TYPE_CHECKING, Any, Optional
|
3
|
+
|
4
|
+
from dspy import Prediction
|
5
|
+
from dspy.utils.callback import BaseCallback
|
6
|
+
|
7
|
+
import mlflow
|
8
|
+
from mlflow.genai.optimize.optimizers.utils.dspy_mipro_utils import format_optimized_prompt
|
9
|
+
|
10
|
+
_FULL_EVAL_NAME = "eval_full"
|
11
|
+
|
12
|
+
if TYPE_CHECKING:
|
13
|
+
import dspy
|
14
|
+
|
15
|
+
|
16
|
+
class _DSPyMIPROv2Callback(BaseCallback):
|
17
|
+
def __init__(self, prompt_name: str, input_fields: dict[str, type]):
|
18
|
+
self.prompt_name = prompt_name
|
19
|
+
self.input_fields = input_fields
|
20
|
+
# call_id: (key, step, program)
|
21
|
+
self._call_id_to_values: dict[str, tuple[str, int, "dspy.Predict"]] = {}
|
22
|
+
self._evaluation_counter = defaultdict(int)
|
23
|
+
self._best_score = None
|
24
|
+
|
25
|
+
def on_evaluate_start(self, call_id: str, instance: Any, inputs: dict[str, Any]):
|
26
|
+
key = inputs.get("callback_metadata", {}).get("metric_key", "eval")
|
27
|
+
step = self._evaluation_counter[key]
|
28
|
+
self._evaluation_counter[key] += 1
|
29
|
+
self._call_id_to_values[call_id] = (key, step, inputs.get("program"))
|
30
|
+
|
31
|
+
def on_evaluate_end(
|
32
|
+
self,
|
33
|
+
call_id: str,
|
34
|
+
outputs: Any,
|
35
|
+
exception: Optional[Exception] = None,
|
36
|
+
):
|
37
|
+
if exception:
|
38
|
+
return
|
39
|
+
|
40
|
+
if call_id not in self._call_id_to_values:
|
41
|
+
return
|
42
|
+
key, step, program = self._call_id_to_values.pop(call_id)
|
43
|
+
|
44
|
+
# Only log the full evaluation result
|
45
|
+
if key != _FULL_EVAL_NAME:
|
46
|
+
return
|
47
|
+
|
48
|
+
if isinstance(outputs, float):
|
49
|
+
score = outputs
|
50
|
+
elif isinstance(outputs, tuple):
|
51
|
+
score = outputs[0]
|
52
|
+
elif isinstance(outputs, Prediction):
|
53
|
+
score = float(outputs)
|
54
|
+
else:
|
55
|
+
return
|
56
|
+
|
57
|
+
if self._best_score is None:
|
58
|
+
# This is the first evaluation with initial prompt,
|
59
|
+
# we don't register this prompt
|
60
|
+
self._best_score = score
|
61
|
+
elif score > self._best_score:
|
62
|
+
# When best score is updated, register the new prompt
|
63
|
+
self._best_score = score
|
64
|
+
template = format_optimized_prompt(program, self.input_fields)
|
65
|
+
mlflow.genai.register_prompt(
|
66
|
+
name=self.prompt_name,
|
67
|
+
template=template,
|
68
|
+
tags={"overall_eval_score": score, key: step},
|
69
|
+
)
|
70
|
+
|
71
|
+
if mlflow.active_run() is not None:
|
72
|
+
mlflow.log_metric(
|
73
|
+
key,
|
74
|
+
score,
|
75
|
+
step=step,
|
76
|
+
)
|
@@ -0,0 +1,18 @@
|
|
1
|
+
from typing import TYPE_CHECKING
|
2
|
+
|
3
|
+
if TYPE_CHECKING:
|
4
|
+
import dspy
|
5
|
+
|
6
|
+
|
7
|
+
def format_optimized_prompt(program: "dspy.Predict", input_fields: dict[str, type]) -> str:
|
8
|
+
import dspy
|
9
|
+
|
10
|
+
messages = dspy.settings.adapter.format(
|
11
|
+
signature=program.signature,
|
12
|
+
demos=program.demos,
|
13
|
+
inputs={key: "{{" + key + "}}" for key in input_fields.keys()},
|
14
|
+
)
|
15
|
+
|
16
|
+
return "\n\n".join(
|
17
|
+
[f"<{message['role']}>\n{message['content']}\n</{message['role']}>" for message in messages]
|
18
|
+
)
|
@@ -0,0 +1,75 @@
|
|
1
|
+
import multiprocessing
|
2
|
+
from dataclasses import dataclass, field
|
3
|
+
from typing import Callable, Optional, Union
|
4
|
+
|
5
|
+
from mlflow.entities import Feedback
|
6
|
+
from mlflow.entities.model_registry import Prompt
|
7
|
+
from mlflow.utils.annotations import experimental
|
8
|
+
|
9
|
+
OBJECTIVE_FN = Callable[[dict[str, Union[bool, float, str, Feedback, list[Feedback]]]], float]
|
10
|
+
|
11
|
+
|
12
|
+
@experimental(version="3.0.0")
|
13
|
+
@dataclass
|
14
|
+
class PromptOptimizationResult:
|
15
|
+
"""
|
16
|
+
Result of the :py:func:`mlflow.genai.optimize_prompt()` API.
|
17
|
+
|
18
|
+
Args:
|
19
|
+
prompt: A prompt entity containing the optimized template.
|
20
|
+
"""
|
21
|
+
|
22
|
+
prompt: Prompt
|
23
|
+
|
24
|
+
|
25
|
+
@experimental(version="3.0.0")
|
26
|
+
@dataclass
|
27
|
+
class LLMParams:
|
28
|
+
"""
|
29
|
+
Parameters for configuring a LLM Model.
|
30
|
+
|
31
|
+
Args:
|
32
|
+
model_name: Name of the model in the format `<provider>/<model name>`.
|
33
|
+
For example, "openai/gpt-4" or "anthropic/claude-4".
|
34
|
+
base_uri: Optional base URI for the API endpoint. If not provided,
|
35
|
+
the default endpoint for the provider will be used.
|
36
|
+
temperature: Optional sampling temperature for the model's outputs.
|
37
|
+
Higher values (e.g., 0.8) make the output more random,
|
38
|
+
while lower values (e.g., 0.2) make it more deterministic.
|
39
|
+
"""
|
40
|
+
|
41
|
+
model_name: str
|
42
|
+
base_uri: Optional[str] = None
|
43
|
+
temperature: Optional[float] = None
|
44
|
+
|
45
|
+
|
46
|
+
@experimental(version="3.0.0")
|
47
|
+
@dataclass
|
48
|
+
class OptimizerConfig:
|
49
|
+
"""
|
50
|
+
Configuration for prompt optimization.
|
51
|
+
|
52
|
+
Args:
|
53
|
+
num_instruction_candidates: Number of candidate instructions to generate
|
54
|
+
during each optimization iteration. Higher values may lead to better
|
55
|
+
results but increase optimization time. Default: 6
|
56
|
+
max_few_show_examples: Maximum number of examples to show in few-shot
|
57
|
+
demonstrations. Default: 6
|
58
|
+
num_threads: Number of threads to use for parallel optimization.
|
59
|
+
Default: (number of CPU cores * 2 + 1)
|
60
|
+
optimizer_llm: Optional LLM parameters for the teacher model. If not provided,
|
61
|
+
the target LLM will be used as the teacher.
|
62
|
+
algorithm: The optimization algorithm to use. Default: "DSPy/MIPROv2"
|
63
|
+
verbose: Whether to show optimizer logs during optimization. Default: False
|
64
|
+
autolog: Whether to log the optimization parameters, datasets and metrics.
|
65
|
+
If set to True, a MLflow run is automatically created to store them.
|
66
|
+
Default: False
|
67
|
+
"""
|
68
|
+
|
69
|
+
num_instruction_candidates: int = 6
|
70
|
+
max_few_show_examples: int = 6
|
71
|
+
num_threads: int = field(default_factory=lambda: (multiprocessing.cpu_count() or 1) * 2 + 1)
|
72
|
+
optimizer_llm: Optional[LLMParams] = None
|
73
|
+
algorithm: str = "DSPy/MIPROv2"
|
74
|
+
verbose: bool = False
|
75
|
+
autolog: bool = False
|
@@ -0,0 +1,30 @@
|
|
1
|
+
from typing import Any, Union
|
2
|
+
|
3
|
+
from pydantic import BaseModel, create_model
|
4
|
+
|
5
|
+
|
6
|
+
def infer_type_from_value(value: Any, model_name: str = "Output") -> type:
|
7
|
+
"""
|
8
|
+
Infer the type from the value.
|
9
|
+
Only supports primitive types, lists, and dict and Pydantic models.
|
10
|
+
"""
|
11
|
+
if value is None:
|
12
|
+
return type(None)
|
13
|
+
elif isinstance(value, (bool, int, float, str)):
|
14
|
+
return type(value)
|
15
|
+
elif isinstance(value, list):
|
16
|
+
if not value:
|
17
|
+
return list[Any]
|
18
|
+
element_types = set()
|
19
|
+
for item in value:
|
20
|
+
element_types.add(infer_type_from_value(item))
|
21
|
+
if len(element_types) == 1:
|
22
|
+
return list[element_types.pop()]
|
23
|
+
else:
|
24
|
+
return list[Union[tuple(element_types)]]
|
25
|
+
elif isinstance(value, dict):
|
26
|
+
fields = {k: (infer_type_from_value(v, model_name=k), ...) for k, v in value.items()}
|
27
|
+
return create_model(model_name, **fields)
|
28
|
+
elif isinstance(value, BaseModel):
|
29
|
+
return type(value)
|
30
|
+
return Any
|