-
Notifications
You must be signed in to change notification settings - Fork 8
Introducing AsyncIO Support & Request Timeouts #18
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from all commits
d79c98c
a3ce309
d67f77f
a70ba4a
6143625
931874c
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
recursive-include knockapi/sync_client * |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,2 +1,14 @@ | ||
from knockapi.client import Knock | ||
from knockapi.resources import * | ||
__version__ = '0.6.0' | ||
|
||
from knockapi.async_client import Knock as AsyncKnock | ||
|
||
try: | ||
from knockapi.sync_client import Knock | ||
except ImportError: | ||
Knock = None | ||
|
||
__all__ = [ | ||
"AsyncKnock", | ||
"Knock", | ||
"__version__" | ||
] |
Original file line number | Diff line number | Diff line change | ||||
---|---|---|---|---|---|---|
@@ -1,94 +1,62 @@ | ||||||
import requests | ||||||
from json.decoder import JSONDecodeError | ||||||
|
||||||
__version__ = '0.5.2' | ||||||
|
||||||
|
||||||
class Connection(object): | ||||||
def __init__(self, api_key, host='https://api.knock.app'): | ||||||
self.api_key = api_key | ||||||
self.host = host | ||||||
self.client_version = __version__ | ||||||
self.headers = { | ||||||
'Authorization': 'Bearer {}'.format(self.api_key), | ||||||
'User-Agent': 'Knock Python - {}'.format(self.client_version) | ||||||
} | ||||||
|
||||||
def request(self, method, endpoint, payload=None): | ||||||
url = '{}/v1{}'.format(self.host, endpoint) | ||||||
|
||||||
r = requests.request( | ||||||
method, | ||||||
url, | ||||||
params=payload if method == 'get' else None, | ||||||
json=payload if method != 'get' else None, | ||||||
headers=self.headers, | ||||||
) | ||||||
|
||||||
# If we got a successful response, then attempt to deserialize as JSON | ||||||
if r.ok: | ||||||
try: | ||||||
return r.json() | ||||||
except JSONDecodeError: | ||||||
return None | ||||||
from knockapi import __version__ | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. PEP8 convention about modules and packages naming states:
So files such as |
||||||
from knockapi.core import AsyncConnection | ||||||
from knockapi.async_client.services import User, Workflows, Preferences, Objects, Tenants, BulkOperations, Messages | ||||||
|
||||||
return r.raise_for_status() | ||||||
|
||||||
|
||||||
class Knock(Connection): | ||||||
class Knock(object): | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Since this PR requires "to drop Python 2 support and require >3.6.", there is no reason to make classes inheriting from object
Suggested change
|
||||||
"""Client to access the Knock features.""" | ||||||
@property | ||||||
def _auth(self): | ||||||
return self.api_key | ||||||
|
||||||
@property | ||||||
def _version(self): | ||||||
return __version__ | ||||||
def __init__( | ||||||
self, | ||||||
api_key: str, | ||||||
api_host: str = 'https://api.knock.app', | ||||||
read_timeout: int = 300 | ||||||
): | ||||||
self.connection = AsyncConnection( | ||||||
api_key, | ||||||
api_host, | ||||||
__version__, | ||||||
read_timeout | ||||||
) | ||||||
|
||||||
@property | ||||||
def users(self): | ||||||
from .resources import User | ||||||
return User(self) | ||||||
|
||||||
@property | ||||||
def workflows(self): | ||||||
from .resources import Workflows | ||||||
return Workflows(self) | ||||||
|
||||||
@property | ||||||
def preferences(self): | ||||||
from .resources import Preferences | ||||||
return Preferences(self) | ||||||
|
||||||
@property | ||||||
def objects(self): | ||||||
from .resources import Objects | ||||||
return Objects(self) | ||||||
|
||||||
@property | ||||||
def tenants(self): | ||||||
from .resources import Tenants | ||||||
return Tenants(self) | ||||||
|
||||||
@property | ||||||
def bulk_operations(self): | ||||||
from .resources import BulkOperations | ||||||
return BulkOperations(self) | ||||||
|
||||||
@property | ||||||
def messages(self): | ||||||
from .resources import Messages | ||||||
return Messages(self) | ||||||
|
||||||
# Defined at the top level here for convenience | ||||||
def notify( | ||||||
self, | ||||||
key, | ||||||
recipients, | ||||||
data={}, | ||||||
actor=None, | ||||||
cancellation_key=None, | ||||||
tenant=None): | ||||||
async def notify( | ||||||
self, | ||||||
key, | ||||||
recipients, | ||||||
data={}, | ||||||
actor=None, | ||||||
cancellation_key=None, | ||||||
tenant=None | ||||||
): | ||||||
""" | ||||||
Triggers a workflow. | ||||||
|
||||||
|
@@ -112,10 +80,11 @@ def notify( | |||||
dict: Response from Knock. | ||||||
""" | ||||||
# Note: this is essentially a delegated method | ||||||
return self.workflows.trigger( | ||||||
return await self.workflows.trigger( | ||||||
key=key, | ||||||
recipients=recipients, | ||||||
data=data, | ||||||
actor=actor, | ||||||
cancellation_key=cancellation_key, | ||||||
tenant=tenant) | ||||||
tenant=tenant | ||||||
) |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
from .Knock import Knock |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,19 @@ | ||
from knockapi.core.Service import Service | ||
|
||
default_set_id = "default" | ||
|
||
|
||
class BulkOperations(Service): | ||
|
||
async def get(self, bulk_operation_id): | ||
""" | ||
Returns a bulk operation. | ||
|
||
Args: | ||
bulk_operation_id (str): The id of the bulk operation | ||
|
||
Returns: | ||
dict: A Knock BulkOperation | ||
""" | ||
endpoint = f'/bulk_operations/{bulk_operation_id}' | ||
return await self.client.connection.request('get', endpoint) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.