@typespec/http-client-python 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +118 -0
- package/dist/emitter/code-model.d.ts +4 -0
- package/dist/emitter/code-model.d.ts.map +1 -0
- package/dist/emitter/code-model.js +195 -0
- package/dist/emitter/code-model.js.map +1 -0
- package/dist/emitter/emitter.d.ts +6 -0
- package/dist/emitter/emitter.d.ts.map +1 -0
- package/dist/emitter/emitter.js +104 -0
- package/dist/emitter/emitter.js.map +1 -0
- package/dist/emitter/external-process.d.ts +20 -0
- package/dist/emitter/external-process.d.ts.map +1 -0
- package/dist/emitter/external-process.js +44 -0
- package/dist/emitter/external-process.js.map +1 -0
- package/dist/emitter/http.d.ts +7 -0
- package/dist/emitter/http.d.ts.map +1 -0
- package/dist/emitter/http.js +268 -0
- package/dist/emitter/http.js.map +1 -0
- package/dist/emitter/index.d.ts +3 -0
- package/dist/emitter/index.d.ts.map +1 -0
- package/dist/emitter/index.js +3 -0
- package/dist/emitter/index.js.map +1 -0
- package/dist/emitter/lib.d.ts +30 -0
- package/dist/emitter/lib.d.ts.map +1 -0
- package/dist/emitter/lib.js +33 -0
- package/dist/emitter/lib.js.map +1 -0
- package/dist/emitter/types.d.ts +36 -0
- package/dist/emitter/types.d.ts.map +1 -0
- package/dist/emitter/types.js +491 -0
- package/dist/emitter/types.js.map +1 -0
- package/dist/emitter/utils.d.ts +26 -0
- package/dist/emitter/utils.d.ts.map +1 -0
- package/dist/emitter/utils.js +155 -0
- package/dist/emitter/utils.js.map +1 -0
- package/emitter/src/code-model.ts +272 -0
- package/emitter/src/emitter.ts +127 -0
- package/emitter/src/external-process.ts +52 -0
- package/emitter/src/http.ts +382 -0
- package/emitter/src/index.ts +2 -0
- package/emitter/src/lib.ts +59 -0
- package/emitter/src/types.ts +573 -0
- package/emitter/src/utils.ts +215 -0
- package/emitter/temp/tsconfig.tsbuildinfo +1 -0
- package/emitter/test/utils.test.ts +22 -0
- package/emitter/tsconfig.build.json +11 -0
- package/emitter/tsconfig.json +7 -0
- package/emitter/vitest.config.ts +4 -0
- package/eng/scripts/Build-Packages.ps1 +86 -0
- package/eng/scripts/Check-GitChanges.ps1 +22 -0
- package/eng/scripts/Functions.ps1 +26 -0
- package/eng/scripts/Generate.ps1 +11 -0
- package/eng/scripts/Generation.psm1 +22 -0
- package/eng/scripts/Initialize-Repository.ps1 +40 -0
- package/eng/scripts/Test-Packages.ps1 +65 -0
- package/eng/scripts/ci/format.ts +3 -0
- package/eng/scripts/ci/lint.ts +39 -0
- package/eng/scripts/ci/mypy.ini +38 -0
- package/eng/scripts/ci/pylintrc +59 -0
- package/eng/scripts/ci/pyproject.toml +18 -0
- package/eng/scripts/ci/pyrightconfig.json +6 -0
- package/eng/scripts/ci/regenerate.ts +299 -0
- package/eng/scripts/ci/run-ci.ts +88 -0
- package/eng/scripts/ci/run_apiview.py +40 -0
- package/eng/scripts/ci/run_mypy.py +49 -0
- package/eng/scripts/ci/run_pylint.py +50 -0
- package/eng/scripts/ci/run_pyright.py +58 -0
- package/eng/scripts/ci/util.py +72 -0
- package/eng/scripts/ci/utils.ts +48 -0
- package/eng/scripts/setup/__pycache__/venvtools.cpython-38.pyc +0 -0
- package/eng/scripts/setup/install.py +53 -0
- package/eng/scripts/setup/prepare.py +42 -0
- package/eng/scripts/setup/run-python3.ts +25 -0
- package/eng/scripts/setup/run_tsp.py +42 -0
- package/eng/scripts/setup/system-requirements.ts +261 -0
- package/eng/scripts/setup/venvtools.py +87 -0
- package/generator/LICENSE +21 -0
- package/generator/README.md +1 -0
- package/generator/dev_requirements.txt +13 -0
- package/generator/pygen/__init__.py +107 -0
- package/generator/pygen/_version.py +7 -0
- package/generator/pygen/black.py +71 -0
- package/generator/pygen/codegen/__init__.py +338 -0
- package/generator/pygen/codegen/_utils.py +17 -0
- package/generator/pygen/codegen/models/__init__.py +204 -0
- package/generator/pygen/codegen/models/base.py +186 -0
- package/generator/pygen/codegen/models/base_builder.py +118 -0
- package/generator/pygen/codegen/models/client.py +433 -0
- package/generator/pygen/codegen/models/code_model.py +237 -0
- package/generator/pygen/codegen/models/combined_type.py +149 -0
- package/generator/pygen/codegen/models/constant_type.py +129 -0
- package/generator/pygen/codegen/models/credential_types.py +214 -0
- package/generator/pygen/codegen/models/dictionary_type.py +127 -0
- package/generator/pygen/codegen/models/enum_type.py +238 -0
- package/generator/pygen/codegen/models/imports.py +291 -0
- package/generator/pygen/codegen/models/list_type.py +143 -0
- package/generator/pygen/codegen/models/lro_operation.py +142 -0
- package/generator/pygen/codegen/models/lro_paging_operation.py +32 -0
- package/generator/pygen/codegen/models/model_type.py +359 -0
- package/generator/pygen/codegen/models/operation.py +530 -0
- package/generator/pygen/codegen/models/operation_group.py +184 -0
- package/generator/pygen/codegen/models/paging_operation.py +155 -0
- package/generator/pygen/codegen/models/parameter.py +412 -0
- package/generator/pygen/codegen/models/parameter_list.py +387 -0
- package/generator/pygen/codegen/models/primitive_types.py +659 -0
- package/generator/pygen/codegen/models/property.py +170 -0
- package/generator/pygen/codegen/models/request_builder.py +189 -0
- package/generator/pygen/codegen/models/request_builder_parameter.py +115 -0
- package/generator/pygen/codegen/models/response.py +348 -0
- package/generator/pygen/codegen/models/utils.py +21 -0
- package/generator/pygen/codegen/serializers/__init__.py +574 -0
- package/generator/pygen/codegen/serializers/base_serializer.py +21 -0
- package/generator/pygen/codegen/serializers/builder_serializer.py +1507 -0
- package/generator/pygen/codegen/serializers/client_serializer.py +294 -0
- package/generator/pygen/codegen/serializers/enum_serializer.py +15 -0
- package/generator/pygen/codegen/serializers/general_serializer.py +213 -0
- package/generator/pygen/codegen/serializers/import_serializer.py +126 -0
- package/generator/pygen/codegen/serializers/metadata_serializer.py +198 -0
- package/generator/pygen/codegen/serializers/model_init_serializer.py +33 -0
- package/generator/pygen/codegen/serializers/model_serializer.py +317 -0
- package/generator/pygen/codegen/serializers/operation_groups_serializer.py +89 -0
- package/generator/pygen/codegen/serializers/operations_init_serializer.py +44 -0
- package/generator/pygen/codegen/serializers/parameter_serializer.py +221 -0
- package/generator/pygen/codegen/serializers/patch_serializer.py +19 -0
- package/generator/pygen/codegen/serializers/request_builders_serializer.py +52 -0
- package/generator/pygen/codegen/serializers/sample_serializer.py +168 -0
- package/generator/pygen/codegen/serializers/test_serializer.py +292 -0
- package/generator/pygen/codegen/serializers/types_serializer.py +31 -0
- package/generator/pygen/codegen/serializers/utils.py +68 -0
- package/generator/pygen/codegen/templates/client.py.jinja2 +37 -0
- package/generator/pygen/codegen/templates/client_container.py.jinja2 +12 -0
- package/generator/pygen/codegen/templates/config.py.jinja2 +73 -0
- package/generator/pygen/codegen/templates/config_container.py.jinja2 +16 -0
- package/generator/pygen/codegen/templates/conftest.py.jinja2 +28 -0
- package/generator/pygen/codegen/templates/enum.py.jinja2 +13 -0
- package/generator/pygen/codegen/templates/enum_container.py.jinja2 +10 -0
- package/generator/pygen/codegen/templates/init.py.jinja2 +24 -0
- package/generator/pygen/codegen/templates/keywords.jinja2 +19 -0
- package/generator/pygen/codegen/templates/lro_operation.py.jinja2 +16 -0
- package/generator/pygen/codegen/templates/lro_paging_operation.py.jinja2 +18 -0
- package/generator/pygen/codegen/templates/macros.jinja2 +12 -0
- package/generator/pygen/codegen/templates/metadata.json.jinja2 +167 -0
- package/generator/pygen/codegen/templates/model_base.py.jinja2 +1157 -0
- package/generator/pygen/codegen/templates/model_container.py.jinja2 +12 -0
- package/generator/pygen/codegen/templates/model_dpg.py.jinja2 +97 -0
- package/generator/pygen/codegen/templates/model_init.py.jinja2 +28 -0
- package/generator/pygen/codegen/templates/model_msrest.py.jinja2 +92 -0
- package/generator/pygen/codegen/templates/operation.py.jinja2 +21 -0
- package/generator/pygen/codegen/templates/operation_group.py.jinja2 +75 -0
- package/generator/pygen/codegen/templates/operation_groups_container.py.jinja2 +19 -0
- package/generator/pygen/codegen/templates/operation_tools.jinja2 +81 -0
- package/generator/pygen/codegen/templates/operations_folder_init.py.jinja2 +17 -0
- package/generator/pygen/codegen/templates/packaging_templates/CHANGELOG.md.jinja2 +6 -0
- package/generator/pygen/codegen/templates/packaging_templates/LICENSE.jinja2 +21 -0
- package/generator/pygen/codegen/templates/packaging_templates/MANIFEST.in.jinja2 +8 -0
- package/generator/pygen/codegen/templates/packaging_templates/README.md.jinja2 +107 -0
- package/generator/pygen/codegen/templates/packaging_templates/dev_requirements.txt.jinja2 +9 -0
- package/generator/pygen/codegen/templates/packaging_templates/setup.py.jinja2 +108 -0
- package/generator/pygen/codegen/templates/paging_operation.py.jinja2 +21 -0
- package/generator/pygen/codegen/templates/patch.py.jinja2 +19 -0
- package/generator/pygen/codegen/templates/pkgutil_init.py.jinja2 +1 -0
- package/generator/pygen/codegen/templates/request_builder.py.jinja2 +28 -0
- package/generator/pygen/codegen/templates/request_builders.py.jinja2 +10 -0
- package/generator/pygen/codegen/templates/rest_init.py.jinja2 +12 -0
- package/generator/pygen/codegen/templates/sample.py.jinja2 +44 -0
- package/generator/pygen/codegen/templates/serialization.py.jinja2 +2114 -0
- package/generator/pygen/codegen/templates/test.py.jinja2 +50 -0
- package/generator/pygen/codegen/templates/testpreparer.py.jinja2 +26 -0
- package/generator/pygen/codegen/templates/types.py.jinja2 +7 -0
- package/generator/pygen/codegen/templates/validation.py.jinja2 +38 -0
- package/generator/pygen/codegen/templates/vendor.py.jinja2 +95 -0
- package/generator/pygen/codegen/templates/version.py.jinja2 +4 -0
- package/generator/pygen/m2r.py +65 -0
- package/generator/pygen/postprocess/__init__.py +183 -0
- package/generator/pygen/postprocess/get_all.py +19 -0
- package/generator/pygen/postprocess/venvtools.py +75 -0
- package/generator/pygen/preprocess/__init__.py +515 -0
- package/generator/pygen/preprocess/helpers.py +27 -0
- package/generator/pygen/preprocess/python_mappings.py +224 -0
- package/generator/pygen/utils.py +163 -0
- package/generator/pygen.egg-info/PKG-INFO +25 -0
- package/generator/pygen.egg-info/SOURCES.txt +66 -0
- package/generator/pygen.egg-info/dependency_links.txt +1 -0
- package/generator/pygen.egg-info/requires.txt +4 -0
- package/generator/pygen.egg-info/top_level.txt +1 -0
- package/generator/requirements.txt +12 -0
- package/generator/setup.py +55 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_arm_models_common_types_managed_identity_async.py +63 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_arm_models_resource_async.py +284 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_client_generator_core_access_async.py +101 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_client_generator_core_flatten_async.py +93 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_client_generator_core_usage_async.py +31 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_core_basic_async.py +76 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_core_lro_rpc_async.py +22 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_core_lro_standard_async.py +39 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_core_model_async.py +33 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_core_page_async.py +58 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_core_scalar_async.py +41 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_core_traits_async.py +87 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_example_basic_async.py +30 -0
- package/generator/test/azure/mock_api_tests/asynctests/test_azure_special_headers_client_request_id_async.py +30 -0
- package/generator/test/azure/mock_api_tests/conftest.py +150 -0
- package/generator/test/azure/mock_api_tests/test_azure_arm_models_common_types_managed_identity.py +60 -0
- package/generator/test/azure/mock_api_tests/test_azure_arm_models_resource.py +254 -0
- package/generator/test/azure/mock_api_tests/test_azure_client_generator_core_access.py +92 -0
- package/generator/test/azure/mock_api_tests/test_azure_client_generator_core_flatten.py +84 -0
- package/generator/test/azure/mock_api_tests/test_azure_client_generator_core_usage.py +28 -0
- package/generator/test/azure/mock_api_tests/test_azure_core_basic.py +70 -0
- package/generator/test/azure/mock_api_tests/test_azure_core_lro_rpc.py +20 -0
- package/generator/test/azure/mock_api_tests/test_azure_core_lro_standard.py +32 -0
- package/generator/test/azure/mock_api_tests/test_azure_core_model.py +30 -0
- package/generator/test/azure/mock_api_tests/test_azure_core_page.py +51 -0
- package/generator/test/azure/mock_api_tests/test_azure_core_scalar.py +35 -0
- package/generator/test/azure/mock_api_tests/test_azure_core_traits.py +85 -0
- package/generator/test/azure/mock_api_tests/test_azure_example_basic.py +29 -0
- package/generator/test/azure/mock_api_tests/test_azure_special_headers_client_request_id.py +29 -0
- package/generator/test/azure/requirements.txt +89 -0
- package/generator/test/azure/tox.ini +56 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_authentication_async.py +121 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_client_naming_async.py +69 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_client_structure_async.py +62 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_encode_bytes_async.py +133 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_encode_datetime_async.py +127 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_encode_duration_async.py +63 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_encode_numeric_async.py +35 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_headasboolean_async.py +35 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_parameters_basic_async.py +24 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_parameters_body_optionality_async.py +30 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_parameters_collection_format_async.py +44 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_parameters_spread_async.py +76 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_payload_content_negotiation_async.py +37 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_payload_json_merge_patch_async.py +98 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_payload_media_type_async.py +27 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_payload_multipart_async.py +153 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_payload_pageable_async.py +19 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_payload_xml_async.py +103 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_resiliency_srv_driven_async.py +128 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_routes_async.py +331 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_serialization_encoded_name_json_async.py +24 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_server_endpoint_not_defined_async.py +18 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_server_path_multiple_async.py +25 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_server_path_single_async.py +18 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_server_versions_not_versioned_async.py +28 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_server_versions_versioned_async.py +34 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_special_headers_conditional_request_async.py +38 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_special_headers_repeatability_async.py +19 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_special_words_async.py +42 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_array_async.py +118 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_dictionary_async.py +98 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_enum_extensible_async.py +25 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_enum_fixed_async.py +27 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_model_empty_async.py +32 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_model_inheritance_enum_discriminator_async.py +70 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_model_inheritance_nested_discriminator_async.py +85 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_model_inheritance_not_discriminated_async.py +34 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_model_inheritance_recursive_async.py +34 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_model_inheritance_single_discriminator_async.py +67 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_model_usage_async.py +32 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_model_visibility_async.py +47 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_property_additionalproperties_async.py +352 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_property_nullable_async.py +110 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_property_optional_async.py +197 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_property_valuetypes_async.py +315 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_scalar_async.py +60 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_typetest_union_async.py +90 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_versioning_added_async.py +36 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_versioning_made_optional_async.py +21 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_versioning_removed_async.py +21 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_versioning_renamed_from_async.py +29 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_versioning_return_type_changed_from_async.py +18 -0
- package/generator/test/generic_mock_api_tests/asynctests/test_versioning_type_changed_from_async.py +22 -0
- package/generator/test/generic_mock_api_tests/conftest.py +113 -0
- package/generator/test/generic_mock_api_tests/data/image.jpg +0 -0
- package/generator/test/generic_mock_api_tests/data/image.png +0 -0
- package/generator/test/generic_mock_api_tests/test_authentication.py +113 -0
- package/generator/test/generic_mock_api_tests/test_client_naming.py +57 -0
- package/generator/test/generic_mock_api_tests/test_client_structure.py +57 -0
- package/generator/test/generic_mock_api_tests/test_encode_bytes.py +128 -0
- package/generator/test/generic_mock_api_tests/test_encode_datetime.py +123 -0
- package/generator/test/generic_mock_api_tests/test_encode_duration.py +60 -0
- package/generator/test/generic_mock_api_tests/test_encode_numeric.py +31 -0
- package/generator/test/generic_mock_api_tests/test_headasboolean.py +33 -0
- package/generator/test/generic_mock_api_tests/test_parameters_basic.py +22 -0
- package/generator/test/generic_mock_api_tests/test_parameters_body_optionality.py +27 -0
- package/generator/test/generic_mock_api_tests/test_parameters_collection_format.py +37 -0
- package/generator/test/generic_mock_api_tests/test_parameters_spread.py +66 -0
- package/generator/test/generic_mock_api_tests/test_payload_content_negotiation.py +33 -0
- package/generator/test/generic_mock_api_tests/test_payload_json_merge_patch.py +93 -0
- package/generator/test/generic_mock_api_tests/test_payload_media_type.py +25 -0
- package/generator/test/generic_mock_api_tests/test_payload_multipart.py +140 -0
- package/generator/test/generic_mock_api_tests/test_payload_pageable.py +18 -0
- package/generator/test/generic_mock_api_tests/test_payload_xml.py +93 -0
- package/generator/test/generic_mock_api_tests/test_resiliency_srv_driven.py +122 -0
- package/generator/test/generic_mock_api_tests/test_routes.py +285 -0
- package/generator/test/generic_mock_api_tests/test_serialization_encoded_name_json.py +21 -0
- package/generator/test/generic_mock_api_tests/test_server_endpoint_not_defined.py +17 -0
- package/generator/test/generic_mock_api_tests/test_server_path_multiple.py +21 -0
- package/generator/test/generic_mock_api_tests/test_server_path_single.py +17 -0
- package/generator/test/generic_mock_api_tests/test_server_versions_not_versioned.py +25 -0
- package/generator/test/generic_mock_api_tests/test_server_versions_versioned.py +30 -0
- package/generator/test/generic_mock_api_tests/test_special_headers_conditional_request.py +34 -0
- package/generator/test/generic_mock_api_tests/test_special_headers_repeatability.py +18 -0
- package/generator/test/generic_mock_api_tests/test_special_words.py +37 -0
- package/generator/test/generic_mock_api_tests/test_typetest_array.py +103 -0
- package/generator/test/generic_mock_api_tests/test_typetest_dictionary.py +86 -0
- package/generator/test/generic_mock_api_tests/test_typetest_enum_extensible.py +23 -0
- package/generator/test/generic_mock_api_tests/test_typetest_enum_fixed.py +25 -0
- package/generator/test/generic_mock_api_tests/test_typetest_model_empty.py +29 -0
- package/generator/test/generic_mock_api_tests/test_typetest_model_inheritance_enum_discriminator.py +58 -0
- package/generator/test/generic_mock_api_tests/test_typetest_model_inheritance_nested_discriminator.py +79 -0
- package/generator/test/generic_mock_api_tests/test_typetest_model_inheritance_not_discriminated.py +31 -0
- package/generator/test/generic_mock_api_tests/test_typetest_model_inheritance_recursive.py +32 -0
- package/generator/test/generic_mock_api_tests/test_typetest_model_inheritance_single_discriminator.py +60 -0
- package/generator/test/generic_mock_api_tests/test_typetest_model_usage.py +28 -0
- package/generator/test/generic_mock_api_tests/test_typetest_model_visibility.py +40 -0
- package/generator/test/generic_mock_api_tests/test_typetest_property_additionalproperties.py +313 -0
- package/generator/test/generic_mock_api_tests/test_typetest_property_nullable.py +102 -0
- package/generator/test/generic_mock_api_tests/test_typetest_property_optional.py +174 -0
- package/generator/test/generic_mock_api_tests/test_typetest_property_valuetypes.py +286 -0
- package/generator/test/generic_mock_api_tests/test_typetest_scalar.py +53 -0
- package/generator/test/generic_mock_api_tests/test_typetest_union.py +80 -0
- package/generator/test/generic_mock_api_tests/test_versioning_added.py +33 -0
- package/generator/test/generic_mock_api_tests/test_versioning_made_optional.py +20 -0
- package/generator/test/generic_mock_api_tests/test_versioning_removed.py +20 -0
- package/generator/test/generic_mock_api_tests/test_versioning_renamed_from.py +27 -0
- package/generator/test/generic_mock_api_tests/test_versioning_return_type_changed_from.py +17 -0
- package/generator/test/generic_mock_api_tests/test_versioning_type_changed_from.py +21 -0
- package/generator/test/generic_mock_api_tests/unittests/test_model_base_serialization.py +4067 -0
- package/generator/test/generic_mock_api_tests/unittests/test_model_base_xml_serialization.py +1001 -0
- package/generator/test/unbranded/mock_api_tests/asynctests/test_unbranded_async.py +24 -0
- package/generator/test/unbranded/mock_api_tests/cadl-ranch-config.yaml +27 -0
- package/generator/test/unbranded/mock_api_tests/conftest.py +35 -0
- package/generator/test/unbranded/mock_api_tests/test_unbranded.py +57 -0
- package/generator/test/unbranded/requirements.txt +72 -0
- package/generator/test/unbranded/tox.ini +56 -0
- package/package.json +93 -0
|
@@ -0,0 +1,261 @@
|
|
|
1
|
+
import { ChildProcess, spawn, SpawnOptions } from "child_process";
|
|
2
|
+
import { coerce, satisfies } from "semver";
|
|
3
|
+
|
|
4
|
+
/*
|
|
5
|
+
* Copied from @autorest/system-requirements
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
const execute = (
|
|
9
|
+
command: string,
|
|
10
|
+
cmdlineargs: Array<string>,
|
|
11
|
+
options: MoreOptions = {},
|
|
12
|
+
): Promise<ExecResult> => {
|
|
13
|
+
return new Promise((resolve, reject) => {
|
|
14
|
+
const cp = spawn(command, cmdlineargs, { ...options, stdio: "pipe", shell: true });
|
|
15
|
+
if (options.onCreate) {
|
|
16
|
+
options.onCreate(cp);
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
options.onStdOutData && cp.stdout.on("data", options.onStdOutData);
|
|
20
|
+
options.onStdErrData && cp.stderr.on("data", options.onStdErrData);
|
|
21
|
+
|
|
22
|
+
let err = "";
|
|
23
|
+
let out = "";
|
|
24
|
+
let all = "";
|
|
25
|
+
cp.stderr.on("data", (chunk) => {
|
|
26
|
+
err += chunk;
|
|
27
|
+
all += chunk;
|
|
28
|
+
});
|
|
29
|
+
cp.stdout.on("data", (chunk) => {
|
|
30
|
+
out += chunk;
|
|
31
|
+
all += chunk;
|
|
32
|
+
});
|
|
33
|
+
|
|
34
|
+
cp.on("error", (err) => {
|
|
35
|
+
reject(err);
|
|
36
|
+
});
|
|
37
|
+
cp.on("close", (code, signal) =>
|
|
38
|
+
resolve({
|
|
39
|
+
stdout: out,
|
|
40
|
+
stderr: err,
|
|
41
|
+
log: all,
|
|
42
|
+
error: code ? new Error("Process Failed.") : null,
|
|
43
|
+
code,
|
|
44
|
+
}),
|
|
45
|
+
);
|
|
46
|
+
});
|
|
47
|
+
};
|
|
48
|
+
|
|
49
|
+
const versionIsSatisfied = (version: string, requirement: string): boolean => {
|
|
50
|
+
const cleanedVersion = coerce(version);
|
|
51
|
+
if (!cleanedVersion) {
|
|
52
|
+
throw new Error(`Invalid version ${version}.`);
|
|
53
|
+
}
|
|
54
|
+
return satisfies(cleanedVersion, requirement, true);
|
|
55
|
+
};
|
|
56
|
+
|
|
57
|
+
/**
|
|
58
|
+
* Validate the provided system requirement resolution is satisfying the version requirement if applicable.
|
|
59
|
+
* @param resolution Command resolution.
|
|
60
|
+
* @param actualVersion Version for that resolution.
|
|
61
|
+
* @param requirement Requirement.
|
|
62
|
+
* @returns the resolution if it is valid or an @see SystemRequirementError if not.
|
|
63
|
+
*/
|
|
64
|
+
const validateVersionRequirement = (
|
|
65
|
+
resolution: SystemRequirementResolution,
|
|
66
|
+
actualVersion: string,
|
|
67
|
+
requirement: SystemRequirement,
|
|
68
|
+
): SystemRequirementResolution | SystemRequirementError => {
|
|
69
|
+
if (!requirement.version) {
|
|
70
|
+
return resolution; // No version requirement.
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
try {
|
|
74
|
+
if (versionIsSatisfied(actualVersion, requirement.version)) {
|
|
75
|
+
return resolution;
|
|
76
|
+
}
|
|
77
|
+
return {
|
|
78
|
+
...resolution,
|
|
79
|
+
error: true,
|
|
80
|
+
message: `'${resolution.command}' version is '${actualVersion}' but doesn't satisfy requirement '${requirement.version}'. Please update.`,
|
|
81
|
+
actualVersion: actualVersion,
|
|
82
|
+
neededVersion: requirement.version,
|
|
83
|
+
};
|
|
84
|
+
} catch {
|
|
85
|
+
return {
|
|
86
|
+
...resolution,
|
|
87
|
+
error: true,
|
|
88
|
+
message: `Couldn't parse the version ${actualVersion}. This is not a valid semver version.`,
|
|
89
|
+
actualVersion: actualVersion,
|
|
90
|
+
neededVersion: requirement.version,
|
|
91
|
+
};
|
|
92
|
+
}
|
|
93
|
+
};
|
|
94
|
+
|
|
95
|
+
const tryPython = async (
|
|
96
|
+
requirement: SystemRequirement,
|
|
97
|
+
command: string,
|
|
98
|
+
additionalArgs: string[] = [],
|
|
99
|
+
): Promise<SystemRequirementResolution | SystemRequirementError> => {
|
|
100
|
+
const resolution: SystemRequirementResolution = {
|
|
101
|
+
name: PythonRequirement,
|
|
102
|
+
command,
|
|
103
|
+
additionalArgs: additionalArgs.length > 0 ? additionalArgs : undefined,
|
|
104
|
+
};
|
|
105
|
+
|
|
106
|
+
try {
|
|
107
|
+
const result = await execute(command, [
|
|
108
|
+
...additionalArgs,
|
|
109
|
+
"-c",
|
|
110
|
+
`"${PRINT_PYTHON_VERSION_SCRIPT}"`,
|
|
111
|
+
]);
|
|
112
|
+
return validateVersionRequirement(resolution, result.stdout.trim(), requirement);
|
|
113
|
+
} catch (e) {
|
|
114
|
+
return {
|
|
115
|
+
error: true,
|
|
116
|
+
...resolution,
|
|
117
|
+
message: `'${command}' command line is not found in the path. Make sure to have it installed.`,
|
|
118
|
+
};
|
|
119
|
+
}
|
|
120
|
+
};
|
|
121
|
+
|
|
122
|
+
/**
|
|
123
|
+
* Returns the path to the executable as asked in the requirement.
|
|
124
|
+
* @param requirement System requirement definition.
|
|
125
|
+
* @returns If the requirement provide an environment variable for the path returns the value of that environment variable. undefined otherwise.
|
|
126
|
+
*/
|
|
127
|
+
const getExecutablePath = (requirement: SystemRequirement): string | undefined =>
|
|
128
|
+
requirement.environmentVariable && process.env[requirement.environmentVariable];
|
|
129
|
+
|
|
130
|
+
const createPythonErrorMessage = (
|
|
131
|
+
requirement: SystemRequirement,
|
|
132
|
+
errors: SystemRequirementError[],
|
|
133
|
+
): SystemRequirementError => {
|
|
134
|
+
const versionReq = requirement.version ?? "*";
|
|
135
|
+
const lines = [
|
|
136
|
+
`Couldn't find a valid python interpreter satisfying the requirement (version: ${versionReq}). Tried:`,
|
|
137
|
+
...errors.map((x) => ` - ${x.command} (${x.message})`),
|
|
138
|
+
];
|
|
139
|
+
|
|
140
|
+
return {
|
|
141
|
+
error: true,
|
|
142
|
+
name: "python",
|
|
143
|
+
command: "python",
|
|
144
|
+
message: lines.join("\n"),
|
|
145
|
+
};
|
|
146
|
+
};
|
|
147
|
+
|
|
148
|
+
const resolvePythonRequirement = async (
|
|
149
|
+
requirement: SystemRequirement,
|
|
150
|
+
): Promise<SystemRequirementResolution | SystemRequirementError> => {
|
|
151
|
+
// Hardcoding AUTOREST_PYTHON_EXE is for backward compatibility
|
|
152
|
+
const path = getExecutablePath(requirement) ?? process.env["AUTOREST_PYTHON_EXE"];
|
|
153
|
+
if (path) {
|
|
154
|
+
return await tryPython(requirement, path);
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
const errors: SystemRequirementError[] = [];
|
|
158
|
+
// On windows try `py` executable with `-3` flag.
|
|
159
|
+
if (process.platform === "win32") {
|
|
160
|
+
const pyResult = await tryPython(requirement, "py", ["-3"]);
|
|
161
|
+
if ("error" in pyResult) {
|
|
162
|
+
errors.push(pyResult);
|
|
163
|
+
} else {
|
|
164
|
+
return pyResult;
|
|
165
|
+
}
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
const python3Result = await tryPython(requirement, "python3");
|
|
169
|
+
if ("error" in python3Result) {
|
|
170
|
+
errors.push(python3Result);
|
|
171
|
+
} else {
|
|
172
|
+
return python3Result;
|
|
173
|
+
}
|
|
174
|
+
|
|
175
|
+
const pythonResult = await tryPython(requirement, "python");
|
|
176
|
+
if ("error" in pythonResult) {
|
|
177
|
+
errors.push(pythonResult);
|
|
178
|
+
} else {
|
|
179
|
+
return pythonResult;
|
|
180
|
+
}
|
|
181
|
+
|
|
182
|
+
return createPythonErrorMessage(requirement, errors);
|
|
183
|
+
};
|
|
184
|
+
|
|
185
|
+
/**
|
|
186
|
+
* @param command list of the command and arguments. First item in array must be a python exe @see KnownPythonExe. (e.g. ["python", "my_python_file.py"]
|
|
187
|
+
* @param requirement
|
|
188
|
+
*/
|
|
189
|
+
export const patchPythonPath = async (
|
|
190
|
+
command: PythonCommandLine,
|
|
191
|
+
requirement: SystemRequirement,
|
|
192
|
+
): Promise<string[]> => {
|
|
193
|
+
const [_, ...args] = command;
|
|
194
|
+
const resolution = await resolvePythonRequirement(requirement);
|
|
195
|
+
if ("error" in resolution) {
|
|
196
|
+
throw new Error(`Failed to find compatible python version. ${resolution.message}`);
|
|
197
|
+
}
|
|
198
|
+
return [resolution.command, ...(resolution.additionalArgs ?? []), ...args];
|
|
199
|
+
};
|
|
200
|
+
|
|
201
|
+
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
|
|
202
|
+
// TYPES
|
|
203
|
+
const PythonRequirement = "python";
|
|
204
|
+
const PRINT_PYTHON_VERSION_SCRIPT = "import sys; print('.'.join(map(str, sys.version_info[:3])))";
|
|
205
|
+
|
|
206
|
+
type KnownPythonExe = "python.exe" | "python3.exe" | "python" | "python3";
|
|
207
|
+
type PythonCommandLine = [KnownPythonExe, ...string[]];
|
|
208
|
+
|
|
209
|
+
interface MoreOptions extends SpawnOptions {
|
|
210
|
+
onCreate?(cp: ChildProcess): void;
|
|
211
|
+
onStdOutData?(chunk: any): void;
|
|
212
|
+
onStdErrData?(chunk: any): void;
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
interface SystemRequirement {
|
|
216
|
+
version?: string;
|
|
217
|
+
/**
|
|
218
|
+
* Name of an environment variable where the user could provide the path to the exe.
|
|
219
|
+
* @example "AUTOREST_PYTHON_PATH"
|
|
220
|
+
*/
|
|
221
|
+
environmentVariable?: string;
|
|
222
|
+
}
|
|
223
|
+
|
|
224
|
+
interface SystemRequirementResolution {
|
|
225
|
+
/**
|
|
226
|
+
* Name of the requirement.
|
|
227
|
+
* @example python, java, etc.
|
|
228
|
+
*/
|
|
229
|
+
name: string;
|
|
230
|
+
|
|
231
|
+
/**
|
|
232
|
+
* Name of the command
|
|
233
|
+
* @example python3, /home/my_user/python39/python, java, etc.
|
|
234
|
+
*/
|
|
235
|
+
command: string;
|
|
236
|
+
|
|
237
|
+
/**
|
|
238
|
+
* List of additional arguments to pass to this command.
|
|
239
|
+
* @example '-3' for 'py' to specify to use python 3
|
|
240
|
+
*/
|
|
241
|
+
additionalArgs?: string[];
|
|
242
|
+
}
|
|
243
|
+
|
|
244
|
+
interface ExecResult {
|
|
245
|
+
stdout: string;
|
|
246
|
+
stderr: string;
|
|
247
|
+
|
|
248
|
+
/**
|
|
249
|
+
* Union of stdout and stderr.
|
|
250
|
+
*/
|
|
251
|
+
log: string;
|
|
252
|
+
error: Error | null;
|
|
253
|
+
code: number | null;
|
|
254
|
+
}
|
|
255
|
+
|
|
256
|
+
interface SystemRequirementError extends SystemRequirementResolution {
|
|
257
|
+
error: true;
|
|
258
|
+
message: string;
|
|
259
|
+
neededVersion?: string;
|
|
260
|
+
actualVersion?: string;
|
|
261
|
+
}
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
# -------------------------------------------------------------------------
|
|
2
|
+
# Copyright (c) Microsoft Corporation. All rights reserved.
|
|
3
|
+
# Licensed under the MIT License. See License.txt in the project root for
|
|
4
|
+
# license information.
|
|
5
|
+
# --------------------------------------------------------------------------
|
|
6
|
+
from contextlib import contextmanager
|
|
7
|
+
import tempfile
|
|
8
|
+
import subprocess
|
|
9
|
+
import venv
|
|
10
|
+
import sys
|
|
11
|
+
from pathlib import Path
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
_ROOT_DIR = Path(__file__).parent.parent.parent.parent
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
class ExtendedEnvBuilder(venv.EnvBuilder):
|
|
18
|
+
"""An extended env builder which saves the context, to have access
|
|
19
|
+
easily to bin path and such.
|
|
20
|
+
"""
|
|
21
|
+
|
|
22
|
+
def __init__(self, *args, **kwargs):
|
|
23
|
+
self.context = None
|
|
24
|
+
if sys.version_info < (3, 9, 0):
|
|
25
|
+
# Not supported on Python 3.8, and we don't need it
|
|
26
|
+
kwargs.pop("upgrade_deps", None)
|
|
27
|
+
super().__init__(*args, **kwargs)
|
|
28
|
+
|
|
29
|
+
def ensure_directories(self, env_dir):
|
|
30
|
+
self.context = super(ExtendedEnvBuilder, self).ensure_directories(env_dir)
|
|
31
|
+
return self.context
|
|
32
|
+
|
|
33
|
+
|
|
34
|
+
def create(
|
|
35
|
+
env_dir,
|
|
36
|
+
system_site_packages=False,
|
|
37
|
+
clear=False,
|
|
38
|
+
symlinks=False,
|
|
39
|
+
with_pip=False,
|
|
40
|
+
prompt=None,
|
|
41
|
+
upgrade_deps=False,
|
|
42
|
+
):
|
|
43
|
+
"""Create a virtual environment in a directory."""
|
|
44
|
+
builder = ExtendedEnvBuilder(
|
|
45
|
+
system_site_packages=system_site_packages,
|
|
46
|
+
clear=clear,
|
|
47
|
+
symlinks=symlinks,
|
|
48
|
+
with_pip=with_pip,
|
|
49
|
+
prompt=prompt,
|
|
50
|
+
upgrade_deps=upgrade_deps,
|
|
51
|
+
)
|
|
52
|
+
builder.create(env_dir)
|
|
53
|
+
return builder.context
|
|
54
|
+
|
|
55
|
+
|
|
56
|
+
@contextmanager
|
|
57
|
+
def create_venv_with_package(packages):
|
|
58
|
+
"""Create a venv with these packages in a temp dir and yield the env.
|
|
59
|
+
|
|
60
|
+
packages should be an iterable of pip version instruction (e.g. package~=1.2.3)
|
|
61
|
+
"""
|
|
62
|
+
with tempfile.TemporaryDirectory() as tempdir:
|
|
63
|
+
my_env = create(tempdir, with_pip=True, upgrade_deps=True)
|
|
64
|
+
pip_call = [
|
|
65
|
+
my_env.env_exe,
|
|
66
|
+
"-m",
|
|
67
|
+
"pip",
|
|
68
|
+
"install",
|
|
69
|
+
]
|
|
70
|
+
subprocess.check_call(pip_call + ["-U", "pip"])
|
|
71
|
+
if packages:
|
|
72
|
+
subprocess.check_call(pip_call + packages)
|
|
73
|
+
yield my_env
|
|
74
|
+
|
|
75
|
+
|
|
76
|
+
def python_run(venv_context, module, command=None, *, additional_dir="."):
|
|
77
|
+
try:
|
|
78
|
+
cmd_line = [venv_context.env_exe, "-m", module] + (command if command else [])
|
|
79
|
+
print("Executing: {}".format(" ".join(cmd_line)))
|
|
80
|
+
subprocess.run(
|
|
81
|
+
cmd_line,
|
|
82
|
+
cwd=_ROOT_DIR / additional_dir,
|
|
83
|
+
check=True,
|
|
84
|
+
)
|
|
85
|
+
except subprocess.CalledProcessError as err:
|
|
86
|
+
print(err)
|
|
87
|
+
sys.exit(1)
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) Microsoft Corporation. All rights reserved.
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
# Core Library for Python Generation
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
# -------------------------------------------------------------------------
|
|
2
|
+
# Copyright (c) Microsoft Corporation. All rights reserved.
|
|
3
|
+
# Licensed under the MIT License. See License.txt in the project root for
|
|
4
|
+
# license information.
|
|
5
|
+
# --------------------------------------------------------------------------
|
|
6
|
+
import logging
|
|
7
|
+
from pathlib import Path
|
|
8
|
+
import json
|
|
9
|
+
from abc import ABC, abstractmethod
|
|
10
|
+
from typing import Any, Dict, Union, List
|
|
11
|
+
|
|
12
|
+
import yaml
|
|
13
|
+
|
|
14
|
+
from ._version import VERSION
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
__version__ = VERSION
|
|
18
|
+
_LOGGER = logging.getLogger(__name__)
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
class ReaderAndWriter:
|
|
22
|
+
def __init__(self, *, output_folder: Union[str, Path], **kwargs: Any) -> None:
|
|
23
|
+
self.output_folder = Path(output_folder)
|
|
24
|
+
self._list_file: List[str] = []
|
|
25
|
+
try:
|
|
26
|
+
with open(
|
|
27
|
+
Path(self.output_folder) / Path("..") / Path("python.json"),
|
|
28
|
+
"r",
|
|
29
|
+
encoding="utf-8-sig",
|
|
30
|
+
) as fd:
|
|
31
|
+
python_json = json.load(fd)
|
|
32
|
+
except Exception: # pylint: disable=broad-except
|
|
33
|
+
python_json = {}
|
|
34
|
+
self.options = kwargs
|
|
35
|
+
if python_json:
|
|
36
|
+
_LOGGER.warning("Loading python.json file. This behavior will be depreacted")
|
|
37
|
+
self.options.update(python_json)
|
|
38
|
+
|
|
39
|
+
def read_file(self, path: Union[str, Path]) -> str:
|
|
40
|
+
"""Directly reading from disk"""
|
|
41
|
+
# make path relative to output folder
|
|
42
|
+
try:
|
|
43
|
+
with open(self.output_folder / Path(path), "r", encoding="utf-8-sig") as fd:
|
|
44
|
+
return fd.read()
|
|
45
|
+
except FileNotFoundError:
|
|
46
|
+
return ""
|
|
47
|
+
|
|
48
|
+
def write_file(self, filename: Union[str, Path], file_content: str) -> None:
|
|
49
|
+
"""Directly writing to disk"""
|
|
50
|
+
file_folder = Path(filename).parent
|
|
51
|
+
if not Path.is_dir(self.output_folder / file_folder):
|
|
52
|
+
Path.mkdir(self.output_folder / file_folder, parents=True)
|
|
53
|
+
with open(self.output_folder / Path(filename), "w", encoding="utf-8") as fd:
|
|
54
|
+
fd.write(file_content)
|
|
55
|
+
|
|
56
|
+
def list_file(self) -> List[str]:
|
|
57
|
+
return [str(f.relative_to(self.output_folder)) for f in self.output_folder.glob("**/*") if f.is_file()]
|
|
58
|
+
|
|
59
|
+
|
|
60
|
+
class Plugin(ReaderAndWriter, ABC):
|
|
61
|
+
"""A base class for autorest plugin.
|
|
62
|
+
|
|
63
|
+
:param autorestapi: An autorest API instance
|
|
64
|
+
"""
|
|
65
|
+
|
|
66
|
+
@abstractmethod
|
|
67
|
+
def process(self) -> bool:
|
|
68
|
+
"""The plugin process.
|
|
69
|
+
|
|
70
|
+
:rtype: bool
|
|
71
|
+
:returns: True if everything's ok, False optherwise
|
|
72
|
+
:raises Exception: Could raise any exception, stacktrace will be sent to autorest API
|
|
73
|
+
"""
|
|
74
|
+
raise NotImplementedError()
|
|
75
|
+
|
|
76
|
+
|
|
77
|
+
class YamlUpdatePlugin(Plugin):
|
|
78
|
+
"""A plugin that update the YAML as input."""
|
|
79
|
+
|
|
80
|
+
def get_yaml(self) -> Dict[str, Any]:
|
|
81
|
+
# cadl file doesn't have to be relative to output folder
|
|
82
|
+
with open(self.options["cadl_file"], "r", encoding="utf-8-sig") as fd:
|
|
83
|
+
return yaml.safe_load(fd.read())
|
|
84
|
+
|
|
85
|
+
def write_yaml(self, yaml_string: str) -> None:
|
|
86
|
+
with open(self.options["cadl_file"], "w", encoding="utf-8-sig") as fd:
|
|
87
|
+
fd.write(yaml_string)
|
|
88
|
+
|
|
89
|
+
def process(self) -> bool:
|
|
90
|
+
# List the input file, should be only one
|
|
91
|
+
yaml_data = self.get_yaml()
|
|
92
|
+
|
|
93
|
+
self.update_yaml(yaml_data)
|
|
94
|
+
|
|
95
|
+
yaml_string = yaml.safe_dump(yaml_data)
|
|
96
|
+
|
|
97
|
+
self.write_yaml(yaml_string)
|
|
98
|
+
return True
|
|
99
|
+
|
|
100
|
+
@abstractmethod
|
|
101
|
+
def update_yaml(self, yaml_data: Dict[str, Any]) -> None:
|
|
102
|
+
"""The code-model-v4-no-tags yaml model tree.
|
|
103
|
+
|
|
104
|
+
:rtype: updated yaml
|
|
105
|
+
:raises Exception: Could raise any exception, stacktrace will be sent to autorest API
|
|
106
|
+
"""
|
|
107
|
+
raise NotImplementedError()
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
# -------------------------------------------------------------------------
|
|
2
|
+
# Copyright (c) Microsoft Corporation. All rights reserved.
|
|
3
|
+
# Licensed under the MIT License. See License.txt in the project root for
|
|
4
|
+
# license information.
|
|
5
|
+
# --------------------------------------------------------------------------
|
|
6
|
+
|
|
7
|
+
VERSION = "0.1.0"
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
# -------------------------------------------------------------------------
|
|
2
|
+
# Copyright (c) Microsoft Corporation. All rights reserved.
|
|
3
|
+
# Licensed under the MIT License. See License.txt in the project root for
|
|
4
|
+
# license information.
|
|
5
|
+
# --------------------------------------------------------------------------
|
|
6
|
+
import logging
|
|
7
|
+
from pathlib import Path
|
|
8
|
+
import os
|
|
9
|
+
import black
|
|
10
|
+
from black.report import NothingChanged
|
|
11
|
+
|
|
12
|
+
from . import Plugin
|
|
13
|
+
from .utils import parse_args
|
|
14
|
+
|
|
15
|
+
_LOGGER = logging.getLogger("blib2to3")
|
|
16
|
+
|
|
17
|
+
_BLACK_MODE = black.Mode() # pyright: ignore [reportPrivateImportUsage]
|
|
18
|
+
_BLACK_MODE.line_length = 120
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
class BlackScriptPlugin(Plugin):
|
|
22
|
+
def __init__(self, **kwargs):
|
|
23
|
+
super().__init__(**kwargs)
|
|
24
|
+
output_folder = self.options.get("output_folder", str(self.output_folder))
|
|
25
|
+
if output_folder.startswith("file:"):
|
|
26
|
+
output_folder = output_folder[5:]
|
|
27
|
+
if os.name == "nt" and output_folder.startswith("///"):
|
|
28
|
+
output_folder = output_folder[3:]
|
|
29
|
+
self.output_folder = Path(output_folder)
|
|
30
|
+
|
|
31
|
+
def process(self) -> bool:
|
|
32
|
+
# apply format_file on every .py file in the output folder
|
|
33
|
+
list(
|
|
34
|
+
map(
|
|
35
|
+
self.format_file,
|
|
36
|
+
[
|
|
37
|
+
Path(f)
|
|
38
|
+
for f in self.list_file()
|
|
39
|
+
if Path(f).parts[0]
|
|
40
|
+
not in (
|
|
41
|
+
"__pycache__",
|
|
42
|
+
"node_modules",
|
|
43
|
+
"venv",
|
|
44
|
+
"env",
|
|
45
|
+
)
|
|
46
|
+
and not Path(f).parts[0].startswith(".")
|
|
47
|
+
and Path(f).suffix == ".py"
|
|
48
|
+
],
|
|
49
|
+
)
|
|
50
|
+
)
|
|
51
|
+
return True
|
|
52
|
+
|
|
53
|
+
def format_file(self, file: Path) -> None:
|
|
54
|
+
try:
|
|
55
|
+
file_content = self.read_file(file)
|
|
56
|
+
file_content = black.format_file_contents(file_content, fast=True, mode=_BLACK_MODE)
|
|
57
|
+
except NothingChanged:
|
|
58
|
+
pass
|
|
59
|
+
except:
|
|
60
|
+
_LOGGER.error("Error: failed to format %s", file)
|
|
61
|
+
raise
|
|
62
|
+
else:
|
|
63
|
+
if len(file_content.splitlines()) > 1000:
|
|
64
|
+
file_content = "# pylint: disable=too-many-lines\n" + file_content
|
|
65
|
+
self.write_file(file, file_content)
|
|
66
|
+
|
|
67
|
+
|
|
68
|
+
if __name__ == "__main__":
|
|
69
|
+
# CADL pipeline will call this
|
|
70
|
+
args, unknown_args = parse_args(need_cadl_file=False)
|
|
71
|
+
BlackScriptPlugin(output_folder=args.output_folder, **unknown_args).process()
|