From b1802ba71bb66f2254b1655b434dab648ee8f63e Mon Sep 17 00:00:00 2001 From: "marius.baseten" Date: Thu, 24 Oct 2024 09:11:07 -0700 Subject: [PATCH] Make all non-optional More comments and stuff WIP Fix more tests Remove top-level symbols. Move more stuff Pre-commit fix constants/tests Fix install commands and builder group Manage poetry extras Isolate base, cleanup trash --- .../workflows/_integration_test_shared.yml | 4 +- .github/workflows/integration-tests.yml | 3 +- .github/workflows/main.yml | 7 +- .github/workflows/pr.yml | 5 +- .github/workflows/release-truss-utils.yml | 2 +- .github/workflows/release.yml | 4 +- .pre-commit-config.yaml | 5 + CONTRIBUTING.md | 6 +- Dockerfile | 8 - bin/codespace_post_create.sh | 2 +- bin/generate_base_images.py | 2 +- bin/pyproject_toml_linter.py | 77 +++ context_builder.Dockerfile | 3 +- docs/chains/doc_gen/API-reference.mdx | 4 +- docs/contribute/contributing.md | 9 - docs/contribute/setup.md | 38 -- poetry.lock | 482 +++++++++--------- pyproject.toml | 187 ++++--- .../audio-transcription/whisper_chainlet.py | 2 +- .../examples/mistral/mistral_chainlet.py | 2 +- truss-chains/truss_chains/code_gen.py | 2 +- truss-chains/truss_chains/definitions.py | 6 +- truss-chains/truss_chains/remote.py | 6 +- truss/__init__.py | 4 +- truss/api/__init__.py | 4 +- .../model => base}/__init__.py | 0 truss/{ => base}/constants.py | 8 +- truss/base/custom_types.py | 35 ++ truss/{ => base}/errors.py | 4 + .../trt_llm.py => base/trt_llm_config.py} | 7 - truss/{ => base}/truss_config.py | 69 ++- truss/{ => base}/truss_spec.py | 10 +- truss/{ => base}/validation.py | 4 +- truss/blob/blob_backend.py | 10 - truss/blob/blob_backend_registry.py | 23 - truss/blob/http_public_blob_backend.py | 23 - truss/cli/cli.py | 25 +- truss/contexts/image_builder/image_builder.py | 2 +- .../image_builder/serving_image_builder.py | 14 +- .../contexts/local_loader/load_model_local.py | 2 +- truss/contexts/local_loader/utils.py | 2 +- truss/local/local_config_handler.py | 2 +- truss/model_inference.py | 124 ----- truss/patch/custom_types.py | 36 -- truss/remote/baseten/core.py | 4 +- truss/remote/baseten/remote.py | 6 +- truss/remote/baseten/service.py | 4 +- truss/remote/truss_remote.py | 2 +- .../truss_patch/model_code_patch_applier.py | 1 + .../model_container_patch_applier.py | 12 +- truss/templates/control/requirements.txt | 2 +- truss/templates/server/common/patches.py | 2 - truss/templates/server/common/schema.py | 5 +- truss/templates/server/requirements.txt | 1 + .../context_builder_image_test/test.py | 4 - .../config.yaml | 4 - truss/tests/conftest.py | 34 +- .../test_serving_image_builder.py | 24 +- .../contexts/local_loader/test_load_local.py | 4 +- .../local_loader/test_truss_module_finder.py | 2 +- truss/tests/patch/test_calc_patch.py | 18 +- truss/tests/patch/test_dir_signature.py | 2 +- truss/tests/patch/test_hash.py | 2 +- truss/tests/patch/test_signature.py | 2 +- .../patch/test_truss_dir_patch_applier.py | 4 +- truss/tests/patch/test_types.py | 4 +- truss/tests/remote/baseten/test_core.py | 2 +- truss/tests/remote/baseten/test_remote.py | 2 +- .../test_model_container_patch_applier.py | 2 +- .../templates/control/control/test_server.py | 2 +- truss/tests/test_build.py | 4 +- truss/tests/test_config.py | 8 +- truss/tests/test_context_builder_image.py | 6 +- truss/tests/test_control_truss_patching.py | 8 +- .../model => tests/test_data}/__init__.py | 0 .../annotated_types_truss}/__init__.py | 0 .../annotated_types_truss/config.yaml | 0 .../annotated_types_truss}/model/__init__.py | 0 .../annotated_types_truss/model/model.py | 0 truss/{ => tests}/test_data/auto-mpg.data | 0 .../context_builder_image_test/Dockerfile | 0 .../context_builder_image_test}/__init__.py | 0 .../context_builder_image_test/test.py | 3 + .../test_data/gcs_fix}/__init__.py | 0 .../{ => tests}/test_data/gcs_fix/config.yaml | 0 .../test_data/gcs_fix}/model/__init__.py | 0 .../test_data/gcs_fix/model/model.py | 0 truss/{ => tests}/test_data/happy.ipynb | 0 .../model_load_failure_test}/__init__.py | 0 .../model_load_failure_test/config.yaml | 0 .../model/__init__.py | 0 .../model_load_failure_test/model/model.py | 0 .../patch_ping_test_server}/__init__.py | 0 .../test_data/patch_ping_test_server/app.py | 0 .../test_data/pima-indians-diabetes.csv | 0 .../test_data/readme_int_example.md | 0 .../test_data/readme_no_example.md | 0 .../test_data/readme_str_example.md | 0 truss/{ => tests}/test_data/server.Dockerfile | 0 .../__init__.py | 0 .../server_conformance_test_truss/config.yaml | 0 .../model}/__init__.py | 0 .../model/model.py | 0 .../test_data/test_async_truss/__init__.py} | 0 .../test_data/test_async_truss/config.yaml | 0 .../test_async_truss/model/__init__.py | 0 .../test_data/test_async_truss/model/model.py | 0 .../test_data/test_basic_truss/__init__.py | 0 .../test_data/test_basic_truss/config.yaml | 0 .../test_basic_truss/model/__init__.py | 0 .../test_data/test_basic_truss/model/model.py | 0 .../test_data/test_build_commands/__init__.py | 0 .../test_data/test_build_commands/config.yaml | 0 .../test_build_commands/model/__init__.py | 0 .../test_build_commands/model/model.py | 0 .../test_build_commands_failure/__init__.py | 0 .../test_build_commands_failure/config.yaml | 0 .../model/__init__.py | 0 .../model/model.py | 0 .../test_concurrency_truss/__init__.py | 0 .../test_concurrency_truss/config.yaml | 0 .../test_concurrency_truss/model/__init__.py | 0 .../test_concurrency_truss/model/model.py | 0 .../test_docker_server_truss/__init__.py | 0 .../test_docker_server_truss/config.yaml | 0 .../test_docker_image/Dockerfile | 0 .../test_docker_image/README.md | 0 .../test_docker_image/VERSION | 0 .../test_docker_image/__init__.py | 0 .../test_docker_image/app.py | 0 .../build_upload_new_image.sh | 0 .../test_data/test_pyantic_v1/__init__.py | 0 .../test_data/test_pyantic_v1/config.yaml | 0 .../test_pyantic_v1/model/__init__.py | 0 .../test_data/test_pyantic_v1/model/model.py | 0 .../test_pyantic_v1/requirements.txt | 0 .../test_data/test_pyantic_v2/__init__.py | 0 .../test_data/test_pyantic_v2/config.yaml | 0 .../test_pyantic_v2/model/__init__.py | 0 .../test_data/test_pyantic_v2/model/model.py | 0 .../test_pyantic_v2/requirements.txt | 0 .../test_requirements_file_truss/__init__.py | 0 .../test_requirements_file_truss/config.yaml | 0 .../model/__init__.py | 0 .../model/model.py | 0 .../requirements.txt | 0 .../__init__.py | 0 .../config.yaml | 0 .../model/__init__.py | 0 .../model/model.py | 0 .../test_streaming_read_timeout/__init__.py | 0 .../test_streaming_read_timeout/config.yaml | 0 .../model/__init__.py | 0 .../model/model.py | 0 .../test_streaming_truss/__init__.py | 0 .../test_streaming_truss/config.yaml | 0 .../test_streaming_truss/model/__init__.py | 0 .../test_streaming_truss/model/model.py | 0 .../__init__.py | 0 .../config.yaml | 0 .../model/__init__.py | 0 .../model/model.py | 0 .../packages/__init__.py | 0 .../packages/helpers_1.py | 0 .../packages/helpers_2.py | 0 .../__init__.py | 0 .../config.yaml | 43 ++ .../model/__init__.py | 0 .../model/model.py | 0 .../test_data/test_trt_llm_truss/__init__.py | 0 .../test_data/test_trt_llm_truss/config.yaml | 0 .../test_trt_llm_truss/model/__init__.py | 0 .../test_trt_llm_truss/model/model.py | 0 truss/tests/test_data/test_truss/__init__.py | 0 .../test_data/test_truss/config.yaml | 0 .../test_data/test_truss/examples.yaml | 0 .../test_data/test_truss/model/__init__.py | 0 truss/tests/test_data/test_truss/model/dummy | 0 .../test_data/test_truss/model/model.py | 0 .../test_data/test_truss/packages/__init__.py | 0 .../packages/test_package/__init__.py | 0 .../test_truss/packages/test_package/test.py | 0 .../__init__.py | 0 .../config.yaml | 0 .../model/__init__.py | 0 .../model/model.py | 0 .../test_truss_with_error/__init__.py | 0 .../test_truss_with_error/config.yaml | 0 .../test_truss_with_error/model/__init__.py | 0 .../test_truss_with_error/model/model.py | 0 .../packages/__init__.py | 0 .../packages/helpers_1.py | 0 .../packages/helpers_2.py | 0 truss/tests/test_docker.py | 2 +- truss/tests/test_model_inference.py | 59 +-- truss/tests/test_model_schema.py | 14 +- .../test_testing_utilities_for_other_tests.py | 5 +- truss/tests/test_truss_gatherer.py | 4 +- truss/tests/test_truss_handle.py | 47 +- truss/tests/test_trussless_docker_server.py | 10 +- truss/tests/test_util.py | 2 +- truss/tests/test_validation.py | 4 +- truss/tests/trt_llm/test_validation.py | 4 +- truss/tests/util/test_config_checks.py | 8 +- truss/tests/util/test_path.py | 2 +- truss/{util => trt_llm}/config_checks.py | 6 +- truss/trt_llm/validation.py | 4 +- truss/truss_handle/__init__.py | 0 truss/{ => truss_handle}/build.py | 31 +- truss/{ => truss_handle}/decorators.py | 2 +- truss/truss_handle/patch/__init__.py | 0 truss/{ => truss_handle}/patch/calc_patch.py | 27 +- truss/{ => truss_handle}/patch/constants.py | 0 .../{ => truss_handle/patch}/custom_types.py | 55 +- .../{ => truss_handle}/patch/dir_signature.py | 2 +- truss/{ => truss_handle}/patch/hash.py | 1 + .../patch/local_truss_patch_applier.py | 2 +- truss/{ => truss_handle}/patch/signature.py | 8 +- .../patch/truss_dir_patch_applier.py | 2 +- truss/{ => truss_handle}/readme_generator.py | 4 +- truss/{ => truss_handle}/truss_gatherer.py | 4 +- truss/{ => truss_handle}/truss_handle.py | 52 +- truss/util/data_structures.py | 11 - truss/{ => util}/docker.py | 6 +- truss/util/download.py | 2 +- truss/util/errors.py | 2 - truss/{ => util}/notebook.py | 0 227 files changed, 942 insertions(+), 937 deletions(-) delete mode 100644 Dockerfile create mode 100644 bin/pyproject_toml_linter.py delete mode 100644 docs/contribute/contributing.md delete mode 100644 docs/contribute/setup.md rename truss/{test_data/annotated_types_truss/model => base}/__init__.py (100%) rename truss/{ => base}/constants.py (93%) create mode 100644 truss/base/custom_types.py rename truss/{ => base}/errors.py (93%) rename truss/{config/trt_llm.py => base/trt_llm_config.py} (97%) rename truss/{ => base}/truss_config.py (93%) rename truss/{ => base}/truss_spec.py (95%) rename truss/{ => base}/validation.py (97%) delete mode 100644 truss/blob/blob_backend.py delete mode 100644 truss/blob/blob_backend_registry.py delete mode 100644 truss/blob/http_public_blob_backend.py delete mode 100644 truss/model_inference.py delete mode 100644 truss/patch/custom_types.py delete mode 100644 truss/test_data/context_builder_image_test/test.py delete mode 100644 truss/test_data/test_streaming_truss_with_tracing/config.yaml rename truss/{test_data/gcs_fix/model => tests/test_data}/__init__.py (100%) rename truss/{test_data/server_conformance_test_truss/model => tests/test_data/annotated_types_truss}/__init__.py (100%) rename truss/{ => tests}/test_data/annotated_types_truss/config.yaml (100%) rename truss/{test_data/test_basic_truss => tests/test_data/annotated_types_truss}/model/__init__.py (100%) rename truss/{ => tests}/test_data/annotated_types_truss/model/model.py (100%) rename truss/{ => tests}/test_data/auto-mpg.data (100%) rename truss/{ => tests}/test_data/context_builder_image_test/Dockerfile (100%) rename truss/{test_data/test_pyantic_v1/model => tests/test_data/context_builder_image_test}/__init__.py (100%) create mode 100644 truss/tests/test_data/context_builder_image_test/test.py rename truss/{test_data/test_pyantic_v2/model => tests/test_data/gcs_fix}/__init__.py (100%) rename truss/{ => tests}/test_data/gcs_fix/config.yaml (100%) rename truss/{test_data/test_requirements_file_truss => tests/test_data/gcs_fix}/model/__init__.py (100%) rename truss/{ => tests}/test_data/gcs_fix/model/model.py (100%) rename truss/{ => tests}/test_data/happy.ipynb (100%) rename truss/{test_data/test_trt_llm_truss/model => tests/test_data/model_load_failure_test}/__init__.py (100%) rename truss/{ => tests}/test_data/model_load_failure_test/config.yaml (100%) rename truss/{test_data/test_truss => tests/test_data/model_load_failure_test}/model/__init__.py (100%) rename truss/{ => tests}/test_data/model_load_failure_test/model/model.py (100%) rename truss/{test_data/test_truss_server_caching_truss/model => tests/test_data/patch_ping_test_server}/__init__.py (100%) rename truss/{ => tests}/test_data/patch_ping_test_server/app.py (100%) rename truss/{ => tests}/test_data/pima-indians-diabetes.csv (100%) rename truss/{ => tests}/test_data/readme_int_example.md (100%) rename truss/{ => tests}/test_data/readme_no_example.md (100%) rename truss/{ => tests}/test_data/readme_str_example.md (100%) rename truss/{ => tests}/test_data/server.Dockerfile (100%) rename truss/{test_data/test_truss_with_error/model => tests/test_data/server_conformance_test_truss}/__init__.py (100%) rename truss/{ => tests}/test_data/server_conformance_test_truss/config.yaml (100%) rename truss/tests/{local => test_data/server_conformance_test_truss/model}/__init__.py (100%) rename truss/{ => tests}/test_data/server_conformance_test_truss/model/model.py (100%) rename truss/{test_data/test_truss/model/dummy => tests/test_data/test_async_truss/__init__.py} (100%) rename truss/{ => tests}/test_data/test_async_truss/config.yaml (100%) create mode 100644 truss/tests/test_data/test_async_truss/model/__init__.py rename truss/{ => tests}/test_data/test_async_truss/model/model.py (100%) create mode 100644 truss/tests/test_data/test_basic_truss/__init__.py rename truss/{ => tests}/test_data/test_basic_truss/config.yaml (100%) create mode 100644 truss/tests/test_data/test_basic_truss/model/__init__.py rename truss/{ => tests}/test_data/test_basic_truss/model/model.py (100%) create mode 100644 truss/tests/test_data/test_build_commands/__init__.py rename truss/{ => tests}/test_data/test_build_commands/config.yaml (100%) create mode 100644 truss/tests/test_data/test_build_commands/model/__init__.py rename truss/{ => tests}/test_data/test_build_commands/model/model.py (100%) create mode 100644 truss/tests/test_data/test_build_commands_failure/__init__.py rename truss/{ => tests}/test_data/test_build_commands_failure/config.yaml (100%) create mode 100644 truss/tests/test_data/test_build_commands_failure/model/__init__.py rename truss/{ => tests}/test_data/test_build_commands_failure/model/model.py (100%) create mode 100644 truss/tests/test_data/test_concurrency_truss/__init__.py rename truss/{ => tests}/test_data/test_concurrency_truss/config.yaml (100%) create mode 100644 truss/tests/test_data/test_concurrency_truss/model/__init__.py rename truss/{ => tests}/test_data/test_concurrency_truss/model/model.py (100%) create mode 100644 truss/tests/test_data/test_docker_server_truss/__init__.py rename truss/{ => tests}/test_data/test_docker_server_truss/config.yaml (100%) rename truss/{ => tests}/test_data/test_docker_server_truss/test_docker_image/Dockerfile (100%) rename truss/{ => tests}/test_data/test_docker_server_truss/test_docker_image/README.md (100%) rename truss/{ => tests}/test_data/test_docker_server_truss/test_docker_image/VERSION (100%) create mode 100644 truss/tests/test_data/test_docker_server_truss/test_docker_image/__init__.py rename truss/{ => tests}/test_data/test_docker_server_truss/test_docker_image/app.py (100%) rename truss/{ => tests}/test_data/test_docker_server_truss/test_docker_image/build_upload_new_image.sh (100%) create mode 100644 truss/tests/test_data/test_pyantic_v1/__init__.py rename truss/{ => tests}/test_data/test_pyantic_v1/config.yaml (100%) create mode 100644 truss/tests/test_data/test_pyantic_v1/model/__init__.py rename truss/{ => tests}/test_data/test_pyantic_v1/model/model.py (100%) rename truss/{ => tests}/test_data/test_pyantic_v1/requirements.txt (100%) create mode 100644 truss/tests/test_data/test_pyantic_v2/__init__.py rename truss/{ => tests}/test_data/test_pyantic_v2/config.yaml (100%) create mode 100644 truss/tests/test_data/test_pyantic_v2/model/__init__.py rename truss/{ => tests}/test_data/test_pyantic_v2/model/model.py (100%) rename truss/{ => tests}/test_data/test_pyantic_v2/requirements.txt (100%) create mode 100644 truss/tests/test_data/test_requirements_file_truss/__init__.py rename truss/{ => tests}/test_data/test_requirements_file_truss/config.yaml (100%) create mode 100644 truss/tests/test_data/test_requirements_file_truss/model/__init__.py rename truss/{ => tests}/test_data/test_requirements_file_truss/model/model.py (100%) rename truss/{ => tests}/test_data/test_requirements_file_truss/requirements.txt (100%) create mode 100644 truss/tests/test_data/test_streaming_async_generator_truss/__init__.py rename truss/{ => tests}/test_data/test_streaming_async_generator_truss/config.yaml (100%) create mode 100644 truss/tests/test_data/test_streaming_async_generator_truss/model/__init__.py rename truss/{ => tests}/test_data/test_streaming_async_generator_truss/model/model.py (100%) create mode 100644 truss/tests/test_data/test_streaming_read_timeout/__init__.py rename truss/{ => tests}/test_data/test_streaming_read_timeout/config.yaml (100%) create mode 100644 truss/tests/test_data/test_streaming_read_timeout/model/__init__.py rename truss/{ => tests}/test_data/test_streaming_read_timeout/model/model.py (100%) create mode 100644 truss/tests/test_data/test_streaming_truss/__init__.py rename truss/{ => tests}/test_data/test_streaming_truss/config.yaml (100%) create mode 100644 truss/tests/test_data/test_streaming_truss/model/__init__.py rename truss/{ => tests}/test_data/test_streaming_truss/model/model.py (100%) create mode 100644 truss/tests/test_data/test_streaming_truss_with_error/__init__.py rename truss/{ => tests}/test_data/test_streaming_truss_with_error/config.yaml (100%) create mode 100644 truss/tests/test_data/test_streaming_truss_with_error/model/__init__.py rename truss/{ => tests}/test_data/test_streaming_truss_with_error/model/model.py (100%) create mode 100644 truss/tests/test_data/test_streaming_truss_with_error/packages/__init__.py rename truss/{ => tests}/test_data/test_streaming_truss_with_error/packages/helpers_1.py (100%) rename truss/{ => tests}/test_data/test_streaming_truss_with_error/packages/helpers_2.py (100%) create mode 100644 truss/tests/test_data/test_streaming_truss_with_tracing/__init__.py create mode 100644 truss/tests/test_data/test_streaming_truss_with_tracing/config.yaml create mode 100644 truss/tests/test_data/test_streaming_truss_with_tracing/model/__init__.py rename truss/{ => tests}/test_data/test_streaming_truss_with_tracing/model/model.py (100%) create mode 100644 truss/tests/test_data/test_trt_llm_truss/__init__.py rename truss/{ => tests}/test_data/test_trt_llm_truss/config.yaml (100%) create mode 100644 truss/tests/test_data/test_trt_llm_truss/model/__init__.py rename truss/{ => tests}/test_data/test_trt_llm_truss/model/model.py (100%) create mode 100644 truss/tests/test_data/test_truss/__init__.py rename truss/{ => tests}/test_data/test_truss/config.yaml (100%) rename truss/{ => tests}/test_data/test_truss/examples.yaml (100%) create mode 100644 truss/tests/test_data/test_truss/model/__init__.py create mode 100644 truss/tests/test_data/test_truss/model/dummy rename truss/{ => tests}/test_data/test_truss/model/model.py (100%) create mode 100644 truss/tests/test_data/test_truss/packages/__init__.py create mode 100644 truss/tests/test_data/test_truss/packages/test_package/__init__.py rename truss/{ => tests}/test_data/test_truss/packages/test_package/test.py (100%) create mode 100644 truss/tests/test_data/test_truss_server_caching_truss/__init__.py rename truss/{ => tests}/test_data/test_truss_server_caching_truss/config.yaml (100%) create mode 100644 truss/tests/test_data/test_truss_server_caching_truss/model/__init__.py rename truss/{ => tests}/test_data/test_truss_server_caching_truss/model/model.py (100%) create mode 100644 truss/tests/test_data/test_truss_with_error/__init__.py rename truss/{ => tests}/test_data/test_truss_with_error/config.yaml (100%) create mode 100644 truss/tests/test_data/test_truss_with_error/model/__init__.py rename truss/{ => tests}/test_data/test_truss_with_error/model/model.py (100%) create mode 100644 truss/tests/test_data/test_truss_with_error/packages/__init__.py rename truss/{ => tests}/test_data/test_truss_with_error/packages/helpers_1.py (100%) rename truss/{ => tests}/test_data/test_truss_with_error/packages/helpers_2.py (100%) rename truss/{util => trt_llm}/config_checks.py (90%) create mode 100644 truss/truss_handle/__init__.py rename truss/{ => truss_handle}/build.py (83%) rename truss/{ => truss_handle}/decorators.py (84%) create mode 100644 truss/truss_handle/patch/__init__.py rename truss/{ => truss_handle}/patch/calc_patch.py (96%) rename truss/{ => truss_handle}/patch/constants.py (100%) rename truss/{ => truss_handle/patch}/custom_types.py (64%) rename truss/{ => truss_handle}/patch/dir_signature.py (93%) rename truss/{ => truss_handle}/patch/hash.py (99%) rename truss/{ => truss_handle}/patch/local_truss_patch_applier.py (98%) rename truss/{ => truss_handle}/patch/signature.py (72%) rename truss/{ => truss_handle}/patch/truss_dir_patch_applier.py (98%) rename truss/{ => truss_handle}/readme_generator.py (84%) rename truss/{ => truss_handle}/truss_gatherer.py (96%) rename truss/{ => truss_handle}/truss_handle.py (97%) delete mode 100644 truss/util/data_structures.py rename truss/{ => util}/docker.py (97%) delete mode 100644 truss/util/errors.py rename truss/{ => util}/notebook.py (100%) diff --git a/.github/workflows/_integration_test_shared.yml b/.github/workflows/_integration_test_shared.yml index 19ba72290..624e459be 100644 --- a/.github/workflows/_integration_test_shared.yml +++ b/.github/workflows/_integration_test_shared.yml @@ -13,7 +13,7 @@ jobs: steps: - uses: actions/checkout@v4 - uses: ./.github/actions/setup-python/ - - run: poetry install + - run: poetry install --with=dev,dev-server --extras=all - run: | poetry run pytest truss/tests \ --durations=0 -m 'integration' \ @@ -34,7 +34,7 @@ jobs: steps: - uses: actions/checkout@v4 - uses: ./.github/actions/setup-python/ - - run: poetry install + - run: poetry install --with=dev,dev-server --extras=all - run: | poetry run pytest truss-chains/tests \ --durations=0 -m 'integration' \ diff --git a/.github/workflows/integration-tests.yml b/.github/workflows/integration-tests.yml index cb29cf6eb..56bfc91c9 100644 --- a/.github/workflows/integration-tests.yml +++ b/.github/workflows/integration-tests.yml @@ -25,6 +25,7 @@ jobs: fetch-depth: 2 - uses: ./.github/actions/detect-versions/ id: versions + build-and-push-truss-base-images-if-needed: needs: [detect-version-changed] if: needs.detect-version-changed.outputs.build_base_images == 'true' @@ -46,7 +47,7 @@ jobs: - uses: actions/checkout@v4 - uses: ./.github/actions/setup-python/ - - run: poetry install + - run: poetry install --with=dev,dev-server --extras=all - shell: bash run: | poetry run bin/generate_base_images.py \ diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index a5493a7e4..ad3e3cdcc 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -28,6 +28,7 @@ jobs: fetch-depth: 2 - uses: ./.github/actions/detect-versions/ id: versions + build-and-push-truss-base-images-if-needed: needs: [detect-version-changed] if: needs.detect-version-changed.outputs.build_base_images == 'true' @@ -49,7 +50,7 @@ jobs: - uses: actions/checkout@v4 - uses: ./.github/actions/setup-python/ - - run: poetry install + - run: poetry install --with=dev,dev-server --extras=all - shell: bash run: | poetry run bin/generate_base_images.py \ @@ -64,7 +65,7 @@ jobs: if: ${{ !failure() && !cancelled() && (needs.build-and-push-truss-base-images-if-needed.result == 'success' || needs.build-and-push-truss-base-images-if-needed.result == 'skipped') }} uses: ./.github/workflows/_integration_test_shared.yml - publish-to-pypi: + publish-rc-to-pypi: needs: [detect-version-changed] if: ${{ !failure() && !cancelled() && needs.detect-version-changed.outputs.release_version == 'true' && needs.detect-version-changed.outputs.is_prerelease_version == 'true' }} runs-on: ubuntu-20.04 @@ -84,7 +85,7 @@ jobs: - uses: ./.github/actions/setup-python/ - name: Install poetry packages - run: poetry install --no-dev + run: poetry install --extras=all - name: Build run: poetry build diff --git a/.github/workflows/pr.yml b/.github/workflows/pr.yml index 5d9a16d7a..b2464fed3 100644 --- a/.github/workflows/pr.yml +++ b/.github/workflows/pr.yml @@ -15,7 +15,7 @@ jobs: with: lfs: true - uses: ./.github/actions/setup-python/ - - run: poetry install + - run: poetry install --with=dev,dev-server --extras=all - run: poetry run pre-commit run --all-files env: SKIP: ruff @@ -31,7 +31,7 @@ jobs: with: lfs: true - uses: ./.github/actions/setup-python/ - - run: poetry install + - run: poetry install --with=dev,dev-server --extras=all - name: run tests run: poetry run pytest --durations=0 -m 'not integration' --junitxml=report.xml - name: Publish Test Report # Not sure how to display this in the UI for non PRs. @@ -50,7 +50,6 @@ jobs: use-verbose-mode: "yes" folder-path: "docs" - enforce-chains-example-docs-sync: runs-on: ubuntu-20.04 steps: diff --git a/.github/workflows/release-truss-utils.yml b/.github/workflows/release-truss-utils.yml index e3604f098..87a4e853a 100644 --- a/.github/workflows/release-truss-utils.yml +++ b/.github/workflows/release-truss-utils.yml @@ -40,7 +40,7 @@ jobs: - name: Install poetry packages working-directory: truss-utils - run: poetry install --no-dev + run: poetry install - name: Build working-directory: truss-utils diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 5744184a5..e0ce4f77b 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -60,7 +60,7 @@ jobs: tags: baseten/truss-context-builder:v${{ needs.detect-version-changed.outputs.new_version }} labels: ${{ steps.meta.outputs.labels }} - publish-to-pypi: + publish-release-to-pypi: needs: [detect-version-changed] if: ${{ !failure() && !cancelled() && needs.detect-version-changed.outputs.release_version == 'true' }} runs-on: ubuntu-20.04 @@ -80,7 +80,7 @@ jobs: - uses: ./.github/actions/setup-python/ - name: Install poetry packages - run: poetry install --no-dev + run: poetry install --extras=all - name: Build run: poetry build diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 19633396f..cad82a0a2 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -22,6 +22,11 @@ repos: - id: ruff-format - repo: local hooks: + - id: pyproject.toml + name: pyproject.toml + entry: poetry run python bin/pyproject_toml_linter.py + language: python + additional_dependencies: [tomlkit] - id: mypy name: mypy-local entry: poetry run mypy diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index ccbf71059..5891038dc 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -4,8 +4,8 @@ Truss was first created at [Baseten](https://baseten.co), but as an open and liv We use GitHub features for project management on Truss: -* For bugs and feature requests, file an issue. -* For changes and updates, create a pull request. +* For bugs and feature requests, [file an issue](https://github.com/basetenlabs/truss/issues). +* For changes and updates, create a [pull request](https://github.com/basetenlabs/truss/pulls). * To view and comment on the roadmap, [check the projects tab](https://github.com/orgs/basetenlabs/projects/3). ## Local development @@ -30,7 +30,7 @@ asdf plugin add poetry asdf install # Install poetry dependencies -poetry install +poetry install --with=dev,dev-server --extras=all # And finally precommit poetry run pre-commit install diff --git a/Dockerfile b/Dockerfile deleted file mode 100644 index e6b9cad0d..000000000 --- a/Dockerfile +++ /dev/null @@ -1,8 +0,0 @@ -FROM python:3.9 - -RUN curl -sSL https://install.python-poetry.org | python - - -ENV PATH="/root/.local/bin:${PATH}" -COPY . . - -RUN poetry install --only main diff --git a/bin/codespace_post_create.sh b/bin/codespace_post_create.sh index 76176509f..dc3a5a381 100755 --- a/bin/codespace_post_create.sh +++ b/bin/codespace_post_create.sh @@ -1,4 +1,4 @@ #! /bin/bash -poetry install +poetry install --with=dev,dev-server --extras=all poetry run pre-commit install git lfs install diff --git a/bin/generate_base_images.py b/bin/generate_base_images.py index 432912fbe..bb93c93dd 100755 --- a/bin/generate_base_images.py +++ b/bin/generate_base_images.py @@ -9,7 +9,7 @@ from typing import List, Optional, Set from jinja2 import Environment, FileSystemLoader -from truss.constants import SUPPORTED_PYTHON_VERSIONS +from truss.base.constants import SUPPORTED_PYTHON_VERSIONS from truss.contexts.image_builder.util import ( truss_base_image_name, truss_base_image_tag, diff --git a/bin/pyproject_toml_linter.py b/bin/pyproject_toml_linter.py new file mode 100644 index 000000000..225b1af32 --- /dev/null +++ b/bin/pyproject_toml_linter.py @@ -0,0 +1,77 @@ +# type: ignore # tomlkit APIs are messy. +import collections +import pathlib +from typing import DefaultDict, Set + +import tomlkit + + +def _populate_extras(pyproject_path: pathlib.Path) -> None: + with pyproject_path.open("r", encoding="utf-8") as file: + original_content = file.read() + content = tomlkit.parse(original_content) + + dependencies = content["tool"]["poetry"]["dependencies"] + dependency_metadata = content["tool"]["dependency_metadata"] + + extra_sections: DefaultDict[str, Set[str]] = collections.defaultdict(set) + all_deps: Set[str] = set() + + for key, value in dependencies.items(): + if isinstance(value, dict): + is_optional = value.get("optional", False) + else: + is_optional = False # Base dependencies. + + if not is_optional: + continue + + if key not in dependency_metadata: + raise ValueError( + f"`{key}` is missing in `[tool.dependency_metadata]`. " + f"(file: {pyproject_path}). Please add metadata." + ) + metadata = dependency_metadata[key] + components = metadata["components"].split(",") + for component in components: + if component == "base": + continue + extra_sections[component].add(key) + all_deps.add(key) + + for key in dependency_metadata.keys(): + if key not in dependencies: + raise ValueError( + f"`{key}` in `[tool.dependency_metadata]` is not in " + "`[tool.poetry.dependencies]`. " + f"(file: {pyproject_path}). Please remove or sync." + ) + + extras_section = tomlkit.table() + for extra_section, deps in extra_sections.items(): + extras_section[extra_section] = tomlkit.array() + extras_section[extra_section].extend(sorted(deps)) + + extras_section["all"] = tomlkit.array() + extras_section["all"].extend(sorted(all_deps)) + + if "extras" not in content["tool"]["poetry"]: + raise ValueError("Expected section [tool.poetry.extras] to be present.") + + content["tool"]["poetry"]["extras"] = extras_section + + updated_content = tomlkit.dumps(content) + + # Compare the content before and after; if changes were made, fail the check + if original_content != updated_content: + with pyproject_path.open("w", encoding="utf-8") as file: + file.write(updated_content) + print(f"File '{pyproject_path}' was updated. Please re-stage the changes.") + exit(1) + + print("No changes detected.") + + +if __name__ == "__main__": + pyproject_file = pathlib.Path(__file__).parent.parent.resolve() / "pyproject.toml" + _populate_extras(pyproject_file) diff --git a/context_builder.Dockerfile b/context_builder.Dockerfile index 39d7b50b3..70d4c0a56 100644 --- a/context_builder.Dockerfile +++ b/context_builder.Dockerfile @@ -24,5 +24,4 @@ COPY ./README.md ./README.md # https://python-poetry.org/docs/configuration/#virtualenvsin-project # to write to project root .venv file to be used for context builder test -RUN poetry config virtualenvs.in-project true \ - && poetry install --only builder +RUN poetry config virtualenvs.in-project true && poetry install --extras=all diff --git a/docs/chains/doc_gen/API-reference.mdx b/docs/chains/doc_gen/API-reference.mdx index 909b33838..43d4de098 100644 --- a/docs/chains/doc_gen/API-reference.mdx +++ b/docs/chains/doc_gen/API-reference.mdx @@ -281,12 +281,12 @@ For example, model weight caching can be used like this: ```python import truss_chains as chains -from truss import truss_config +from truss.base import truss_config mistral_cache = truss_config.ModelRepo( repo_id="mistralai/Mistral-7B-Instruct-v0.2", allow_patterns=["*.json", "*.safetensors", ".model"] - ) +) chains.Assets(cached=[mistral_cache], ...) ``` diff --git a/docs/contribute/contributing.md b/docs/contribute/contributing.md deleted file mode 100644 index df156a152..000000000 --- a/docs/contribute/contributing.md +++ /dev/null @@ -1,9 +0,0 @@ -# Contributing to Truss - -Truss was first created at [Baseten](https://baseten.co), but as an open and living project eagerly accepts contributions of all kinds from the broader developer community. Please note that all participation with Truss falls under our [code of conduct](https://github.com/basetenlabs/truss/blob/main/CODE_OF_CONDUCT.md). - -We use GitHub features for project management on Truss: - -* For bugs and feature requests, [file an issue](https://github.com/basetenlabs/truss/issues). -* For changes and updates, create a [pull request](https://github.com/basetenlabs/truss/pulls). -* To view and comment on the roadmap, [check the projects tab](https://github.com/orgs/basetenlabs/projects/3). diff --git a/docs/contribute/setup.md b/docs/contribute/setup.md deleted file mode 100644 index 3cf7fd464..000000000 --- a/docs/contribute/setup.md +++ /dev/null @@ -1,38 +0,0 @@ -# Setting up local development (contributor) - -To get started contributing to Truss, first fork the repository. - -## Truss setup - -**PLEASE NOTE:** the ML ecosystem in general is still not well supported on M1 Macs, and as such, we do not recommend or support local development on M1 for Truss. Truss is well-optimized for use with GitHub Codespaces and other container-based development environments. - -We use `asdf` to manage Python binaries and `poetry` to manage Python dependencies. - -For development in a macOS environment, we use `brew` to manage system packages. - -``` -# Install asdf (or use another method https://asdf-vm.com/) -brew install asdf - -# Install `asdf` managed python and poetry -asdf plugin add python -asdf plugin add poetry - -# Install poetry dependencies -poetry install - -# And finally precommit -poetry run pre-commit install -``` - -Then to run the entire test suite - -``` -poetry run pytest truss/tests -``` - -## Docs setup - -Contributions to documentation are very welcome! Simply edit the appropriate markdown files in the `docs/` folder and make a pull request. For larger changes, tutorials, or any questions please contact [team@trussml.com](mailto:team@trussml.com). - -Baseten docs are built using Mintlify. To run the docs site locally, use Mintlify's [getting started guide](https://mintlify.com/docs/development). diff --git a/poetry.lock b/poetry.lock index 752a46f5d..7806d66e6 100644 --- a/poetry.lock +++ b/poetry.lock @@ -1,4 +1,4 @@ -# This file is automatically @generated by Poetry 1.8.3 and should not be changed by hand. +# This file is automatically @generated by Poetry 1.8.0 and should not be changed by hand. [[package]] name = "aiofiles" @@ -27,13 +27,13 @@ typing-extensions = {version = ">=4.0.0", markers = "python_version < \"3.9\""} [[package]] name = "anyio" -version = "4.5.0" +version = "4.5.2" description = "High level compatibility layer for multiple asynchronous event loop implementations" optional = false python-versions = ">=3.8" files = [ - {file = "anyio-4.5.0-py3-none-any.whl", hash = "sha256:fdeb095b7cc5a5563175eedd926ec4ae55413bb4be5770c424af0ba46ccb4a78"}, - {file = "anyio-4.5.0.tar.gz", hash = "sha256:c5a275fe5ca0afd788001f58fca1e69e29ce706d746e317d660e21f70c530ef9"}, + {file = "anyio-4.5.2-py3-none-any.whl", hash = "sha256:c011ee36bc1e8ba40e5a81cb9df91925c218fe9b778554e0b56a21e1b5d4716f"}, + {file = "anyio-4.5.2.tar.gz", hash = "sha256:23009af4ed04ce05991845451e11ef02fc7c5ed29179ac9a420e5ad0ac7ddc5b"}, ] [package.dependencies] @@ -44,7 +44,7 @@ typing-extensions = {version = ">=4.1", markers = "python_version < \"3.11\""} [package.extras] doc = ["Sphinx (>=7.4,<8.0)", "packaging", "sphinx-autodoc-typehints (>=1.2.0)", "sphinx-rtd-theme"] -test = ["anyio[trio]", "coverage[toml] (>=7)", "exceptiongroup (>=1.2.0)", "hypothesis (>=4.0)", "psutil (>=5.9)", "pytest (>=7.0)", "pytest-mock (>=3.6.1)", "trustme", "uvloop (>=0.21.0b1)"] +test = ["anyio[trio]", "coverage[toml] (>=7)", "exceptiongroup (>=1.2.0)", "hypothesis (>=4.0)", "psutil (>=5.9)", "pytest (>=7.0)", "pytest-mock (>=3.6.1)", "trustme", "truststore (>=0.9.1)", "uvloop (>=0.21.0b1)"] trio = ["trio (>=0.26.1)"] [[package]] @@ -179,17 +179,17 @@ files = [ [[package]] name = "boto3" -version = "1.35.38" +version = "1.35.50" description = "The AWS SDK for Python" optional = false python-versions = ">=3.8" files = [ - {file = "boto3-1.35.38-py3-none-any.whl", hash = "sha256:234a475fe56b65e99b4f5cfff50adaac6b23d39558d6b55137bbf1e50dd0ef08"}, - {file = "boto3-1.35.38.tar.gz", hash = "sha256:90c8cddc4a08c8040057ad44c7468ff82fea9fe8b6517db5ff01a9b2900299cc"}, + {file = "boto3-1.35.50-py3-none-any.whl", hash = "sha256:14724b905fd13f26d9d8f7cdcea0fa65a9acad79f60f41f7662667f4e233d97c"}, + {file = "boto3-1.35.50.tar.gz", hash = "sha256:4f15d1ccb481d66f6925b8c91c970ce41b956b6ecf7c479f23e2159531b37eec"}, ] [package.dependencies] -botocore = ">=1.35.38,<1.36.0" +botocore = ">=1.35.50,<1.36.0" jmespath = ">=0.7.1,<2.0.0" s3transfer = ">=0.10.0,<0.11.0" @@ -198,13 +198,13 @@ crt = ["botocore[crt] (>=1.21.0,<2.0a0)"] [[package]] name = "botocore" -version = "1.35.38" +version = "1.35.50" description = "Low-level, data-driven core of boto 3." optional = false python-versions = ">=3.8" files = [ - {file = "botocore-1.35.38-py3-none-any.whl", hash = "sha256:2eb17d32fa2d3bb5d475132a83564d28e3acc2161534f24b75a54418a1d51359"}, - {file = "botocore-1.35.38.tar.gz", hash = "sha256:55d9305c44e5ba29476df456120fa4fb919f03f066afa82f2ae400485e7465f4"}, + {file = "botocore-1.35.50-py3-none-any.whl", hash = "sha256:965d3b99179ac04aa98e4c4baf4a970ebce77a5e02bb2a0a21cb6304e2bc0955"}, + {file = "botocore-1.35.50.tar.gz", hash = "sha256:136ecef8d5a1088f1ba485c0bbfca40abd42b9f9fe9e11d8cde4e53b4c05b188"}, ] [package.dependencies] @@ -666,18 +666,18 @@ test = ["pytest (>=6)"] [[package]] name = "fastapi" -version = "0.115.0" +version = "0.115.4" description = "FastAPI framework, high performance, easy to learn, fast to code, ready for production" optional = false python-versions = ">=3.8" files = [ - {file = "fastapi-0.115.0-py3-none-any.whl", hash = "sha256:17ea427674467486e997206a5ab25760f6b09e069f099b96f5b55a32fb6f1631"}, - {file = "fastapi-0.115.0.tar.gz", hash = "sha256:f93b4ca3529a8ebc6fc3fcf710e5efa8de3df9b41570958abf1d97d843138004"}, + {file = "fastapi-0.115.4-py3-none-any.whl", hash = "sha256:0b504a063ffb3cf96a5e27dc1bc32c80ca743a2528574f9cdc77daa2d31b4742"}, + {file = "fastapi-0.115.4.tar.gz", hash = "sha256:db653475586b091cb8b2fec2ac54a680ac6a158e07406e1abae31679e8826349"}, ] [package.dependencies] pydantic = ">=1.7.4,<1.8 || >1.8,<1.8.1 || >1.8.1,<2.0.0 || >2.0.0,<2.0.1 || >2.0.1,<2.1.0 || >2.1.0,<3.0.0" -starlette = ">=0.37.2,<0.39.0" +starlette = ">=0.40.0,<0.42.0" typing-extensions = ">=4.8.0" [package.extras] @@ -739,13 +739,13 @@ dotenv = ["python-dotenv"] [[package]] name = "fsspec" -version = "2024.9.0" +version = "2024.10.0" description = "File-system specification" optional = false python-versions = ">=3.8" files = [ - {file = "fsspec-2024.9.0-py3-none-any.whl", hash = "sha256:a0947d552d8a6efa72cc2c730b12c41d043509156966cca4fb157b0f2a0c574b"}, - {file = "fsspec-2024.9.0.tar.gz", hash = "sha256:4b0afb90c2f21832df142f292649035d80b421f60a9e1c027802e5a0da2b04e8"}, + {file = "fsspec-2024.10.0-py3-none-any.whl", hash = "sha256:03b9a6785766a4de40368b88906366755e2819e758b83705c88cd7cb5fe81871"}, + {file = "fsspec-2024.10.0.tar.gz", hash = "sha256:eda2d8a4116d4f2429db8550f2457da57279247dd930bb12f821b58391359493"}, ] [package.extras] @@ -778,13 +778,13 @@ tqdm = ["tqdm"] [[package]] name = "google-api-core" -version = "2.21.0" +version = "2.22.0" description = "Google API client core library" optional = false python-versions = ">=3.7" files = [ - {file = "google_api_core-2.21.0-py3-none-any.whl", hash = "sha256:6869eacb2a37720380ba5898312af79a4d30b8bca1548fb4093e0697dc4bdf5d"}, - {file = "google_api_core-2.21.0.tar.gz", hash = "sha256:4a152fd11a9f774ea606388d423b68aa7e6d6a0ffe4c8266f74979613ec09f81"}, + {file = "google_api_core-2.22.0-py3-none-any.whl", hash = "sha256:a6652b6bd51303902494998626653671703c420f6f4c88cfd3f50ed723e9d021"}, + {file = "google_api_core-2.22.0.tar.gz", hash = "sha256:26f8d76b96477db42b55fd02a33aae4a42ec8b86b98b94969b7333a2c828bf35"}, ] [package.dependencies] @@ -979,70 +979,70 @@ grpc = ["grpcio (>=1.44.0,<2.0.0.dev0)"] [[package]] name = "grpcio" -version = "1.66.2" +version = "1.67.1" description = "HTTP/2-based RPC framework" optional = false python-versions = ">=3.8" files = [ - {file = "grpcio-1.66.2-cp310-cp310-linux_armv7l.whl", hash = "sha256:fe96281713168a3270878255983d2cb1a97e034325c8c2c25169a69289d3ecfa"}, - {file = "grpcio-1.66.2-cp310-cp310-macosx_12_0_universal2.whl", hash = "sha256:73fc8f8b9b5c4a03e802b3cd0c18b2b06b410d3c1dcbef989fdeb943bd44aff7"}, - {file = "grpcio-1.66.2-cp310-cp310-manylinux_2_17_aarch64.whl", hash = "sha256:03b0b307ba26fae695e067b94cbb014e27390f8bc5ac7a3a39b7723fed085604"}, - {file = "grpcio-1.66.2-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:7d69ce1f324dc2d71e40c9261d3fdbe7d4c9d60f332069ff9b2a4d8a257c7b2b"}, - {file = "grpcio-1.66.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:05bc2ceadc2529ab0b227b1310d249d95d9001cd106aa4d31e8871ad3c428d73"}, - {file = "grpcio-1.66.2-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:8ac475e8da31484efa25abb774674d837b343afb78bb3bcdef10f81a93e3d6bf"}, - {file = "grpcio-1.66.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:0be4e0490c28da5377283861bed2941d1d20ec017ca397a5df4394d1c31a9b50"}, - {file = "grpcio-1.66.2-cp310-cp310-win32.whl", hash = "sha256:4e504572433f4e72b12394977679161d495c4c9581ba34a88d843eaf0f2fbd39"}, - {file = "grpcio-1.66.2-cp310-cp310-win_amd64.whl", hash = "sha256:2018b053aa15782db2541ca01a7edb56a0bf18c77efed975392583725974b249"}, - {file = "grpcio-1.66.2-cp311-cp311-linux_armv7l.whl", hash = "sha256:2335c58560a9e92ac58ff2bc5649952f9b37d0735608242973c7a8b94a6437d8"}, - {file = "grpcio-1.66.2-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:45a3d462826f4868b442a6b8fdbe8b87b45eb4f5b5308168c156b21eca43f61c"}, - {file = "grpcio-1.66.2-cp311-cp311-manylinux_2_17_aarch64.whl", hash = "sha256:a9539f01cb04950fd4b5ab458e64a15f84c2acc273670072abe49a3f29bbad54"}, - {file = "grpcio-1.66.2-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ce89f5876662f146d4c1f695dda29d4433a5d01c8681fbd2539afff535da14d4"}, - {file = "grpcio-1.66.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:d25a14af966438cddf498b2e338f88d1c9706f3493b1d73b93f695c99c5f0e2a"}, - {file = "grpcio-1.66.2-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:6001e575b8bbd89eee11960bb640b6da6ae110cf08113a075f1e2051cc596cae"}, - {file = "grpcio-1.66.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:4ea1d062c9230278793820146c95d038dc0f468cbdd172eec3363e42ff1c7d01"}, - {file = "grpcio-1.66.2-cp311-cp311-win32.whl", hash = "sha256:38b68498ff579a3b1ee8f93a05eb48dc2595795f2f62716e797dc24774c1aaa8"}, - {file = "grpcio-1.66.2-cp311-cp311-win_amd64.whl", hash = "sha256:6851de821249340bdb100df5eacfecfc4e6075fa85c6df7ee0eb213170ec8e5d"}, - {file = "grpcio-1.66.2-cp312-cp312-linux_armv7l.whl", hash = "sha256:802d84fd3d50614170649853d121baaaa305de7b65b3e01759247e768d691ddf"}, - {file = "grpcio-1.66.2-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:80fd702ba7e432994df208f27514280b4b5c6843e12a48759c9255679ad38db8"}, - {file = "grpcio-1.66.2-cp312-cp312-manylinux_2_17_aarch64.whl", hash = "sha256:12fda97ffae55e6526825daf25ad0fa37483685952b5d0f910d6405c87e3adb6"}, - {file = "grpcio-1.66.2-cp312-cp312-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:950da58d7d80abd0ea68757769c9db0a95b31163e53e5bb60438d263f4bed7b7"}, - {file = "grpcio-1.66.2-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e636ce23273683b00410f1971d209bf3689238cf5538d960adc3cdfe80dd0dbd"}, - {file = "grpcio-1.66.2-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:a917d26e0fe980b0ac7bfcc1a3c4ad6a9a4612c911d33efb55ed7833c749b0ee"}, - {file = "grpcio-1.66.2-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:49f0ca7ae850f59f828a723a9064cadbed90f1ece179d375966546499b8a2c9c"}, - {file = "grpcio-1.66.2-cp312-cp312-win32.whl", hash = "sha256:31fd163105464797a72d901a06472860845ac157389e10f12631025b3e4d0453"}, - {file = "grpcio-1.66.2-cp312-cp312-win_amd64.whl", hash = "sha256:ff1f7882e56c40b0d33c4922c15dfa30612f05fb785074a012f7cda74d1c3679"}, - {file = "grpcio-1.66.2-cp313-cp313-linux_armv7l.whl", hash = "sha256:3b00efc473b20d8bf83e0e1ae661b98951ca56111feb9b9611df8efc4fe5d55d"}, - {file = "grpcio-1.66.2-cp313-cp313-macosx_10_13_universal2.whl", hash = "sha256:1caa38fb22a8578ab8393da99d4b8641e3a80abc8fd52646f1ecc92bcb8dee34"}, - {file = "grpcio-1.66.2-cp313-cp313-manylinux_2_17_aarch64.whl", hash = "sha256:c408f5ef75cfffa113cacd8b0c0e3611cbfd47701ca3cdc090594109b9fcbaed"}, - {file = "grpcio-1.66.2-cp313-cp313-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c806852deaedee9ce8280fe98955c9103f62912a5b2d5ee7e3eaa284a6d8d8e7"}, - {file = "grpcio-1.66.2-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f145cc21836c332c67baa6fc81099d1d27e266401565bf481948010d6ea32d46"}, - {file = "grpcio-1.66.2-cp313-cp313-musllinux_1_1_i686.whl", hash = "sha256:73e3b425c1e155730273f73e419de3074aa5c5e936771ee0e4af0814631fb30a"}, - {file = "grpcio-1.66.2-cp313-cp313-musllinux_1_1_x86_64.whl", hash = "sha256:9c509a4f78114cbc5f0740eb3d7a74985fd2eff022971bc9bc31f8bc93e66a3b"}, - {file = "grpcio-1.66.2-cp313-cp313-win32.whl", hash = "sha256:20657d6b8cfed7db5e11b62ff7dfe2e12064ea78e93f1434d61888834bc86d75"}, - {file = "grpcio-1.66.2-cp313-cp313-win_amd64.whl", hash = "sha256:fb70487c95786e345af5e854ffec8cb8cc781bcc5df7930c4fbb7feaa72e1cdf"}, - {file = "grpcio-1.66.2-cp38-cp38-linux_armv7l.whl", hash = "sha256:a18e20d8321c6400185b4263e27982488cb5cdd62da69147087a76a24ef4e7e3"}, - {file = "grpcio-1.66.2-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:02697eb4a5cbe5a9639f57323b4c37bcb3ab2d48cec5da3dc2f13334d72790dd"}, - {file = "grpcio-1.66.2-cp38-cp38-manylinux_2_17_aarch64.whl", hash = "sha256:99a641995a6bc4287a6315989ee591ff58507aa1cbe4c2e70d88411c4dcc0839"}, - {file = "grpcio-1.66.2-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:3ed71e81782966ffead60268bbda31ea3f725ebf8aa73634d5dda44f2cf3fb9c"}, - {file = "grpcio-1.66.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:bbd27c24a4cc5e195a7f56cfd9312e366d5d61b86e36d46bbe538457ea6eb8dd"}, - {file = "grpcio-1.66.2-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:d9a9724a156c8ec6a379869b23ba3323b7ea3600851c91489b871e375f710bc8"}, - {file = "grpcio-1.66.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:d8d4732cc5052e92cea2f78b233c2e2a52998ac40cd651f40e398893ad0d06ec"}, - {file = "grpcio-1.66.2-cp38-cp38-win32.whl", hash = "sha256:7b2c86457145ce14c38e5bf6bdc19ef88e66c5fee2c3d83285c5aef026ba93b3"}, - {file = "grpcio-1.66.2-cp38-cp38-win_amd64.whl", hash = "sha256:e88264caad6d8d00e7913996030bac8ad5f26b7411495848cc218bd3a9040b6c"}, - {file = "grpcio-1.66.2-cp39-cp39-linux_armv7l.whl", hash = "sha256:c400ba5675b67025c8a9f48aa846f12a39cf0c44df5cd060e23fda5b30e9359d"}, - {file = "grpcio-1.66.2-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:66a0cd8ba6512b401d7ed46bb03f4ee455839957f28b8d61e7708056a806ba6a"}, - {file = "grpcio-1.66.2-cp39-cp39-manylinux_2_17_aarch64.whl", hash = "sha256:06de8ec0bd71be123eec15b0e0d457474931c2c407869b6c349bd9bed4adbac3"}, - {file = "grpcio-1.66.2-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:fb57870449dfcfac428afbb5a877829fcb0d6db9d9baa1148705739e9083880e"}, - {file = "grpcio-1.66.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b672abf90a964bfde2d0ecbce30f2329a47498ba75ce6f4da35a2f4532b7acbc"}, - {file = "grpcio-1.66.2-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:ad2efdbe90c73b0434cbe64ed372e12414ad03c06262279b104a029d1889d13e"}, - {file = "grpcio-1.66.2-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:9c3a99c519f4638e700e9e3f83952e27e2ea10873eecd7935823dab0c1c9250e"}, - {file = "grpcio-1.66.2-cp39-cp39-win32.whl", hash = "sha256:78fa51ebc2d9242c0fc5db0feecc57a9943303b46664ad89921f5079e2e4ada7"}, - {file = "grpcio-1.66.2-cp39-cp39-win_amd64.whl", hash = "sha256:728bdf36a186e7f51da73be7f8d09457a03061be848718d0edf000e709418987"}, - {file = "grpcio-1.66.2.tar.gz", hash = "sha256:563588c587b75c34b928bc428548e5b00ea38c46972181a4d8b75ba7e3f24231"}, -] - -[package.extras] -protobuf = ["grpcio-tools (>=1.66.2)"] + {file = "grpcio-1.67.1-cp310-cp310-linux_armv7l.whl", hash = "sha256:8b0341d66a57f8a3119b77ab32207072be60c9bf79760fa609c5609f2deb1f3f"}, + {file = "grpcio-1.67.1-cp310-cp310-macosx_12_0_universal2.whl", hash = "sha256:f5a27dddefe0e2357d3e617b9079b4bfdc91341a91565111a21ed6ebbc51b22d"}, + {file = "grpcio-1.67.1-cp310-cp310-manylinux_2_17_aarch64.whl", hash = "sha256:43112046864317498a33bdc4797ae6a268c36345a910de9b9c17159d8346602f"}, + {file = "grpcio-1.67.1-cp310-cp310-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:c9b929f13677b10f63124c1a410994a401cdd85214ad83ab67cc077fc7e480f0"}, + {file = "grpcio-1.67.1-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e7d1797a8a3845437d327145959a2c0c47c05947c9eef5ff1a4c80e499dcc6fa"}, + {file = "grpcio-1.67.1-cp310-cp310-musllinux_1_1_i686.whl", hash = "sha256:0489063974d1452436139501bf6b180f63d4977223ee87488fe36858c5725292"}, + {file = "grpcio-1.67.1-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:9fd042de4a82e3e7aca44008ee2fb5da01b3e5adb316348c21980f7f58adc311"}, + {file = "grpcio-1.67.1-cp310-cp310-win32.whl", hash = "sha256:638354e698fd0c6c76b04540a850bf1db27b4d2515a19fcd5cf645c48d3eb1ed"}, + {file = "grpcio-1.67.1-cp310-cp310-win_amd64.whl", hash = "sha256:608d87d1bdabf9e2868b12338cd38a79969eaf920c89d698ead08f48de9c0f9e"}, + {file = "grpcio-1.67.1-cp311-cp311-linux_armv7l.whl", hash = "sha256:7818c0454027ae3384235a65210bbf5464bd715450e30a3d40385453a85a70cb"}, + {file = "grpcio-1.67.1-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:ea33986b70f83844cd00814cee4451055cd8cab36f00ac64a31f5bb09b31919e"}, + {file = "grpcio-1.67.1-cp311-cp311-manylinux_2_17_aarch64.whl", hash = "sha256:c7a01337407dd89005527623a4a72c5c8e2894d22bead0895306b23c6695698f"}, + {file = "grpcio-1.67.1-cp311-cp311-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:80b866f73224b0634f4312a4674c1be21b2b4afa73cb20953cbbb73a6b36c3cc"}, + {file = "grpcio-1.67.1-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f9fff78ba10d4250bfc07a01bd6254a6d87dc67f9627adece85c0b2ed754fa96"}, + {file = "grpcio-1.67.1-cp311-cp311-musllinux_1_1_i686.whl", hash = "sha256:8a23cbcc5bb11ea7dc6163078be36c065db68d915c24f5faa4f872c573bb400f"}, + {file = "grpcio-1.67.1-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:1a65b503d008f066e994f34f456e0647e5ceb34cfcec5ad180b1b44020ad4970"}, + {file = "grpcio-1.67.1-cp311-cp311-win32.whl", hash = "sha256:e29ca27bec8e163dca0c98084040edec3bc49afd10f18b412f483cc68c712744"}, + {file = "grpcio-1.67.1-cp311-cp311-win_amd64.whl", hash = "sha256:786a5b18544622bfb1e25cc08402bd44ea83edfb04b93798d85dca4d1a0b5be5"}, + {file = "grpcio-1.67.1-cp312-cp312-linux_armv7l.whl", hash = "sha256:267d1745894200e4c604958da5f856da6293f063327cb049a51fe67348e4f953"}, + {file = "grpcio-1.67.1-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:85f69fdc1d28ce7cff8de3f9c67db2b0ca9ba4449644488c1e0303c146135ddb"}, + {file = "grpcio-1.67.1-cp312-cp312-manylinux_2_17_aarch64.whl", hash = "sha256:f26b0b547eb8d00e195274cdfc63ce64c8fc2d3e2d00b12bf468ece41a0423a0"}, + {file = "grpcio-1.67.1-cp312-cp312-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:4422581cdc628f77302270ff839a44f4c24fdc57887dc2a45b7e53d8fc2376af"}, + {file = "grpcio-1.67.1-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:1d7616d2ded471231c701489190379e0c311ee0a6c756f3c03e6a62b95a7146e"}, + {file = "grpcio-1.67.1-cp312-cp312-musllinux_1_1_i686.whl", hash = "sha256:8a00efecde9d6fcc3ab00c13f816313c040a28450e5e25739c24f432fc6d3c75"}, + {file = "grpcio-1.67.1-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:699e964923b70f3101393710793289e42845791ea07565654ada0969522d0a38"}, + {file = "grpcio-1.67.1-cp312-cp312-win32.whl", hash = "sha256:4e7b904484a634a0fff132958dabdb10d63e0927398273917da3ee103e8d1f78"}, + {file = "grpcio-1.67.1-cp312-cp312-win_amd64.whl", hash = "sha256:5721e66a594a6c4204458004852719b38f3d5522082be9061d6510b455c90afc"}, + {file = "grpcio-1.67.1-cp313-cp313-linux_armv7l.whl", hash = "sha256:aa0162e56fd10a5547fac8774c4899fc3e18c1aa4a4759d0ce2cd00d3696ea6b"}, + {file = "grpcio-1.67.1-cp313-cp313-macosx_10_13_universal2.whl", hash = "sha256:beee96c8c0b1a75d556fe57b92b58b4347c77a65781ee2ac749d550f2a365dc1"}, + {file = "grpcio-1.67.1-cp313-cp313-manylinux_2_17_aarch64.whl", hash = "sha256:a93deda571a1bf94ec1f6fcda2872dad3ae538700d94dc283c672a3b508ba3af"}, + {file = "grpcio-1.67.1-cp313-cp313-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:0e6f255980afef598a9e64a24efce87b625e3e3c80a45162d111a461a9f92955"}, + {file = "grpcio-1.67.1-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9e838cad2176ebd5d4a8bb03955138d6589ce9e2ce5d51c3ada34396dbd2dba8"}, + {file = "grpcio-1.67.1-cp313-cp313-musllinux_1_1_i686.whl", hash = "sha256:a6703916c43b1d468d0756c8077b12017a9fcb6a1ef13faf49e67d20d7ebda62"}, + {file = "grpcio-1.67.1-cp313-cp313-musllinux_1_1_x86_64.whl", hash = "sha256:917e8d8994eed1d86b907ba2a61b9f0aef27a2155bca6cbb322430fc7135b7bb"}, + {file = "grpcio-1.67.1-cp313-cp313-win32.whl", hash = "sha256:e279330bef1744040db8fc432becc8a727b84f456ab62b744d3fdb83f327e121"}, + {file = "grpcio-1.67.1-cp313-cp313-win_amd64.whl", hash = "sha256:fa0c739ad8b1996bd24823950e3cb5152ae91fca1c09cc791190bf1627ffefba"}, + {file = "grpcio-1.67.1-cp38-cp38-linux_armv7l.whl", hash = "sha256:178f5db771c4f9a9facb2ab37a434c46cb9be1a75e820f187ee3d1e7805c4f65"}, + {file = "grpcio-1.67.1-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:0f3e49c738396e93b7ba9016e153eb09e0778e776df6090c1b8c91877cc1c426"}, + {file = "grpcio-1.67.1-cp38-cp38-manylinux_2_17_aarch64.whl", hash = "sha256:24e8a26dbfc5274d7474c27759b54486b8de23c709d76695237515bc8b5baeab"}, + {file = "grpcio-1.67.1-cp38-cp38-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:3b6c16489326d79ead41689c4b84bc40d522c9a7617219f4ad94bc7f448c5085"}, + {file = "grpcio-1.67.1-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:60e6a4dcf5af7bbc36fd9f81c9f372e8ae580870a9e4b6eafe948cd334b81cf3"}, + {file = "grpcio-1.67.1-cp38-cp38-musllinux_1_1_i686.whl", hash = "sha256:95b5f2b857856ed78d72da93cd7d09b6db8ef30102e5e7fe0961fe4d9f7d48e8"}, + {file = "grpcio-1.67.1-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:b49359977c6ec9f5d0573ea4e0071ad278ef905aa74e420acc73fd28ce39e9ce"}, + {file = "grpcio-1.67.1-cp38-cp38-win32.whl", hash = "sha256:f5b76ff64aaac53fede0cc93abf57894ab2a7362986ba22243d06218b93efe46"}, + {file = "grpcio-1.67.1-cp38-cp38-win_amd64.whl", hash = "sha256:804c6457c3cd3ec04fe6006c739579b8d35c86ae3298ffca8de57b493524b771"}, + {file = "grpcio-1.67.1-cp39-cp39-linux_armv7l.whl", hash = "sha256:a25bdea92b13ff4d7790962190bf6bf5c4639876e01c0f3dda70fc2769616335"}, + {file = "grpcio-1.67.1-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:cdc491ae35a13535fd9196acb5afe1af37c8237df2e54427be3eecda3653127e"}, + {file = "grpcio-1.67.1-cp39-cp39-manylinux_2_17_aarch64.whl", hash = "sha256:85f862069b86a305497e74d0dc43c02de3d1d184fc2c180993aa8aa86fbd19b8"}, + {file = "grpcio-1.67.1-cp39-cp39-manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:ec74ef02010186185de82cc594058a3ccd8d86821842bbac9873fd4a2cf8be8d"}, + {file = "grpcio-1.67.1-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:01f616a964e540638af5130469451cf580ba8c7329f45ca998ab66e0c7dcdb04"}, + {file = "grpcio-1.67.1-cp39-cp39-musllinux_1_1_i686.whl", hash = "sha256:299b3d8c4f790c6bcca485f9963b4846dd92cf6f1b65d3697145d005c80f9fe8"}, + {file = "grpcio-1.67.1-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:60336bff760fbb47d7e86165408126f1dded184448e9a4c892189eb7c9d3f90f"}, + {file = "grpcio-1.67.1-cp39-cp39-win32.whl", hash = "sha256:5ed601c4c6008429e3d247ddb367fe8c7259c355757448d7c1ef7bd4a6739e8e"}, + {file = "grpcio-1.67.1-cp39-cp39-win_amd64.whl", hash = "sha256:5db70d32d6703b89912af16d6d45d78406374a8b8ef0d28140351dd0ec610e98"}, + {file = "grpcio-1.67.1.tar.gz", hash = "sha256:3dc2ed4cabea4dc14d5e708c2b426205956077cc5de419b4d4079315017e9732"}, +] + +[package.extras] +protobuf = ["grpcio-tools (>=1.67.1)"] [[package]] name = "h11" @@ -1106,13 +1106,13 @@ zstd = ["zstandard (>=0.18.0)"] [[package]] name = "huggingface-hub" -version = "0.25.2" +version = "0.26.2" description = "Client library to download and publish models, datasets and other repos on the huggingface.co hub" optional = false python-versions = ">=3.8.0" files = [ - {file = "huggingface_hub-0.25.2-py3-none-any.whl", hash = "sha256:1897caf88ce7f97fe0110603d8f66ac264e3ba6accdf30cd66cc0fed5282ad25"}, - {file = "huggingface_hub-0.25.2.tar.gz", hash = "sha256:a1014ea111a5f40ccd23f7f7ba8ac46e20fa3b658ced1f86a00c75c06ec6423c"}, + {file = "huggingface_hub-0.26.2-py3-none-any.whl", hash = "sha256:98c2a5a8e786c7b2cb6fdeb2740893cba4d53e312572ed3d8afafda65b128c46"}, + {file = "huggingface_hub-0.26.2.tar.gz", hash = "sha256:b100d853465d965733964d123939ba287da60a547087783ddff8a323f340332b"}, ] [package.dependencies] @@ -1125,16 +1125,16 @@ tqdm = ">=4.42.1" typing-extensions = ">=3.7.4.3" [package.extras] -all = ["InquirerPy (==0.3.4)", "Jinja2", "Pillow", "aiohttp", "fastapi", "gradio", "jedi", "minijinja (>=1.0)", "mypy (==1.5.1)", "numpy", "pytest (>=8.1.1,<8.2.2)", "pytest-asyncio", "pytest-cov", "pytest-env", "pytest-mock", "pytest-rerunfailures", "pytest-vcr", "pytest-xdist", "ruff (>=0.5.0)", "soundfile", "types-PyYAML", "types-requests", "types-simplejson", "types-toml", "types-tqdm", "types-urllib3", "typing-extensions (>=4.8.0)", "urllib3 (<2.0)"] +all = ["InquirerPy (==0.3.4)", "Jinja2", "Pillow", "aiohttp", "fastapi", "gradio (>=4.0.0)", "jedi", "libcst (==1.4.0)", "mypy (==1.5.1)", "numpy", "pytest (>=8.1.1,<8.2.2)", "pytest-asyncio", "pytest-cov", "pytest-env", "pytest-mock", "pytest-rerunfailures", "pytest-vcr", "pytest-xdist", "ruff (>=0.5.0)", "soundfile", "types-PyYAML", "types-requests", "types-simplejson", "types-toml", "types-tqdm", "types-urllib3", "typing-extensions (>=4.8.0)", "urllib3 (<2.0)"] cli = ["InquirerPy (==0.3.4)"] -dev = ["InquirerPy (==0.3.4)", "Jinja2", "Pillow", "aiohttp", "fastapi", "gradio", "jedi", "minijinja (>=1.0)", "mypy (==1.5.1)", "numpy", "pytest (>=8.1.1,<8.2.2)", "pytest-asyncio", "pytest-cov", "pytest-env", "pytest-mock", "pytest-rerunfailures", "pytest-vcr", "pytest-xdist", "ruff (>=0.5.0)", "soundfile", "types-PyYAML", "types-requests", "types-simplejson", "types-toml", "types-tqdm", "types-urllib3", "typing-extensions (>=4.8.0)", "urllib3 (<2.0)"] +dev = ["InquirerPy (==0.3.4)", "Jinja2", "Pillow", "aiohttp", "fastapi", "gradio (>=4.0.0)", "jedi", "libcst (==1.4.0)", "mypy (==1.5.1)", "numpy", "pytest (>=8.1.1,<8.2.2)", "pytest-asyncio", "pytest-cov", "pytest-env", "pytest-mock", "pytest-rerunfailures", "pytest-vcr", "pytest-xdist", "ruff (>=0.5.0)", "soundfile", "types-PyYAML", "types-requests", "types-simplejson", "types-toml", "types-tqdm", "types-urllib3", "typing-extensions (>=4.8.0)", "urllib3 (<2.0)"] fastai = ["fastai (>=2.4)", "fastcore (>=1.3.27)", "toml"] hf-transfer = ["hf-transfer (>=0.1.4)"] -inference = ["aiohttp", "minijinja (>=1.0)"] -quality = ["mypy (==1.5.1)", "ruff (>=0.5.0)"] +inference = ["aiohttp"] +quality = ["libcst (==1.4.0)", "mypy (==1.5.1)", "ruff (>=0.5.0)"] tensorflow = ["graphviz", "pydot", "tensorflow"] tensorflow-testing = ["keras (<3.0)", "tensorflow"] -testing = ["InquirerPy (==0.3.4)", "Jinja2", "Pillow", "aiohttp", "fastapi", "gradio", "jedi", "minijinja (>=1.0)", "numpy", "pytest (>=8.1.1,<8.2.2)", "pytest-asyncio", "pytest-cov", "pytest-env", "pytest-mock", "pytest-rerunfailures", "pytest-vcr", "pytest-xdist", "soundfile", "urllib3 (<2.0)"] +testing = ["InquirerPy (==0.3.4)", "Jinja2", "Pillow", "aiohttp", "fastapi", "gradio (>=4.0.0)", "jedi", "numpy", "pytest (>=8.1.1,<8.2.2)", "pytest-asyncio", "pytest-cov", "pytest-env", "pytest-mock", "pytest-rerunfailures", "pytest-vcr", "pytest-xdist", "soundfile", "urllib3 (<2.0)"] torch = ["safetensors[torch]", "torch"] typing = ["types-PyYAML", "types-requests", "types-simplejson", "types-toml", "types-tqdm", "types-urllib3", "typing-extensions (>=4.8.0)"] @@ -1756,38 +1756,43 @@ numpy = ">=1.9.0" [[package]] name = "mypy" -version = "1.11.2" +version = "1.13.0" description = "Optional static typing for Python" optional = false python-versions = ">=3.8" files = [ - {file = "mypy-1.11.2-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:d42a6dd818ffce7be66cce644f1dff482f1d97c53ca70908dff0b9ddc120b77a"}, - {file = "mypy-1.11.2-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:801780c56d1cdb896eacd5619a83e427ce436d86a3bdf9112527f24a66618fef"}, - {file = "mypy-1.11.2-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:41ea707d036a5307ac674ea172875f40c9d55c5394f888b168033177fce47383"}, - {file = "mypy-1.11.2-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:6e658bd2d20565ea86da7d91331b0eed6d2eee22dc031579e6297f3e12c758c8"}, - {file = "mypy-1.11.2-cp310-cp310-win_amd64.whl", hash = "sha256:478db5f5036817fe45adb7332d927daa62417159d49783041338921dcf646fc7"}, - {file = "mypy-1.11.2-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:75746e06d5fa1e91bfd5432448d00d34593b52e7e91a187d981d08d1f33d4385"}, - {file = "mypy-1.11.2-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:a976775ab2256aadc6add633d44f100a2517d2388906ec4f13231fafbb0eccca"}, - {file = "mypy-1.11.2-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:cd953f221ac1379050a8a646585a29574488974f79d8082cedef62744f0a0104"}, - {file = "mypy-1.11.2-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:57555a7715c0a34421013144a33d280e73c08df70f3a18a552938587ce9274f4"}, - {file = "mypy-1.11.2-cp311-cp311-win_amd64.whl", hash = "sha256:36383a4fcbad95f2657642a07ba22ff797de26277158f1cc7bd234821468b1b6"}, - {file = "mypy-1.11.2-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:e8960dbbbf36906c5c0b7f4fbf2f0c7ffb20f4898e6a879fcf56a41a08b0d318"}, - {file = "mypy-1.11.2-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:06d26c277962f3fb50e13044674aa10553981ae514288cb7d0a738f495550b36"}, - {file = "mypy-1.11.2-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:6e7184632d89d677973a14d00ae4d03214c8bc301ceefcdaf5c474866814c987"}, - {file = "mypy-1.11.2-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:3a66169b92452f72117e2da3a576087025449018afc2d8e9bfe5ffab865709ca"}, - {file = "mypy-1.11.2-cp312-cp312-win_amd64.whl", hash = "sha256:969ea3ef09617aff826885a22ece0ddef69d95852cdad2f60c8bb06bf1f71f70"}, - {file = "mypy-1.11.2-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:37c7fa6121c1cdfcaac97ce3d3b5588e847aa79b580c1e922bb5d5d2902df19b"}, - {file = "mypy-1.11.2-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:4a8a53bc3ffbd161b5b2a4fff2f0f1e23a33b0168f1c0778ec70e1a3d66deb86"}, - {file = "mypy-1.11.2-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:2ff93107f01968ed834f4256bc1fc4475e2fecf6c661260066a985b52741ddce"}, - {file = "mypy-1.11.2-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:edb91dded4df17eae4537668b23f0ff6baf3707683734b6a818d5b9d0c0c31a1"}, - {file = "mypy-1.11.2-cp38-cp38-win_amd64.whl", hash = "sha256:ee23de8530d99b6db0573c4ef4bd8f39a2a6f9b60655bf7a1357e585a3486f2b"}, - {file = "mypy-1.11.2-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:801ca29f43d5acce85f8e999b1e431fb479cb02d0e11deb7d2abb56bdaf24fd6"}, - {file = "mypy-1.11.2-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:af8d155170fcf87a2afb55b35dc1a0ac21df4431e7d96717621962e4b9192e70"}, - {file = "mypy-1.11.2-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:f7821776e5c4286b6a13138cc935e2e9b6fde05e081bdebf5cdb2bb97c9df81d"}, - {file = "mypy-1.11.2-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:539c570477a96a4e6fb718b8d5c3e0c0eba1f485df13f86d2970c91f0673148d"}, - {file = "mypy-1.11.2-cp39-cp39-win_amd64.whl", hash = "sha256:3f14cd3d386ac4d05c5a39a51b84387403dadbd936e17cb35882134d4f8f0d24"}, - {file = "mypy-1.11.2-py3-none-any.whl", hash = "sha256:b499bc07dbdcd3de92b0a8b29fdf592c111276f6a12fe29c30f6c417dd546d12"}, - {file = "mypy-1.11.2.tar.gz", hash = "sha256:7f9993ad3e0ffdc95c2a14b66dee63729f021968bff8ad911867579c65d13a79"}, + {file = "mypy-1.13.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:6607e0f1dd1fb7f0aca14d936d13fd19eba5e17e1cd2a14f808fa5f8f6d8f60a"}, + {file = "mypy-1.13.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:8a21be69bd26fa81b1f80a61ee7ab05b076c674d9b18fb56239d72e21d9f4c80"}, + {file = "mypy-1.13.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:7b2353a44d2179846a096e25691d54d59904559f4232519d420d64da6828a3a7"}, + {file = "mypy-1.13.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:0730d1c6a2739d4511dc4253f8274cdd140c55c32dfb0a4cf8b7a43f40abfa6f"}, + {file = "mypy-1.13.0-cp310-cp310-win_amd64.whl", hash = "sha256:c5fc54dbb712ff5e5a0fca797e6e0aa25726c7e72c6a5850cfd2adbc1eb0a372"}, + {file = "mypy-1.13.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:581665e6f3a8a9078f28d5502f4c334c0c8d802ef55ea0e7276a6e409bc0d82d"}, + {file = "mypy-1.13.0-cp311-cp311-macosx_11_0_arm64.whl", hash = "sha256:3ddb5b9bf82e05cc9a627e84707b528e5c7caaa1c55c69e175abb15a761cec2d"}, + {file = "mypy-1.13.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:20c7ee0bc0d5a9595c46f38beb04201f2620065a93755704e141fcac9f59db2b"}, + {file = "mypy-1.13.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:3790ded76f0b34bc9c8ba4def8f919dd6a46db0f5a6610fb994fe8efdd447f73"}, + {file = "mypy-1.13.0-cp311-cp311-win_amd64.whl", hash = "sha256:51f869f4b6b538229c1d1bcc1dd7d119817206e2bc54e8e374b3dfa202defcca"}, + {file = "mypy-1.13.0-cp312-cp312-macosx_10_13_x86_64.whl", hash = "sha256:5c7051a3461ae84dfb5dd15eff5094640c61c5f22257c8b766794e6dd85e72d5"}, + {file = "mypy-1.13.0-cp312-cp312-macosx_11_0_arm64.whl", hash = "sha256:39bb21c69a5d6342f4ce526e4584bc5c197fd20a60d14a8624d8743fffb9472e"}, + {file = "mypy-1.13.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:164f28cb9d6367439031f4c81e84d3ccaa1e19232d9d05d37cb0bd880d3f93c2"}, + {file = "mypy-1.13.0-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:a4c1bfcdbce96ff5d96fc9b08e3831acb30dc44ab02671eca5953eadad07d6d0"}, + {file = "mypy-1.13.0-cp312-cp312-win_amd64.whl", hash = "sha256:a0affb3a79a256b4183ba09811e3577c5163ed06685e4d4b46429a271ba174d2"}, + {file = "mypy-1.13.0-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:a7b44178c9760ce1a43f544e595d35ed61ac2c3de306599fa59b38a6048e1aa7"}, + {file = "mypy-1.13.0-cp313-cp313-macosx_11_0_arm64.whl", hash = "sha256:5d5092efb8516d08440e36626f0153b5006d4088c1d663d88bf79625af3d1d62"}, + {file = "mypy-1.13.0-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:de2904956dac40ced10931ac967ae63c5089bd498542194b436eb097a9f77bc8"}, + {file = "mypy-1.13.0-cp313-cp313-musllinux_1_1_x86_64.whl", hash = "sha256:7bfd8836970d33c2105562650656b6846149374dc8ed77d98424b40b09340ba7"}, + {file = "mypy-1.13.0-cp313-cp313-win_amd64.whl", hash = "sha256:9f73dba9ec77acb86457a8fc04b5239822df0c14a082564737833d2963677dbc"}, + {file = "mypy-1.13.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:100fac22ce82925f676a734af0db922ecfea991e1d7ec0ceb1e115ebe501301a"}, + {file = "mypy-1.13.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:7bcb0bb7f42a978bb323a7c88f1081d1b5dee77ca86f4100735a6f541299d8fb"}, + {file = "mypy-1.13.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:bde31fc887c213e223bbfc34328070996061b0833b0a4cfec53745ed61f3519b"}, + {file = "mypy-1.13.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:07de989f89786f62b937851295ed62e51774722e5444a27cecca993fc3f9cd74"}, + {file = "mypy-1.13.0-cp38-cp38-win_amd64.whl", hash = "sha256:4bde84334fbe19bad704b3f5b78c4abd35ff1026f8ba72b29de70dda0916beb6"}, + {file = "mypy-1.13.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:0246bcb1b5de7f08f2826451abd947bf656945209b140d16ed317f65a17dc7dc"}, + {file = "mypy-1.13.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:7f5b7deae912cf8b77e990b9280f170381fdfbddf61b4ef80927edd813163732"}, + {file = "mypy-1.13.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:7029881ec6ffb8bc233a4fa364736789582c738217b133f1b55967115288a2bc"}, + {file = "mypy-1.13.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:3e38b980e5681f28f033f3be86b099a247b13c491f14bb8b1e1e134d23bb599d"}, + {file = "mypy-1.13.0-cp39-cp39-win_amd64.whl", hash = "sha256:a6789be98a2017c912ae6ccb77ea553bbaf13d27605d2ca20a76dfbced631b24"}, + {file = "mypy-1.13.0-py3-none-any.whl", hash = "sha256:9c250883f9fd81d212e0952c92dbfcc96fc237f4b7c92f56ac81fd48460b3e5a"}, + {file = "mypy-1.13.0.tar.gz", hash = "sha256:0291a61b6fbf3e6673e3405cfcc0e7650bebc7939659fdca2702958038bd835e"}, ] [package.dependencies] @@ -1797,6 +1802,7 @@ typing-extensions = ">=4.6.0" [package.extras] dmypy = ["psutil (>=4.0)"] +faster-cache = ["orjson"] install-types = ["pip"] mypyc = ["setuptools (>=50)"] reports = ["lxml"] @@ -2244,13 +2250,13 @@ wcwidth = "*" [[package]] name = "proto-plus" -version = "1.24.0" +version = "1.25.0" description = "Beautiful, Pythonic protocol buffers." optional = false python-versions = ">=3.7" files = [ - {file = "proto-plus-1.24.0.tar.gz", hash = "sha256:30b72a5ecafe4406b0d339db35b56c4059064e69227b8c3bda7462397f966445"}, - {file = "proto_plus-1.24.0-py3-none-any.whl", hash = "sha256:402576830425e5f6ce4c2a6702400ac79897dab0b4343821aa5188b0fab81a12"}, + {file = "proto_plus-1.25.0-py3-none-any.whl", hash = "sha256:c91fc4a65074ade8e458e95ef8bac34d4008daa7cce4a12d6707066fca648961"}, + {file = "proto_plus-1.25.0.tar.gz", hash = "sha256:fbb17f57f7bd05a68b7707e745e26528b0b3c34e378db91eef93912c54982d91"}, ] [package.dependencies] @@ -2281,32 +2287,33 @@ files = [ [[package]] name = "psutil" -version = "6.0.0" +version = "6.1.0" description = "Cross-platform lib for process and system monitoring in Python." optional = false python-versions = "!=3.0.*,!=3.1.*,!=3.2.*,!=3.3.*,!=3.4.*,!=3.5.*,>=2.7" files = [ - {file = "psutil-6.0.0-cp27-cp27m-macosx_10_9_x86_64.whl", hash = "sha256:a021da3e881cd935e64a3d0a20983bda0bb4cf80e4f74fa9bfcb1bc5785360c6"}, - {file = "psutil-6.0.0-cp27-cp27m-manylinux2010_i686.whl", hash = "sha256:1287c2b95f1c0a364d23bc6f2ea2365a8d4d9b726a3be7294296ff7ba97c17f0"}, - {file = "psutil-6.0.0-cp27-cp27m-manylinux2010_x86_64.whl", hash = "sha256:a9a3dbfb4de4f18174528d87cc352d1f788b7496991cca33c6996f40c9e3c92c"}, - {file = "psutil-6.0.0-cp27-cp27mu-manylinux2010_i686.whl", hash = "sha256:6ec7588fb3ddaec7344a825afe298db83fe01bfaaab39155fa84cf1c0d6b13c3"}, - {file = "psutil-6.0.0-cp27-cp27mu-manylinux2010_x86_64.whl", hash = "sha256:1e7c870afcb7d91fdea2b37c24aeb08f98b6d67257a5cb0a8bc3ac68d0f1a68c"}, - {file = "psutil-6.0.0-cp27-none-win32.whl", hash = "sha256:02b69001f44cc73c1c5279d02b30a817e339ceb258ad75997325e0e6169d8b35"}, - {file = "psutil-6.0.0-cp27-none-win_amd64.whl", hash = "sha256:21f1fb635deccd510f69f485b87433460a603919b45e2a324ad65b0cc74f8fb1"}, - {file = "psutil-6.0.0-cp36-abi3-macosx_10_9_x86_64.whl", hash = "sha256:c588a7e9b1173b6e866756dde596fd4cad94f9399daf99ad8c3258b3cb2b47a0"}, - {file = "psutil-6.0.0-cp36-abi3-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:6ed2440ada7ef7d0d608f20ad89a04ec47d2d3ab7190896cd62ca5fc4fe08bf0"}, - {file = "psutil-6.0.0-cp36-abi3-manylinux_2_12_x86_64.manylinux2010_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:5fd9a97c8e94059b0ef54a7d4baf13b405011176c3b6ff257c247cae0d560ecd"}, - {file = "psutil-6.0.0-cp36-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:e2e8d0054fc88153ca0544f5c4d554d42e33df2e009c4ff42284ac9ebdef4132"}, - {file = "psutil-6.0.0-cp36-cp36m-win32.whl", hash = "sha256:fc8c9510cde0146432bbdb433322861ee8c3efbf8589865c8bf8d21cb30c4d14"}, - {file = "psutil-6.0.0-cp36-cp36m-win_amd64.whl", hash = "sha256:34859b8d8f423b86e4385ff3665d3f4d94be3cdf48221fbe476e883514fdb71c"}, - {file = "psutil-6.0.0-cp37-abi3-win32.whl", hash = "sha256:a495580d6bae27291324fe60cea0b5a7c23fa36a7cd35035a16d93bdcf076b9d"}, - {file = "psutil-6.0.0-cp37-abi3-win_amd64.whl", hash = "sha256:33ea5e1c975250a720b3a6609c490db40dae5d83a4eb315170c4fe0d8b1f34b3"}, - {file = "psutil-6.0.0-cp38-abi3-macosx_11_0_arm64.whl", hash = "sha256:ffe7fc9b6b36beadc8c322f84e1caff51e8703b88eee1da46d1e3a6ae11b4fd0"}, - {file = "psutil-6.0.0.tar.gz", hash = "sha256:8faae4f310b6d969fa26ca0545338b21f73c6b15db7c4a8d934a5482faa818f2"}, + {file = "psutil-6.1.0-cp27-cp27m-macosx_10_9_x86_64.whl", hash = "sha256:ff34df86226c0227c52f38b919213157588a678d049688eded74c76c8ba4a5d0"}, + {file = "psutil-6.1.0-cp27-cp27m-manylinux2010_i686.whl", hash = "sha256:c0e0c00aa18ca2d3b2b991643b799a15fc8f0563d2ebb6040f64ce8dc027b942"}, + {file = "psutil-6.1.0-cp27-cp27m-manylinux2010_x86_64.whl", hash = "sha256:000d1d1ebd634b4efb383f4034437384e44a6d455260aaee2eca1e9c1b55f047"}, + {file = "psutil-6.1.0-cp27-cp27mu-manylinux2010_i686.whl", hash = "sha256:5cd2bcdc75b452ba2e10f0e8ecc0b57b827dd5d7aaffbc6821b2a9a242823a76"}, + {file = "psutil-6.1.0-cp27-cp27mu-manylinux2010_x86_64.whl", hash = "sha256:045f00a43c737f960d273a83973b2511430d61f283a44c96bf13a6e829ba8fdc"}, + {file = "psutil-6.1.0-cp27-none-win32.whl", hash = "sha256:9118f27452b70bb1d9ab3198c1f626c2499384935aaf55388211ad982611407e"}, + {file = "psutil-6.1.0-cp27-none-win_amd64.whl", hash = "sha256:a8506f6119cff7015678e2bce904a4da21025cc70ad283a53b099e7620061d85"}, + {file = "psutil-6.1.0-cp36-abi3-macosx_10_9_x86_64.whl", hash = "sha256:6e2dcd475ce8b80522e51d923d10c7871e45f20918e027ab682f94f1c6351688"}, + {file = "psutil-6.1.0-cp36-abi3-macosx_11_0_arm64.whl", hash = "sha256:0895b8414afafc526712c498bd9de2b063deaac4021a3b3c34566283464aff8e"}, + {file = "psutil-6.1.0-cp36-abi3-manylinux_2_12_i686.manylinux2010_i686.manylinux_2_17_i686.manylinux2014_i686.whl", hash = "sha256:9dcbfce5d89f1d1f2546a2090f4fcf87c7f669d1d90aacb7d7582addece9fb38"}, + {file = "psutil-6.1.0-cp36-abi3-manylinux_2_12_x86_64.manylinux2010_x86_64.manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:498c6979f9c6637ebc3a73b3f87f9eb1ec24e1ce53a7c5173b8508981614a90b"}, + {file = "psutil-6.1.0-cp36-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:d905186d647b16755a800e7263d43df08b790d709d575105d419f8b6ef65423a"}, + {file = "psutil-6.1.0-cp36-cp36m-win32.whl", hash = "sha256:6d3fbbc8d23fcdcb500d2c9f94e07b1342df8ed71b948a2649b5cb060a7c94ca"}, + {file = "psutil-6.1.0-cp36-cp36m-win_amd64.whl", hash = "sha256:1209036fbd0421afde505a4879dee3b2fd7b1e14fee81c0069807adcbbcca747"}, + {file = "psutil-6.1.0-cp37-abi3-win32.whl", hash = "sha256:1ad45a1f5d0b608253b11508f80940985d1d0c8f6111b5cb637533a0e6ddc13e"}, + {file = "psutil-6.1.0-cp37-abi3-win_amd64.whl", hash = "sha256:a8fb3752b491d246034fa4d279ff076501588ce8cbcdbb62c32fd7a377d996be"}, + {file = "psutil-6.1.0.tar.gz", hash = "sha256:353815f59a7f64cdaca1c0307ee13558a0512f6db064e92fe833784f08539c7a"}, ] [package.extras] -test = ["enum34", "ipaddress", "mock", "pywin32", "wmi"] +dev = ["black", "check-manifest", "coverage", "packaging", "pylint", "pyperf", "pypinfo", "pytest-cov", "requests", "rstcheck", "ruff", "sphinx", "sphinx_rtd_theme", "toml-sort", "twine", "virtualenv", "wheel"] +test = ["pytest", "pytest-xdist", "setuptools"] [[package]] name = "ptyprocess" @@ -2611,29 +2618,29 @@ test = ["pytest"] [[package]] name = "pywin32" -version = "307" +version = "308" description = "Python for Window Extensions" optional = false python-versions = "*" files = [ - {file = "pywin32-307-cp310-cp310-win32.whl", hash = "sha256:f8f25d893c1e1ce2d685ef6d0a481e87c6f510d0f3f117932781f412e0eba31b"}, - {file = "pywin32-307-cp310-cp310-win_amd64.whl", hash = "sha256:36e650c5e5e6b29b5d317385b02d20803ddbac5d1031e1f88d20d76676dd103d"}, - {file = "pywin32-307-cp310-cp310-win_arm64.whl", hash = "sha256:0c12d61e0274e0c62acee79e3e503c312426ddd0e8d4899c626cddc1cafe0ff4"}, - {file = "pywin32-307-cp311-cp311-win32.whl", hash = "sha256:fec5d27cc893178fab299de911b8e4d12c5954e1baf83e8a664311e56a272b75"}, - {file = "pywin32-307-cp311-cp311-win_amd64.whl", hash = "sha256:987a86971753ed7fdd52a7fb5747aba955b2c7fbbc3d8b76ec850358c1cc28c3"}, - {file = "pywin32-307-cp311-cp311-win_arm64.whl", hash = "sha256:fd436897c186a2e693cd0437386ed79f989f4d13d6f353f8787ecbb0ae719398"}, - {file = "pywin32-307-cp312-cp312-win32.whl", hash = "sha256:07649ec6b01712f36debf39fc94f3d696a46579e852f60157a729ac039df0815"}, - {file = "pywin32-307-cp312-cp312-win_amd64.whl", hash = "sha256:00d047992bb5dcf79f8b9b7c81f72e0130f9fe4b22df613f755ab1cc021d8347"}, - {file = "pywin32-307-cp312-cp312-win_arm64.whl", hash = "sha256:b53658acbfc6a8241d72cc09e9d1d666be4e6c99376bc59e26cdb6223c4554d2"}, - {file = "pywin32-307-cp313-cp313-win32.whl", hash = "sha256:ea4d56e48dc1ab2aa0a5e3c0741ad6e926529510516db7a3b6981a1ae74405e5"}, - {file = "pywin32-307-cp313-cp313-win_amd64.whl", hash = "sha256:576d09813eaf4c8168d0bfd66fb7cb3b15a61041cf41598c2db4a4583bf832d2"}, - {file = "pywin32-307-cp313-cp313-win_arm64.whl", hash = "sha256:b30c9bdbffda6a260beb2919f918daced23d32c79109412c2085cbc513338a0a"}, - {file = "pywin32-307-cp37-cp37m-win32.whl", hash = "sha256:5101472f5180c647d4525a0ed289ec723a26231550dbfd369ec19d5faf60e511"}, - {file = "pywin32-307-cp37-cp37m-win_amd64.whl", hash = "sha256:05de55a7c110478dc4b202230e98af5e0720855360d2b31a44bb4e296d795fba"}, - {file = "pywin32-307-cp38-cp38-win32.whl", hash = "sha256:13d059fb7f10792542082f5731d5d3d9645320fc38814759313e5ee97c3fac01"}, - {file = "pywin32-307-cp38-cp38-win_amd64.whl", hash = "sha256:7e0b2f93769d450a98ac7a31a087e07b126b6d571e8b4386a5762eb85325270b"}, - {file = "pywin32-307-cp39-cp39-win32.whl", hash = "sha256:55ee87f2f8c294e72ad9d4261ca423022310a6e79fb314a8ca76ab3f493854c6"}, - {file = "pywin32-307-cp39-cp39-win_amd64.whl", hash = "sha256:e9d5202922e74985b037c9ef46778335c102b74b95cec70f629453dbe7235d87"}, + {file = "pywin32-308-cp310-cp310-win32.whl", hash = "sha256:796ff4426437896550d2981b9c2ac0ffd75238ad9ea2d3bfa67a1abd546d262e"}, + {file = "pywin32-308-cp310-cp310-win_amd64.whl", hash = "sha256:4fc888c59b3c0bef905ce7eb7e2106a07712015ea1c8234b703a088d46110e8e"}, + {file = "pywin32-308-cp310-cp310-win_arm64.whl", hash = "sha256:a5ab5381813b40f264fa3495b98af850098f814a25a63589a8e9eb12560f450c"}, + {file = "pywin32-308-cp311-cp311-win32.whl", hash = "sha256:5d8c8015b24a7d6855b1550d8e660d8daa09983c80e5daf89a273e5c6fb5095a"}, + {file = "pywin32-308-cp311-cp311-win_amd64.whl", hash = "sha256:575621b90f0dc2695fec346b2d6302faebd4f0f45c05ea29404cefe35d89442b"}, + {file = "pywin32-308-cp311-cp311-win_arm64.whl", hash = "sha256:100a5442b7332070983c4cd03f2e906a5648a5104b8a7f50175f7906efd16bb6"}, + {file = "pywin32-308-cp312-cp312-win32.whl", hash = "sha256:587f3e19696f4bf96fde9d8a57cec74a57021ad5f204c9e627e15c33ff568897"}, + {file = "pywin32-308-cp312-cp312-win_amd64.whl", hash = "sha256:00b3e11ef09ede56c6a43c71f2d31857cf7c54b0ab6e78ac659497abd2834f47"}, + {file = "pywin32-308-cp312-cp312-win_arm64.whl", hash = "sha256:9b4de86c8d909aed15b7011182c8cab38c8850de36e6afb1f0db22b8959e3091"}, + {file = "pywin32-308-cp313-cp313-win32.whl", hash = "sha256:1c44539a37a5b7b21d02ab34e6a4d314e0788f1690d65b48e9b0b89f31abbbed"}, + {file = "pywin32-308-cp313-cp313-win_amd64.whl", hash = "sha256:fd380990e792eaf6827fcb7e187b2b4b1cede0585e3d0c9e84201ec27b9905e4"}, + {file = "pywin32-308-cp313-cp313-win_arm64.whl", hash = "sha256:ef313c46d4c18dfb82a2431e3051ac8f112ccee1a34f29c263c583c568db63cd"}, + {file = "pywin32-308-cp37-cp37m-win32.whl", hash = "sha256:1f696ab352a2ddd63bd07430080dd598e6369152ea13a25ebcdd2f503a38f1ff"}, + {file = "pywin32-308-cp37-cp37m-win_amd64.whl", hash = "sha256:13dcb914ed4347019fbec6697a01a0aec61019c1046c2b905410d197856326a6"}, + {file = "pywin32-308-cp38-cp38-win32.whl", hash = "sha256:5794e764ebcabf4ff08c555b31bd348c9025929371763b2183172ff4708152f0"}, + {file = "pywin32-308-cp38-cp38-win_amd64.whl", hash = "sha256:3b92622e29d651c6b783e368ba7d6722b1634b8e70bd376fd7610fe1992e19de"}, + {file = "pywin32-308-cp39-cp39-win32.whl", hash = "sha256:7873ca4dc60ab3287919881a7d4f88baee4a6e639aa6962de25a98ba6b193341"}, + {file = "pywin32-308-cp39-cp39-win_amd64.whl", hash = "sha256:71b3322d949b4cc20776436a9c9ba0eeedcbc9c650daa536df63f0ff111bb920"}, ] [[package]] @@ -2874,13 +2881,13 @@ fixture = ["fixtures"] [[package]] name = "rich" -version = "13.9.2" +version = "13.9.3" description = "Render rich text, tables, progress bars, syntax highlighting, markdown and more to the terminal" optional = false python-versions = ">=3.8.0" files = [ - {file = "rich-13.9.2-py3-none-any.whl", hash = "sha256:8c82a3d3f8dcfe9e734771313e606b39d8247bb6b826e196f4914b333b743cf1"}, - {file = "rich-13.9.2.tar.gz", hash = "sha256:51a2c62057461aaf7152b4d611168f93a9fc73068f8ded2790f29fe2b5366d0c"}, + {file = "rich-13.9.3-py3-none-any.whl", hash = "sha256:9836f5096eb2172c9e77df411c1b009bace4193d6a481d534fea75ebba758283"}, + {file = "rich-13.9.3.tar.gz", hash = "sha256:bc1e01b899537598cf02579d2b9f4a415104d3fc439313a7a2c165d76557a08e"}, ] [package.dependencies] @@ -3082,23 +3089,23 @@ crt = ["botocore[crt] (>=1.33.2,<2.0a.0)"] [[package]] name = "setuptools" -version = "75.1.0" +version = "75.3.0" description = "Easily download, build, install, upgrade, and uninstall Python packages" optional = false python-versions = ">=3.8" files = [ - {file = "setuptools-75.1.0-py3-none-any.whl", hash = "sha256:35ab7fd3bcd95e6b7fd704e4a1539513edad446c097797f2985e0e4b960772f2"}, - {file = "setuptools-75.1.0.tar.gz", hash = "sha256:d59a21b17a275fb872a9c3dae73963160ae079f1049ed956880cd7c09b120538"}, + {file = "setuptools-75.3.0-py3-none-any.whl", hash = "sha256:f2504966861356aa38616760c0f66568e535562374995367b4e69c7143cf6bcd"}, + {file = "setuptools-75.3.0.tar.gz", hash = "sha256:fba5dd4d766e97be1b1681d98712680ae8f2f26d7881245f2ce9e40714f1a686"}, ] [package.extras] check = ["pytest-checkdocs (>=2.4)", "pytest-ruff (>=0.2.1)", "ruff (>=0.5.2)"] -core = ["importlib-metadata (>=6)", "importlib-resources (>=5.10.2)", "jaraco.collections", "jaraco.functools", "jaraco.text (>=3.7)", "more-itertools", "more-itertools (>=8.8)", "packaging", "packaging (>=24)", "platformdirs (>=2.6.2)", "tomli (>=2.0.1)", "wheel (>=0.43.0)"] +core = ["importlib-metadata (>=6)", "importlib-resources (>=5.10.2)", "jaraco.collections", "jaraco.functools", "jaraco.text (>=3.7)", "more-itertools", "more-itertools (>=8.8)", "packaging", "packaging (>=24)", "platformdirs (>=4.2.2)", "tomli (>=2.0.1)", "wheel (>=0.43.0)"] cover = ["pytest-cov"] doc = ["furo", "jaraco.packaging (>=9.3)", "jaraco.tidelift (>=1.4)", "pygments-github-lexers (==0.0.5)", "pyproject-hooks (!=1.1)", "rst.linker (>=1.9)", "sphinx (>=3.5)", "sphinx-favicon", "sphinx-inline-tabs", "sphinx-lint", "sphinx-notfound-page (>=1,<2)", "sphinx-reredirects", "sphinxcontrib-towncrier", "towncrier (<24.7)"] enabler = ["pytest-enabler (>=2.2)"] -test = ["build[virtualenv] (>=1.0.3)", "filelock (>=3.4.0)", "ini2toml[lite] (>=0.14)", "jaraco.develop (>=7.21)", "jaraco.envs (>=2.2)", "jaraco.path (>=3.2.0)", "jaraco.test", "packaging (>=23.2)", "pip (>=19.1)", "pyproject-hooks (!=1.1)", "pytest (>=6,!=8.1.*)", "pytest-home (>=0.5)", "pytest-perf", "pytest-subprocess", "pytest-timeout", "pytest-xdist (>=3)", "tomli-w (>=1.0.0)", "virtualenv (>=13.0.0)", "wheel (>=0.44.0)"] -type = ["importlib-metadata (>=7.0.2)", "jaraco.develop (>=7.21)", "mypy (==1.11.*)", "pytest-mypy"] +test = ["build[virtualenv] (>=1.0.3)", "filelock (>=3.4.0)", "ini2toml[lite] (>=0.14)", "jaraco.develop (>=7.21)", "jaraco.envs (>=2.2)", "jaraco.path (>=3.2.0)", "jaraco.test (>=5.5)", "packaging (>=23.2)", "pip (>=19.1)", "pyproject-hooks (!=1.1)", "pytest (>=6,!=8.1.*)", "pytest-home (>=0.5)", "pytest-perf", "pytest-subprocess", "pytest-timeout", "pytest-xdist (>=3)", "tomli-w (>=1.0.0)", "virtualenv (>=13.0.0)", "wheel (>=0.44.0)"] +type = ["importlib-metadata (>=7.0.2)", "jaraco.develop (>=7.21)", "mypy (==1.12.*)", "pytest-mypy"] [[package]] name = "shellingham" @@ -3157,13 +3164,13 @@ files = [ [[package]] name = "starlette" -version = "0.38.6" +version = "0.41.2" description = "The little ASGI library that shines." optional = false python-versions = ">=3.8" files = [ - {file = "starlette-0.38.6-py3-none-any.whl", hash = "sha256:4517a1409e2e73ee4951214ba012052b9e16f60e90d73cfb06192c19203bbb05"}, - {file = "starlette-0.38.6.tar.gz", hash = "sha256:863a1588f5574e70a821dadefb41e4881ea451a47a3cd1b4df359d4ffefe5ead"}, + {file = "starlette-0.41.2-py3-none-any.whl", hash = "sha256:fbc189474b4731cf30fcef52f18a8d070e3f3b46c6a04c97579e85e6ffca942d"}, + {file = "starlette-0.41.2.tar.gz", hash = "sha256:9834fd799d1a87fd346deb76158668cfa0b0d56f85caefe8268e2d97c3468b62"}, ] [package.dependencies] @@ -3190,13 +3197,13 @@ test = ["pytest", "tornado (>=4.5)", "typeguard"] [[package]] name = "tinycss2" -version = "1.3.0" +version = "1.4.0" description = "A tiny CSS parser" optional = false python-versions = ">=3.8" files = [ - {file = "tinycss2-1.3.0-py3-none-any.whl", hash = "sha256:54a8dbdffb334d536851be0226030e9505965bb2f30f21a4a82c55fb2a80fae7"}, - {file = "tinycss2-1.3.0.tar.gz", hash = "sha256:152f9acabd296a8375fbca5b84c961ff95971fcfc32e79550c8df8e29118c54d"}, + {file = "tinycss2-1.4.0-py3-none-any.whl", hash = "sha256:3a49cf47b7675da0b15d0c6e1df8df4ebd96e9394bb905a5775adb0d884c5289"}, + {file = "tinycss2-1.4.0.tar.gz", hash = "sha256:10c0972f6fc0fbee87c3edb76549357415e94548c1ae10ebccdea16fb404a9b7"}, ] [package.dependencies] @@ -3217,6 +3224,17 @@ files = [ {file = "tomli-2.0.2.tar.gz", hash = "sha256:d46d457a85337051c36524bc5349dd91b1877838e2979ac5ced3e710ed8a60ed"}, ] +[[package]] +name = "tomlkit" +version = "0.13.2" +description = "Style preserving TOML library" +optional = false +python-versions = ">=3.8" +files = [ + {file = "tomlkit-0.13.2-py3-none-any.whl", hash = "sha256:7a974427f6e119197f670fbbbeae7bef749a6c14e793db934baefc1b5f03efde"}, + {file = "tomlkit-0.13.2.tar.gz", hash = "sha256:fff5fe59a87295b278abd31bec92c15d9bc4a06885ab12bcea52c71119392e79"}, +] + [[package]] name = "tornado" version = "6.4.1" @@ -3239,13 +3257,13 @@ files = [ [[package]] name = "tqdm" -version = "4.66.5" +version = "4.66.6" description = "Fast, Extensible Progress Meter" optional = false python-versions = ">=3.7" files = [ - {file = "tqdm-4.66.5-py3-none-any.whl", hash = "sha256:90279a3770753eafc9194a0364852159802111925aa30eb3f9d85b0e805ac7cd"}, - {file = "tqdm-4.66.5.tar.gz", hash = "sha256:e1020aef2e5096702d8a025ac7d16b1577279c9d63f8375b63083e9a5f0fcbad"}, + {file = "tqdm-4.66.6-py3-none-any.whl", hash = "sha256:223e8b5359c2efc4b30555531f09e9f2f3589bcd7fdd389271191031b49b7a63"}, + {file = "tqdm-4.66.6.tar.gz", hash = "sha256:4bdd694238bef1485ce839d67967ab50af8f9272aab687c0d7702a01da0be090"}, ] [package.dependencies] @@ -3327,13 +3345,13 @@ types-urllib3 = "*" [[package]] name = "types-requests" -version = "2.32.0.20240914" +version = "2.32.0.20241016" description = "Typing stubs for requests" optional = false python-versions = ">=3.8" files = [ - {file = "types-requests-2.32.0.20240914.tar.gz", hash = "sha256:2850e178db3919d9bf809e434eef65ba49d0e7e33ac92d588f4a5e295fffd405"}, - {file = "types_requests-2.32.0.20240914-py3-none-any.whl", hash = "sha256:59c2f673eb55f32a99b2894faf6020e1a9f4a402ad0f192bfee0b64469054310"}, + {file = "types-requests-2.32.0.20241016.tar.gz", hash = "sha256:0d9cad2f27515d0e3e3da7134a1b6f28fb97129d86b867f24d9c726452634d95"}, + {file = "types_requests-2.32.0.20241016-py3-none-any.whl", hash = "sha256:4195d62d6d3e043a4eaaf08ff8a62184584d2e8684e9d2aa178c7915a7da3747"}, ] [package.dependencies] @@ -3422,13 +3440,13 @@ zstd = ["zstandard (>=0.18.0)"] [[package]] name = "uvicorn" -version = "0.24.0.post1" +version = "0.32.0" description = "The lightning-fast ASGI server." optional = false python-versions = ">=3.8" files = [ - {file = "uvicorn-0.24.0.post1-py3-none-any.whl", hash = "sha256:7c84fea70c619d4a710153482c0d230929af7bcf76c7bfa6de151f0a3a80121e"}, - {file = "uvicorn-0.24.0.post1.tar.gz", hash = "sha256:09c8e5a79dc466bdf28dead50093957db184de356fcdc48697bad3bde4c2588e"}, + {file = "uvicorn-0.32.0-py3-none-any.whl", hash = "sha256:60b8f3a5ac027dcd31448f411ced12b5ef452c646f76f02f8cc3f25d8d26fd82"}, + {file = "uvicorn-0.32.0.tar.gz", hash = "sha256:f78b36b143c16f54ccdb8190d0a26b5f1901fe5a3c777e1ab29f26391af8551e"}, ] [package.dependencies] @@ -3441,57 +3459,64 @@ standard = ["colorama (>=0.4)", "httptools (>=0.5.0)", "python-dotenv (>=0.13)", [[package]] name = "uvloop" -version = "0.20.0" +version = "0.21.0" description = "Fast implementation of asyncio event loop on top of libuv" optional = false python-versions = ">=3.8.0" files = [ - {file = "uvloop-0.20.0-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:9ebafa0b96c62881d5cafa02d9da2e44c23f9f0cd829f3a32a6aff771449c996"}, - {file = "uvloop-0.20.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:35968fc697b0527a06e134999eef859b4034b37aebca537daeb598b9d45a137b"}, - {file = "uvloop-0.20.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b16696f10e59d7580979b420eedf6650010a4a9c3bd8113f24a103dfdb770b10"}, - {file = "uvloop-0.20.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:9b04d96188d365151d1af41fa2d23257b674e7ead68cfd61c725a422764062ae"}, - {file = "uvloop-0.20.0-cp310-cp310-musllinux_1_1_aarch64.whl", hash = "sha256:94707205efbe809dfa3a0d09c08bef1352f5d3d6612a506f10a319933757c006"}, - {file = "uvloop-0.20.0-cp310-cp310-musllinux_1_1_x86_64.whl", hash = "sha256:89e8d33bb88d7263f74dc57d69f0063e06b5a5ce50bb9a6b32f5fcbe655f9e73"}, - {file = "uvloop-0.20.0-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:e50289c101495e0d1bb0bfcb4a60adde56e32f4449a67216a1ab2750aa84f037"}, - {file = "uvloop-0.20.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:e237f9c1e8a00e7d9ddaa288e535dc337a39bcbf679f290aee9d26df9e72bce9"}, - {file = "uvloop-0.20.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:746242cd703dc2b37f9d8b9f173749c15e9a918ddb021575a0205ec29a38d31e"}, - {file = "uvloop-0.20.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:82edbfd3df39fb3d108fc079ebc461330f7c2e33dbd002d146bf7c445ba6e756"}, - {file = "uvloop-0.20.0-cp311-cp311-musllinux_1_1_aarch64.whl", hash = "sha256:80dc1b139516be2077b3e57ce1cb65bfed09149e1d175e0478e7a987863b68f0"}, - {file = "uvloop-0.20.0-cp311-cp311-musllinux_1_1_x86_64.whl", hash = "sha256:4f44af67bf39af25db4c1ac27e82e9665717f9c26af2369c404be865c8818dcf"}, - {file = "uvloop-0.20.0-cp312-cp312-macosx_10_9_universal2.whl", hash = "sha256:4b75f2950ddb6feed85336412b9a0c310a2edbcf4cf931aa5cfe29034829676d"}, - {file = "uvloop-0.20.0-cp312-cp312-macosx_10_9_x86_64.whl", hash = "sha256:77fbc69c287596880ecec2d4c7a62346bef08b6209749bf6ce8c22bbaca0239e"}, - {file = "uvloop-0.20.0-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:6462c95f48e2d8d4c993a2950cd3d31ab061864d1c226bbf0ee2f1a8f36674b9"}, - {file = "uvloop-0.20.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:649c33034979273fa71aa25d0fe120ad1777c551d8c4cd2c0c9851d88fcb13ab"}, - {file = "uvloop-0.20.0-cp312-cp312-musllinux_1_1_aarch64.whl", hash = "sha256:3a609780e942d43a275a617c0839d85f95c334bad29c4c0918252085113285b5"}, - {file = "uvloop-0.20.0-cp312-cp312-musllinux_1_1_x86_64.whl", hash = "sha256:aea15c78e0d9ad6555ed201344ae36db5c63d428818b4b2a42842b3870127c00"}, - {file = "uvloop-0.20.0-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:f0e94b221295b5e69de57a1bd4aeb0b3a29f61be6e1b478bb8a69a73377db7ba"}, - {file = "uvloop-0.20.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:fee6044b64c965c425b65a4e17719953b96e065c5b7e09b599ff332bb2744bdf"}, - {file = "uvloop-0.20.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:265a99a2ff41a0fd56c19c3838b29bf54d1d177964c300dad388b27e84fd7847"}, - {file = "uvloop-0.20.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:b10c2956efcecb981bf9cfb8184d27d5d64b9033f917115a960b83f11bfa0d6b"}, - {file = "uvloop-0.20.0-cp38-cp38-musllinux_1_1_aarch64.whl", hash = "sha256:e7d61fe8e8d9335fac1bf8d5d82820b4808dd7a43020c149b63a1ada953d48a6"}, - {file = "uvloop-0.20.0-cp38-cp38-musllinux_1_1_x86_64.whl", hash = "sha256:2beee18efd33fa6fdb0976e18475a4042cd31c7433c866e8a09ab604c7c22ff2"}, - {file = "uvloop-0.20.0-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:d8c36fdf3e02cec92aed2d44f63565ad1522a499c654f07935c8f9d04db69e95"}, - {file = "uvloop-0.20.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:a0fac7be202596c7126146660725157d4813aa29a4cc990fe51346f75ff8fde7"}, - {file = "uvloop-0.20.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:9d0fba61846f294bce41eb44d60d58136090ea2b5b99efd21cbdf4e21927c56a"}, - {file = "uvloop-0.20.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:95720bae002ac357202e0d866128eb1ac82545bcf0b549b9abe91b5178d9b541"}, - {file = "uvloop-0.20.0-cp39-cp39-musllinux_1_1_aarch64.whl", hash = "sha256:36c530d8fa03bfa7085af54a48f2ca16ab74df3ec7108a46ba82fd8b411a2315"}, - {file = "uvloop-0.20.0-cp39-cp39-musllinux_1_1_x86_64.whl", hash = "sha256:e97152983442b499d7a71e44f29baa75b3b02e65d9c44ba53b10338e98dedb66"}, - {file = "uvloop-0.20.0.tar.gz", hash = "sha256:4603ca714a754fc8d9b197e325db25b2ea045385e8a3ad05d3463de725fdf469"}, -] - -[package.extras] + {file = "uvloop-0.21.0-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:ec7e6b09a6fdded42403182ab6b832b71f4edaf7f37a9a0e371a01db5f0cb45f"}, + {file = "uvloop-0.21.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:196274f2adb9689a289ad7d65700d37df0c0930fd8e4e743fa4834e850d7719d"}, + {file = "uvloop-0.21.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f38b2e090258d051d68a5b14d1da7203a3c3677321cf32a95a6f4db4dd8b6f26"}, + {file = "uvloop-0.21.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:87c43e0f13022b998eb9b973b5e97200c8b90823454d4bc06ab33829e09fb9bb"}, + {file = "uvloop-0.21.0-cp310-cp310-musllinux_1_2_aarch64.whl", hash = "sha256:10d66943def5fcb6e7b37310eb6b5639fd2ccbc38df1177262b0640c3ca68c1f"}, + {file = "uvloop-0.21.0-cp310-cp310-musllinux_1_2_x86_64.whl", hash = "sha256:67dd654b8ca23aed0a8e99010b4c34aca62f4b7fce88f39d452ed7622c94845c"}, + {file = "uvloop-0.21.0-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:c0f3fa6200b3108919f8bdabb9a7f87f20e7097ea3c543754cabc7d717d95cf8"}, + {file = "uvloop-0.21.0-cp311-cp311-macosx_10_9_x86_64.whl", hash = "sha256:0878c2640cf341b269b7e128b1a5fed890adc4455513ca710d77d5e93aa6d6a0"}, + {file = "uvloop-0.21.0-cp311-cp311-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:b9fb766bb57b7388745d8bcc53a359b116b8a04c83a2288069809d2b3466c37e"}, + {file = "uvloop-0.21.0-cp311-cp311-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:8a375441696e2eda1c43c44ccb66e04d61ceeffcd76e4929e527b7fa401b90fb"}, + {file = "uvloop-0.21.0-cp311-cp311-musllinux_1_2_aarch64.whl", hash = "sha256:baa0e6291d91649c6ba4ed4b2f982f9fa165b5bbd50a9e203c416a2797bab3c6"}, + {file = "uvloop-0.21.0-cp311-cp311-musllinux_1_2_x86_64.whl", hash = "sha256:4509360fcc4c3bd2c70d87573ad472de40c13387f5fda8cb58350a1d7475e58d"}, + {file = "uvloop-0.21.0-cp312-cp312-macosx_10_13_universal2.whl", hash = "sha256:359ec2c888397b9e592a889c4d72ba3d6befba8b2bb01743f72fffbde663b59c"}, + {file = "uvloop-0.21.0-cp312-cp312-macosx_10_13_x86_64.whl", hash = "sha256:f7089d2dc73179ce5ac255bdf37c236a9f914b264825fdaacaded6990a7fb4c2"}, + {file = "uvloop-0.21.0-cp312-cp312-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:baa4dcdbd9ae0a372f2167a207cd98c9f9a1ea1188a8a526431eef2f8116cc8d"}, + {file = "uvloop-0.21.0-cp312-cp312-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:86975dca1c773a2c9864f4c52c5a55631038e387b47eaf56210f873887b6c8dc"}, + {file = "uvloop-0.21.0-cp312-cp312-musllinux_1_2_aarch64.whl", hash = "sha256:461d9ae6660fbbafedd07559c6a2e57cd553b34b0065b6550685f6653a98c1cb"}, + {file = "uvloop-0.21.0-cp312-cp312-musllinux_1_2_x86_64.whl", hash = "sha256:183aef7c8730e54c9a3ee3227464daed66e37ba13040bb3f350bc2ddc040f22f"}, + {file = "uvloop-0.21.0-cp313-cp313-macosx_10_13_universal2.whl", hash = "sha256:bfd55dfcc2a512316e65f16e503e9e450cab148ef11df4e4e679b5e8253a5281"}, + {file = "uvloop-0.21.0-cp313-cp313-macosx_10_13_x86_64.whl", hash = "sha256:787ae31ad8a2856fc4e7c095341cccc7209bd657d0e71ad0dc2ea83c4a6fa8af"}, + {file = "uvloop-0.21.0-cp313-cp313-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:5ee4d4ef48036ff6e5cfffb09dd192c7a5027153948d85b8da7ff705065bacc6"}, + {file = "uvloop-0.21.0-cp313-cp313-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:f3df876acd7ec037a3d005b3ab85a7e4110422e4d9c1571d4fc89b0fc41b6816"}, + {file = "uvloop-0.21.0-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:bd53ecc9a0f3d87ab847503c2e1552b690362e005ab54e8a48ba97da3924c0dc"}, + {file = "uvloop-0.21.0-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:a5c39f217ab3c663dc699c04cbd50c13813e31d917642d459fdcec07555cc553"}, + {file = "uvloop-0.21.0-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:17df489689befc72c39a08359efac29bbee8eee5209650d4b9f34df73d22e414"}, + {file = "uvloop-0.21.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:bc09f0ff191e61c2d592a752423c767b4ebb2986daa9ed62908e2b1b9a9ae206"}, + {file = "uvloop-0.21.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:f0ce1b49560b1d2d8a2977e3ba4afb2414fb46b86a1b64056bc4ab929efdafbe"}, + {file = "uvloop-0.21.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:e678ad6fe52af2c58d2ae3c73dc85524ba8abe637f134bf3564ed07f555c5e79"}, + {file = "uvloop-0.21.0-cp38-cp38-musllinux_1_2_aarch64.whl", hash = "sha256:460def4412e473896ef179a1671b40c039c7012184b627898eea5072ef6f017a"}, + {file = "uvloop-0.21.0-cp38-cp38-musllinux_1_2_x86_64.whl", hash = "sha256:10da8046cc4a8f12c91a1c39d1dd1585c41162a15caaef165c2174db9ef18bdc"}, + {file = "uvloop-0.21.0-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:c097078b8031190c934ed0ebfee8cc5f9ba9642e6eb88322b9958b649750f72b"}, + {file = "uvloop-0.21.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:46923b0b5ee7fc0020bef24afe7836cb068f5050ca04caf6b487c513dc1a20b2"}, + {file = "uvloop-0.21.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:53e420a3afe22cdcf2a0f4846e377d16e718bc70103d7088a4f7623567ba5fb0"}, + {file = "uvloop-0.21.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:88cb67cdbc0e483da00af0b2c3cdad4b7c61ceb1ee0f33fe00e09c81e3a6cb75"}, + {file = "uvloop-0.21.0-cp39-cp39-musllinux_1_2_aarch64.whl", hash = "sha256:221f4f2a1f46032b403bf3be628011caf75428ee3cc204a22addf96f586b19fd"}, + {file = "uvloop-0.21.0-cp39-cp39-musllinux_1_2_x86_64.whl", hash = "sha256:2d1f581393673ce119355d56da84fe1dd9d2bb8b3d13ce792524e1607139feff"}, + {file = "uvloop-0.21.0.tar.gz", hash = "sha256:3bf12b0fda68447806a7ad847bfa591613177275d35b6724b1ee573faa3704e3"}, +] + +[package.extras] +dev = ["Cython (>=3.0,<4.0)", "setuptools (>=60)"] docs = ["Sphinx (>=4.1.2,<4.2.0)", "sphinx-rtd-theme (>=0.5.2,<0.6.0)", "sphinxcontrib-asyncio (>=0.3.0,<0.4.0)"] -test = ["Cython (>=0.29.36,<0.30.0)", "aiohttp (==3.9.0b0)", "aiohttp (>=3.8.1)", "flake8 (>=5.0,<6.0)", "mypy (>=0.800)", "psutil", "pyOpenSSL (>=23.0.0,<23.1.0)", "pycodestyle (>=2.9.0,<2.10.0)"] +test = ["aiohttp (>=3.10.5)", "flake8 (>=5.0,<6.0)", "mypy (>=0.800)", "psutil", "pyOpenSSL (>=23.0.0,<23.1.0)", "pycodestyle (>=2.9.0,<2.10.0)"] [[package]] name = "virtualenv" -version = "20.26.6" +version = "20.27.1" description = "Virtual Python Environment builder" optional = false -python-versions = ">=3.7" +python-versions = ">=3.8" files = [ - {file = "virtualenv-20.26.6-py3-none-any.whl", hash = "sha256:7345cc5b25405607a624d8418154577459c3e0277f5466dd79c49d5e492995f2"}, - {file = "virtualenv-20.26.6.tar.gz", hash = "sha256:280aede09a2a5c317e409a00102e7077c6432c5a38f0ef938e643805a7ad2c48"}, + {file = "virtualenv-20.27.1-py3-none-any.whl", hash = "sha256:f11f1b8a29525562925f745563bfd48b189450f61fb34c4f9cc79dd5aa32a1f4"}, + {file = "virtualenv-20.27.1.tar.gz", hash = "sha256:142c6be10212543b32c6c45d3d3893dff89112cc588b7d0879ae5a1ec03a47ba"}, ] [package.dependencies] @@ -3561,13 +3586,13 @@ files = [ [[package]] name = "werkzeug" -version = "3.0.4" +version = "3.0.6" description = "The comprehensive WSGI web application library." optional = false python-versions = ">=3.8" files = [ - {file = "werkzeug-3.0.4-py3-none-any.whl", hash = "sha256:02c9eb92b7d6c06f31a782811505d2157837cea66aaede3e217c7c27c039476c"}, - {file = "werkzeug-3.0.4.tar.gz", hash = "sha256:34f2371506b250df4d4f84bfe7b0921e4762525762bbd936614909fe25cd7306"}, + {file = "werkzeug-3.0.6-py3-none-any.whl", hash = "sha256:1bc0c2310d2fbb07b1dd1105eba2f7af72f322e1e455f2f93c993bee8c8a5f17"}, + {file = "werkzeug-3.0.6.tar.gz", hash = "sha256:a8dd59d4de28ca70471a34cba79bed5f7ef2e036a76b3ab0835474246eb41f8d"}, ] [package.dependencies] @@ -3688,7 +3713,10 @@ enabler = ["pytest-enabler (>=2.2)"] test = ["big-O", "importlib-resources", "jaraco.functools", "jaraco.itertools", "jaraco.test", "more-itertools", "pytest (>=6,!=8.1.*)", "pytest-ignore-flaky"] type = ["pytest-mypy"] +[extras] +all = [] + [metadata] lock-version = "2.0" python-versions = ">=3.8,<3.13" -content-hash = "5fce459cdf66cb0ffea1c4076cf745398f007ba4c21db78835d2afc1823cde78" +content-hash = "0d17acaff9b40380a1627cb7fc2277f415158bc6026876081abc816e56e32e04" diff --git a/pyproject.toml b/pyproject.toml index 3c71ae3c3..3b2daaaa4 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -14,11 +14,14 @@ keywords = [ "Model Deployment", "Machine Learning", ] + packages = [ { include = "truss", from = "." }, { include = "truss_chains", from = "./truss-chains" }, ] +[tool.poetry.scripts] +truss = "truss.cli:truss_cli" [tool.poetry.urls] "Homepage" = "https://truss.baseten.co" @@ -26,89 +29,136 @@ packages = [ "Documentation" = "https://truss.baseten.co" "Baseten" = "https://baseten.co" +# Note: *why* are dependencies and defined like this? +# The goal is to factorize the overall truss package into a light-weight `base` part that includes +# e.g. the Truss config and has no heavy dependencies. Other functionalities are organzied into +# components (or "extras") sub-packages, that can be selectively installed (and heavy dependencies +# are only installed as needed). +# +# These sub-packages should have clear separation of concerns, and it should be carefully designed +# how they depend on and import each other (e.g. `base` must not depend on anything else, the +# server does not need local CLI tools). +# +# We want components to be selectable via pip installs (e.g. `pip install truss[server]`). +# Unfortunately poetry dependency groups don't integrate natively with the "extras" concept: +# Specifically, dependencies listed in groups (other than the implicit main group) cannot be used +# for extras. +# +# This leaves us with the following process: +# +# * Use poetry groups only for dev dependencies. These are never included in pip. For dev envs +# use the following installation command `poetry install --with=dev,dev-server --extras=all`. +# * All other dependencies are in the main group `tool.poetry.dependencies`. Base dependencies are +# at the top and non-optional. +# * Dependencies from other compoents are listed after, and marked with `optional = false`. If a +# dependency is needed by mutlipe extras, only add it once, but see next step. This also ensures +# that poetry resolves *all* dependencies from all extras to be globally consistent. +# * Since poetry groups don't work with extras, we need to make the association between a dependency +# and the componnent(s) in which it is used in a different way. Because it's cumbersome to fill +# in `tool.poetry.extras` manually, we automate this process and only define +# `tool.dependency_metadata` where we map for each extra dependency to one or multiple components +# that need it. +# * As a pre-commit step `pyproject_toml_linter.py` populates `tool.poetry.extras` groups and also +# creates an "all"-extras. +# +# TODO: The full factorization is WIP, so far only `base` has been cleanly factored out. +# All other dependencies are lumped together in "other". Customers should install truss +# as `pip install truss[local]`, so we temporarily fill local with all deps, until it is properly +# isolated. [tool.poetry.dependencies] -aiofiles = "^24.1.0" -blake3 = "^0.3.3" -boto3 = "^1.34.85" -fastapi = ">=0.109.1" -google-cloud-storage = "2.10.0" -httpcore = ">=1.0.5" # Need min version because of https://github.com/encode/httpx/issues/1171. -httpx = ">=0.24.1" -huggingface_hub = ">=0.25.0" -inquirerpy = "^0.3.4" -Jinja2 = "^3.1.2" -libcst = "<1.2.0" -loguru = ">=0.7.2" -msgpack = ">=1.0.2" -msgpack-numpy = ">=0.4.8" -numpy = ">=1.23.5" -opentelemetry-api = ">=1.25.0" -opentelemetry-sdk = ">=1.25.0" -opentelemetry-exporter-otlp = ">=1.25.0" -packaging = ">=20.9" -pathspec = ">=0.9.0" -psutil = ">=5.9.4" -pydantic = ">=1.10.0" -pytest-asyncio = "^0.23.6" -# Note: when using chains, 3.9 will be required at runtime, but other truss functionality works with 3.8. +# "base" dependencies. +# "When using chains, 3.9 will be required at runtime, but other truss functionality works with 3.8. python = ">=3.8,<3.13" -python-json-logger = ">=2.0.2" -python-on-whales = "^0.68.0" -PyYAML = ">=6.0" -rich = "^13.4.2" -rich-click = "^1.6.1" -ruff = "^0.4.8" # Not a dev dep, needed for chains code gen. -single-source = "^0.3.0" -tenacity = "^8.0.1" -watchfiles = "^0.19.0" - -[tool.poetry.group.builder.dependencies] -blake3 = "^0.3.3" -boto3 = "^1.26.157" -click = "^8.0.3" -fastapi = ">=0.109.1" -google-cloud-storage = "2.10.0" -httpx = ">=0.24.1" huggingface_hub = ">=0.25.0" -Jinja2 = "^3.1.2" -loguru = ">=0.7.2" -packaging = ">=20.9" -pathspec = ">=0.9.0" -psutil = ">=5.9.4" -python = ">=3.8,<3.12" -python-json-logger = ">=2.0.2" +pydantic = ">=1.10.0" # We cannot upgrade to v2, due to customer needs. PyYAML = ">=6.0" -requests = ">=2.31" -rich = "^13.4.2" single-source = "^0.3.0" -tenacity = "^8.0.1" -uvicorn = "^0.24.0" -watchfiles = "^0.19.0" +# "non-base" dependencies. +# TODO: until we have resolved the question on how users can install the local tools frictionless +# (extras cannot be marked to be included by default), all below packages are non-optional. +# This also means that so far extras defined in `[tool.poetry.extras]` don't have any meaning, +# since everything is globally included anyway. +Jinja2 = { version = "^3.1.2", optional = false } +aiofiles = { version = "^24.1.0", optional = false } +blake3 = { version = "^0.3.3", optional = false } +boto3 = { version = "^1.34.85", optional = false } +click = { version = "^8.0.3", optional = false } +fastapi = { version = ">=0.109.1", optional = false } +google-cloud-storage = { version = "2.10.0", optional = false } +httpx = { version = ">=0.24.1", optional = false } +inquirerpy = { version = "^0.3.4", optional = false } +libcst = { version = "<1.2.0", optional = false } +loguru = { version = ">=0.7.2", optional = false } +packaging = { version = ">=20.9", optional = false } +pathspec = { version = ">=0.9.0", optional = false } +psutil = { version = ">=5.9.4", optional = false } +python-json-logger = { version = ">=2.0.2", optional = false } +python-on-whales = { version = "^0.68.0", optional = false } +requests = { version = ">=2.31", optional = false } +rich = { version = "^13.4.2", optional = false } +rich-click = { version = "^1.6.1", optional = false } +ruff = { version = "^0.4.8", optional = false } # Not a dev dep, needed for chains code gen. +tenacity = { version = "^8.0.1", optional = false } +watchfiles = { version = "^0.19.0", optional = false } + -[tool.poetry.dev-dependencies] +[tool.dependency_metadata] +# `base` / `main` deps which are non-optional are always included and don't need to be added here. +Jinja2 = { components = "other" } +aiofiles = { components = "other" } +blake3 = { components = "other" } +boto3 = { components = "other" } +click = { components = "other" } +fastapi = { components = "other" } +google-cloud-storage = { components = "other" } +httpx = { components = "other" } +inquirerpy = { components = "other" } +libcst = { components = "other" } +loguru = { components = "other" } +packaging = { components = "other" } +pathspec = { components = "other" } +psutil = { components = "other" } +python-json-logger = { components = "other" } +python-on-whales = { components = "other" } +requests = { components = "other" } +rich = { components = "other" } +rich-click = { components = "other" } +ruff = { components = "other" } +tenacity = { components = "other" } +watchfiles = { components = "other" } + +[tool.poetry.group.dev.dependencies] +# These packages are needed as the dev/testing tooling coverage = "^6.4.1" -dockerfile = "^3.2.0" +httpx = { extras = ["cli"], version = "*" } ipdb = "^0.13.9" ipykernel = "^6.16.0" ipython = "^7.16" +mypy = "^1.0.0" nbconvert = "^7.2.1" pre-commit = "^2.18.1" pytest = "7.2.0" +pytest-asyncio = "^0.23.6" pytest-cov = "^3.0.0" +pytest-split = "^0.8.1" +requests-mock = ">=1.11.0" +tomlkit = ">=0.12" types-PyYAML = "^6.0.12.12" +types-aiofiles = ">=24.1.0" +types-requests = ">=2.31.0.2" types-setuptools = "^69.0.0.0" -types-aiofiles = "^24.1.0.20240626" -[tool.poetry.scripts] -truss = 'truss.cli:truss_cli' - -[tool.poetry.group.dev.dependencies] +[tool.poetry.group.dev-server.dependencies] +# These packages are needed to run local tests of server components. Note that the actual +# server deps for building the docker image are (so far) defined in `requirements.txt`-files. +dockerfile = "^3.2.0" flask = "^2.3.3" -httpx = { extras = ["cli"], version = "*" } -mypy = "^1.0.0" -pytest-split = "^0.8.1" -requests-mock = ">=1.11.0" -types-requests = ">=2.31.0.2" +msgpack = ">=1.0.2" +msgpack-numpy = ">=0.4.8" +numpy = ">=1.23.5" +opentelemetry-api = ">=1.25.0" +opentelemetry-exporter-otlp = ">=1.25.0" +opentelemetry-sdk = ">=1.25.0" uvicorn = ">=0.24.0" uvloop = ">=0.17.0" @@ -159,5 +209,10 @@ section-order = [ ] [tool.ruff.lint.pycodestyle] -# The formatter can go sometimes go over the 88 character limit, so we want to provide some buffer. +# The formatter can go sometimes go over the 88-character limit, so we want to provide some buffer. max-line-length = 120 + + +# Note: `tool.poetry.extras` was autogenerated by `pyproject_toml_linter.py`, do not edit manually. +[tool.poetry.extras] +all = [] diff --git a/truss-chains/examples/audio-transcription/whisper_chainlet.py b/truss-chains/examples/audio-transcription/whisper_chainlet.py index 54f01256d..7fff4da52 100644 --- a/truss-chains/examples/audio-transcription/whisper_chainlet.py +++ b/truss-chains/examples/audio-transcription/whisper_chainlet.py @@ -2,7 +2,7 @@ import tempfile import data_types -from truss import truss_config +from truss.base import truss_config import truss_chains as chains diff --git a/truss-chains/examples/mistral/mistral_chainlet.py b/truss-chains/examples/mistral/mistral_chainlet.py index b2ed8168b..d71ea96cd 100644 --- a/truss-chains/examples/mistral/mistral_chainlet.py +++ b/truss-chains/examples/mistral/mistral_chainlet.py @@ -1,6 +1,6 @@ from typing import Protocol -from truss import truss_config +from truss.base import truss_config import truss_chains as chains diff --git a/truss-chains/truss_chains/code_gen.py b/truss-chains/truss_chains/code_gen.py index e00f39ee7..261c394c3 100644 --- a/truss-chains/truss_chains/code_gen.py +++ b/truss-chains/truss_chains/code_gen.py @@ -36,7 +36,7 @@ import libcst import truss -from truss import truss_config +from truss.base import truss_config from truss.contexts.image_builder import serving_image_builder from truss.util import path as truss_path diff --git a/truss-chains/truss_chains/definitions.py b/truss-chains/truss_chains/definitions.py index c8c912273..6cf163129 100644 --- a/truss-chains/truss_chains/definitions.py +++ b/truss-chains/truss_chains/definitions.py @@ -23,8 +23,8 @@ ) import pydantic -from truss import truss_config -from truss.constants import PRODUCTION_ENVIRONMENT_NAME +from truss.base import truss_config +from truss.base.constants import PRODUCTION_ENVIRONMENT_NAME from truss.remote import baseten as baseten_remote from truss.remote import remote_cli, remote_factory @@ -296,7 +296,7 @@ class Assets: For example, model weight caching can be used like this:: import truss_chains as chains - from truss import truss_config + from truss.base import truss_config mistral_cache = truss_config.ModelRepo( repo_id="mistralai/Mistral-7B-Instruct-v0.2", diff --git a/truss-chains/truss_chains/remote.py b/truss-chains/truss_chains/remote.py index 34ce3b895..f79050099 100644 --- a/truss-chains/truss_chains/remote.py +++ b/truss-chains/truss_chains/remote.py @@ -24,7 +24,6 @@ ) import tenacity -import truss import watchfiles if TYPE_CHECKING: @@ -34,6 +33,7 @@ from truss.remote.baseten import custom_types as b10_types from truss.remote.baseten import remote as b10_remote from truss.remote.baseten import service as b10_service +from truss.truss_handle import build as truss_build from truss.util import log_utils from truss.util import path as truss_path @@ -45,7 +45,7 @@ def _push_to_baseten( truss_dir: pathlib.Path, options: definitions.PushOptionsBaseten ) -> b10_service.BasetenService: - truss_handle = truss.load(str(truss_dir)) + truss_handle = truss_build.load(str(truss_dir)) model_name = truss_handle.spec.config.model_name assert model_name is not None assert bool(_MODEL_NAME_RE.match(model_name)) @@ -107,7 +107,7 @@ def _push_service( f"Running in docker container `{chainlet_descriptor.display_name}` " ) port = utils.get_free_port() - truss_handle = truss.load(str(truss_dir)) + truss_handle = truss_build.load(str(truss_dir)) truss_handle.add_secret( definitions.BASETEN_API_SECRET_NAME, options.baseten_chain_api_key ) diff --git a/truss/__init__.py b/truss/__init__.py index e381fa15d..2b9e6c41b 100644 --- a/truss/__init__.py +++ b/truss/__init__.py @@ -7,7 +7,6 @@ # Suppress Pydantic V1 warnings, because we have to use it for backwards compat. warnings.filterwarnings("ignore", category=PydanticDeprecatedSince20) - __version__ = get_version(__name__, Path(__file__).parent.parent) @@ -16,6 +15,5 @@ def version(): from truss.api import login, push -from truss.build import from_directory, init, kill_all, load -__all__ = ["from_directory", "init", "kill_all", "load", "push", "login"] +__all__ = ["push", "login"] diff --git a/truss/api/__init__.py b/truss/api/__init__.py index e0248452b..c02e87711 100644 --- a/truss/api/__init__.py +++ b/truss/api/__init__.py @@ -1,10 +1,10 @@ from typing import Optional, cast -import truss from truss.api import definitions from truss.remote.baseten.service import BasetenService from truss.remote.remote_factory import RemoteFactory from truss.remote.truss_remote import RemoteConfig +from truss.truss_handle.build import load def login(api_key: str): @@ -74,7 +74,7 @@ def push( ) remote_provider = RemoteFactory.create(remote=remote) - tr = truss.load(target_directory) + tr = load(target_directory) model_name = model_name or tr.spec.config.model_name if not model_name: raise ValueError( diff --git a/truss/test_data/annotated_types_truss/model/__init__.py b/truss/base/__init__.py similarity index 100% rename from truss/test_data/annotated_types_truss/model/__init__.py rename to truss/base/__init__.py diff --git a/truss/constants.py b/truss/base/constants.py similarity index 93% rename from truss/constants.py rename to truss/base/constants.py index b8ab86da5..45ea5aaef 100644 --- a/truss/constants.py +++ b/truss/base/constants.py @@ -1,4 +1,3 @@ -import os import pathlib from typing import Set @@ -11,11 +10,10 @@ HUGGINGFACE_TRANSFORMER = "huggingface_transformer" LIGHTGBM = "lightgbm" -BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) -CODE_DIR = pathlib.Path(BASE_DIR, "truss") +_TRUSS_ROOT = pathlib.Path(__file__).parent.parent.resolve() -TEMPLATES_DIR = pathlib.Path(CODE_DIR, "templates") -DOCKER_SERVER_TEMPLATES_DIR = pathlib.Path(CODE_DIR, "templates", "docker_server") +TEMPLATES_DIR = _TRUSS_ROOT / "templates" +DOCKER_SERVER_TEMPLATES_DIR = TEMPLATES_DIR / "docker_server" SERVER_CODE_DIR: pathlib.Path = TEMPLATES_DIR / "server" TRITON_SERVER_CODE_DIR: pathlib.Path = TEMPLATES_DIR / "triton" AUDIO_MODEL_TRTLLM_TRUSS_DIR: pathlib.Path = TEMPLATES_DIR / "trtllm-audio" diff --git a/truss/base/custom_types.py b/truss/base/custom_types.py new file mode 100644 index 000000000..5463575d1 --- /dev/null +++ b/truss/base/custom_types.py @@ -0,0 +1,35 @@ +from dataclasses import dataclass +from enum import Enum +from typing import Any + + +# TODO: kill this. +class ModelFrameworkType(Enum): + SKLEARN = "sklearn" + TENSORFLOW = "tensorflow" + KERAS = "keras" + PYTORCH = "pytorch" + HUGGINGFACE_TRANSFORMER = "huggingface_transformer" + XGBOOST = "xgboost" + LIGHTGBM = "lightgbm" + MLFLOW = "mlflow" + CUSTOM = "custom" + + +@dataclass +class Example: + name: str + input: Any + + @staticmethod + def from_dict(example_dict): + return Example( + name=example_dict["name"], + input=example_dict["input"], + ) + + def to_dict(self) -> dict: + return { + "name": self.name, + "input": self.input, + } diff --git a/truss/errors.py b/truss/base/errors.py similarity index 93% rename from truss/errors.py rename to truss/base/errors.py index d3fb49a28..f096d5732 100644 --- a/truss/errors.py +++ b/truss/base/errors.py @@ -38,3 +38,7 @@ class ContainerNotFoundError(Error): class ContainerAPINoResponseError(Error): pass + + +class RemoteNetworkError(Exception): + pass diff --git a/truss/config/trt_llm.py b/truss/base/trt_llm_config.py similarity index 97% rename from truss/config/trt_llm.py rename to truss/base/trt_llm_config.py index 73c633d2e..a9696be8b 100644 --- a/truss/config/trt_llm.py +++ b/truss/base/trt_llm_config.py @@ -1,5 +1,4 @@ import json -import logging import warnings from enum import Enum from typing import Optional @@ -7,16 +6,10 @@ from huggingface_hub.errors import HFValidationError from huggingface_hub.utils import validate_repo_id from pydantic import BaseModel, PydanticDeprecatedSince20, validator -from rich.console import Console # Suppress Pydantic V1 warnings, because we have to use it for backwards compat. warnings.filterwarnings("ignore", category=PydanticDeprecatedSince20) -logging.basicConfig(level=logging.INFO) -logger = logging.getLogger(__name__) - -console = Console() - class TrussTRTLLMModel(str, Enum): LLAMA = "llama" diff --git a/truss/truss_config.py b/truss/base/truss_config.py similarity index 93% rename from truss/truss_config.py rename to truss/base/truss_config.py index d1da2582d..c9fdad97b 100644 --- a/truss/truss_config.py +++ b/truss/base/truss_config.py @@ -1,17 +1,17 @@ import logging +import sys from dataclasses import _MISSING_TYPE, dataclass, field, fields from enum import Enum from pathlib import Path -from typing import Any, Dict, List, Optional +from typing import Any, Callable, Dict, List, Optional, TypeVar import yaml -from truss.config.trt_llm import TRTLLMConfiguration, TrussTRTLLMQuantizationType -from truss.constants import HTTP_PUBLIC_BLOB_BACKEND -from truss.custom_types import ModelFrameworkType -from truss.errors import ValidationError -from truss.util.data_structures import transform_optional -from truss.validation import ( +from truss.base.constants import HTTP_PUBLIC_BLOB_BACKEND +from truss.base.custom_types import ModelFrameworkType +from truss.base.errors import ValidationError +from truss.base.trt_llm_config import TRTLLMConfiguration, TrussTRTLLMQuantizationType +from truss.base.validation import ( validate_cpu_spec, validate_memory_spec, validate_python_executable_path, @@ -44,8 +44,17 @@ VALID_PYTHON_VERSIONS = ["py38", "py39", "py310", "py311"] -# Set up logging -logging.basicConfig(level=logging.INFO) +X = TypeVar("X") +Y = TypeVar("Y") + + +def transform_optional(x: Optional[X], fn: Callable[[X], Optional[Y]]) -> Optional[Y]: + if x is None: + return None + + return fn(x) + + logger = logging.getLogger(__name__) @@ -791,3 +800,45 @@ def obj_to_dict(obj, verbose: bool = False): d[field_name] = field_curr_value return d + + +# TODO(marius): consolidate this with config/validation: +def _infer_python_version() -> str: + return f"py{sys.version_info.major}{sys.version_info.minor}" + + +def map_local_to_supported_python_version() -> str: + return map_to_supported_python_version(_infer_python_version()) + + +def map_to_supported_python_version(python_version: str) -> str: + """Map python version to truss supported python version. + + Currently, it maps any versions greater than 3.11 to 3.11. + + Args: + python_version: in the form py[major_version][minor_version] e.g. py39, + py310. + """ + python_major_version = int(python_version[2:3]) + python_minor_version = int(python_version[3:]) + + if python_major_version != 3: + raise NotImplementedError("Only python version 3 is supported") + + if python_minor_version > 11: + logger.info( + f"Mapping python version {python_major_version}.{python_minor_version}" + " to 3.11, the highest version that Truss currently supports." + ) + return "py311" + + if python_minor_version < 8: + # TODO: consider raising an error instead - it doesn't' seem safe. + logger.info( + f"Mapping python version {python_major_version}.{python_minor_version}" + " to 3.8, the lowest version that Truss currently supports." + ) + return "py38" + + return python_version diff --git a/truss/truss_spec.py b/truss/base/truss_spec.py similarity index 95% rename from truss/truss_spec.py rename to truss/base/truss_spec.py index 85af0b2c1..340b27b4e 100644 --- a/truss/truss_spec.py +++ b/truss/base/truss_spec.py @@ -4,11 +4,11 @@ import yaml -from truss.constants import CONFIG_FILE -from truss.custom_types import Example, ModelFrameworkType -from truss.errors import ValidationError -from truss.truss_config import ExternalData, ModelServer, TrussConfig -from truss.validation import validate_memory_spec +from truss.base.constants import CONFIG_FILE +from truss.base.custom_types import Example, ModelFrameworkType +from truss.base.errors import ValidationError +from truss.base.truss_config import ExternalData, ModelServer, TrussConfig +from truss.base.validation import validate_memory_spec class TrussSpec: diff --git a/truss/validation.py b/truss/base/validation.py similarity index 97% rename from truss/validation.py rename to truss/base/validation.py index c4cfeba58..f071ab8d1 100644 --- a/truss/validation.py +++ b/truss/base/validation.py @@ -3,8 +3,8 @@ from pathlib import PosixPath from typing import Dict, Pattern -from truss.constants import REGISTRY_BUILD_SECRET_PREFIX -from truss.errors import ValidationError +from truss.base.constants import REGISTRY_BUILD_SECRET_PREFIX +from truss.base.errors import ValidationError SECRET_NAME_MATCH_REGEX: Pattern[str] = re.compile(r"^[-._a-zA-Z0-9]+$") MILLI_CPU_REGEX: Pattern[str] = re.compile(r"^[0-9.]*m$") diff --git a/truss/blob/blob_backend.py b/truss/blob/blob_backend.py deleted file mode 100644 index f93d1c67f..000000000 --- a/truss/blob/blob_backend.py +++ /dev/null @@ -1,10 +0,0 @@ -from abc import ABC, abstractmethod -from pathlib import Path - - -class BlobBackend(ABC): - """A blob backend downloads large remote files.""" - - @abstractmethod - def download(self, url: str, download_to: Path): - raise NotImplementedError() diff --git a/truss/blob/blob_backend_registry.py b/truss/blob/blob_backend_registry.py deleted file mode 100644 index a624a0997..000000000 --- a/truss/blob/blob_backend_registry.py +++ /dev/null @@ -1,23 +0,0 @@ -from typing import Dict - -from truss.blob.blob_backend import BlobBackend -from truss.blob.http_public_blob_backend import HttpPublic -from truss.constants import HTTP_PUBLIC_BLOB_BACKEND - - -class _BlobBackendRegistry: - def __init__(self) -> None: - self._backends: Dict[str, BlobBackend] = {} - # Register default backend - self._backends[HTTP_PUBLIC_BLOB_BACKEND] = HttpPublic() - - def register_backend(self, name: str, backend: BlobBackend): - self._backends[name] = backend - - def get_backend(self, name: str): - if name not in self._backends: - raise ValueError(f"Backend {name} is not registered.") - return self._backends[name] - - -BLOB_BACKEND_REGISTRY = _BlobBackendRegistry() diff --git a/truss/blob/http_public_blob_backend.py b/truss/blob/http_public_blob_backend.py deleted file mode 100644 index 55910551e..000000000 --- a/truss/blob/http_public_blob_backend.py +++ /dev/null @@ -1,23 +0,0 @@ -import shutil -from pathlib import Path - -import requests -from truss.blob.blob_backend import BlobBackend - -BLOB_DOWNLOAD_TIMEOUT_SECS = 600 # 10 minutes - - -class HttpPublic(BlobBackend): - """Downloads without auth, files must be publicly available.""" - - def download(self, URL: str, download_to: Path): - # Streaming download to keep memory usage low - resp = requests.get( - URL, - allow_redirects=True, - stream=True, - timeout=BLOB_DOWNLOAD_TIMEOUT_SECS, - ) - resp.raise_for_status() - with download_to.open("wb") as file: - shutil.copyfileobj(resp.raw, file) diff --git a/truss/cli/cli.py b/truss/cli/cli.py index d505ed41b..e23d0088f 100644 --- a/truss/cli/cli.py +++ b/truss/cli/cli.py @@ -20,8 +20,13 @@ from rich.console import Console import truss -from truss.config.trt_llm import TrussTRTLLMQuantizationType -from truss.constants import PRODUCTION_ENVIRONMENT_NAME, TRTLLM_MIN_MEMORY_REQUEST_GI +from truss.base.constants import ( + PRODUCTION_ENVIRONMENT_NAME, + TRTLLM_MIN_MEMORY_REQUEST_GI, +) +from truss.base.errors import RemoteNetworkError +from truss.base.trt_llm_config import TrussTRTLLMQuantizationType +from truss.base.truss_config import Build, ModelServer from truss.remote.baseten.core import ( ACTIVE_STATUS, DEPLOYING_STATUSES, @@ -38,13 +43,15 @@ inquire_remote_name, ) from truss.remote.remote_factory import USER_TRUSSRC_PATH, RemoteFactory -from truss.truss_config import Build, ModelServer -from truss.util.config_checks import ( +from truss.trt_llm.config_checks import ( check_and_update_memory_for_trt_llm_builder, check_secrets_for_trt_llm_builder, uses_trt_llm_builder, ) -from truss.util.errors import RemoteNetworkError +from truss.truss_handle.build import cleanup as _cleanup +from truss.truss_handle.build import init as _init +from truss.truss_handle.build import load +from truss.util import docker from truss.util.log_utils import LogInterceptor rich.spinner.SPINNERS["deploying"] = {"interval": 500, "frames": ["👾 ", " 👾"]} @@ -213,7 +220,7 @@ def init(target_directory, backend, name) -> None: model_name = name else: model_name = inquire_model_name() - truss.init( + _init( target_directory=target_directory, build_config=build_config, model_name=model_name, @@ -1303,7 +1310,7 @@ def kill(target_directory: str) -> None: @container.command() # type: ignore def kill_all() -> None: """Kills all truss containers that are not manually persisted.""" - truss.kill_all() + docker.kill_all() @truss_cli.command() @@ -1316,14 +1323,14 @@ def cleanup() -> None: such as for building docker images. This command clears that data to free up disk space. """ - truss.build.cleanup() + _cleanup() def _get_truss_from_directory(target_directory: Optional[str] = None): """Gets Truss from directory. If none, use the current directory""" if target_directory is None: target_directory = os.getcwd() - return truss.load(target_directory) + return load(target_directory) truss_cli.add_command(container) diff --git a/truss/contexts/image_builder/image_builder.py b/truss/contexts/image_builder/image_builder.py index 81d60cb25..e8f3fb539 100644 --- a/truss/contexts/image_builder/image_builder.py +++ b/truss/contexts/image_builder/image_builder.py @@ -2,7 +2,7 @@ from pathlib import Path from typing import Optional -from truss.docker import Docker +from truss.util.docker import Docker from truss.util.path import given_or_temporary_dir diff --git a/truss/contexts/image_builder/serving_image_builder.py b/truss/contexts/image_builder/serving_image_builder.py index e917a5cb5..183c4a94c 100644 --- a/truss/contexts/image_builder/serving_image_builder.py +++ b/truss/contexts/image_builder/serving_image_builder.py @@ -12,9 +12,8 @@ from google.cloud import storage from huggingface_hub import get_hf_file_metadata, hf_hub_url, list_repo_files from huggingface_hub.utils import filter_repo_objects -from truss import constants -from truss.config.trt_llm import TrussTRTLLMModel -from truss.constants import ( +from truss.base import constants +from truss.base.constants import ( AUDIO_MODEL_TRTLLM_REQUIREMENTS, AUDIO_MODEL_TRTLLM_SYSTEM_PACKAGES, AUDIO_MODEL_TRTLLM_TRUSS_DIR, @@ -40,6 +39,9 @@ TRTLLM_TRUSS_DIR, USER_SUPPLIED_REQUIREMENTS_TXT_FILENAME, ) +from truss.base.trt_llm_config import TrussTRTLLMModel +from truss.base.truss_config import DEFAULT_BUNDLED_PACKAGES_DIR, BaseImage, TrussConfig +from truss.base.truss_spec import TrussSpec from truss.contexts.image_builder.cache_warmer import ( AWSCredentials, parse_s3_credentials_file, @@ -53,9 +55,7 @@ truss_base_image_tag, ) from truss.contexts.truss_context import TrussContext -from truss.patch.hash import directory_content_hash -from truss.truss_config import DEFAULT_BUNDLED_PACKAGES_DIR, BaseImage, TrussConfig -from truss.truss_spec import TrussSpec +from truss.truss_handle.patch.hash import directory_content_hash from truss.util.jinja import read_template_from_fs from truss.util.path import ( build_truss_target_directory, @@ -150,7 +150,7 @@ def prepare_for_cache(self, filenames): class S3Cache(RemoteCache): - def list_files(self, revision=None): + def list_files(self, revision=None) -> List[str]: s3_credentials_file = self.data_dir / S3_CREDENTIALS if s3_credentials_file.exists(): diff --git a/truss/contexts/local_loader/load_model_local.py b/truss/contexts/local_loader/load_model_local.py index dd621cf70..b6acbbb40 100644 --- a/truss/contexts/local_loader/load_model_local.py +++ b/truss/contexts/local_loader/load_model_local.py @@ -1,6 +1,7 @@ import inspect from pathlib import Path +from truss.base.truss_spec import TrussSpec from truss.contexts.local_loader.truss_module_loader import truss_module_loaded from truss.contexts.local_loader.utils import ( prepare_secrets, @@ -8,7 +9,6 @@ ) from truss.contexts.truss_context import TrussContext from truss.templates.server.common.patches import apply_patches -from truss.truss_spec import TrussSpec class LoadModelLocal(TrussContext): diff --git a/truss/contexts/local_loader/utils.py b/truss/contexts/local_loader/utils.py index 0eb869310..15a1efded 100644 --- a/truss/contexts/local_loader/utils.py +++ b/truss/contexts/local_loader/utils.py @@ -2,8 +2,8 @@ import inspect from typing import Dict +from truss.base.truss_spec import TrussSpec from truss.local.local_config_handler import LocalConfigHandler -from truss.truss_spec import TrussSpec def prepare_secrets(spec: TrussSpec) -> Dict[str, str]: diff --git a/truss/local/local_config_handler.py b/truss/local/local_config_handler.py index 6ec2a6151..a9ae4a2ee 100644 --- a/truss/local/local_config_handler.py +++ b/truss/local/local_config_handler.py @@ -3,8 +3,8 @@ from pathlib import Path from typing import Optional +from truss.base.validation import validate_secret_name from truss.local.local_config import LocalConfig -from truss.validation import validate_secret_name class LocalConfigHandler: diff --git a/truss/model_inference.py b/truss/model_inference.py deleted file mode 100644 index 7229be9f0..000000000 --- a/truss/model_inference.py +++ /dev/null @@ -1,124 +0,0 @@ -import inspect -import logging -import sys -from ast import ClassDef, FunctionDef -from dataclasses import dataclass -from typing import Any, Dict, List, Tuple - -logger: logging.Logger = logging.getLogger(__name__) - - -@dataclass -class ModelBuildStageOne: - # the Python Class of the model - model_type: str - # the framework that the model is built in - model_framework: str - - -def _model_class(model: Any): - return model.__class__ - - -def infer_python_version() -> str: - return f"py{sys.version_info.major}{sys.version_info.minor}" - - -def map_to_supported_python_version(python_version: str) -> str: - """Map python version to truss supported python version. - - Currently, it maps any versions greater than 3.11 to 3.11. - - Args: - python_version: in the form py[major_version][minor_version] e.g. py39, - py310 - """ - python_major_version = int(python_version[2:3]) - python_minor_version = int(python_version[3:]) - - if python_major_version != 3: - raise NotImplementedError("Only python version 3 is supported") - - if python_minor_version > 11: - logger.info( - f"Mapping python version {python_major_version}.{python_minor_version}" - " to 3.11, the highest version that Truss currently supports." - ) - return "py311" - - if python_minor_version < 8: - # TODO: consider raising an error instead - it doesn't' seem safe. - logger.info( - f"Mapping python version {python_major_version}.{python_minor_version}" - " to 3.8, the lowest version that Truss currently supports." - ) - return "py38" - - return python_version - - -def _infer_model_init_parameters(model_class: Any) -> Tuple[List, List]: - full_arg_spec = inspect.getfullargspec(model_class.__init__) - named_args = full_arg_spec.args[1:] - number_of_kwargs = full_arg_spec.defaults and len(full_arg_spec.defaults) or 0 - required_args = full_arg_spec.args[1:-number_of_kwargs] - return named_args, required_args - - -def _infer_model_init_parameters_ast(model_class_def: ClassDef) -> Tuple[List, List]: - named_args: List[str] = [] - required_args: List[str] = [] - init_model_functions = [ - node - for node in model_class_def.body - if isinstance(node, FunctionDef) and node.name == "__init__" - ] - - if not init_model_functions: - return named_args, required_args - - assert ( - len(init_model_functions) == 1 - ), "There should only be one __init__ function in the model class" - init_model_function = init_model_functions[0] - named_args = [arg.arg for arg in init_model_function.args.args][1:] - number_of_defaults = len(init_model_function.args.defaults) - required_args = named_args[:-number_of_defaults] - return named_args, required_args - - -def validate_provided_parameters_with_model( - model_class: Any, provided_parameters: Dict[str, Any] -) -> None: - """ - Validates that all provided parameters match the signature of the model. - - Args: - model_class: The model class to validate against - provided_parameters: The parameters to validate - """ - if type(model_class) == ClassDef: - named_args, required_args = _infer_model_init_parameters_ast(model_class) - else: - named_args, required_args = _infer_model_init_parameters(model_class) - - # Check that there are no extra parameters - if not named_args: - return - - if provided_parameters and not isinstance(provided_parameters, dict): - raise TypeError( - f"Provided parameters must be a dict, not {type(provided_parameters)}" - ) - - for arg in provided_parameters: - if arg not in named_args: - raise ValueError( - f"Provided parameter {arg} is not a valid init parameter for the model." - ) - - for arg in required_args: - if arg not in provided_parameters: - raise ValueError( - f"Required init parameter {arg} was not provided for this model." - ) diff --git a/truss/patch/custom_types.py b/truss/patch/custom_types.py deleted file mode 100644 index ab81ad275..000000000 --- a/truss/patch/custom_types.py +++ /dev/null @@ -1,36 +0,0 @@ -from dataclasses import dataclass, field -from typing import Dict, List - - -@dataclass -class TrussSignature: - """Truss signature stores information for calculating patches for future - changes to Truss. - - Currently, it stores hashes of all of the paths in the truss directory excluding the data dir, - and the truss config contents. Path hashes allow calculating added/updated/removes - paths in future trusses compared to this. Config contents allow calculating - config changes, such as add/update/remove of python requirements etc. - """ - - content_hashes_by_path: Dict[str, str] - config: str - requirements_file_requirements: List[str] = field(default_factory=list) - - def to_dict(self) -> dict: - return { - "content_hashes_by_path": self.content_hashes_by_path, - "config": self.config, - "requirements_file_requirements": self.requirements_file_requirements, - } - - @staticmethod - def from_dict(d) -> "TrussSignature": - return TrussSignature( - content_hashes_by_path=d["content_hashes_by_path"], - config=d["config"], - requirements_file_requirements=d.get("requirements_file_requirements", []), - ) - - -ChangedPaths = Dict[str, List[str]] diff --git a/truss/remote/baseten/core.py b/truss/remote/baseten/core.py index a25e3f8e9..39d3818aa 100644 --- a/truss/remote/baseten/core.py +++ b/truss/remote/baseten/core.py @@ -4,13 +4,13 @@ from typing import IO, List, Optional, Tuple import truss -from truss.constants import PRODUCTION_ENVIRONMENT_NAME +from truss.base.constants import PRODUCTION_ENVIRONMENT_NAME from truss.remote.baseten import custom_types as b10_types from truss.remote.baseten.api import BasetenApi from truss.remote.baseten.error import ApiError from truss.remote.baseten.utils.tar import create_tar_with_progress_bar from truss.remote.baseten.utils.transfer import multipart_upload_boto3 -from truss.truss_handle import TrussHandle +from truss.truss_handle.truss_handle import TrussHandle from truss.util.path import load_trussignore_patterns logger = logging.getLogger(__name__) diff --git a/truss/remote/baseten/remote.py b/truss/remote/baseten/remote.py index 9fcc1f41c..e318de45d 100644 --- a/truss/remote/baseten/remote.py +++ b/truss/remote/baseten/remote.py @@ -6,10 +6,11 @@ import yaml from requests import ReadTimeout -from truss.constants import PRODUCTION_ENVIRONMENT_NAME +from truss.base.constants import PRODUCTION_ENVIRONMENT_NAME if TYPE_CHECKING: from rich import console as rich_console +from truss.base.truss_config import ModelServer from truss.local.local_config_handler import LocalConfigHandler from truss.remote.baseten import custom_types from truss.remote.baseten.api import BasetenApi @@ -35,8 +36,7 @@ from truss.remote.baseten.service import BasetenService, URLConfig from truss.remote.baseten.utils.transfer import base64_encoded_json_str from truss.remote.truss_remote import TrussRemote -from truss.truss_config import ModelServer -from truss.truss_handle import TrussHandle +from truss.truss_handle.truss_handle import TrussHandle from truss.util.path import is_ignored, load_trussignore_patterns from watchfiles import watch diff --git a/truss/remote/baseten/service.py b/truss/remote/baseten/service.py index 7392ace6b..52cb3f402 100644 --- a/truss/remote/baseten/service.py +++ b/truss/remote/baseten/service.py @@ -12,11 +12,11 @@ import requests from tenacity import retry, stop_after_delay, wait_fixed +from truss.base.errors import RemoteNetworkError from truss.remote.baseten.api import BasetenApi from truss.remote.baseten.auth import AuthService from truss.remote.truss_remote import TrussService -from truss.truss_handle import TrussHandle -from truss.util.errors import RemoteNetworkError +from truss.truss_handle.truss_handle import TrussHandle # "classes created inside an enum will not become a member" -> intended here anyway. warnings.filterwarnings("ignore", category=DeprecationWarning, message=".*enum.*") diff --git a/truss/remote/truss_remote.py b/truss/remote/truss_remote.py index e64815e95..3a5bdc1a8 100644 --- a/truss/remote/truss_remote.py +++ b/truss/remote/truss_remote.py @@ -6,7 +6,7 @@ if TYPE_CHECKING: from rich import console as rich_console -from truss.truss_handle import TrussHandle +from truss.truss_handle.truss_handle import TrussHandle class TrussService(ABC): diff --git a/truss/templates/control/control/helpers/truss_patch/model_code_patch_applier.py b/truss/templates/control/control/helpers/truss_patch/model_code_patch_applier.py index 1a1ebc9f2..7caaf6bc1 100644 --- a/truss/templates/control/control/helpers/truss_patch/model_code_patch_applier.py +++ b/truss/templates/control/control/helpers/truss_patch/model_code_patch_applier.py @@ -2,6 +2,7 @@ import os from pathlib import Path +# TODO(marius): remove try-except after TaT. # TODO(pankaj) In desparate need of refactoring into separate library try: from helpers.custom_types import Action, Patch diff --git a/truss/templates/control/control/helpers/truss_patch/model_container_patch_applier.py b/truss/templates/control/control/helpers/truss_patch/model_container_patch_applier.py index 98be96d71..7040a184c 100644 --- a/truss/templates/control/control/helpers/truss_patch/model_container_patch_applier.py +++ b/truss/templates/control/control/helpers/truss_patch/model_container_patch_applier.py @@ -16,7 +16,17 @@ ) from helpers.errors import UnsupportedPatch from helpers.truss_patch.model_code_patch_applier import apply_code_patch -from truss.truss_config import ExternalData, ExternalDataItem, TrussConfig + +# TODO(marius): remove try-except after TaT. +try: + from truss.base.truss_config import ExternalData, ExternalDataItem, TrussConfig +except ImportError: + from truss.truss_config import ( # type: ignore[no-redef] + ExternalData, + ExternalDataItem, + TrussConfig, + ) + from truss.util.download import download_external_data diff --git a/truss/templates/control/requirements.txt b/truss/templates/control/requirements.txt index 16aa11117..a930b2213 100644 --- a/truss/templates/control/requirements.txt +++ b/truss/templates/control/requirements.txt @@ -1,5 +1,5 @@ dataclasses-json==0.5.7 -truss==0.9.14 +truss==0.9.14 # This is insane. fastapi==0.114.1 uvicorn==0.24.0 uvloop==0.19.0 diff --git a/truss/templates/server/common/patches.py b/truss/templates/server/common/patches.py index 4f2ca6364..1e9d87715 100644 --- a/truss/templates/server/common/patches.py +++ b/truss/templates/server/common/patches.py @@ -2,8 +2,6 @@ import logging from pathlib import Path -# Set up logging -logging.basicConfig(level=logging.INFO) logger = logging.getLogger(__name__) diff --git a/truss/templates/server/common/schema.py b/truss/templates/server/common/schema.py index 1e7d3533e..ad5839d7f 100644 --- a/truss/templates/server/common/schema.py +++ b/truss/templates/server/common/schema.py @@ -8,6 +8,7 @@ Optional, Type, Union, + cast, get_args, get_origin, ) @@ -159,7 +160,9 @@ def _extract_pydantic_base_models(union_args: tuple) -> List[Type[BaseModel]]: So for Awaitables, we need to extract the base class from the Awaitable type """ return [ - retrieve_base_class_from_awaitable(arg) if _is_awaitable_type(arg) else arg + cast(Type[BaseModel], retrieve_base_class_from_awaitable(arg)) + if _is_awaitable_type(arg) + else arg for arg in union_args if _is_awaitable_type(arg) or (isinstance(arg, type) and issubclass(arg, BaseModel)) diff --git a/truss/templates/server/requirements.txt b/truss/templates/server/requirements.txt index 328a99149..e5f0dd23d 100644 --- a/truss/templates/server/requirements.txt +++ b/truss/templates/server/requirements.txt @@ -8,6 +8,7 @@ joblib==1.2.0 loguru==0.7.2 msgpack-numpy==0.4.8 msgpack==1.0.2 +numpy>=1.23.5 opentelemetry-api>=1.25.0 opentelemetry-sdk>=1.25.0 opentelemetry-exporter-otlp>=1.25.0 diff --git a/truss/test_data/context_builder_image_test/test.py b/truss/test_data/context_builder_image_test/test.py deleted file mode 100644 index 6e04cb56f..000000000 --- a/truss/test_data/context_builder_image_test/test.py +++ /dev/null @@ -1,4 +0,0 @@ -from truss import init - -th = init("test_truss") -th.docker_build_setup() diff --git a/truss/test_data/test_streaming_truss_with_tracing/config.yaml b/truss/test_data/test_streaming_truss_with_tracing/config.yaml deleted file mode 100644 index b897fc6ee..000000000 --- a/truss/test_data/test_streaming_truss_with_tracing/config.yaml +++ /dev/null @@ -1,4 +0,0 @@ -model_name: Test Streaming -python_version: py39 -environment_variables: - OTEL_TRACING_NDJSON_FILE: "/tmp/otel_traces.ndjson" diff --git a/truss/tests/conftest.py b/truss/tests/conftest.py index ce9c6a99e..47fa212a1 100644 --- a/truss/tests/conftest.py +++ b/truss/tests/conftest.py @@ -11,14 +11,14 @@ import requests import yaml -from truss.build import init +from truss.base.custom_types import Example +from truss.base.truss_config import DEFAULT_BUNDLED_PACKAGES_DIR from truss.contexts.image_builder.serving_image_builder import ( ServingImageBuilderContext, ) from truss.contexts.local_loader.docker_build_emulator import DockerBuildEmulator -from truss.custom_types import Example -from truss.truss_config import DEFAULT_BUNDLED_PACKAGES_DIR -from truss.truss_handle import TrussHandle +from truss.truss_handle.build import init +from truss.truss_handle.truss_handle import TrussHandle CUSTOM_MODEL_CODE = """ class Model: @@ -220,6 +220,11 @@ def predict(self, model_input): """ +@pytest.fixture +def test_data_path() -> Path: + return Path(__file__).parent.resolve() / "test_data" + + @pytest.fixture def pytorch_model_init_args(): return {"arg1": 1, "arg2": 2, "kwarg1": 3, "kwarg2": 4} @@ -556,23 +561,18 @@ def custom_model_truss_dir_for_secrets(tmp_path): @pytest.fixture -def truss_container_fs(tmp_path): - ROOT = Path(__file__).parent.parent.parent.resolve() - return _build_truss_fs(ROOT / "truss" / "test_data" / "test_truss", tmp_path) +def truss_container_fs(tmp_path, test_data_path): + return _build_truss_fs(test_data_path / "test_truss", tmp_path) @pytest.fixture -def trt_llm_truss_container_fs(tmp_path): - ROOT = Path(__file__).parent.parent.parent.resolve() - return _build_truss_fs( - ROOT / "truss" / "test_data" / "test_trt_llm_truss", tmp_path - ) +def trt_llm_truss_container_fs(tmp_path, test_data_path): + return _build_truss_fs(test_data_path / "test_trt_llm_truss", tmp_path) @pytest.fixture -def truss_control_container_fs(tmp_path): - ROOT = Path(__file__).parent.parent.parent.resolve() - test_truss_dir = ROOT / "truss" / "test_data" / "test_truss" +def truss_control_container_fs(tmp_path, test_data_path): + test_truss_dir = test_data_path / "test_truss" control_truss_dir = tmp_path / "control_truss" shutil.copytree(str(test_truss_dir), str(control_truss_dir)) with _modify_yaml(control_truss_dir / "config.yaml") as content: @@ -581,7 +581,7 @@ def truss_control_container_fs(tmp_path): @pytest.fixture -def patch_ping_test_server(): +def patch_ping_test_server(test_data_path): port = "5001" proc = subprocess.Popen( [ @@ -596,7 +596,7 @@ def patch_ping_test_server(): "--host", "0.0.0.0", ], - cwd=str(Path(__file__).parent.parent / "test_data" / "patch_ping_test_server"), + cwd=str(test_data_path / "patch_ping_test_server"), ) base_url = f"http://127.0.0.1:{port}" retry_secs = 10 diff --git a/truss/tests/contexts/image_builder/test_serving_image_builder.py b/truss/tests/contexts/image_builder/test_serving_image_builder.py index 2a6d0f730..7531fa800 100644 --- a/truss/tests/contexts/image_builder/test_serving_image_builder.py +++ b/truss/tests/contexts/image_builder/test_serving_image_builder.py @@ -6,26 +6,28 @@ from unittest.mock import patch import pytest -from truss.constants import ( +from truss.base.constants import ( BASE_TRTLLM_REQUIREMENTS, TRTLLM_BASE_IMAGE, TRTLLM_PREDICT_CONCURRENCY, TRTLLM_PYTHON_EXECUTABLE, TRTLLM_TRUSS_DIR, ) +from truss.base.truss_config import ModelCache, ModelRepo, TrussConfig from truss.contexts.image_builder.serving_image_builder import ( HF_ACCESS_TOKEN_FILE_NAME, ServingImageBuilderContext, get_files_to_cache, ) from truss.tests.test_testing_utilities_for_other_tests import ensure_kill_all -from truss.truss_config import ModelCache, ModelRepo, TrussConfig -from truss.truss_handle import TrussHandle +from truss.truss_handle.truss_handle import TrussHandle BASE_DIR = Path(__file__).parent -def test_serving_image_dockerfile_from_user_base_image(custom_model_truss_dir): +def test_serving_image_dockerfile_from_user_base_image( + test_data_path, custom_model_truss_dir +): th = TrussHandle(custom_model_truss_dir) # The test fixture python varies with host version, need to pin here. th.update_python_version("py39") @@ -38,7 +40,7 @@ def test_serving_image_dockerfile_from_user_base_image(custom_model_truss_dir): with open(tmp_path / "Dockerfile", "r") as f: gen_docker_lines = f.readlines() with open( - f"{BASE_DIR}/../../../test_data/server.Dockerfile", + test_data_path / "server.Dockerfile", "r", ) as f: server_docker_lines = f.readlines() @@ -248,12 +250,9 @@ def test_correct_nested_s3_files_accessed_for_caching(mock_list_bucket_files): @pytest.mark.integration -def test_truss_server_caching_truss(): +def test_truss_server_caching_truss(test_data_path): with ensure_kill_all(): - truss_root = ( - Path(__file__).parent.parent.parent.parent.parent.resolve() / "truss" - ) - truss_dir = truss_root / "test_data" / "test_truss_server_caching_truss" + truss_dir = test_data_path / "test_truss_server_caching_truss" tr = TrussHandle(truss_dir) container = tr.docker_run( @@ -263,9 +262,8 @@ def test_truss_server_caching_truss(): assert "Downloading model.safetensors:" not in container.logs() -def test_model_cache_dockerfile(): - truss_root = Path(__file__).parent.parent.parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "test_truss_server_caching_truss" +def test_model_cache_dockerfile(test_data_path): + truss_dir = test_data_path / "test_truss_server_caching_truss" tr = TrussHandle(truss_dir) builder_context = ServingImageBuilderContext diff --git a/truss/tests/contexts/local_loader/test_load_local.py b/truss/tests/contexts/local_loader/test_load_local.py index 1d5d77df7..2c196e9df 100644 --- a/truss/tests/contexts/local_loader/test_load_local.py +++ b/truss/tests/contexts/local_loader/test_load_local.py @@ -1,7 +1,7 @@ +from truss.base.truss_spec import TrussSpec from truss.contexts.local_loader.utils import prepare_secrets from truss.local.local_config_handler import LocalConfigHandler -from truss.truss_handle import TrussHandle -from truss.truss_spec import TrussSpec +from truss.truss_handle.truss_handle import TrussHandle def test_prepare_secrets(custom_model_truss_dir, tmp_path): diff --git a/truss/tests/contexts/local_loader/test_truss_module_finder.py b/truss/tests/contexts/local_loader/test_truss_module_finder.py index 370bf7cae..07785ccaa 100644 --- a/truss/tests/contexts/local_loader/test_truss_module_finder.py +++ b/truss/tests/contexts/local_loader/test_truss_module_finder.py @@ -1,8 +1,8 @@ import tempfile from pathlib import Path +from truss.base.truss_config import DEFAULT_BUNDLED_PACKAGES_DIR from truss.contexts.local_loader.truss_module_loader import truss_module_loaded -from truss.truss_config import DEFAULT_BUNDLED_PACKAGES_DIR ORIG_MODEL_CLASS_CONTENT = """ class Model: diff --git a/truss/tests/patch/test_calc_patch.py b/truss/tests/patch/test_calc_patch.py index 9ff696b15..6e96529d2 100644 --- a/truss/tests/patch/test_calc_patch.py +++ b/truss/tests/patch/test_calc_patch.py @@ -4,12 +4,7 @@ import pytest import yaml -from truss.patch.calc_patch import ( - _calc_python_requirements_patches, - calc_truss_patch, - calc_unignored_paths, -) -from truss.patch.signature import calc_truss_signature +from truss.base.truss_config import TrussConfig from truss.templates.control.control.helpers.custom_types import ( Action, ConfigPatch, @@ -22,8 +17,13 @@ PythonRequirementPatch, SystemPackagePatch, ) -from truss.truss_config import TrussConfig -from truss.truss_handle import TrussHandle +from truss.truss_handle.patch.calc_patch import ( + _calc_python_requirements_patches, + _calc_unignored_paths, + calc_truss_patch, +) +from truss.truss_handle.patch.signature import calc_truss_signature +from truss.truss_handle.truss_handle import TrussHandle def test_calc_truss_patch_unsupported(custom_model_truss_dir: Path): @@ -995,7 +995,7 @@ def test_calc_unignored_paths(): "model/model.py", } - unignored_paths = calc_unignored_paths(root_relative_paths, ignore_patterns) + unignored_paths = _calc_unignored_paths(root_relative_paths, ignore_patterns) assert unignored_paths == { "config.yaml", "model/model.py", diff --git a/truss/tests/patch/test_dir_signature.py b/truss/tests/patch/test_dir_signature.py index 907e8c83c..f62d48757 100644 --- a/truss/tests/patch/test_dir_signature.py +++ b/truss/tests/patch/test_dir_signature.py @@ -1,4 +1,4 @@ -from truss.patch.dir_signature import directory_content_signature +from truss.truss_handle.patch.dir_signature import directory_content_signature def test_directory_content_signature(tmp_path): diff --git a/truss/tests/patch/test_hash.py b/truss/tests/patch/test_hash.py index 04210d126..0b5d872d7 100644 --- a/truss/tests/patch/test_hash.py +++ b/truss/tests/patch/test_hash.py @@ -4,7 +4,7 @@ from typing import Callable, List import pytest -from truss.patch.hash import ( +from truss.truss_handle.patch.hash import ( directory_content_hash, file_content_hash, file_content_hash_str, diff --git a/truss/tests/patch/test_signature.py b/truss/tests/patch/test_signature.py index 83632c558..37a343f51 100644 --- a/truss/tests/patch/test_signature.py +++ b/truss/tests/patch/test_signature.py @@ -1,4 +1,4 @@ -from truss.patch.signature import calc_truss_signature +from truss.truss_handle.patch.signature import calc_truss_signature def test_calc_truss_signature(custom_model_truss_dir): diff --git a/truss/tests/patch/test_truss_dir_patch_applier.py b/truss/tests/patch/test_truss_dir_patch_applier.py index 403059975..8902b2583 100644 --- a/truss/tests/patch/test_truss_dir_patch_applier.py +++ b/truss/tests/patch/test_truss_dir_patch_applier.py @@ -2,7 +2,7 @@ from pathlib import Path import yaml -from truss.patch.truss_dir_patch_applier import TrussDirPatchApplier +from truss.base.truss_config import TrussConfig from truss.templates.control.control.helpers.custom_types import ( Action, ConfigPatch, @@ -12,7 +12,7 @@ PythonRequirementPatch, SystemPackagePatch, ) -from truss.truss_config import TrussConfig +from truss.truss_handle.patch.truss_dir_patch_applier import TrussDirPatchApplier TEST_LOGGER = logging.getLogger("test_logger") diff --git a/truss/tests/patch/test_types.py b/truss/tests/patch/test_types.py index 373cf869d..12ff0ee47 100644 --- a/truss/tests/patch/test_types.py +++ b/truss/tests/patch/test_types.py @@ -1,5 +1,5 @@ -from truss.patch.custom_types import TrussSignature -from truss.patch.signature import calc_truss_signature +from truss.truss_handle.patch.custom_types import TrussSignature +from truss.truss_handle.patch.signature import calc_truss_signature def test_truss_signature_type(custom_model_truss_dir): diff --git a/truss/tests/remote/baseten/test_core.py b/truss/tests/remote/baseten/test_core.py index 5f3727ac4..eb39f4a93 100644 --- a/truss/tests/remote/baseten/test_core.py +++ b/truss/tests/remote/baseten/test_core.py @@ -2,7 +2,7 @@ from unittest.mock import MagicMock import pytest -from truss.constants import PRODUCTION_ENVIRONMENT_NAME +from truss.base.constants import PRODUCTION_ENVIRONMENT_NAME from truss.remote.baseten import core from truss.remote.baseten.api import BasetenApi from truss.remote.baseten.core import create_truss_service diff --git a/truss/tests/remote/baseten/test_remote.py b/truss/tests/remote/baseten/test_remote.py index 65929143e..34c202baa 100644 --- a/truss/tests/remote/baseten/test_remote.py +++ b/truss/tests/remote/baseten/test_remote.py @@ -6,7 +6,7 @@ from truss.remote.baseten.custom_types import ChainletData from truss.remote.baseten.error import RemoteError from truss.remote.baseten.remote import BasetenRemote -from truss.truss_handle import TrussHandle +from truss.truss_handle.truss_handle import TrussHandle _TEST_REMOTE_URL = "http://test_remote.com" _TEST_REMOTE_GRAPHQL_PATH = "http://test_remote.com/graphql/" diff --git a/truss/tests/templates/control/control/helpers/test_model_container_patch_applier.py b/truss/tests/templates/control/control/helpers/test_model_container_patch_applier.py index b14a74a3e..35487a239 100644 --- a/truss/tests/templates/control/control/helpers/test_model_container_patch_applier.py +++ b/truss/tests/templates/control/control/helpers/test_model_container_patch_applier.py @@ -4,7 +4,7 @@ from unittest import mock import pytest -from truss.truss_config import TrussConfig +from truss.base.truss_config import TrussConfig # Needed to simulate the set up on the model docker container sys.path.append( diff --git a/truss/tests/templates/control/control/test_server.py b/truss/tests/templates/control/control/test_server.py index b9bf0fc6d..33999129e 100644 --- a/truss/tests/templates/control/control/test_server.py +++ b/truss/tests/templates/control/control/test_server.py @@ -6,7 +6,7 @@ import pytest from httpx import AsyncClient -from truss.custom_types import PatchRequest +from truss.truss_handle.patch.custom_types import PatchRequest # Needed to simulate the set up on the model docker container sys.path.append( diff --git a/truss/tests/test_build.py b/truss/tests/test_build.py index 675aa74a7..6c5041e63 100644 --- a/truss/tests/test_build.py +++ b/truss/tests/test_build.py @@ -1,7 +1,7 @@ from pathlib import Path -from truss.build import init -from truss.truss_spec import TrussSpec +from truss.base.truss_spec import TrussSpec +from truss.truss_handle.build import init def test_truss_init(tmp_path): diff --git a/truss/tests/test_config.py b/truss/tests/test_config.py index 6529475e7..1fcbfced5 100644 --- a/truss/tests/test_config.py +++ b/truss/tests/test_config.py @@ -6,9 +6,9 @@ import pytest import yaml -from truss.config.trt_llm import TrussTRTLLMQuantizationType -from truss.custom_types import ModelFrameworkType -from truss.truss_config import ( +from truss.base.custom_types import ModelFrameworkType +from truss.base.trt_llm_config import TrussTRTLLMQuantizationType +from truss.base.truss_config import ( DEFAULT_CPU, DEFAULT_MEMORY, DEFAULT_USE_GPU, @@ -22,7 +22,7 @@ Resources, TrussConfig, ) -from truss.truss_handle import TrussHandle +from truss.truss_handle.truss_handle import TrussHandle @pytest.fixture diff --git a/truss/tests/test_context_builder_image.py b/truss/tests/test_context_builder_image.py index 314532a20..d245a0268 100644 --- a/truss/tests/test_context_builder_image.py +++ b/truss/tests/test_context_builder_image.py @@ -5,12 +5,10 @@ @pytest.mark.integration -def test_build_docker_image(): +def test_build_docker_image(test_data_path): root_path = Path(__file__).parent.parent.parent root = str(root_path) - context_builder_image_test_dir = str( - root_path / "truss" / "test_data" / "context_builder_image_test" - ) + context_builder_image_test_dir = str(test_data_path / "context_builder_image_test") subprocess.run( [ diff --git a/truss/tests/test_control_truss_patching.py b/truss/tests/test_control_truss_patching.py index 20abcb539..f792cd03c 100644 --- a/truss/tests/test_control_truss_patching.py +++ b/truss/tests/test_control_truss_patching.py @@ -3,7 +3,8 @@ import pytest -from truss.constants import SUPPORTED_PYTHON_VERSIONS +from truss.base.constants import SUPPORTED_PYTHON_VERSIONS +from truss.base.truss_config import ExternalDataItem from truss.local.local_config_handler import LocalConfigHandler from truss.tests.test_testing_utilities_for_other_tests import ensure_kill_all from truss.tests.test_truss_handle import ( @@ -12,9 +13,8 @@ verify_system_package_installed_on_container, verify_system_requirement_not_installed_on_container, ) -from truss.truss_config import ExternalDataItem -from truss.truss_gatherer import calc_shadow_truss_dirname -from truss.truss_handle import TrussHandle +from truss.truss_handle.truss_gatherer import calc_shadow_truss_dirname +from truss.truss_handle.truss_handle import TrussHandle def current_num_docker_images(th: TrussHandle) -> int: diff --git a/truss/test_data/gcs_fix/model/__init__.py b/truss/tests/test_data/__init__.py similarity index 100% rename from truss/test_data/gcs_fix/model/__init__.py rename to truss/tests/test_data/__init__.py diff --git a/truss/test_data/server_conformance_test_truss/model/__init__.py b/truss/tests/test_data/annotated_types_truss/__init__.py similarity index 100% rename from truss/test_data/server_conformance_test_truss/model/__init__.py rename to truss/tests/test_data/annotated_types_truss/__init__.py diff --git a/truss/test_data/annotated_types_truss/config.yaml b/truss/tests/test_data/annotated_types_truss/config.yaml similarity index 100% rename from truss/test_data/annotated_types_truss/config.yaml rename to truss/tests/test_data/annotated_types_truss/config.yaml diff --git a/truss/test_data/test_basic_truss/model/__init__.py b/truss/tests/test_data/annotated_types_truss/model/__init__.py similarity index 100% rename from truss/test_data/test_basic_truss/model/__init__.py rename to truss/tests/test_data/annotated_types_truss/model/__init__.py diff --git a/truss/test_data/annotated_types_truss/model/model.py b/truss/tests/test_data/annotated_types_truss/model/model.py similarity index 100% rename from truss/test_data/annotated_types_truss/model/model.py rename to truss/tests/test_data/annotated_types_truss/model/model.py diff --git a/truss/test_data/auto-mpg.data b/truss/tests/test_data/auto-mpg.data similarity index 100% rename from truss/test_data/auto-mpg.data rename to truss/tests/test_data/auto-mpg.data diff --git a/truss/test_data/context_builder_image_test/Dockerfile b/truss/tests/test_data/context_builder_image_test/Dockerfile similarity index 100% rename from truss/test_data/context_builder_image_test/Dockerfile rename to truss/tests/test_data/context_builder_image_test/Dockerfile diff --git a/truss/test_data/test_pyantic_v1/model/__init__.py b/truss/tests/test_data/context_builder_image_test/__init__.py similarity index 100% rename from truss/test_data/test_pyantic_v1/model/__init__.py rename to truss/tests/test_data/context_builder_image_test/__init__.py diff --git a/truss/tests/test_data/context_builder_image_test/test.py b/truss/tests/test_data/context_builder_image_test/test.py new file mode 100644 index 000000000..f0952f982 --- /dev/null +++ b/truss/tests/test_data/context_builder_image_test/test.py @@ -0,0 +1,3 @@ +from truss.base import truss_config + +print(truss_config) diff --git a/truss/test_data/test_pyantic_v2/model/__init__.py b/truss/tests/test_data/gcs_fix/__init__.py similarity index 100% rename from truss/test_data/test_pyantic_v2/model/__init__.py rename to truss/tests/test_data/gcs_fix/__init__.py diff --git a/truss/test_data/gcs_fix/config.yaml b/truss/tests/test_data/gcs_fix/config.yaml similarity index 100% rename from truss/test_data/gcs_fix/config.yaml rename to truss/tests/test_data/gcs_fix/config.yaml diff --git a/truss/test_data/test_requirements_file_truss/model/__init__.py b/truss/tests/test_data/gcs_fix/model/__init__.py similarity index 100% rename from truss/test_data/test_requirements_file_truss/model/__init__.py rename to truss/tests/test_data/gcs_fix/model/__init__.py diff --git a/truss/test_data/gcs_fix/model/model.py b/truss/tests/test_data/gcs_fix/model/model.py similarity index 100% rename from truss/test_data/gcs_fix/model/model.py rename to truss/tests/test_data/gcs_fix/model/model.py diff --git a/truss/test_data/happy.ipynb b/truss/tests/test_data/happy.ipynb similarity index 100% rename from truss/test_data/happy.ipynb rename to truss/tests/test_data/happy.ipynb diff --git a/truss/test_data/test_trt_llm_truss/model/__init__.py b/truss/tests/test_data/model_load_failure_test/__init__.py similarity index 100% rename from truss/test_data/test_trt_llm_truss/model/__init__.py rename to truss/tests/test_data/model_load_failure_test/__init__.py diff --git a/truss/test_data/model_load_failure_test/config.yaml b/truss/tests/test_data/model_load_failure_test/config.yaml similarity index 100% rename from truss/test_data/model_load_failure_test/config.yaml rename to truss/tests/test_data/model_load_failure_test/config.yaml diff --git a/truss/test_data/test_truss/model/__init__.py b/truss/tests/test_data/model_load_failure_test/model/__init__.py similarity index 100% rename from truss/test_data/test_truss/model/__init__.py rename to truss/tests/test_data/model_load_failure_test/model/__init__.py diff --git a/truss/test_data/model_load_failure_test/model/model.py b/truss/tests/test_data/model_load_failure_test/model/model.py similarity index 100% rename from truss/test_data/model_load_failure_test/model/model.py rename to truss/tests/test_data/model_load_failure_test/model/model.py diff --git a/truss/test_data/test_truss_server_caching_truss/model/__init__.py b/truss/tests/test_data/patch_ping_test_server/__init__.py similarity index 100% rename from truss/test_data/test_truss_server_caching_truss/model/__init__.py rename to truss/tests/test_data/patch_ping_test_server/__init__.py diff --git a/truss/test_data/patch_ping_test_server/app.py b/truss/tests/test_data/patch_ping_test_server/app.py similarity index 100% rename from truss/test_data/patch_ping_test_server/app.py rename to truss/tests/test_data/patch_ping_test_server/app.py diff --git a/truss/test_data/pima-indians-diabetes.csv b/truss/tests/test_data/pima-indians-diabetes.csv similarity index 100% rename from truss/test_data/pima-indians-diabetes.csv rename to truss/tests/test_data/pima-indians-diabetes.csv diff --git a/truss/test_data/readme_int_example.md b/truss/tests/test_data/readme_int_example.md similarity index 100% rename from truss/test_data/readme_int_example.md rename to truss/tests/test_data/readme_int_example.md diff --git a/truss/test_data/readme_no_example.md b/truss/tests/test_data/readme_no_example.md similarity index 100% rename from truss/test_data/readme_no_example.md rename to truss/tests/test_data/readme_no_example.md diff --git a/truss/test_data/readme_str_example.md b/truss/tests/test_data/readme_str_example.md similarity index 100% rename from truss/test_data/readme_str_example.md rename to truss/tests/test_data/readme_str_example.md diff --git a/truss/test_data/server.Dockerfile b/truss/tests/test_data/server.Dockerfile similarity index 100% rename from truss/test_data/server.Dockerfile rename to truss/tests/test_data/server.Dockerfile diff --git a/truss/test_data/test_truss_with_error/model/__init__.py b/truss/tests/test_data/server_conformance_test_truss/__init__.py similarity index 100% rename from truss/test_data/test_truss_with_error/model/__init__.py rename to truss/tests/test_data/server_conformance_test_truss/__init__.py diff --git a/truss/test_data/server_conformance_test_truss/config.yaml b/truss/tests/test_data/server_conformance_test_truss/config.yaml similarity index 100% rename from truss/test_data/server_conformance_test_truss/config.yaml rename to truss/tests/test_data/server_conformance_test_truss/config.yaml diff --git a/truss/tests/local/__init__.py b/truss/tests/test_data/server_conformance_test_truss/model/__init__.py similarity index 100% rename from truss/tests/local/__init__.py rename to truss/tests/test_data/server_conformance_test_truss/model/__init__.py diff --git a/truss/test_data/server_conformance_test_truss/model/model.py b/truss/tests/test_data/server_conformance_test_truss/model/model.py similarity index 100% rename from truss/test_data/server_conformance_test_truss/model/model.py rename to truss/tests/test_data/server_conformance_test_truss/model/model.py diff --git a/truss/test_data/test_truss/model/dummy b/truss/tests/test_data/test_async_truss/__init__.py similarity index 100% rename from truss/test_data/test_truss/model/dummy rename to truss/tests/test_data/test_async_truss/__init__.py diff --git a/truss/test_data/test_async_truss/config.yaml b/truss/tests/test_data/test_async_truss/config.yaml similarity index 100% rename from truss/test_data/test_async_truss/config.yaml rename to truss/tests/test_data/test_async_truss/config.yaml diff --git a/truss/tests/test_data/test_async_truss/model/__init__.py b/truss/tests/test_data/test_async_truss/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_async_truss/model/model.py b/truss/tests/test_data/test_async_truss/model/model.py similarity index 100% rename from truss/test_data/test_async_truss/model/model.py rename to truss/tests/test_data/test_async_truss/model/model.py diff --git a/truss/tests/test_data/test_basic_truss/__init__.py b/truss/tests/test_data/test_basic_truss/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_basic_truss/config.yaml b/truss/tests/test_data/test_basic_truss/config.yaml similarity index 100% rename from truss/test_data/test_basic_truss/config.yaml rename to truss/tests/test_data/test_basic_truss/config.yaml diff --git a/truss/tests/test_data/test_basic_truss/model/__init__.py b/truss/tests/test_data/test_basic_truss/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_basic_truss/model/model.py b/truss/tests/test_data/test_basic_truss/model/model.py similarity index 100% rename from truss/test_data/test_basic_truss/model/model.py rename to truss/tests/test_data/test_basic_truss/model/model.py diff --git a/truss/tests/test_data/test_build_commands/__init__.py b/truss/tests/test_data/test_build_commands/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_build_commands/config.yaml b/truss/tests/test_data/test_build_commands/config.yaml similarity index 100% rename from truss/test_data/test_build_commands/config.yaml rename to truss/tests/test_data/test_build_commands/config.yaml diff --git a/truss/tests/test_data/test_build_commands/model/__init__.py b/truss/tests/test_data/test_build_commands/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_build_commands/model/model.py b/truss/tests/test_data/test_build_commands/model/model.py similarity index 100% rename from truss/test_data/test_build_commands/model/model.py rename to truss/tests/test_data/test_build_commands/model/model.py diff --git a/truss/tests/test_data/test_build_commands_failure/__init__.py b/truss/tests/test_data/test_build_commands_failure/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_build_commands_failure/config.yaml b/truss/tests/test_data/test_build_commands_failure/config.yaml similarity index 100% rename from truss/test_data/test_build_commands_failure/config.yaml rename to truss/tests/test_data/test_build_commands_failure/config.yaml diff --git a/truss/tests/test_data/test_build_commands_failure/model/__init__.py b/truss/tests/test_data/test_build_commands_failure/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_build_commands_failure/model/model.py b/truss/tests/test_data/test_build_commands_failure/model/model.py similarity index 100% rename from truss/test_data/test_build_commands_failure/model/model.py rename to truss/tests/test_data/test_build_commands_failure/model/model.py diff --git a/truss/tests/test_data/test_concurrency_truss/__init__.py b/truss/tests/test_data/test_concurrency_truss/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_concurrency_truss/config.yaml b/truss/tests/test_data/test_concurrency_truss/config.yaml similarity index 100% rename from truss/test_data/test_concurrency_truss/config.yaml rename to truss/tests/test_data/test_concurrency_truss/config.yaml diff --git a/truss/tests/test_data/test_concurrency_truss/model/__init__.py b/truss/tests/test_data/test_concurrency_truss/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_concurrency_truss/model/model.py b/truss/tests/test_data/test_concurrency_truss/model/model.py similarity index 100% rename from truss/test_data/test_concurrency_truss/model/model.py rename to truss/tests/test_data/test_concurrency_truss/model/model.py diff --git a/truss/tests/test_data/test_docker_server_truss/__init__.py b/truss/tests/test_data/test_docker_server_truss/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_docker_server_truss/config.yaml b/truss/tests/test_data/test_docker_server_truss/config.yaml similarity index 100% rename from truss/test_data/test_docker_server_truss/config.yaml rename to truss/tests/test_data/test_docker_server_truss/config.yaml diff --git a/truss/test_data/test_docker_server_truss/test_docker_image/Dockerfile b/truss/tests/test_data/test_docker_server_truss/test_docker_image/Dockerfile similarity index 100% rename from truss/test_data/test_docker_server_truss/test_docker_image/Dockerfile rename to truss/tests/test_data/test_docker_server_truss/test_docker_image/Dockerfile diff --git a/truss/test_data/test_docker_server_truss/test_docker_image/README.md b/truss/tests/test_data/test_docker_server_truss/test_docker_image/README.md similarity index 100% rename from truss/test_data/test_docker_server_truss/test_docker_image/README.md rename to truss/tests/test_data/test_docker_server_truss/test_docker_image/README.md diff --git a/truss/test_data/test_docker_server_truss/test_docker_image/VERSION b/truss/tests/test_data/test_docker_server_truss/test_docker_image/VERSION similarity index 100% rename from truss/test_data/test_docker_server_truss/test_docker_image/VERSION rename to truss/tests/test_data/test_docker_server_truss/test_docker_image/VERSION diff --git a/truss/tests/test_data/test_docker_server_truss/test_docker_image/__init__.py b/truss/tests/test_data/test_docker_server_truss/test_docker_image/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_docker_server_truss/test_docker_image/app.py b/truss/tests/test_data/test_docker_server_truss/test_docker_image/app.py similarity index 100% rename from truss/test_data/test_docker_server_truss/test_docker_image/app.py rename to truss/tests/test_data/test_docker_server_truss/test_docker_image/app.py diff --git a/truss/test_data/test_docker_server_truss/test_docker_image/build_upload_new_image.sh b/truss/tests/test_data/test_docker_server_truss/test_docker_image/build_upload_new_image.sh similarity index 100% rename from truss/test_data/test_docker_server_truss/test_docker_image/build_upload_new_image.sh rename to truss/tests/test_data/test_docker_server_truss/test_docker_image/build_upload_new_image.sh diff --git a/truss/tests/test_data/test_pyantic_v1/__init__.py b/truss/tests/test_data/test_pyantic_v1/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_pyantic_v1/config.yaml b/truss/tests/test_data/test_pyantic_v1/config.yaml similarity index 100% rename from truss/test_data/test_pyantic_v1/config.yaml rename to truss/tests/test_data/test_pyantic_v1/config.yaml diff --git a/truss/tests/test_data/test_pyantic_v1/model/__init__.py b/truss/tests/test_data/test_pyantic_v1/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_pyantic_v1/model/model.py b/truss/tests/test_data/test_pyantic_v1/model/model.py similarity index 100% rename from truss/test_data/test_pyantic_v1/model/model.py rename to truss/tests/test_data/test_pyantic_v1/model/model.py diff --git a/truss/test_data/test_pyantic_v1/requirements.txt b/truss/tests/test_data/test_pyantic_v1/requirements.txt similarity index 100% rename from truss/test_data/test_pyantic_v1/requirements.txt rename to truss/tests/test_data/test_pyantic_v1/requirements.txt diff --git a/truss/tests/test_data/test_pyantic_v2/__init__.py b/truss/tests/test_data/test_pyantic_v2/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_pyantic_v2/config.yaml b/truss/tests/test_data/test_pyantic_v2/config.yaml similarity index 100% rename from truss/test_data/test_pyantic_v2/config.yaml rename to truss/tests/test_data/test_pyantic_v2/config.yaml diff --git a/truss/tests/test_data/test_pyantic_v2/model/__init__.py b/truss/tests/test_data/test_pyantic_v2/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_pyantic_v2/model/model.py b/truss/tests/test_data/test_pyantic_v2/model/model.py similarity index 100% rename from truss/test_data/test_pyantic_v2/model/model.py rename to truss/tests/test_data/test_pyantic_v2/model/model.py diff --git a/truss/test_data/test_pyantic_v2/requirements.txt b/truss/tests/test_data/test_pyantic_v2/requirements.txt similarity index 100% rename from truss/test_data/test_pyantic_v2/requirements.txt rename to truss/tests/test_data/test_pyantic_v2/requirements.txt diff --git a/truss/tests/test_data/test_requirements_file_truss/__init__.py b/truss/tests/test_data/test_requirements_file_truss/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_requirements_file_truss/config.yaml b/truss/tests/test_data/test_requirements_file_truss/config.yaml similarity index 100% rename from truss/test_data/test_requirements_file_truss/config.yaml rename to truss/tests/test_data/test_requirements_file_truss/config.yaml diff --git a/truss/tests/test_data/test_requirements_file_truss/model/__init__.py b/truss/tests/test_data/test_requirements_file_truss/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_requirements_file_truss/model/model.py b/truss/tests/test_data/test_requirements_file_truss/model/model.py similarity index 100% rename from truss/test_data/test_requirements_file_truss/model/model.py rename to truss/tests/test_data/test_requirements_file_truss/model/model.py diff --git a/truss/test_data/test_requirements_file_truss/requirements.txt b/truss/tests/test_data/test_requirements_file_truss/requirements.txt similarity index 100% rename from truss/test_data/test_requirements_file_truss/requirements.txt rename to truss/tests/test_data/test_requirements_file_truss/requirements.txt diff --git a/truss/tests/test_data/test_streaming_async_generator_truss/__init__.py b/truss/tests/test_data/test_streaming_async_generator_truss/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_streaming_async_generator_truss/config.yaml b/truss/tests/test_data/test_streaming_async_generator_truss/config.yaml similarity index 100% rename from truss/test_data/test_streaming_async_generator_truss/config.yaml rename to truss/tests/test_data/test_streaming_async_generator_truss/config.yaml diff --git a/truss/tests/test_data/test_streaming_async_generator_truss/model/__init__.py b/truss/tests/test_data/test_streaming_async_generator_truss/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_streaming_async_generator_truss/model/model.py b/truss/tests/test_data/test_streaming_async_generator_truss/model/model.py similarity index 100% rename from truss/test_data/test_streaming_async_generator_truss/model/model.py rename to truss/tests/test_data/test_streaming_async_generator_truss/model/model.py diff --git a/truss/tests/test_data/test_streaming_read_timeout/__init__.py b/truss/tests/test_data/test_streaming_read_timeout/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_streaming_read_timeout/config.yaml b/truss/tests/test_data/test_streaming_read_timeout/config.yaml similarity index 100% rename from truss/test_data/test_streaming_read_timeout/config.yaml rename to truss/tests/test_data/test_streaming_read_timeout/config.yaml diff --git a/truss/tests/test_data/test_streaming_read_timeout/model/__init__.py b/truss/tests/test_data/test_streaming_read_timeout/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_streaming_read_timeout/model/model.py b/truss/tests/test_data/test_streaming_read_timeout/model/model.py similarity index 100% rename from truss/test_data/test_streaming_read_timeout/model/model.py rename to truss/tests/test_data/test_streaming_read_timeout/model/model.py diff --git a/truss/tests/test_data/test_streaming_truss/__init__.py b/truss/tests/test_data/test_streaming_truss/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_streaming_truss/config.yaml b/truss/tests/test_data/test_streaming_truss/config.yaml similarity index 100% rename from truss/test_data/test_streaming_truss/config.yaml rename to truss/tests/test_data/test_streaming_truss/config.yaml diff --git a/truss/tests/test_data/test_streaming_truss/model/__init__.py b/truss/tests/test_data/test_streaming_truss/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_streaming_truss/model/model.py b/truss/tests/test_data/test_streaming_truss/model/model.py similarity index 100% rename from truss/test_data/test_streaming_truss/model/model.py rename to truss/tests/test_data/test_streaming_truss/model/model.py diff --git a/truss/tests/test_data/test_streaming_truss_with_error/__init__.py b/truss/tests/test_data/test_streaming_truss_with_error/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_streaming_truss_with_error/config.yaml b/truss/tests/test_data/test_streaming_truss_with_error/config.yaml similarity index 100% rename from truss/test_data/test_streaming_truss_with_error/config.yaml rename to truss/tests/test_data/test_streaming_truss_with_error/config.yaml diff --git a/truss/tests/test_data/test_streaming_truss_with_error/model/__init__.py b/truss/tests/test_data/test_streaming_truss_with_error/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_streaming_truss_with_error/model/model.py b/truss/tests/test_data/test_streaming_truss_with_error/model/model.py similarity index 100% rename from truss/test_data/test_streaming_truss_with_error/model/model.py rename to truss/tests/test_data/test_streaming_truss_with_error/model/model.py diff --git a/truss/tests/test_data/test_streaming_truss_with_error/packages/__init__.py b/truss/tests/test_data/test_streaming_truss_with_error/packages/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_streaming_truss_with_error/packages/helpers_1.py b/truss/tests/test_data/test_streaming_truss_with_error/packages/helpers_1.py similarity index 100% rename from truss/test_data/test_streaming_truss_with_error/packages/helpers_1.py rename to truss/tests/test_data/test_streaming_truss_with_error/packages/helpers_1.py diff --git a/truss/test_data/test_streaming_truss_with_error/packages/helpers_2.py b/truss/tests/test_data/test_streaming_truss_with_error/packages/helpers_2.py similarity index 100% rename from truss/test_data/test_streaming_truss_with_error/packages/helpers_2.py rename to truss/tests/test_data/test_streaming_truss_with_error/packages/helpers_2.py diff --git a/truss/tests/test_data/test_streaming_truss_with_tracing/__init__.py b/truss/tests/test_data/test_streaming_truss_with_tracing/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/tests/test_data/test_streaming_truss_with_tracing/config.yaml b/truss/tests/test_data/test_streaming_truss_with_tracing/config.yaml new file mode 100644 index 000000000..66a8b2e00 --- /dev/null +++ b/truss/tests/test_data/test_streaming_truss_with_tracing/config.yaml @@ -0,0 +1,43 @@ +apply_library_patches: true +base_image: null +build: + arguments: {} + model_server: TrussServer + secret_to_path_mapping: {} +build_commands: [] +bundled_packages_dir: packages +data_dir: data +description: null +docker_server: null +environment_variables: + OTEL_TRACING_NDJSON_FILE: /tmp/otel_traces.ndjson +examples_filename: examples.yaml +external_data: null +external_package_dirs: [] +input_type: Any +live_reload: false +model_cache: [] +model_class_filename: model.py +model_class_name: Model +model_framework: custom +model_metadata: {} +model_module_dir: model +model_name: Test Streaming +model_type: Model +python_version: py39 +requirements: [] +requirements_file: null +resources: + accelerator: null + cpu: '1' + memory: 2Gi + use_gpu: false +runtime: + enable_tracing_data: false + num_workers: 1 + predict_concurrency: 1 + streaming_read_timeout: 60 +secrets: {} +spec_version: '2.0' +system_packages: [] +trt_llm: null diff --git a/truss/tests/test_data/test_streaming_truss_with_tracing/model/__init__.py b/truss/tests/test_data/test_streaming_truss_with_tracing/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_streaming_truss_with_tracing/model/model.py b/truss/tests/test_data/test_streaming_truss_with_tracing/model/model.py similarity index 100% rename from truss/test_data/test_streaming_truss_with_tracing/model/model.py rename to truss/tests/test_data/test_streaming_truss_with_tracing/model/model.py diff --git a/truss/tests/test_data/test_trt_llm_truss/__init__.py b/truss/tests/test_data/test_trt_llm_truss/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_trt_llm_truss/config.yaml b/truss/tests/test_data/test_trt_llm_truss/config.yaml similarity index 100% rename from truss/test_data/test_trt_llm_truss/config.yaml rename to truss/tests/test_data/test_trt_llm_truss/config.yaml diff --git a/truss/tests/test_data/test_trt_llm_truss/model/__init__.py b/truss/tests/test_data/test_trt_llm_truss/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_trt_llm_truss/model/model.py b/truss/tests/test_data/test_trt_llm_truss/model/model.py similarity index 100% rename from truss/test_data/test_trt_llm_truss/model/model.py rename to truss/tests/test_data/test_trt_llm_truss/model/model.py diff --git a/truss/tests/test_data/test_truss/__init__.py b/truss/tests/test_data/test_truss/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_truss/config.yaml b/truss/tests/test_data/test_truss/config.yaml similarity index 100% rename from truss/test_data/test_truss/config.yaml rename to truss/tests/test_data/test_truss/config.yaml diff --git a/truss/test_data/test_truss/examples.yaml b/truss/tests/test_data/test_truss/examples.yaml similarity index 100% rename from truss/test_data/test_truss/examples.yaml rename to truss/tests/test_data/test_truss/examples.yaml diff --git a/truss/tests/test_data/test_truss/model/__init__.py b/truss/tests/test_data/test_truss/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/tests/test_data/test_truss/model/dummy b/truss/tests/test_data/test_truss/model/dummy new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_truss/model/model.py b/truss/tests/test_data/test_truss/model/model.py similarity index 100% rename from truss/test_data/test_truss/model/model.py rename to truss/tests/test_data/test_truss/model/model.py diff --git a/truss/tests/test_data/test_truss/packages/__init__.py b/truss/tests/test_data/test_truss/packages/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/tests/test_data/test_truss/packages/test_package/__init__.py b/truss/tests/test_data/test_truss/packages/test_package/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_truss/packages/test_package/test.py b/truss/tests/test_data/test_truss/packages/test_package/test.py similarity index 100% rename from truss/test_data/test_truss/packages/test_package/test.py rename to truss/tests/test_data/test_truss/packages/test_package/test.py diff --git a/truss/tests/test_data/test_truss_server_caching_truss/__init__.py b/truss/tests/test_data/test_truss_server_caching_truss/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_truss_server_caching_truss/config.yaml b/truss/tests/test_data/test_truss_server_caching_truss/config.yaml similarity index 100% rename from truss/test_data/test_truss_server_caching_truss/config.yaml rename to truss/tests/test_data/test_truss_server_caching_truss/config.yaml diff --git a/truss/tests/test_data/test_truss_server_caching_truss/model/__init__.py b/truss/tests/test_data/test_truss_server_caching_truss/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_truss_server_caching_truss/model/model.py b/truss/tests/test_data/test_truss_server_caching_truss/model/model.py similarity index 100% rename from truss/test_data/test_truss_server_caching_truss/model/model.py rename to truss/tests/test_data/test_truss_server_caching_truss/model/model.py diff --git a/truss/tests/test_data/test_truss_with_error/__init__.py b/truss/tests/test_data/test_truss_with_error/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_truss_with_error/config.yaml b/truss/tests/test_data/test_truss_with_error/config.yaml similarity index 100% rename from truss/test_data/test_truss_with_error/config.yaml rename to truss/tests/test_data/test_truss_with_error/config.yaml diff --git a/truss/tests/test_data/test_truss_with_error/model/__init__.py b/truss/tests/test_data/test_truss_with_error/model/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_truss_with_error/model/model.py b/truss/tests/test_data/test_truss_with_error/model/model.py similarity index 100% rename from truss/test_data/test_truss_with_error/model/model.py rename to truss/tests/test_data/test_truss_with_error/model/model.py diff --git a/truss/tests/test_data/test_truss_with_error/packages/__init__.py b/truss/tests/test_data/test_truss_with_error/packages/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/test_data/test_truss_with_error/packages/helpers_1.py b/truss/tests/test_data/test_truss_with_error/packages/helpers_1.py similarity index 100% rename from truss/test_data/test_truss_with_error/packages/helpers_1.py rename to truss/tests/test_data/test_truss_with_error/packages/helpers_1.py diff --git a/truss/test_data/test_truss_with_error/packages/helpers_2.py b/truss/tests/test_data/test_truss_with_error/packages/helpers_2.py similarity index 100% rename from truss/test_data/test_truss_with_error/packages/helpers_2.py rename to truss/tests/test_data/test_truss_with_error/packages/helpers_2.py diff --git a/truss/tests/test_docker.py b/truss/tests/test_docker.py index a127d3f57..0efd045d0 100644 --- a/truss/tests/test_docker.py +++ b/truss/tests/test_docker.py @@ -1,7 +1,7 @@ import pytest from python_on_whales import docker -from truss.docker import get_urls_from_container +from truss.util.docker import get_urls_from_container @pytest.fixture diff --git a/truss/tests/test_model_inference.py b/truss/tests/test_model_inference.py index 04db1b7fa..de8706cb2 100644 --- a/truss/tests/test_model_inference.py +++ b/truss/tests/test_model_inference.py @@ -20,11 +20,11 @@ from opentelemetry import context, trace from requests.exceptions import RequestException +from truss.base.truss_config import map_to_supported_python_version from truss.local.local_config_handler import LocalConfigHandler -from truss.model_inference import map_to_supported_python_version from truss.tests.helpers import create_truss from truss.tests.test_testing_utilities_for_other_tests import ensure_kill_all -from truss.truss_handle import TrussHandle +from truss.truss_handle.truss_handle import TrussHandle logger = logging.getLogger(__name__) @@ -94,10 +94,9 @@ def test_map_to_supported_python_version(python_version, expected_python_version @pytest.mark.integration -def test_model_load_failure_truss(): +def test_model_load_failure_truss(test_data_path): with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "model_load_failure_test" + truss_dir = test_data_path / "model_load_failure_test" tr = TrussHandle(truss_dir) _ = tr.docker_run(local_port=8090, detach=True, wait_for_server_ready=False) @@ -149,11 +148,10 @@ def _test_invocations(expected_code): @pytest.mark.integration -def test_concurrency_truss(): +def test_concurrency_truss(test_data_path): # Tests that concurrency limits work correctly with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "test_concurrency_truss" + truss_dir = test_data_path / "test_concurrency_truss" tr = TrussHandle(truss_dir) _ = tr.docker_run(local_port=8090, detach=True, wait_for_server_ready=True) @@ -181,10 +179,9 @@ def make_request(): @pytest.mark.integration -def test_requirements_file_truss(): +def test_requirements_file_truss(test_data_path): with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "test_requirements_file_truss" + truss_dir = test_data_path / "test_requirements_file_truss" tr = TrussHandle(truss_dir) _ = tr.docker_run(local_port=8090, detach=True, wait_for_server_ready=True) @@ -196,10 +193,9 @@ def test_requirements_file_truss(): @pytest.mark.integration @pytest.mark.parametrize("pydantic_major_version", ["1", "2"]) -def test_requirements_pydantic(pydantic_major_version): +def test_requirements_pydantic(test_data_path, pydantic_major_version): with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / f"test_pyantic_v{pydantic_major_version}" + truss_dir = test_data_path / f"test_pyantic_v{pydantic_major_version}" tr = TrussHandle(truss_dir) _ = tr.docker_run(local_port=8090, detach=True, wait_for_server_ready=True) @@ -209,10 +205,9 @@ def test_requirements_pydantic(pydantic_major_version): @pytest.mark.integration -def test_async_truss(): +def test_async_truss(test_data_path): with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "test_async_truss" + truss_dir = test_data_path / "test_async_truss" tr = TrussHandle(truss_dir) _ = tr.docker_run(local_port=8090, detach=True, wait_for_server_ready=True) @@ -224,10 +219,9 @@ def test_async_truss(): @pytest.mark.integration -def test_async_streaming(): +def test_async_streaming(test_data_path): with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "test_streaming_async_generator_truss" + truss_dir = test_data_path / "test_streaming_async_generator_truss" tr = TrussHandle(truss_dir) _ = tr.docker_run(local_port=8090, detach=True, wait_for_server_ready=True) @@ -248,10 +242,9 @@ def test_async_streaming(): @pytest.mark.integration -def test_async_streaming_timeout(): +def test_async_streaming_timeout(test_data_path): with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "test_streaming_read_timeout" + truss_dir = test_data_path / "test_streaming_read_timeout" tr = TrussHandle(truss_dir) container = tr.docker_run( local_port=8090, detach=True, wait_for_server_ready=True @@ -274,10 +267,9 @@ def test_async_streaming_timeout(): @pytest.mark.integration -def test_streaming_with_error_and_stacktrace(): +def test_streaming_with_error_and_stacktrace(test_data_path): with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "test_streaming_truss_with_error" + truss_dir = test_data_path / "test_streaming_truss_with_error" tr = TrussHandle(truss_dir) container = tr.docker_run( local_port=8090, detach=True, wait_for_server_ready=True @@ -659,10 +651,9 @@ def predict(self, request): @pytest.mark.integration -def test_truss_with_error_stacktrace(): +def test_truss_with_error_stacktrace(test_data_path): with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "test_truss_with_error" + truss_dir = test_data_path / "test_truss_with_error" tr = TrussHandle(truss_dir) container = tr.docker_run( local_port=8090, detach=True, wait_for_server_ready=True @@ -694,10 +685,9 @@ def test_truss_with_error_stacktrace(): @pytest.mark.integration -def test_slow_truss(): +def test_slow_truss(test_data_path): with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "server_conformance_test_truss" + truss_dir = test_data_path / "server_conformance_test_truss" tr = TrussHandle(truss_dir) _ = tr.docker_run(local_port=8090, detach=True, wait_for_server_ready=False) @@ -903,10 +893,9 @@ def _make_otel_headers() -> Mapping[str, str]: @pytest.mark.integration @pytest.mark.parametrize("enable_tracing_data", [True, False]) -def test_streaming_truss_with_user_tracing(enable_tracing_data): +def test_streaming_truss_with_user_tracing(test_data_path, enable_tracing_data): with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "test_streaming_truss_with_tracing" + truss_dir = test_data_path / "test_streaming_truss_with_tracing" tr = TrussHandle(truss_dir) def enable_gpu_fn(conf): diff --git a/truss/tests/test_model_schema.py b/truss/tests/test_model_schema.py index c786b1b6f..a95654465 100644 --- a/truss/tests/test_model_schema.py +++ b/truss/tests/test_model_schema.py @@ -8,7 +8,7 @@ from truss.templates.shared import serialization from truss.tests.helpers import create_truss from truss.tests.test_testing_utilities_for_other_tests import ensure_kill_all -from truss.truss_handle import TrussHandle +from truss.truss_handle.truss_handle import TrussHandle DEFAULT_CONFIG = """model_name: test-truss""" TRUSS_SERVER_ADDR = "http://localhost:8090" @@ -17,10 +17,8 @@ @pytest.mark.integration -def test_truss_with_no_annotations(): - truss_root = Path(__file__).parent.parent.parent.resolve() - - truss_dir = truss_root / "truss" / "test_data" / "test_basic_truss" +def test_truss_with_no_annotations(test_data_path): + truss_dir = test_data_path / "test_basic_truss" tr = TrussHandle(truss_dir) @@ -97,10 +95,8 @@ def predict(self, request): @pytest.mark.integration -def test_truss_with_annotated_inputs_outputs(): - truss_root = Path(__file__).parent.parent.resolve() - - truss_dir = truss_root / "test_data" / "annotated_types_truss" +def test_truss_with_annotated_inputs_outputs(test_data_path): + truss_dir = test_data_path / "annotated_types_truss" tr = TrussHandle(truss_dir) diff --git a/truss/tests/test_testing_utilities_for_other_tests.py b/truss/tests/test_testing_utilities_for_other_tests.py index 7ec085a84..f7f10edae 100644 --- a/truss/tests/test_testing_utilities_for_other_tests.py +++ b/truss/tests/test_testing_utilities_for_other_tests.py @@ -7,9 +7,8 @@ import time from contextlib import contextmanager -from truss.build import kill_all -from truss.constants import TRUSS -from truss.docker import get_containers +from truss.base.constants import TRUSS +from truss.util.docker import get_containers, kill_all DISK_SPACE_LOW_PERCENTAGE = 20 diff --git a/truss/tests/test_truss_gatherer.py b/truss/tests/test_truss_gatherer.py index 2e660d906..5a62d94ca 100644 --- a/truss/tests/test_truss_gatherer.py +++ b/truss/tests/test_truss_gatherer.py @@ -1,8 +1,8 @@ from pathlib import Path from typing import List -from truss.patch.dir_signature import directory_content_signature -from truss.truss_gatherer import gather +from truss.truss_handle.patch.dir_signature import directory_content_signature +from truss.truss_handle.truss_gatherer import gather def test_gather(custom_model_with_external_package): diff --git a/truss/tests/test_truss_handle.py b/truss/tests/test_truss_handle.py index 5b74c349f..7f29ee5aa 100644 --- a/truss/tests/test_truss_handle.py +++ b/truss/tests/test_truss_handle.py @@ -8,11 +8,10 @@ from python_on_whales.exceptions import DockerException from tenacity import RetryError -from truss.custom_types import Example, PatchRequest -from truss.docker import Docker, DockerStates -from truss.errors import ContainerIsDownError, ContainerNotFoundError +from truss.base.custom_types import Example +from truss.base.errors import ContainerIsDownError, ContainerNotFoundError +from truss.base.truss_config import map_local_to_supported_python_version from truss.local.local_config_handler import LocalConfigHandler -from truss.model_inference import infer_python_version, map_to_supported_python_version from truss.templates.control.control.helpers.custom_types import ( Action, ModelCodePatch, @@ -23,7 +22,9 @@ ensure_kill_all, kill_all_with_retries, ) -from truss.truss_handle import TrussHandle, wait_for_truss +from truss.truss_handle.patch.custom_types import PatchRequest +from truss.truss_handle.truss_handle import TrussHandle, wait_for_truss +from truss.util.docker import Docker, DockerStates def test_spec(custom_model_truss_dir_with_pre_and_post): @@ -58,15 +59,18 @@ def test_server_predict(custom_model_truss_dir_with_pre_and_post): assert resp == {"predictions": [4, 5, 6, 7]} -def test_readme_generation_int_example(custom_model_truss_dir_with_pre_and_post): +def test_readme_generation_int_example( + test_data_path, custom_model_truss_dir_with_pre_and_post +): th = TrussHandle(custom_model_truss_dir_with_pre_and_post) readme_contents = th.generate_readme() readme_contents = readme_contents.replace("\n", "") - correct_readme_contents = _read_readme("readme_int_example.md") + correct_readme_contents = _read_readme(test_data_path / "readme_int_example.md") assert readme_contents == correct_readme_contents def test_readme_generation_no_example( + test_data_path, custom_model_truss_dir_with_pre_and_post_no_example, ): th = TrussHandle(custom_model_truss_dir_with_pre_and_post_no_example) @@ -75,17 +79,18 @@ def test_readme_generation_no_example( os.remove(th._spec.examples_path) readme_contents = th.generate_readme() readme_contents = readme_contents.replace("\n", "") - correct_readme_contents = _read_readme("readme_no_example.md") + correct_readme_contents = _read_readme(test_data_path / "readme_no_example.md") assert readme_contents == correct_readme_contents def test_readme_generation_str_example( + test_data_path, custom_model_truss_dir_with_pre_and_post_str_example, ): th = TrussHandle(custom_model_truss_dir_with_pre_and_post_str_example) readme_contents = th.generate_readme() readme_contents = readme_contents.replace("\n", "") - correct_readme_contents = _read_readme("readme_str_example.md") + correct_readme_contents = _read_readme(test_data_path / "readme_str_example.md") assert readme_contents == correct_readme_contents @@ -461,9 +466,8 @@ def test_add_environment_variable(custom_model_truss_dir_with_pre_and_post): @pytest.mark.integration -def test_build_commands(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "test_build_commands" +def test_build_commands(test_data_path): + truss_dir = test_data_path / "test_build_commands" tr = TrussHandle(truss_dir) with ensure_kill_all(): r1 = tr.docker_predict([1, 2]) @@ -471,9 +475,8 @@ def test_build_commands(): @pytest.mark.integration -def test_build_commands_failure(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - truss_dir = truss_root / "test_data" / "test_build_commands_failure" +def test_build_commands_failure(test_data_path): + truss_dir = test_data_path / "test_build_commands_failure" tr = TrussHandle(truss_dir) try: tr.docker_run(local_port=8090, detach=True, wait_for_server_ready=True) @@ -635,7 +638,7 @@ def predict(self, model_input): assert len(th.get_all_docker_images()) == orig_num_truss_images + 1 -@patch("truss.truss_handle.directory_content_hash") +@patch("truss.truss_handle.truss_handle.directory_content_hash") def test_truss_hash_caching_based_on_max_mod_time( directory_content_patcher, custom_model_truss_dir, @@ -654,14 +657,14 @@ def test_truss_hash_caching_based_on_max_mod_time( directory_content_patcher.call_count == 2 -@patch("truss.truss_handle.get_container_state") +@patch("truss.truss_handle.truss_handle.get_container_state") def test_container_oom_caught_during_waiting(container_state_mock): container_state_mock.return_value = DockerStates.OOMKILLED with pytest.raises(ContainerIsDownError): wait_for_truss(url="localhost:8000", container=MagicMock()) -@patch("truss.truss_handle.get_container_state") +@patch("truss.truss_handle.truss_handle.get_container_state") @pytest.mark.integration def test_container_stuck_in_created(container_state_mock): container_state_mock.return_value = DockerStates.CREATED @@ -815,15 +818,13 @@ def verify_environment_variable_on_container( assert needle in resp.splitlines() -def _read_readme(filename: str) -> str: - readme_correct_path = Path(__file__).parent.parent / "test_data" / filename - readme_contents = readme_correct_path.open().read().replace("\n", "") - return readme_contents +def _read_readme(readme_correct_path: Path) -> str: + return readme_correct_path.open().read().replace("\n", "") def generate_default_config(): # The test fixture varies with host version. - python_version = map_to_supported_python_version(infer_python_version()) + python_version = map_local_to_supported_python_version() config = { "build_commands": [], "environment_variables": {}, diff --git a/truss/tests/test_trussless_docker_server.py b/truss/tests/test_trussless_docker_server.py index 0ee6207a5..f703f99de 100644 --- a/truss/tests/test_trussless_docker_server.py +++ b/truss/tests/test_trussless_docker_server.py @@ -1,19 +1,15 @@ -from pathlib import Path - import pytest import requests from truss.local.local_config_handler import LocalConfigHandler from truss.tests.test_testing_utilities_for_other_tests import ensure_kill_all -from truss.truss_handle import TrussHandle +from truss.truss_handle.truss_handle import TrussHandle @pytest.mark.integration -def test_docker_server_truss(): +def test_docker_server_truss(test_data_path): with ensure_kill_all(): - truss_root = Path(__file__).parent.parent.parent.resolve() / "truss" - - truss_dir = truss_root / "test_data" / "test_docker_server_truss" + truss_dir = test_data_path / "test_docker_server_truss" tr = TrussHandle(truss_dir) LocalConfigHandler.set_secret("hf_access_token", "123") diff --git a/truss/tests/test_util.py b/truss/tests/test_util.py index 42727c78b..abed75d95 100644 --- a/truss/tests/test_util.py +++ b/truss/tests/test_util.py @@ -3,7 +3,7 @@ import requests_mock -from truss.truss_config import ExternalData +from truss.base.truss_config import ExternalData from truss.util.download import download_external_data TEST_DOWNLOAD_URL = "http://example.com/some-download-url" diff --git a/truss/tests/test_validation.py b/truss/tests/test_validation.py index 27e0e02b9..8a8e1b319 100644 --- a/truss/tests/test_validation.py +++ b/truss/tests/test_validation.py @@ -1,7 +1,7 @@ import pytest -from truss.errors import ValidationError -from truss.validation import ( +from truss.base.errors import ValidationError +from truss.base.validation import ( validate_cpu_spec, validate_memory_spec, validate_secret_name, diff --git a/truss/tests/trt_llm/test_validation.py b/truss/tests/trt_llm/test_validation.py index 41011904a..0cba5b31e 100644 --- a/truss/tests/trt_llm/test_validation.py +++ b/truss/tests/trt_llm/test_validation.py @@ -1,7 +1,7 @@ import pytest -from truss.errors import ValidationError +from truss.base.errors import ValidationError +from truss.base.truss_spec import TrussSpec from truss.trt_llm.validation import _verify_has_class_init_arg, validate -from truss.truss_spec import TrussSpec @pytest.mark.parametrize( diff --git a/truss/tests/util/test_config_checks.py b/truss/tests/util/test_config_checks.py index bc46472bd..65154de60 100644 --- a/truss/tests/util/test_config_checks.py +++ b/truss/tests/util/test_config_checks.py @@ -1,15 +1,15 @@ from unittest.mock import patch import pytest -from truss.constants import TRTLLM_MIN_MEMORY_REQUEST_GI -from truss.truss_handle import TrussHandle -from truss.util.config_checks import ( +from truss.base.constants import TRTLLM_MIN_MEMORY_REQUEST_GI +from truss.trt_llm.config_checks import ( check_and_update_memory_for_trt_llm_builder, check_secrets_for_trt_llm_builder, ) +from truss.truss_handle.truss_handle import TrussHandle -@patch("truss.util.config_checks._is_model_public") +@patch("truss.trt_llm.config_checks._is_model_public") @pytest.mark.parametrize( "has_secret, is_model_public, expected_result", [ diff --git a/truss/tests/util/test_path.py b/truss/tests/util/test_path.py index 4764801ce..6f4e6bd56 100644 --- a/truss/tests/util/test_path.py +++ b/truss/tests/util/test_path.py @@ -3,10 +3,10 @@ import time from pathlib import Path -from truss import load from truss.contexts.image_builder.serving_image_builder import ( ServingImageBuilderContext, ) +from truss.truss_handle.build import load from truss.util import path diff --git a/truss/util/config_checks.py b/truss/trt_llm/config_checks.py similarity index 90% rename from truss/util/config_checks.py rename to truss/trt_llm/config_checks.py index a9683e353..fc6964151 100644 --- a/truss/util/config_checks.py +++ b/truss/trt_llm/config_checks.py @@ -1,11 +1,11 @@ import requests -from truss.config.trt_llm import CheckpointSource -from truss.constants import ( +from truss.base.constants import ( HF_ACCESS_TOKEN_KEY, HF_MODELS_API_URL, TRTLLM_MIN_MEMORY_REQUEST_GI, ) -from truss.truss_handle import TrussHandle +from truss.base.trt_llm_config import CheckpointSource +from truss.truss_handle.truss_handle import TrussHandle def check_secrets_for_trt_llm_builder(tr: TrussHandle) -> bool: diff --git a/truss/trt_llm/validation.py b/truss/trt_llm/validation.py index d4bd2c659..32070bf54 100644 --- a/truss/trt_llm/validation.py +++ b/truss/trt_llm/validation.py @@ -1,7 +1,7 @@ import ast -from truss.errors import ValidationError -from truss.truss_spec import TrussSpec +from truss.base.errors import ValidationError +from truss.base.truss_spec import TrussSpec def validate(truss_spec: TrussSpec): diff --git a/truss/truss_handle/__init__.py b/truss/truss_handle/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/build.py b/truss/truss_handle/build.py similarity index 83% rename from truss/build.py rename to truss/truss_handle/build.py index e7202c5ba..5eae8821d 100644 --- a/truss/build.py +++ b/truss/truss_handle/build.py @@ -6,12 +6,14 @@ import yaml -from truss.constants import CONFIG_FILE, TEMPLATES_DIR, TRUSS -from truss.docker import kill_containers -from truss.model_inference import infer_python_version, map_to_supported_python_version -from truss.notebook import is_notebook_or_ipython -from truss.truss_config import Build, TrussConfig -from truss.truss_handle import TrussHandle +from truss.base.constants import CONFIG_FILE, TEMPLATES_DIR +from truss.base.truss_config import ( + Build, + TrussConfig, + map_local_to_supported_python_version, +) +from truss.truss_handle.truss_handle import TrussHandle +from truss.util.notebook import is_notebook_or_ipython from truss.util.path import build_truss_target_directory, copy_tree_path logger: logging.Logger = logging.getLogger(__name__) @@ -21,7 +23,7 @@ logger.addHandler(logging.StreamHandler(sys.stdout)) -def populate_target_directory( +def _populate_target_directory( config: TrussConfig, target_directory_path: Optional[str] = None, template: str = "custom", @@ -74,13 +76,13 @@ def init( """ config = TrussConfig( model_name=model_name, - python_version=map_to_supported_python_version(infer_python_version()), + python_version=map_local_to_supported_python_version(), ) if build_config: config.build = build_config - target_directory_path = populate_target_directory( + target_directory_path = _populate_target_directory( config=config, target_directory_path=target_directory, populate_dirs=True, @@ -103,13 +105,6 @@ def load(truss_directory: str) -> TrussHandle: return TrussHandle(Path(truss_directory)) -def from_directory(*args, **kwargs): - logger.warn( - "DeprecationWarning: from_directory() is deprecated. Use load() instead." - ) - return load(*args, **kwargs) - - def cleanup() -> None: """ Cleans up .truss directory. @@ -138,7 +133,3 @@ def _update_truss_props( if requirements_file is not None: scaf.update_requirements_from_file(requirements_file) - - -def kill_all() -> None: - kill_containers({TRUSS: True}) diff --git a/truss/decorators.py b/truss/truss_handle/decorators.py similarity index 84% rename from truss/decorators.py rename to truss/truss_handle/decorators.py index bfd672cf0..a0620413b 100644 --- a/truss/decorators.py +++ b/truss/truss_handle/decorators.py @@ -1,6 +1,6 @@ def proxy_to_shadow_if_scattered(func): def wrapper(*args, **kwargs): - from truss.truss_handle import TrussHandle + from truss.truss_handle.truss_handle import TrussHandle truss_handle = args[0] if not truss_handle.is_scattered(): diff --git a/truss/truss_handle/patch/__init__.py b/truss/truss_handle/patch/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/truss/patch/calc_patch.py b/truss/truss_handle/patch/calc_patch.py similarity index 96% rename from truss/patch/calc_patch.py rename to truss/truss_handle/patch/calc_patch.py index a66905dbc..69346e6f1 100644 --- a/truss/patch/calc_patch.py +++ b/truss/truss_handle/patch/calc_patch.py @@ -3,9 +3,10 @@ from typing import Dict, List, Optional, Set import yaml -from truss.constants import CONFIG_FILE -from truss.patch.custom_types import ChangedPaths, TrussSignature -from truss.patch.hash import file_content_hash_str + +from truss.base.constants import CONFIG_FILE +from truss.base.truss_config import ExternalData, TrussConfig +from truss.base.truss_spec import TrussSpec from truss.templates.control.control.helpers.custom_types import ( Action, ConfigPatch, @@ -25,8 +26,8 @@ from truss.templates.control.control.helpers.truss_patch.system_packages import ( system_packages_set, ) -from truss.truss_config import ExternalData, TrussConfig -from truss.truss_spec import TrussSpec +from truss.truss_handle.patch.custom_types import ChangedPaths, TrussSignature +from truss.truss_handle.patch.hash import file_content_hash_str from truss.util.path import get_ignored_relative_paths logger: logging.Logger = logging.getLogger(__name__) @@ -150,7 +151,7 @@ def _under_unsupported_patch_dir(path: str) -> bool: # or from the config file's path. In any case, we only want to calculate these # patches once. has_calculated_config = True - config_patches = calc_config_patches( + config_patches = _calc_config_patches( truss_dir, previous_truss_signature, prev_config, new_config ) if config_patches: @@ -198,9 +199,11 @@ def _calc_changed_paths( root_relative_new_paths = set( (str(path.relative_to(root)) for path in root.glob("**/*")) ) - unignored_new_paths = calc_unignored_paths(root_relative_new_paths, ignore_patterns) + unignored_new_paths = _calc_unignored_paths( + root_relative_new_paths, ignore_patterns + ) previous_root_relative_paths = set(previous_root_path_content_hashes.keys()) - unignored_prev_paths = calc_unignored_paths( + unignored_prev_paths = _calc_unignored_paths( previous_root_relative_paths, ignore_patterns ) @@ -224,7 +227,7 @@ def _calc_changed_paths( } -def calc_unignored_paths( +def _calc_unignored_paths( root_relative_paths: Set[str], ignore_patterns: Optional[List[str]] = None, ) -> Set[str]: @@ -234,7 +237,7 @@ def calc_unignored_paths( return root_relative_paths - ignored_paths # type: ignore -def calc_config_patches( +def _calc_config_patches( truss_dir: Path, prev_signature: TrussSignature, prev_config: TrussConfig, @@ -247,7 +250,7 @@ def calc_config_patches( """ try: config_patches = _calc_general_config_patches(prev_config, new_config) - python_requirements_patches = calc_requirements_patches( + python_requirements_patches = _calc_requirements_patches( truss_dir, prev_signature, prev_config, new_config ) system_package_patches = _calc_system_packages_patches(prev_config, new_config) @@ -340,7 +343,7 @@ def _calc_external_data_patches( return patches -def calc_requirements_patches( +def _calc_requirements_patches( truss_dir: Path, prev_signature: TrussSignature, prev_config: TrussConfig, diff --git a/truss/patch/constants.py b/truss/truss_handle/patch/constants.py similarity index 100% rename from truss/patch/constants.py rename to truss/truss_handle/patch/constants.py diff --git a/truss/custom_types.py b/truss/truss_handle/patch/custom_types.py similarity index 64% rename from truss/custom_types.py rename to truss/truss_handle/patch/custom_types.py index d44ba9deb..6528697e1 100644 --- a/truss/custom_types.py +++ b/truss/truss_handle/patch/custom_types.py @@ -1,43 +1,44 @@ -from dataclasses import dataclass -from enum import Enum -from typing import Any, Dict, List +from dataclasses import dataclass, field +from typing import Dict, List from pydantic import BaseModel -from truss.patch.custom_types import TrussSignature from truss.templates.control.control.helpers.custom_types import Patch -class ModelFrameworkType(Enum): - SKLEARN = "sklearn" - TENSORFLOW = "tensorflow" - KERAS = "keras" - PYTORCH = "pytorch" - HUGGINGFACE_TRANSFORMER = "huggingface_transformer" - XGBOOST = "xgboost" - LIGHTGBM = "lightgbm" - MLFLOW = "mlflow" - CUSTOM = "custom" - - @dataclass -class Example: - name: str - input: Any +class TrussSignature: + """Truss signature stores information for calculating patches for future + changes to Truss. - @staticmethod - def from_dict(example_dict): - return Example( - name=example_dict["name"], - input=example_dict["input"], - ) + Currently, it stores hashes of all of the paths in the truss directory excluding the data dir, + and the truss config contents. Path hashes allow calculating added/updated/removes + paths in future trusses compared to this. Config contents allow calculating + config changes, such as add/update/remove of python requirements etc. + """ + + content_hashes_by_path: Dict[str, str] + config: str + requirements_file_requirements: List[str] = field(default_factory=list) def to_dict(self) -> dict: return { - "name": self.name, - "input": self.input, + "content_hashes_by_path": self.content_hashes_by_path, + "config": self.config, + "requirements_file_requirements": self.requirements_file_requirements, } + @staticmethod + def from_dict(d) -> "TrussSignature": + return TrussSignature( + content_hashes_by_path=d["content_hashes_by_path"], + config=d["config"], + requirements_file_requirements=d.get("requirements_file_requirements", []), + ) + + +ChangedPaths = Dict[str, List[str]] + @dataclass class PatchDetails: diff --git a/truss/patch/dir_signature.py b/truss/truss_handle/patch/dir_signature.py similarity index 93% rename from truss/patch/dir_signature.py rename to truss/truss_handle/patch/dir_signature.py index 9bc8aad13..0ab9d12e0 100644 --- a/truss/patch/dir_signature.py +++ b/truss/truss_handle/patch/dir_signature.py @@ -1,7 +1,7 @@ from pathlib import Path from typing import Dict, List, Optional -from truss.patch.hash import file_content_hash_str +from truss.truss_handle.patch.hash import file_content_hash_str from truss.util.path import get_unignored_relative_paths_from_root diff --git a/truss/patch/hash.py b/truss/truss_handle/patch/hash.py similarity index 99% rename from truss/patch/hash.py rename to truss/truss_handle/patch/hash.py index bdd25e054..fb4e7e51d 100644 --- a/truss/patch/hash.py +++ b/truss/truss_handle/patch/hash.py @@ -2,6 +2,7 @@ from typing import Any, List, Optional from blake3 import blake3 + from truss.util.path import get_unignored_relative_paths_from_root diff --git a/truss/patch/local_truss_patch_applier.py b/truss/truss_handle/patch/local_truss_patch_applier.py similarity index 98% rename from truss/patch/local_truss_patch_applier.py rename to truss/truss_handle/patch/local_truss_patch_applier.py index 1c4ec8a82..0b57991c4 100644 --- a/truss/patch/local_truss_patch_applier.py +++ b/truss/truss_handle/patch/local_truss_patch_applier.py @@ -3,6 +3,7 @@ from pathlib import Path from typing import List +from truss.base.truss_config import TrussConfig from truss.templates.control.control.helpers.custom_types import ( Action, ModelCodePatch, @@ -14,7 +15,6 @@ from truss.templates.control.control.helpers.truss_patch.model_code_patch_applier import ( apply_code_patch, ) -from truss.truss_config import TrussConfig class LocalTrussPatchApplier: diff --git a/truss/patch/signature.py b/truss/truss_handle/patch/signature.py similarity index 72% rename from truss/patch/signature.py rename to truss/truss_handle/patch/signature.py index 21cbac48f..a35f4921d 100644 --- a/truss/patch/signature.py +++ b/truss/truss_handle/patch/signature.py @@ -1,10 +1,10 @@ from pathlib import Path from typing import List, Optional -from truss.constants import CONFIG_FILE -from truss.patch.custom_types import TrussSignature -from truss.patch.dir_signature import directory_content_signature -from truss.truss_config import TrussConfig +from truss.base.constants import CONFIG_FILE +from truss.base.truss_config import TrussConfig +from truss.truss_handle.patch.custom_types import TrussSignature +from truss.truss_handle.patch.dir_signature import directory_content_signature def calc_truss_signature( diff --git a/truss/patch/truss_dir_patch_applier.py b/truss/truss_handle/patch/truss_dir_patch_applier.py similarity index 98% rename from truss/patch/truss_dir_patch_applier.py rename to truss/truss_handle/patch/truss_dir_patch_applier.py index da08b6e83..873423825 100644 --- a/truss/patch/truss_dir_patch_applier.py +++ b/truss/truss_handle/patch/truss_dir_patch_applier.py @@ -2,6 +2,7 @@ from pathlib import Path from typing import List +from truss.base.truss_config import TrussConfig from truss.templates.control.control.helpers.custom_types import ( Action, ConfigPatch, @@ -23,7 +24,6 @@ from truss.templates.control.control.helpers.truss_patch.system_packages import ( system_packages_set, ) -from truss.truss_config import TrussConfig class TrussDirPatchApplier: diff --git a/truss/readme_generator.py b/truss/truss_handle/readme_generator.py similarity index 84% rename from truss/readme_generator.py rename to truss/truss_handle/readme_generator.py index a2f383029..82f9cbdc3 100644 --- a/truss/readme_generator.py +++ b/truss/truss_handle/readme_generator.py @@ -1,7 +1,7 @@ from jinja2 import Template -from truss.constants import README_TEMPLATE_NAME, TEMPLATES_DIR -from truss.truss_spec import TrussSpec +from truss.base.constants import README_TEMPLATE_NAME, TEMPLATES_DIR +from truss.base.truss_spec import TrussSpec def generate_readme(_spec: TrussSpec) -> str: diff --git a/truss/truss_gatherer.py b/truss/truss_handle/truss_gatherer.py similarity index 96% rename from truss/truss_gatherer.py rename to truss/truss_handle/truss_gatherer.py index e8f5f3250..39760fa41 100644 --- a/truss/truss_gatherer.py +++ b/truss/truss_handle/truss_gatherer.py @@ -3,8 +3,8 @@ import yaml from truss.local.local_config_handler import LocalConfigHandler -from truss.patch.hash import str_hash_str -from truss.truss_handle import TrussHandle +from truss.truss_handle.patch.hash import str_hash_str +from truss.truss_handle.truss_handle import TrussHandle from truss.util.path import copy_file_path, copy_tree_path, remove_tree_path diff --git a/truss/truss_handle.py b/truss/truss_handle/truss_handle.py similarity index 97% rename from truss/truss_handle.py rename to truss/truss_handle/truss_handle.py index d79ac9ef8..3ce1bad90 100644 --- a/truss/truss_handle.py +++ b/truss/truss_handle/truss_handle.py @@ -25,20 +25,44 @@ wait_fixed, ) -from truss.constants import ( +from truss.base.constants import ( INFERENCE_SERVER_PORT, TRUSS, TRUSS_DIR, TRUSS_HASH, TRUSS_MODIFIED_TIME, ) +from truss.base.custom_types import Example +from truss.base.errors import ContainerIsDownError, ContainerNotFoundError +from truss.base.truss_config import ( + BaseImage, + ExternalData, + ExternalDataItem, + TrussConfig, +) +from truss.base.truss_spec import TrussSpec +from truss.base.validation import validate_secret_name from truss.contexts.image_builder.serving_image_builder import ( ServingImageBuilderContext, ) from truss.contexts.local_loader.load_model_local import LoadModelLocal -from truss.custom_types import Example, PatchDetails, PatchRequest -from truss.decorators import proxy_to_shadow_if_scattered -from truss.docker import ( +from truss.local.local_config_handler import LocalConfigHandler +from truss.templates.shared.serialization import ( + truss_msgpack_deserialize, + truss_msgpack_serialize, +) +from truss.trt_llm.validation import validate +from truss.truss_handle.decorators import proxy_to_shadow_if_scattered +from truss.truss_handle.patch.calc_patch import calc_truss_patch +from truss.truss_handle.patch.custom_types import ( + PatchDetails, + PatchRequest, + TrussSignature, +) +from truss.truss_handle.patch.hash import directory_content_hash +from truss.truss_handle.patch.signature import calc_truss_signature +from truss.truss_handle.readme_generator import generate_readme +from truss.util.docker import ( Docker, DockerStates, get_container_logs, @@ -48,28 +72,13 @@ get_urls_from_container, kill_containers, ) -from truss.errors import ContainerIsDownError, ContainerNotFoundError -from truss.local.local_config_handler import LocalConfigHandler -from truss.notebook import is_notebook_or_ipython -from truss.patch.calc_patch import calc_truss_patch -from truss.patch.custom_types import TrussSignature -from truss.patch.hash import directory_content_hash -from truss.patch.signature import calc_truss_signature -from truss.readme_generator import generate_readme -from truss.templates.shared.serialization import ( - truss_msgpack_deserialize, - truss_msgpack_serialize, -) -from truss.trt_llm.validation import validate -from truss.truss_config import BaseImage, ExternalData, ExternalDataItem, TrussConfig -from truss.truss_spec import TrussSpec +from truss.util.notebook import is_notebook_or_ipython from truss.util.path import ( copy_file_path, copy_tree_path, get_max_modified_time_of_dir, load_trussignore_patterns, ) -from truss.validation import validate_secret_name logger: logging.Logger = logging.getLogger(__name__) @@ -357,6 +366,7 @@ def predict( else: return self.server_predict(request) + # TODO(marius): can we kill this? def server_predict(self, request: Dict): """Run the prediction flow locally.""" model = LoadModelLocal.run(self._truss_dir) @@ -876,7 +886,7 @@ def gather(self) -> Path: gatherer and a handle to that truss is returned. These gathered trusses are caches and resused. """ - from truss.truss_gatherer import gather + from truss.truss_handle.truss_gatherer import gather if not self.is_scattered(): return self._truss_dir diff --git a/truss/util/data_structures.py b/truss/util/data_structures.py deleted file mode 100644 index 0834dbfe6..000000000 --- a/truss/util/data_structures.py +++ /dev/null @@ -1,11 +0,0 @@ -from typing import Callable, Optional, TypeVar - -X = TypeVar("X") -Y = TypeVar("Y") - - -def transform_optional(x: Optional[X], fn: Callable[[X], Optional[Y]]) -> Optional[Y]: - if x is None: - return None - - return fn(x) diff --git a/truss/docker.py b/truss/util/docker.py similarity index 97% rename from truss/docker.py rename to truss/util/docker.py index ad8558896..dc00c664d 100644 --- a/truss/docker.py +++ b/truss/util/docker.py @@ -5,7 +5,7 @@ if TYPE_CHECKING: from python_on_whales.components.container.cli_wrapper import Container -from truss.constants import TRUSS_DIR +from truss.base.constants import TRUSS, TRUSS_DIR from truss.local.local_config_handler import LocalConfigHandler @@ -115,3 +115,7 @@ def _create_label_filters(labels: Dict) -> Dict[str, Any]: return { f"label={label_key}": label_value for label_key, label_value in labels.items() } + + +def kill_all() -> None: + kill_containers({TRUSS: True}) diff --git a/truss/util/download.py b/truss/util/download.py index 4a27520c0..9c327aded 100644 --- a/truss/util/download.py +++ b/truss/util/download.py @@ -5,7 +5,7 @@ from typing import Optional import requests -from truss.truss_config import ExternalData +from truss.base.truss_config import ExternalData B10CP_EXECUTABLE_NAME = "b10cp" BLOB_DOWNLOAD_TIMEOUT_SECS = 600 # 10 minutes diff --git a/truss/util/errors.py b/truss/util/errors.py deleted file mode 100644 index 1a6df56ec..000000000 --- a/truss/util/errors.py +++ /dev/null @@ -1,2 +0,0 @@ -class RemoteNetworkError(Exception): - pass diff --git a/truss/notebook.py b/truss/util/notebook.py similarity index 100% rename from truss/notebook.py rename to truss/util/notebook.py