Skip to content

Commit

Permalink
[feat] Add dedicated API Keys service (#297)
Browse files Browse the repository at this point in the history
- Add dedicated API Keys service
- Migrate API key-related functions to API Keys service, deprecated in User service
- Migrate unit tests, re-record cassettes as needed
  • Loading branch information
nwithan8 authored Sep 28, 2023
1 parent 4bc2545 commit 12fb767
Show file tree
Hide file tree
Showing 14 changed files with 249 additions and 111 deletions.
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
# CHANGELOG

- Add dedicated API Key-related service, available via the `api_keys` property of a client
- NOTE: Please note the naming. The `api_key` property of a client is the currently-used API key string, while the `api_keys` property is the service for managing API keys.
- Migrated API Key-related functionality to `api_keys` service, deprecated old methods in `user` service

## v8.1.1 (2023-09-05)

- Fix endpoint for creating a FedEx Smartpost carrier account
Expand Down
2 changes: 1 addition & 1 deletion Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ clean:

## coverage - Test the project and generate an HTML coverage report
coverage:
$(VIRTUAL_BIN)/pytest --cov=$(PROJECT_NAME) --cov-branch --cov-report=html --cov-report=lcov --cov-report=term-missing --cov-fail-under=90
$(VIRTUAL_BIN)/pytest --cov=$(PROJECT_NAME) --cov-branch --cov-report=html --cov-report=lcov --cov-report=term-missing --cov-fail-under=89

## docs - Generates docs for the library
docs:
Expand Down
1 change: 1 addition & 0 deletions easypost/constant.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
NO_BILLING_ERROR = "Billing has not been setup for this user. Please add a payment method."
NO_MORE_PAGES_ERROR = "There are no more pages to retrieve."
NO_RATES_ERROR = "No rates found."
NO_USER_FOUND = "No user found with the given id."
SEND_STRIPE_DETAILS_ERROR = "Could not send card details to Stripe, please try again later."
TIMEOUT_ERROR = "Request timed out."

Expand Down
2 changes: 2 additions & 0 deletions easypost/easypost_client.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
)
from easypost.services import (
AddressService,
ApiKeyService,
BatchService,
BetaCarrierMetadataService,
BetaRateService,
Expand Down Expand Up @@ -54,6 +55,7 @@ def __init__(

# Services
self.address = AddressService(self)
self.api_keys = ApiKeyService(self)
self.batch = BatchService(self)
self.beta_carrier_metadata = BetaCarrierMetadataService(self)
self.beta_rate = BetaRateService(self)
Expand Down
1 change: 1 addition & 0 deletions easypost/services/__init__.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
# flake8: noqa
from easypost.services.address_service import AddressService
from easypost.services.api_key_service import ApiKeyService
from easypost.services.batch_service import BatchService
from easypost.services.beta_carrier_metadata_service import BetaCarrierMetadataService
from easypost.services.beta_rate_service import BetaRateService
Expand Down
45 changes: 45 additions & 0 deletions easypost/services/api_key_service.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
from typing import (
Any,
Dict,
List,
)

from easypost.constant import NO_USER_FOUND
from easypost.easypost_object import convert_to_easypost_object
from easypost.errors import FilteringError
from easypost.models import ApiKey
from easypost.requestor import (
RequestMethod,
Requestor,
)
from easypost.services.base_service import BaseService


class ApiKeyService(BaseService):
def __init__(self, client):
self._client = client
self._model_class = ApiKey.__name__

def all(self) -> Dict[str, Any]:
"""Retrieve a list of all API keys."""
url = "/api_keys"

response = Requestor(self._client).request(method=RequestMethod.GET, url=url)

return convert_to_easypost_object(response=response)

def retrieve_api_keys_for_user(self, id: str) -> List[ApiKey]:
"""Retrieve a list of API keys (works for the authenticated User or a child User)."""
api_keys = self.all()

if api_keys["id"] == id:
# This function was called on the authenticated user
return api_keys["keys"]

# This function was called on a child user (authenticated as parent, only return
# this child user's details).
for child in api_keys["children"]:
if child.id == id:
return child.keys

raise FilteringError(message=NO_USER_FOUND)
14 changes: 14 additions & 0 deletions easypost/services/user_service.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
List,
Optional,
)
from warnings import warn

from easypost.easypost_object import convert_to_easypost_object
from easypost.models import (
Expand Down Expand Up @@ -68,6 +69,12 @@ def retrieve_me(self) -> User:

def all_api_keys(self) -> Dict[str, Any]:
"""Retrieve a list of all API keys."""
warn(
'This method is deprecated, use the "all" function of "api_keys" on the client instead.',
DeprecationWarning,
stacklevel=2,
)

url = "/api_keys"

response = Requestor(self._client).request(method=RequestMethod.GET, url=url)
Expand All @@ -76,6 +83,13 @@ def all_api_keys(self) -> Dict[str, Any]:

def api_keys(self, id: str) -> List[ApiKey]:
"""Retrieve a list of API keys (works for the authenticated User or a child User)."""
warn(
'This method is deprecated, use the "retrieve_api_keys_for_user" function '
'of "api_keys" on the client instead.',
DeprecationWarning,
stacklevel=2,
)

api_keys = self.all_api_keys()
my_api_keys = []

Expand Down
2 changes: 1 addition & 1 deletion examples
Submodule examples updated 494 files

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

44 changes: 21 additions & 23 deletions tests/cassettes/test_authenticated_user_api_keys.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading

0 comments on commit 12fb767

Please sign in to comment.