Skip to content
This repository was archived by the owner on Jun 28, 2024. It is now read-only.

Commit 4dfc546

Browse files
committed
Introduce routes & make_request wrapper
1 parent 84d2f16 commit 4dfc546

File tree

3 files changed

+74
-23
lines changed

3 files changed

+74
-23
lines changed

seamapi/routes.py

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
from .types import AbstractRoutes
2+
from .workspaces import Workspaces
3+
from .devices import Devices
4+
from .events import Events
5+
from .connected_accounts import ConnectedAccounts
6+
from .connect_webviews import ConnectWebviews
7+
from .locks import Locks
8+
from .access_codes import AccessCodes
9+
from .action_attempts import ActionAttempts
10+
11+
class Routes(AbstractRoutes):
12+
def __init__(self):
13+
self.workspaces = Workspaces(seam=self)
14+
self.connected_accounts = ConnectedAccounts(seam=self)
15+
self.connect_webviews = ConnectWebviews(seam=self)
16+
self.devices = Devices(seam=self)
17+
self.events = Events(seam=self)
18+
self.locks = Locks(seam=self)
19+
self.access_codes = AccessCodes(seam=self)
20+
self.action_attempts = ActionAttempts(seam=self)
21+
22+
def make_request(self):
23+
raise NotImplementedError()

seamapi/seam.py

Lines changed: 32 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,8 @@
11
import os
2+
from .routes import Routes
3+
import requests
24
from typing import Optional, cast
3-
from .workspaces import Workspaces
4-
from .devices import Devices
5-
from .events import Events
6-
from .connected_accounts import ConnectedAccounts
7-
from .connect_webviews import ConnectWebviews
8-
from .locks import Locks
9-
from .access_codes import AccessCodes
10-
from .action_attempts import ActionAttempts
11-
from .types import AbstractSeam
5+
from .types import AbstractSeam, SeamAPIException
126

137

148
class Seam(AbstractSeam):
@@ -57,6 +51,7 @@ def __init__(
5751
api_url : str, optional
5852
API url
5953
"""
54+
Routes.__init__(self)
6055

6156
if api_key is None:
6257
api_key = os.environ.get("SEAM_API_KEY", None)
@@ -68,11 +63,31 @@ def __init__(
6863
api_url = os.environ.get("SEAM_API_URL", self.api_url)
6964
self.api_key = api_key
7065
self.api_url = cast(str, api_url)
71-
self.workspaces = Workspaces(seam=self)
72-
self.connected_accounts = ConnectedAccounts(seam=self)
73-
self.connect_webviews = ConnectWebviews(seam=self)
74-
self.devices = Devices(seam=self)
75-
self.events = Events(seam=self)
76-
self.locks = Locks(seam=self)
77-
self.access_codes = AccessCodes(seam=self)
78-
self.action_attempts = ActionAttempts(seam=self)
66+
67+
def make_request(self, method: str, path: str, **kwargs):
68+
"""
69+
Makes a request to the API
70+
71+
Parameters
72+
----------
73+
method : str
74+
Request method
75+
path : str
76+
Request path
77+
**kwargs
78+
Keyword arguments passed to requests.request
79+
"""
80+
81+
url = self.api_url + path
82+
headers = {
83+
"Authorization": "Bearer " + self.api_key,
84+
"Content-Type": "application/json",
85+
}
86+
response = requests.request(method, url, headers=headers, **kwargs)
87+
88+
parsed_response = response.json()
89+
90+
if response.status_code != 200:
91+
raise SeamAPIException(response.status_code, response.headers["seam-request-id"], parsed_response["error"])
92+
93+
return parsed_response

seamapi/types.py

Lines changed: 19 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,13 @@
1616
DeviceType = str # e.g. august_lock
1717
WorkspaceId = str
1818

19+
class SeamAPIException(Exception):
20+
def __init__(self, status_code: int, request_id: str, metadata: Optional[Dict[str, any]]):
21+
self.status_code = status_code
22+
self.request_id = request_id
23+
self.metadata = metadata
24+
25+
super().__init__(f"SeamAPIException: status={status_code}, request_id={request_id}, metadata={metadata}")
1926

2027
class ActionAttemptFailedException(Exception):
2128
def __init__(
@@ -266,19 +273,25 @@ def get(
266273
) -> ConnectedAccount:
267274
raise NotImplementedError
268275

269-
270276
@dataclass
271-
class AbstractSeam(abc.ABC):
272-
api_key: str
273-
api_url: str
274-
277+
class AbstractRoutes(abc.ABC):
275278
workspaces: AbstractWorkspaces
276279
connect_webviews: AbstractConnectWebviews
277280
locks: AbstractLocks
278281
devices: AbstractDevices
279282
access_codes: AbstractAccessCodes
280283
action_attempts: AbstractActionAttempts
281284

285+
@abc.abstractmethod
286+
def make_request(self, method: str, path: str, **kwargs) -> Any:
287+
raise NotImplementedError
288+
289+
290+
@dataclass
291+
class AbstractSeam(AbstractRoutes):
292+
api_key: str
293+
api_url: str
294+
282295
@abc.abstractmethod
283296
def __init__(self, api_key: Optional[str] = None):
284297
raise NotImplementedError
@@ -287,4 +300,4 @@ def __init__(self, api_key: Optional[str] = None):
287300
@dataclass
288301
class ResetSandBoxResponse:
289302
message: str
290-
ok: bool
303+
ok: bool

0 commit comments

Comments
 (0)