From 77012f5c8e3be225178dd8ceef27b7e48590e7c3 Mon Sep 17 00:00:00 2001 From: Justintime50 <39606064+Justintime50@users.noreply.github.com> Date: Wed, 3 Jul 2024 15:22:29 -0600 Subject: [PATCH 1/7] feat: add new create_ups and update_ups functions --- CHANGELOG.md | 5 ++ easypost/constant.py | 1 - easypost/services/carrier_account_service.py | 17 +++++ .../test_carrier_account_create_ups.yaml | 69 ++++++++++++++++++ ...r_account_create_with_custom_workflow.yaml | 48 +++++++------ .../test_carrier_account_update_ups.yaml | 70 +++++++++++++++++++ tests/test_carrier_account.py | 42 ++++++++++- 7 files changed, 228 insertions(+), 24 deletions(-) create mode 100644 tests/cassettes/test_carrier_account_create_ups.yaml create mode 100644 tests/cassettes/test_carrier_account_update_ups.yaml diff --git a/CHANGELOG.md b/CHANGELOG.md index 0b882aef..c35aedef 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,10 @@ # CHANGELOG +## Next Release + +- Adds new `create_ups` and `update_ups` functions under `carrier_account` + - Starting `2024-08-05`, UPS accounts can no longer be created or updated through the normal create and update functions and must use these UPS specific functions + ## v9.2.0 (2024-04-10) - Fix payment method funding and deletion failures due to undetermined payment method type diff --git a/easypost/constant.py b/easypost/constant.py index 0f9feb18..b076129a 100644 --- a/easypost/constant.py +++ b/easypost/constant.py @@ -35,6 +35,5 @@ _CARRIER_ACCOUNT_TYPES_WITH_CUSTOM_WORKFLOWS = [ "FedexAccount", "FedexSmartpostAccount", - "UpsAccount", ] _FILTERS_KEY = "filters" diff --git a/easypost/services/carrier_account_service.py b/easypost/services/carrier_account_service.py index f78ab78e..9b210262 100644 --- a/easypost/services/carrier_account_service.py +++ b/easypost/services/carrier_account_service.py @@ -60,6 +60,23 @@ def types(self) -> List[Dict[str, Any]]: return convert_to_easypost_object(response=response) + def create_ups(self, **params) -> CarrierAccount: + """Create a UPS CarrierAccount which has its own custom workflow.""" + url = "/ups_oauth_registrations" + wrapped_params = {"ups_oauth_registrations": params} + + response = Requestor(self._client).request( + method=RequestMethod.POST, + url=url, + params=wrapped_params, + ) + + return convert_to_easypost_object(response=response) + + def update_ups(self, id: str, **params) -> CarrierAccount: + """Update a UPS CarrierAccount which has its own custom workflow.""" + return self._update_resource("UpsOauthRegistrations", id, **params) + def _select_carrier_account_creation_endpoint(self, carrier_account_type: Optional[Any]) -> str: """Determines which API endpoint to use for the creation call.""" if carrier_account_type in _CARRIER_ACCOUNT_TYPES_WITH_CUSTOM_WORKFLOWS: diff --git a/tests/cassettes/test_carrier_account_create_ups.yaml b/tests/cassettes/test_carrier_account_create_ups.yaml new file mode 100644 index 00000000..5cf98f8b --- /dev/null +++ b/tests/cassettes/test_carrier_account_create_ups.yaml @@ -0,0 +1,69 @@ +interactions: +- request: + body: '{"ups_oauth_registrations": {"type": "UpsAccount"}}' + headers: + Accept: + - '*/*' + Accept-Encoding: + - gzip, deflate + Connection: + - keep-alive + Content-Length: + - '51' + Content-Type: + - application/json + authorization: + - + user-agent: + - + method: POST + uri: https://api.easypost.com/v2/ups_oauth_registrations + response: + body: + string: '{"error": {"code": "PARAMETER.REQUIRED", "message": "Missing required + parameter.", "errors": [{"field": "ups_oauth_registrations.account_number", + "message": "is required but missing"}]}}' + headers: + cache-control: + - private, no-cache, no-store + content-length: + - '177' + content-type: + - application/json; charset=utf-8 + expires: + - '0' + pragma: + - no-cache + referrer-policy: + - strict-origin-when-cross-origin + strict-transport-security: + - max-age=31536000; includeSubDomains; preload + transfer-encoding: + - chunked + x-backend: + - easypost + x-content-type-options: + - nosniff + x-download-options: + - noopen + x-ep-request-uuid: + - cbf7748e6685bf59e2bc356000275a02 + x-frame-options: + - SAMEORIGIN + x-node: + - bigweb35nuq + x-permitted-cross-domain-policies: + - none + x-proxied: + - intlb3nuq fa152d4755 + - extlb1nuq fa152d4755 + x-runtime: + - '0.043536' + x-version-label: + - easypost-202407031852-b015027e75-master + x-xss-protection: + - 1; mode=block + status: + code: 422 + message: Unprocessable Entity +version: 1 diff --git a/tests/cassettes/test_carrier_account_create_with_custom_workflow.yaml b/tests/cassettes/test_carrier_account_create_with_custom_workflow.yaml index 4a3567ac..38a5a314 100644 --- a/tests/cassettes/test_carrier_account_create_with_custom_workflow.yaml +++ b/tests/cassettes/test_carrier_account_create_with_custom_workflow.yaml @@ -1,6 +1,6 @@ interactions: - request: - body: '{"carrier_account": {"type": "UpsAccount", "registration_data": {}}}' + body: '{"carrier_account": {"type": "FedexAccount", "registration_data": {}}}' headers: Accept: - '*/*' @@ -9,7 +9,7 @@ interactions: Connection: - keep-alive Content-Length: - - '68' + - '70' Content-Type: - application/json authorization: @@ -21,22 +21,29 @@ interactions: response: body: string: '{"error": {"code": "UNPROCESSABLE_ENTITY", "message": "The request - was understood, but cannot be processed.", "errors": [{"field": "account_number", - "message": "must be present and a string"}, {"field": "city", "message": "must - be present and a string"}, {"field": "company", "message": "must be present - and a string"}, {"field": "country", "message": "must be present and a string"}, - {"field": "email", "message": "must be present and a string"}, {"field": "name", - "message": "must be present and a string"}, {"field": "phone", "message": - "must be present and a string"}, {"field": "postal_code", "message": "must - be present and a string"}, {"field": "state", "message": "must be present - and a string"}, {"field": "street1", "message": "must be present and a string"}, - {"field": "title", "message": "must be present and a string"}, {"field": "website", - "message": "must be present and a string"}]}}' + was understood, but cannot be processed.", "errors": [{"field": "shipping_streets", + "message": "must be present and a string"}, {"field": "shipping_city", "message": + "must be present and a string"}, {"field": "shipping_state", "message": "must + be present and a string"}, {"field": "shipping_postal_code", "message": "must + be present and a string"}, {"field": "shipping_country_code", "message": "must + be present and a string"}, {"field": "corporate_first_name", "message": "must + be present and a string"}, {"field": "corporate_last_name", "message": "must + be present and a string"}, {"field": "corporate_job_title", "message": "must + be present and a string"}, {"field": "corporate_company_name", "message": + "must be present and a string"}, {"field": "corporate_phone_number", "message": + "must be present and a string"}, {"field": "corporate_email_address", "message": + "must be present and a string"}, {"field": "corporate_streets", "message": + "must be present and a string"}, {"field": "corporate_city", "message": "must + be present and a string"}, {"field": "corporate_state", "message": "must be + present and a string"}, {"field": "corporate_postal_code", "message": "must + be present and a string"}, {"field": "corporate_country_code", "message": + "must be present and a string"}, {"field": "account_number", "message": "must + be present and a string"}]}}' headers: cache-control: - private, no-cache, no-store content-length: - - '846' + - '1347' content-type: - application/json; charset=utf-8 expires: @@ -56,21 +63,20 @@ interactions: x-download-options: - noopen x-ep-request-uuid: - - cdb1f665645ead1ce2aabe8300016878 + - cbf774926685bfece2bc38790027cf8b x-frame-options: - SAMEORIGIN x-node: - - bigweb12nuq + - bigweb39nuq x-permitted-cross-domain-policies: - none x-proxied: - - intlb1nuq a29e4ad05c - - intlb1wdc a29e4ad05c - - extlb3wdc 5ab12a3ed2 + - intlb3nuq fa152d4755 + - extlb1nuq fa152d4755 x-runtime: - - '0.033932' + - '0.042392' x-version-label: - - easypost-202305121849-b449e9bf47-master + - easypost-202407031852-b015027e75-master x-xss-protection: - 1; mode=block status: diff --git a/tests/cassettes/test_carrier_account_update_ups.yaml b/tests/cassettes/test_carrier_account_update_ups.yaml new file mode 100644 index 00000000..ba6d51d4 --- /dev/null +++ b/tests/cassettes/test_carrier_account_update_ups.yaml @@ -0,0 +1,70 @@ +interactions: +- request: + body: '{"ups_oauth_registrations": {"type": "UpsAccount"}}' + headers: + Accept: + - '*/*' + Accept-Encoding: + - gzip, deflate + Connection: + - keep-alive + Content-Length: + - '51' + Content-Type: + - application/json + authorization: + - + user-agent: + - + method: PATCH + uri: https://api.easypost.com/v2/ups_oauth_registrationses/ca_123 + response: + body: + string: '{"error": {"code": "NOT_FOUND", "message": "The requested resource + could not be found.", "errors": []}}' + headers: + cache-control: + - private, no-cache, no-store + content-length: + - '97' + content-type: + - application/json; charset=utf-8 + expires: + - '0' + pragma: + - no-cache + referrer-policy: + - strict-origin-when-cross-origin + strict-transport-security: + - max-age=31536000; includeSubDomains; preload + transfer-encoding: + - chunked + vary: + - Accept + x-backend: + - easypost + x-content-type-options: + - nosniff + x-download-options: + - noopen + x-ep-request-uuid: + - cbf774916685c061e2bc38b300282931 + x-frame-options: + - SAMEORIGIN + x-node: + - bigweb39nuq + x-permitted-cross-domain-policies: + - none + x-proxied: + - intlb4nuq fa152d4755 + - extlb1nuq fa152d4755 + x-runtime: + - '0.023543' + x-version-label: + - easypost-202407031852-b015027e75-master + x-xss-protection: + - 1; mode=block + status: + code: 404 + message: Not Found +version: 1 diff --git a/tests/test_carrier_account.py b/tests/test_carrier_account.py index c6d19f9f..114358b9 100644 --- a/tests/test_carrier_account.py +++ b/tests/test_carrier_account.py @@ -75,13 +75,13 @@ def test_carrier_account_type(prod_client): @pytest.mark.vcr() def test_carrier_account_create_with_custom_workflow(prod_client): - """Test register a Carrier Account with custom registration such as FedEx or UPS. + """Test registering a Carrier Account with custom workflow. We purposefully don't pass data here because real data is required for this endpoint which we don't have in a test context, simply assert the error matches when no data is passed. """ carrier_account = { - "type": "UpsAccount", + "type": "FedexAccount", "registration_data": {}, } @@ -93,3 +93,41 @@ def test_carrier_account_create_with_custom_workflow(prod_client): [error["field"] == "account_number" and error["message"] == "must be present and a string"] for error in error.errors ) + + +@pytest.mark.vcr() +def test_carrier_account_create_ups(prod_client): + """Test registering a UPS Carrier Account. + + We purposefully don't pass data here because real data is required for this endpoint + which we don't have in a test context, simply assert the error matches when no data is passed. + """ + carrier_account = { + "type": "UpsAccount", + } + + try: + prod_client.carrier_account.create_ups(**carrier_account) + except ApiError as error: + assert error.http_status == 422 + assert any( + [error["field"] == "account_number" and error["message"] == "must be present and a string"] + for error in error.errors + ) + + +@pytest.mark.vcr() +def test_carrier_account_update_ups(prod_client): + """Test updating a UPS Carrier Account. + + We purposefully don't pass data here because real data is required for this endpoint + which we don't have in a test context, simply assert that we routed the request correctly. + """ + carrier_account = { + "type": "UpsAccount", + } + + try: + prod_client.carrier_account.update_ups("ca_123", **carrier_account) + except ApiError as error: + assert error.http_status == 404 From 5036b2accd2fb708314cb0726c08e5442fabdf3b Mon Sep 17 00:00:00 2001 From: Justintime50 <39606064+Justintime50@users.noreply.github.com> Date: Mon, 8 Jul 2024 14:27:16 -0600 Subject: [PATCH 2/7] fix: route normal create/update functions based on type --- easypost/constant.py | 5 +++ easypost/services/carrier_account_service.py | 31 +++++++------------ .../test_carrier_account_create_ups.yaml | 24 +++++++------- .../test_carrier_account_update_ups.yaml | 14 ++++----- tests/test_carrier_account.py | 8 +++-- 5 files changed, 41 insertions(+), 41 deletions(-) diff --git a/easypost/constant.py b/easypost/constant.py index b076129a..b90ae707 100644 --- a/easypost/constant.py +++ b/easypost/constant.py @@ -36,4 +36,9 @@ "FedexAccount", "FedexSmartpostAccount", ] +_UPS_OATH_CARRIER_ACCOUNT_TYPES = [ + "UpsAccount", + "UpsMailInnovationsAccount", + "UpsSurepostAccount", +] _FILTERS_KEY = "filters" diff --git a/easypost/services/carrier_account_service.py b/easypost/services/carrier_account_service.py index 9b210262..995c8d18 100644 --- a/easypost/services/carrier_account_service.py +++ b/easypost/services/carrier_account_service.py @@ -7,6 +7,7 @@ from easypost.constant import ( _CARRIER_ACCOUNT_TYPES_WITH_CUSTOM_WORKFLOWS, + _UPS_OATH_CARRIER_ACCOUNT_TYPES, MISSING_PARAMETER_ERROR, ) from easypost.easypost_object import convert_to_easypost_object @@ -32,7 +33,10 @@ def create(self, **params) -> CarrierAccount: raise MissingParameterError(MISSING_PARAMETER_ERROR.format("type")) url = self._select_carrier_account_creation_endpoint(carrier_account_type=carrier_account_type) - wrapped_params = {self._snakecase_name(self._model_class): params} + if carrier_account_type in _UPS_OATH_CARRIER_ACCOUNT_TYPES: + wrapped_params = {"ups_oauth_registrations": params} + else: + wrapped_params = {self._snakecase_name(self._model_class): params} response = Requestor(self._client).request(method=RequestMethod.POST, url=url, params=wrapped_params) @@ -48,7 +52,11 @@ def retrieve(self, id: str) -> CarrierAccount: def update(self, id: str, **params) -> CarrierAccount: """Update a CarrierAccount.""" - return self._update_resource(self._model_class, id, **params) + if params.get("type") in _UPS_OATH_CARRIER_ACCOUNT_TYPES: + class_name = "UpsOauthRegistrations" + else: + class_name = self._model_class + return self._update_resource(class_name, id, **params) def delete(self, id: str) -> None: """Delete a CarrierAccount.""" @@ -60,26 +68,11 @@ def types(self) -> List[Dict[str, Any]]: return convert_to_easypost_object(response=response) - def create_ups(self, **params) -> CarrierAccount: - """Create a UPS CarrierAccount which has its own custom workflow.""" - url = "/ups_oauth_registrations" - wrapped_params = {"ups_oauth_registrations": params} - - response = Requestor(self._client).request( - method=RequestMethod.POST, - url=url, - params=wrapped_params, - ) - - return convert_to_easypost_object(response=response) - - def update_ups(self, id: str, **params) -> CarrierAccount: - """Update a UPS CarrierAccount which has its own custom workflow.""" - return self._update_resource("UpsOauthRegistrations", id, **params) - def _select_carrier_account_creation_endpoint(self, carrier_account_type: Optional[Any]) -> str: """Determines which API endpoint to use for the creation call.""" if carrier_account_type in _CARRIER_ACCOUNT_TYPES_WITH_CUSTOM_WORKFLOWS: return "/carrier_accounts/register" + elif carrier_account_type in _UPS_OATH_CARRIER_ACCOUNT_TYPES: + return "/ups_oauth_registrations" return "/carrier_accounts" diff --git a/tests/cassettes/test_carrier_account_create_ups.yaml b/tests/cassettes/test_carrier_account_create_ups.yaml index 5cf98f8b..07ff059c 100644 --- a/tests/cassettes/test_carrier_account_create_ups.yaml +++ b/tests/cassettes/test_carrier_account_create_ups.yaml @@ -1,6 +1,6 @@ interactions: - request: - body: '{"ups_oauth_registrations": {"type": "UpsAccount"}}' + body: '{"ups_oauth_registrations": {"type": "UpsAccount", "account_number": 123}}' headers: Accept: - '*/*' @@ -9,7 +9,7 @@ interactions: Connection: - keep-alive Content-Length: - - '51' + - '74' Content-Type: - application/json authorization: @@ -20,14 +20,14 @@ interactions: uri: https://api.easypost.com/v2/ups_oauth_registrations response: body: - string: '{"error": {"code": "PARAMETER.REQUIRED", "message": "Missing required - parameter.", "errors": [{"field": "ups_oauth_registrations.account_number", - "message": "is required but missing"}]}}' + string: '{"error": {"code": "PARAMETER.INVALID_TYPE", "message": "Wrong parameter + type.", "errors": [{"field": "ups_oauth_registrations.account_number", "message": + "must be a string"}]}}' headers: cache-control: - private, no-cache, no-store content-length: - - '177' + - '168' content-type: - application/json; charset=utf-8 expires: @@ -47,20 +47,20 @@ interactions: x-download-options: - noopen x-ep-request-uuid: - - cbf7748e6685bf59e2bc356000275a02 + - b98ca9f3668c49a7e2cb1d1f001f7231 x-frame-options: - SAMEORIGIN x-node: - - bigweb35nuq + - bigweb36nuq x-permitted-cross-domain-policies: - none x-proxied: - - intlb3nuq fa152d4755 - - extlb1nuq fa152d4755 + - intlb4nuq fa152d4755 + - extlb2nuq fa152d4755 x-runtime: - - '0.043536' + - '0.053482' x-version-label: - - easypost-202407031852-b015027e75-master + - easypost-202407081949-3228d5845b-master x-xss-protection: - 1; mode=block status: diff --git a/tests/cassettes/test_carrier_account_update_ups.yaml b/tests/cassettes/test_carrier_account_update_ups.yaml index ba6d51d4..7957e5de 100644 --- a/tests/cassettes/test_carrier_account_update_ups.yaml +++ b/tests/cassettes/test_carrier_account_update_ups.yaml @@ -1,6 +1,6 @@ interactions: - request: - body: '{"ups_oauth_registrations": {"type": "UpsAccount"}}' + body: '{"ups_oauth_registrations": {"type": "UpsAccount", "account_number": 123}}' headers: Accept: - '*/*' @@ -9,7 +9,7 @@ interactions: Connection: - keep-alive Content-Length: - - '51' + - '74' Content-Type: - application/json authorization: @@ -48,20 +48,20 @@ interactions: x-download-options: - noopen x-ep-request-uuid: - - cbf774916685c061e2bc38b300282931 + - b98ca9f4668c4b72e2cb215a00213aef x-frame-options: - SAMEORIGIN x-node: - - bigweb39nuq + - bigweb36nuq x-permitted-cross-domain-policies: - none x-proxied: - intlb4nuq fa152d4755 - - extlb1nuq fa152d4755 + - extlb2nuq fa152d4755 x-runtime: - - '0.023543' + - '0.033617' x-version-label: - - easypost-202407031852-b015027e75-master + - easypost-202407081949-3228d5845b-master x-xss-protection: - 1; mode=block status: diff --git a/tests/test_carrier_account.py b/tests/test_carrier_account.py index 114358b9..b129c3f6 100644 --- a/tests/test_carrier_account.py +++ b/tests/test_carrier_account.py @@ -104,10 +104,11 @@ def test_carrier_account_create_ups(prod_client): """ carrier_account = { "type": "UpsAccount", + "account_number": 123, } try: - prod_client.carrier_account.create_ups(**carrier_account) + prod_client.carrier_account.create(**carrier_account) except ApiError as error: assert error.http_status == 422 assert any( @@ -121,13 +122,14 @@ def test_carrier_account_update_ups(prod_client): """Test updating a UPS Carrier Account. We purposefully don't pass data here because real data is required for this endpoint - which we don't have in a test context, simply assert that we routed the request correctly. + which we don't have in a test context, simply assert that we sent the request correctly. """ carrier_account = { "type": "UpsAccount", + "account_number": 123, } try: - prod_client.carrier_account.update_ups("ca_123", **carrier_account) + prod_client.carrier_account.update("ca_123", **carrier_account) except ApiError as error: assert error.http_status == 404 From bff5a0d8490d727f06c5cf08b41919c313641381 Mon Sep 17 00:00:00 2001 From: Justintime50 <39606064+Justintime50@users.noreply.github.com> Date: Mon, 8 Jul 2024 14:29:41 -0600 Subject: [PATCH 3/7] docs: fix changelog --- CHANGELOG.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index c35aedef..ac031441 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,8 +2,8 @@ ## Next Release -- Adds new `create_ups` and `update_ups` functions under `carrier_account` - - Starting `2024-08-05`, UPS accounts can no longer be created or updated through the normal create and update functions and must use these UPS specific functions +- Routes `UpsAccount`, `UpsMailInnovationsAccount`, and `UpsSurepostAccount` create/update requests to the new `/ups_oauth_registrations` endpoint + - Starting `2024-08-05`, UPS accounts will require a new payload to register or update. See [UPS OAuth 2.0 Update](https://support.easypost.com/hc/en-us/articles/26635027512717-UPS-OAuth-2-0-Update?utm_medium=email&_hsenc=p2ANqtz-96MmFtWICOzy9sKRbbcZSiMovZSrY3MSX1_bgY9N3f9yLVfWQdLhjAGq-SmNcOnDIS6GYhZ0OApjDBrGkKyLLMx1z6_TFOVp6-wllhEFQINrkuRuc&_hsmi=313130292&utm_content=313130292&utm_source=hs_email) for more details ## v9.2.0 (2024-04-10) From 5331fe4a2ec760c4f0a802d422b70408c057d43d Mon Sep 17 00:00:00 2001 From: Justintime50 <39606064+Justintime50@users.noreply.github.com> Date: Mon, 8 Jul 2024 15:00:29 -0600 Subject: [PATCH 4/7] fix: update method --- easypost/services/carrier_account_service.py | 5 +- .../test_carrier_account_update.yaml | 131 +++++++++++++----- .../test_carrier_account_update_ups.yaml | 16 +-- tests/test_carrier_account.py | 7 +- 4 files changed, 113 insertions(+), 46 deletions(-) diff --git a/easypost/services/carrier_account_service.py b/easypost/services/carrier_account_service.py index 995c8d18..0864c035 100644 --- a/easypost/services/carrier_account_service.py +++ b/easypost/services/carrier_account_service.py @@ -52,10 +52,13 @@ def retrieve(self, id: str) -> CarrierAccount: def update(self, id: str, **params) -> CarrierAccount: """Update a CarrierAccount.""" - if params.get("type") in _UPS_OATH_CARRIER_ACCOUNT_TYPES: + carrier_account = self.retrieve(id) + + if carrier_account.get("type") in _UPS_OATH_CARRIER_ACCOUNT_TYPES: class_name = "UpsOauthRegistrations" else: class_name = self._model_class + return self._update_resource(class_name, id, **params) def delete(self, id: str) -> None: diff --git a/tests/cassettes/test_carrier_account_update.yaml b/tests/cassettes/test_carrier_account_update.yaml index 9ff62938..712b8f12 100644 --- a/tests/cassettes/test_carrier_account_update.yaml +++ b/tests/cassettes/test_carrier_account_update.yaml @@ -23,9 +23,9 @@ interactions: uri: https://api.easypost.com/v2/carrier_accounts response: body: - string: '{"id": "ca_a575738b0d994778a960c5c19e748baa", "object": "CarrierAccount", - "type": "DhlEcsAccount", "clone": false, "created_at": "2023-05-12T21:21:53Z", - "updated_at": "2023-05-12T21:21:53Z", "description": "DHL eCommerce Solutions + string: '{"id": "ca_c58170a2b708469eb2828ce150f818c5", "object": "CarrierAccount", + "type": "DhlEcsAccount", "clone": false, "created_at": "2024-07-08T20:54:18Z", + "updated_at": "2024-07-08T20:54:18Z", "description": "DHL eCommerce Solutions Account", "reference": null, "billing_type": "carrier", "readable": "DHL eCommerce Solutions", "logo": null, "fields": [], "credentials": {}, "test_credentials": {}}' @@ -36,8 +36,6 @@ interactions: - '1469' content-type: - application/json; charset=utf-8 - etag: - - W/"ae937268738bf972b34e687a182d5a17" expires: - '0' pragma: @@ -50,31 +48,100 @@ interactions: - chunked x-backend: - easypost + x-canary: + - direct x-content-type-options: - nosniff x-download-options: - noopen x-ep-request-uuid: - - fe8d870a645eadf1e2aac27e000e79d2 + - df6fc7b2668c51fae2cba07700263f54 x-frame-options: - SAMEORIGIN x-node: - - bigweb9nuq + - bigweb43nuq x-permitted-cross-domain-policies: - none x-proxied: - - intlb1nuq a29e4ad05c - - intlb2wdc a29e4ad05c - - extlb4wdc 5ab12a3ed2 + - intlb4nuq fa152d4755 + - extlb1nuq fa152d4755 x-runtime: - - '0.111611' + - '0.127030' x-version-label: - - easypost-202305122104-29dd2d738a-master + - easypost-202407081949-3228d5845b-master x-xss-protection: - 1; mode=block status: code: 201 message: Created +- request: + body: null + headers: + Accept: + - '*/*' + Accept-Encoding: + - gzip, deflate + Connection: + - keep-alive + authorization: + - + user-agent: + - + method: GET + uri: https://api.easypost.com/v2/carrier_accounts/ca_c58170a2b708469eb2828ce150f818c5 + response: + body: + string: '{"id": "ca_c58170a2b708469eb2828ce150f818c5", "object": "CarrierAccount", + "type": "DhlEcsAccount", "clone": false, "created_at": "2024-07-08T20:54:18Z", + "updated_at": "2024-07-08T20:54:18Z", "description": "DHL eCommerce Solutions + Account", "reference": null, "billing_type": "carrier", "readable": "DHL eCommerce + Solutions", "logo": null, "fields": [], "credentials": {}, "test_credentials": + {}}' + headers: + cache-control: + - private, no-cache, no-store + content-length: + - '1469' + content-type: + - application/json; charset=utf-8 + expires: + - '0' + pragma: + - no-cache + referrer-policy: + - strict-origin-when-cross-origin + strict-transport-security: + - max-age=31536000; includeSubDomains; preload + transfer-encoding: + - chunked + x-backend: + - easypost + x-canary: + - direct + x-content-type-options: + - nosniff + x-download-options: + - noopen + x-ep-request-uuid: + - df6fc7b2668c51fbe2cba07700263f78 + x-frame-options: + - SAMEORIGIN + x-node: + - bigweb32nuq + x-permitted-cross-domain-policies: + - none + x-proxied: + - intlb4nuq fa152d4755 + - extlb1nuq fa152d4755 + x-runtime: + - '0.036536' + x-version-label: + - easypost-202407081949-3228d5845b-master + x-xss-protection: + - 1; mode=block + status: + code: 200 + message: OK - request: body: '{"carrier_account": {"description": "My custom description"}}' headers: @@ -93,12 +160,12 @@ interactions: user-agent: - method: PATCH - uri: https://api.easypost.com/v2/carrier_accounts/ca_a575738b0d994778a960c5c19e748baa + uri: https://api.easypost.com/v2/carrier_accounts/ca_c58170a2b708469eb2828ce150f818c5 response: body: - string: '{"id": "ca_a575738b0d994778a960c5c19e748baa", "object": "CarrierAccount", - "type": "DhlEcsAccount", "clone": false, "created_at": "2023-05-12T21:21:53Z", - "updated_at": "2023-05-12T21:21:54Z", "description": "My custom description", + string: '{"id": "ca_c58170a2b708469eb2828ce150f818c5", "object": "CarrierAccount", + "type": "DhlEcsAccount", "clone": false, "created_at": "2024-07-08T20:54:18Z", + "updated_at": "2024-07-08T20:54:19Z", "description": "My custom description", "reference": null, "billing_type": "carrier", "readable": "DHL eCommerce Solutions", "logo": null, "fields": [], "credentials": {}, "test_credentials": {}}' headers: @@ -108,8 +175,6 @@ interactions: - '1459' content-type: - application/json; charset=utf-8 - etag: - - W/"f872eb829c218950953d19ed5a7de737" expires: - '0' pragma: @@ -127,21 +192,20 @@ interactions: x-download-options: - noopen x-ep-request-uuid: - - fe8d870a645eadf1e2aac27e000e79f4 + - df6fc7b2668c51fbe2cba07700263f8d x-frame-options: - SAMEORIGIN x-node: - - bigweb5nuq + - bigweb39nuq x-permitted-cross-domain-policies: - none x-proxied: - - intlb1nuq a29e4ad05c - - intlb2wdc a29e4ad05c - - extlb4wdc 5ab12a3ed2 + - intlb3nuq fa152d4755 + - extlb1nuq fa152d4755 x-runtime: - - '0.127137' + - '0.113688' x-version-label: - - easypost-202305121849-b449e9bf47-master + - easypost-202407081949-3228d5845b-master x-xss-protection: - 1; mode=block status: @@ -163,7 +227,7 @@ interactions: user-agent: - method: DELETE - uri: https://api.easypost.com/v2/carrier_accounts/ca_a575738b0d994778a960c5c19e748baa + uri: https://api.easypost.com/v2/carrier_accounts/ca_c58170a2b708469eb2828ce150f818c5 response: body: string: '{}' @@ -174,8 +238,6 @@ interactions: - '2' content-type: - application/json; charset=utf-8 - etag: - - W/"44136fa355b3678a1146ad16f7e8649e" expires: - '0' pragma: @@ -193,21 +255,20 @@ interactions: x-download-options: - noopen x-ep-request-uuid: - - fe8d870a645eadf2e2aac27e000e7a0c + - df6fc7b2668c51fbe2cba07700263fb1 x-frame-options: - SAMEORIGIN x-node: - - bigweb4nuq + - bigweb38nuq x-permitted-cross-domain-policies: - none x-proxied: - - intlb2nuq a29e4ad05c - - intlb1wdc a29e4ad05c - - extlb4wdc 5ab12a3ed2 + - intlb3nuq fa152d4755 + - extlb1nuq fa152d4755 x-runtime: - - '0.113851' + - '0.066036' x-version-label: - - easypost-202305121849-b449e9bf47-master + - easypost-202407081949-3228d5845b-master x-xss-protection: - 1; mode=block status: diff --git a/tests/cassettes/test_carrier_account_update_ups.yaml b/tests/cassettes/test_carrier_account_update_ups.yaml index 7957e5de..a1887fb0 100644 --- a/tests/cassettes/test_carrier_account_update_ups.yaml +++ b/tests/cassettes/test_carrier_account_update_ups.yaml @@ -1,6 +1,6 @@ interactions: - request: - body: '{"ups_oauth_registrations": {"type": "UpsAccount", "account_number": 123}}' + body: '{"carrier_account": {"type": "UpsAccount", "account_number": 123}}' headers: Accept: - '*/*' @@ -9,7 +9,7 @@ interactions: Connection: - keep-alive Content-Length: - - '74' + - '66' Content-Type: - application/json authorization: @@ -17,7 +17,7 @@ interactions: user-agent: - method: PATCH - uri: https://api.easypost.com/v2/ups_oauth_registrationses/ca_123 + uri: https://api.easypost.com/v2/carrier_accounts/ca_123 response: body: string: '{"error": {"code": "NOT_FOUND", "message": "The requested resource @@ -39,8 +39,6 @@ interactions: - max-age=31536000; includeSubDomains; preload transfer-encoding: - chunked - vary: - - Accept x-backend: - easypost x-content-type-options: @@ -48,18 +46,18 @@ interactions: x-download-options: - noopen x-ep-request-uuid: - - b98ca9f4668c4b72e2cb215a00213aef + - df6fc7b5668c5334e2cba540002749ac x-frame-options: - SAMEORIGIN x-node: - - bigweb36nuq + - bigweb34nuq x-permitted-cross-domain-policies: - none x-proxied: - intlb4nuq fa152d4755 - - extlb2nuq fa152d4755 + - extlb1nuq fa152d4755 x-runtime: - - '0.033617' + - '0.052189' x-version-label: - easypost-202407081949-3228d5845b-master x-xss-protection: diff --git a/tests/test_carrier_account.py b/tests/test_carrier_account.py index b129c3f6..1b0f734d 100644 --- a/tests/test_carrier_account.py +++ b/tests/test_carrier_account.py @@ -1,3 +1,5 @@ +from unittest.mock import patch + import pytest from easypost.errors.api.api_error import ApiError from easypost.models import CarrierAccount @@ -118,11 +120,14 @@ def test_carrier_account_create_ups(prod_client): @pytest.mark.vcr() -def test_carrier_account_update_ups(prod_client): +@patch("easypost.services.carrier_account_service.CarrierAccountService.retrieve") +def test_carrier_account_update_ups(mock_retrieve, prod_client): """Test updating a UPS Carrier Account. We purposefully don't pass data here because real data is required for this endpoint which we don't have in a test context, simply assert that we sent the request correctly. + + This test will require someone to ensure the cassette looks the way we want (URL) """ carrier_account = { "type": "UpsAccount", From 4f93a56bd86f5177b4ffe3ba4152ba0923d86f23 Mon Sep 17 00:00:00 2001 From: Justintime50 <39606064+Justintime50@users.noreply.github.com> Date: Mon, 8 Jul 2024 15:28:24 -0600 Subject: [PATCH 5/7] fix: return type of mock --- .../test_carrier_account_update_ups.yaml | 16 +++++++++------- tests/test_carrier_account.py | 5 ++++- 2 files changed, 13 insertions(+), 8 deletions(-) diff --git a/tests/cassettes/test_carrier_account_update_ups.yaml b/tests/cassettes/test_carrier_account_update_ups.yaml index a1887fb0..e1f605e9 100644 --- a/tests/cassettes/test_carrier_account_update_ups.yaml +++ b/tests/cassettes/test_carrier_account_update_ups.yaml @@ -1,6 +1,6 @@ interactions: - request: - body: '{"carrier_account": {"type": "UpsAccount", "account_number": 123}}' + body: '{"ups_oauth_registrations": {"type": "UpsAccount", "account_number": 123}}' headers: Accept: - '*/*' @@ -9,7 +9,7 @@ interactions: Connection: - keep-alive Content-Length: - - '66' + - '74' Content-Type: - application/json authorization: @@ -17,7 +17,7 @@ interactions: user-agent: - method: PATCH - uri: https://api.easypost.com/v2/carrier_accounts/ca_123 + uri: https://api.easypost.com/v2/ups_oauth_registrationses/ca_123 response: body: string: '{"error": {"code": "NOT_FOUND", "message": "The requested resource @@ -39,6 +39,8 @@ interactions: - max-age=31536000; includeSubDomains; preload transfer-encoding: - chunked + vary: + - Accept x-backend: - easypost x-content-type-options: @@ -46,18 +48,18 @@ interactions: x-download-options: - noopen x-ep-request-uuid: - - df6fc7b5668c5334e2cba540002749ac + - b98ca9f4668c59ebe2cc2cd8002eee16 x-frame-options: - SAMEORIGIN x-node: - - bigweb34nuq + - bigweb42nuq x-permitted-cross-domain-policies: - none x-proxied: - intlb4nuq fa152d4755 - - extlb1nuq fa152d4755 + - extlb2nuq fa152d4755 x-runtime: - - '0.052189' + - '0.024976' x-version-label: - easypost-202407081949-3228d5845b-master x-xss-protection: diff --git a/tests/test_carrier_account.py b/tests/test_carrier_account.py index 1b0f734d..573b1b2c 100644 --- a/tests/test_carrier_account.py +++ b/tests/test_carrier_account.py @@ -120,7 +120,10 @@ def test_carrier_account_create_ups(prod_client): @pytest.mark.vcr() -@patch("easypost.services.carrier_account_service.CarrierAccountService.retrieve") +@patch( + "easypost.services.carrier_account_service.CarrierAccountService.retrieve", + return_value={"type": "UpsAccount"}, +) def test_carrier_account_update_ups(mock_retrieve, prod_client): """Test updating a UPS Carrier Account. From 5be741a2132b01db42c441b5e72451264307cead Mon Sep 17 00:00:00 2001 From: Justintime50 <39606064+Justintime50@users.noreply.github.com> Date: Tue, 9 Jul 2024 11:24:06 -0600 Subject: [PATCH 6/7] fix: ups carrier account tests --- easypost/constant.py | 3 +- easypost/services/base_service.py | 5 +- easypost/services/carrier_account_service.py | 8 +- .../test_carrier_account_create_ups.yaml | 93 ++++++- .../test_carrier_account_update_ups.yaml | 230 ++++++++++++++++-- tests/test_carrier_account.py | 54 ++-- 6 files changed, 326 insertions(+), 67 deletions(-) diff --git a/easypost/constant.py b/easypost/constant.py index b90ae707..3d153e65 100644 --- a/easypost/constant.py +++ b/easypost/constant.py @@ -36,9 +36,10 @@ "FedexAccount", "FedexSmartpostAccount", ] -_UPS_OATH_CARRIER_ACCOUNT_TYPES = [ +_UPS_OAUTH_CARRIER_ACCOUNT_TYPES = [ "UpsAccount", "UpsMailInnovationsAccount", "UpsSurepostAccount", ] _FILTERS_KEY = "filters" +_EXCLUDED_CLASS_NAMES = ["ups_oauth_registrations"] diff --git a/easypost/services/base_service.py b/easypost/services/base_service.py index 2e6c5c53..203aa5f2 100644 --- a/easypost/services/base_service.py +++ b/easypost/services/base_service.py @@ -6,6 +6,7 @@ ) from easypost.constant import ( + _EXCLUDED_CLASS_NAMES, _FILTERS_KEY, NO_MORE_PAGES_ERROR, ) @@ -30,7 +31,9 @@ def _snakecase_name(self, class_name: str) -> str: def _class_url(self, class_name: str) -> str: """Generate a URL based on class name.""" transformed_class_name = self._snakecase_name(class_name) - if transformed_class_name[-1:] in ("s", "h"): + if transformed_class_name in _EXCLUDED_CLASS_NAMES: + return f"/{transformed_class_name}" + elif transformed_class_name[-1:] in ("s", "h"): return f"/{transformed_class_name}es" else: return f"/{transformed_class_name}s" diff --git a/easypost/services/carrier_account_service.py b/easypost/services/carrier_account_service.py index 0864c035..53d3cead 100644 --- a/easypost/services/carrier_account_service.py +++ b/easypost/services/carrier_account_service.py @@ -7,7 +7,7 @@ from easypost.constant import ( _CARRIER_ACCOUNT_TYPES_WITH_CUSTOM_WORKFLOWS, - _UPS_OATH_CARRIER_ACCOUNT_TYPES, + _UPS_OAUTH_CARRIER_ACCOUNT_TYPES, MISSING_PARAMETER_ERROR, ) from easypost.easypost_object import convert_to_easypost_object @@ -33,7 +33,7 @@ def create(self, **params) -> CarrierAccount: raise MissingParameterError(MISSING_PARAMETER_ERROR.format("type")) url = self._select_carrier_account_creation_endpoint(carrier_account_type=carrier_account_type) - if carrier_account_type in _UPS_OATH_CARRIER_ACCOUNT_TYPES: + if carrier_account_type in _UPS_OAUTH_CARRIER_ACCOUNT_TYPES: wrapped_params = {"ups_oauth_registrations": params} else: wrapped_params = {self._snakecase_name(self._model_class): params} @@ -54,7 +54,7 @@ def update(self, id: str, **params) -> CarrierAccount: """Update a CarrierAccount.""" carrier_account = self.retrieve(id) - if carrier_account.get("type") in _UPS_OATH_CARRIER_ACCOUNT_TYPES: + if carrier_account.get("type") in _UPS_OAUTH_CARRIER_ACCOUNT_TYPES: class_name = "UpsOauthRegistrations" else: class_name = self._model_class @@ -75,7 +75,7 @@ def _select_carrier_account_creation_endpoint(self, carrier_account_type: Option """Determines which API endpoint to use for the creation call.""" if carrier_account_type in _CARRIER_ACCOUNT_TYPES_WITH_CUSTOM_WORKFLOWS: return "/carrier_accounts/register" - elif carrier_account_type in _UPS_OATH_CARRIER_ACCOUNT_TYPES: + elif carrier_account_type in _UPS_OAUTH_CARRIER_ACCOUNT_TYPES: return "/ups_oauth_registrations" return "/carrier_accounts" diff --git a/tests/cassettes/test_carrier_account_create_ups.yaml b/tests/cassettes/test_carrier_account_create_ups.yaml index 07ff059c..36a389f4 100644 --- a/tests/cassettes/test_carrier_account_create_ups.yaml +++ b/tests/cassettes/test_carrier_account_create_ups.yaml @@ -1,6 +1,6 @@ interactions: - request: - body: '{"ups_oauth_registrations": {"type": "UpsAccount", "account_number": 123}}' + body: '{"ups_oauth_registrations": {"type": "UpsAccount", "account_number": "123456789"}}' headers: Accept: - '*/*' @@ -9,7 +9,7 @@ interactions: Connection: - keep-alive Content-Length: - - '74' + - '82' Content-Type: - application/json authorization: @@ -20,14 +20,16 @@ interactions: uri: https://api.easypost.com/v2/ups_oauth_registrations response: body: - string: '{"error": {"code": "PARAMETER.INVALID_TYPE", "message": "Wrong parameter - type.", "errors": [{"field": "ups_oauth_registrations.account_number", "message": - "must be a string"}]}}' + string: '{"id": "ca_032bd1041a5d4418b8378bcc2a738a45", "object": "CarrierAccount", + "type": "UpsAccount", "clone": false, "created_at": "2024-07-09T17:02:56Z", + "updated_at": "2024-07-09T17:02:56Z", "description": null, "reference": null, + "billing_type": "carrier", "readable": "UPS", "logo": null, "fields": [], + "credentials": {}, "test_credentials": {}}' headers: cache-control: - private, no-cache, no-store content-length: - - '168' + - '1392' content-type: - application/json; charset=utf-8 expires: @@ -47,23 +49,88 @@ interactions: x-download-options: - noopen x-ep-request-uuid: - - b98ca9f3668c49a7e2cb1d1f001f7231 + - 52ecff22668d6d40e2b7ddea00434ef1 x-frame-options: - SAMEORIGIN x-node: - - bigweb36nuq + - bigweb34nuq x-permitted-cross-domain-policies: - none x-proxied: - intlb4nuq fa152d4755 - - extlb2nuq fa152d4755 + - extlb1nuq fa152d4755 x-runtime: - - '0.053482' + - '0.087747' x-version-label: - - easypost-202407081949-3228d5845b-master + - easypost-202407091438-d7c6f02f06-master x-xss-protection: - 1; mode=block status: - code: 422 - message: Unprocessable Entity + code: 201 + message: Created +- request: + body: null + headers: + Accept: + - '*/*' + Accept-Encoding: + - gzip, deflate + Connection: + - keep-alive + Content-Length: + - '0' + authorization: + - + user-agent: + - + method: DELETE + uri: https://api.easypost.com/v2/carrier_accounts/ca_032bd1041a5d4418b8378bcc2a738a45 + response: + body: + string: '{}' + headers: + cache-control: + - private, no-cache, no-store + content-length: + - '2' + content-type: + - application/json; charset=utf-8 + expires: + - '0' + pragma: + - no-cache + referrer-policy: + - strict-origin-when-cross-origin + strict-transport-security: + - max-age=31536000; includeSubDomains; preload + transfer-encoding: + - chunked + x-backend: + - easypost + x-canary: + - direct + x-content-type-options: + - nosniff + x-download-options: + - noopen + x-ep-request-uuid: + - 52ecff22668d6d40e2b7ddea00434f1f + x-frame-options: + - SAMEORIGIN + x-node: + - bigweb43nuq + x-permitted-cross-domain-policies: + - none + x-proxied: + - intlb3nuq fa152d4755 + - extlb1nuq fa152d4755 + x-runtime: + - '0.208397' + x-version-label: + - easypost-202407091438-d7c6f02f06-master + x-xss-protection: + - 1; mode=block + status: + code: 200 + message: OK version: 1 diff --git a/tests/cassettes/test_carrier_account_update_ups.yaml b/tests/cassettes/test_carrier_account_update_ups.yaml index e1f605e9..005b5423 100644 --- a/tests/cassettes/test_carrier_account_update_ups.yaml +++ b/tests/cassettes/test_carrier_account_update_ups.yaml @@ -1,6 +1,6 @@ interactions: - request: - body: '{"ups_oauth_registrations": {"type": "UpsAccount", "account_number": 123}}' + body: '{"ups_oauth_registrations": {"type": "UpsAccount", "account_number": "123456789"}}' headers: Accept: - '*/*' @@ -9,24 +9,92 @@ interactions: Connection: - keep-alive Content-Length: - - '74' + - '82' Content-Type: - application/json authorization: - user-agent: - - method: PATCH - uri: https://api.easypost.com/v2/ups_oauth_registrationses/ca_123 + method: POST + uri: https://api.easypost.com/v2/ups_oauth_registrations + response: + body: + string: '{"id": "ca_e5527ea2bd0f44c59f85fd198428da2b", "object": "CarrierAccount", + "type": "UpsAccount", "clone": false, "created_at": "2024-07-09T17:22:32Z", + "updated_at": "2024-07-09T17:22:32Z", "description": null, "reference": null, + "billing_type": "carrier", "readable": "UPS", "logo": null, "fields": [], + "credentials": {}, "test_credentials": {}}' + headers: + cache-control: + - private, no-cache, no-store + content-length: + - '1388' + content-type: + - application/json; charset=utf-8 + expires: + - '0' + pragma: + - no-cache + referrer-policy: + - strict-origin-when-cross-origin + strict-transport-security: + - max-age=31536000; includeSubDomains; preload + transfer-encoding: + - chunked + x-backend: + - easypost + x-content-type-options: + - nosniff + x-download-options: + - noopen + x-ep-request-uuid: + - 52ecff1e668d71d8e2b7eef000485d09 + x-frame-options: + - SAMEORIGIN + x-node: + - bigweb53nuq + x-permitted-cross-domain-policies: + - none + x-proxied: + - intlb4nuq fa152d4755 + - extlb1nuq fa152d4755 + x-runtime: + - '0.090996' + x-version-label: + - easypost-202407091438-d7c6f02f06-master + x-xss-protection: + - 1; mode=block + status: + code: 201 + message: Created +- request: + body: null + headers: + Accept: + - '*/*' + Accept-Encoding: + - gzip, deflate + Connection: + - keep-alive + authorization: + - + user-agent: + - + method: GET + uri: https://api.easypost.com/v2/carrier_accounts/ca_e5527ea2bd0f44c59f85fd198428da2b response: body: - string: '{"error": {"code": "NOT_FOUND", "message": "The requested resource - could not be found.", "errors": []}}' + string: '{"id": "ca_e5527ea2bd0f44c59f85fd198428da2b", "object": "CarrierAccount", + "type": "UpsAccount", "clone": false, "created_at": "2024-07-09T17:22:32Z", + "updated_at": "2024-07-09T17:22:32Z", "description": null, "reference": null, + "billing_type": "carrier", "readable": "UPS", "logo": null, "fields": [], + "credentials": {}, "test_credentials": {}}' headers: cache-control: - private, no-cache, no-store content-length: - - '97' + - '1388' content-type: - application/json; charset=utf-8 expires: @@ -39,8 +107,6 @@ interactions: - max-age=31536000; includeSubDomains; preload transfer-encoding: - chunked - vary: - - Accept x-backend: - easypost x-content-type-options: @@ -48,23 +114,155 @@ interactions: x-download-options: - noopen x-ep-request-uuid: - - b98ca9f4668c59ebe2cc2cd8002eee16 + - 52ecff1e668d71d8e2b7eef000485d33 x-frame-options: - SAMEORIGIN x-node: - - bigweb42nuq + - bigweb36nuq x-permitted-cross-domain-policies: - none x-proxied: - intlb4nuq fa152d4755 - - extlb2nuq fa152d4755 + - extlb1nuq fa152d4755 + x-runtime: + - '0.040106' + x-version-label: + - easypost-202407091438-d7c6f02f06-master + x-xss-protection: + - 1; mode=block + status: + code: 200 + message: OK +- request: + body: '{"ups_oauth_registrations": {"account_number": "987654321"}}' + headers: + Accept: + - '*/*' + Accept-Encoding: + - gzip, deflate + Connection: + - keep-alive + Content-Length: + - '60' + Content-Type: + - application/json + authorization: + - + user-agent: + - + method: PATCH + uri: https://api.easypost.com/v2/ups_oauth_registrations/ca_e5527ea2bd0f44c59f85fd198428da2b + response: + body: + string: '{"id": "ca_e5527ea2bd0f44c59f85fd198428da2b", "object": "CarrierAccount", + "type": "UpsAccount", "clone": false, "created_at": "2024-07-09T17:22:32Z", + "updated_at": "2024-07-09T17:22:32Z", "description": null, "reference": null, + "billing_type": "carrier", "readable": "UPS", "logo": null, "fields": [], + "credentials": {}, "test_credentials": {}}' + headers: + cache-control: + - private, no-cache, no-store + content-length: + - '1416' + content-type: + - application/json; charset=utf-8 + expires: + - '0' + pragma: + - no-cache + referrer-policy: + - strict-origin-when-cross-origin + strict-transport-security: + - max-age=31536000; includeSubDomains; preload + transfer-encoding: + - chunked + x-backend: + - easypost + x-content-type-options: + - nosniff + x-download-options: + - noopen + x-ep-request-uuid: + - 52ecff1e668d71d8e2b7eef000485d4a + x-frame-options: + - SAMEORIGIN + x-node: + - bigweb39nuq + x-permitted-cross-domain-policies: + - none + x-proxied: + - intlb3nuq fa152d4755 + - extlb1nuq fa152d4755 + x-runtime: + - '0.079076' + x-version-label: + - easypost-202407091438-d7c6f02f06-master + x-xss-protection: + - 1; mode=block + status: + code: 200 + message: OK +- request: + body: null + headers: + Accept: + - '*/*' + Accept-Encoding: + - gzip, deflate + Connection: + - keep-alive + Content-Length: + - '0' + authorization: + - + user-agent: + - + method: DELETE + uri: https://api.easypost.com/v2/carrier_accounts/ca_e5527ea2bd0f44c59f85fd198428da2b + response: + body: + string: '{}' + headers: + cache-control: + - private, no-cache, no-store + content-length: + - '2' + content-type: + - application/json; charset=utf-8 + expires: + - '0' + pragma: + - no-cache + referrer-policy: + - strict-origin-when-cross-origin + strict-transport-security: + - max-age=31536000; includeSubDomains; preload + transfer-encoding: + - chunked + x-backend: + - easypost + x-content-type-options: + - nosniff + x-download-options: + - noopen + x-ep-request-uuid: + - 52ecff1e668d71d9e2b7eef000485d62 + x-frame-options: + - SAMEORIGIN + x-node: + - bigweb36nuq + x-permitted-cross-domain-policies: + - none + x-proxied: + - intlb3nuq fa152d4755 + - extlb1nuq fa152d4755 x-runtime: - - '0.024976' + - '0.078431' x-version-label: - - easypost-202407081949-3228d5845b-master + - easypost-202407091438-d7c6f02f06-master x-xss-protection: - 1; mode=block status: - code: 404 - message: Not Found + code: 200 + message: OK version: 1 diff --git a/tests/test_carrier_account.py b/tests/test_carrier_account.py index 573b1b2c..37d6fe89 100644 --- a/tests/test_carrier_account.py +++ b/tests/test_carrier_account.py @@ -99,45 +99,35 @@ def test_carrier_account_create_with_custom_workflow(prod_client): @pytest.mark.vcr() def test_carrier_account_create_ups(prod_client): - """Test registering a UPS Carrier Account. - - We purposefully don't pass data here because real data is required for this endpoint - which we don't have in a test context, simply assert the error matches when no data is passed. - """ - carrier_account = { + """Test registering a UPS Carrier Account which uses a different URL and schema.""" + params = { "type": "UpsAccount", - "account_number": 123, + "account_number": "123456789", } - try: - prod_client.carrier_account.create(**carrier_account) - except ApiError as error: - assert error.http_status == 422 - assert any( - [error["field"] == "account_number" and error["message"] == "must be present and a string"] - for error in error.errors - ) + carrier_account = prod_client.carrier_account.create(**params) + assert isinstance(carrier_account, CarrierAccount) + assert str.startswith(carrier_account.id, "ca_") + assert carrier_account.type == "UpsAccount" -@pytest.mark.vcr() -@patch( - "easypost.services.carrier_account_service.CarrierAccountService.retrieve", - return_value={"type": "UpsAccount"}, -) -def test_carrier_account_update_ups(mock_retrieve, prod_client): - """Test updating a UPS Carrier Account. + prod_client.carrier_account.delete(carrier_account.id) # Delete the carrier account once it's done being tested. - We purposefully don't pass data here because real data is required for this endpoint - which we don't have in a test context, simply assert that we sent the request correctly. - This test will require someone to ensure the cassette looks the way we want (URL) - """ - carrier_account = { +@pytest.mark.vcr() +def test_carrier_account_update_ups(prod_client): + """Test updating a UPS Carrier Account which uses a different URL and schema.""" + params = { "type": "UpsAccount", - "account_number": 123, + "account_number": "123456789", } - try: - prod_client.carrier_account.update("ca_123", **carrier_account) - except ApiError as error: - assert error.http_status == 404 + carrier_account = prod_client.carrier_account.create(**params) + + updated_carrier_account = prod_client.carrier_account.update(carrier_account.id, account_number="987654321") + + assert isinstance(carrier_account, CarrierAccount) + assert str.startswith(carrier_account.id, "ca_") + assert carrier_account.type == "UpsAccount" + + prod_client.carrier_account.delete(carrier_account.id) # Delete the carrier account once it's done being tested. From 61d8fcbe15a146e726410d305c436e2f43a48ab8 Mon Sep 17 00:00:00 2001 From: Justintime50 <39606064+Justintime50@users.noreply.github.com> Date: Tue, 9 Jul 2024 11:27:16 -0600 Subject: [PATCH 7/7] fix: lint --- tests/test_carrier_account.py | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/tests/test_carrier_account.py b/tests/test_carrier_account.py index 37d6fe89..07be3cfa 100644 --- a/tests/test_carrier_account.py +++ b/tests/test_carrier_account.py @@ -1,5 +1,3 @@ -from unittest.mock import patch - import pytest from easypost.errors.api.api_error import ApiError from easypost.models import CarrierAccount @@ -124,7 +122,7 @@ def test_carrier_account_update_ups(prod_client): carrier_account = prod_client.carrier_account.create(**params) - updated_carrier_account = prod_client.carrier_account.update(carrier_account.id, account_number="987654321") + prod_client.carrier_account.update(carrier_account.id, account_number="987654321") assert isinstance(carrier_account, CarrierAccount) assert str.startswith(carrier_account.id, "ca_")