"""
Wrap all common calls to the divera api as defined by
https://api.divera247.com/?urls.primaryName=api%2Fv2%2Falarm
https://api.divera247.com/?urls.primaryName=api%2Fv2%2Fevent
https://api.divera247.com/?urls.primaryName=api%2Fv2%2Fnews
"""
import abc
import json
import mimetypes
import aiohttp
from divera.api import endpointwrappers as epw
[docs]class GetAll(epw.FunctionalEndPoint, abc.ABC):
method = 'GET'
[docs] @staticmethod
def process_result(
result,
):
return list((result['data']['items'] or {}).values())
def __call__(
self,
base_url: str,
access_token: str,
*args, **kwargs
):
args_ = (
base_url.rstrip('/') + self.path + f'?accesskey={access_token}',
)
kwargs_ = {}
return args_, kwargs_
[docs]class Get(GetAll, epw.ObjectRelated, abc.ABC):
@property
def path(self):
return f'/api/v2/{type(self.obj).__name__.lower().rstrip("s")}s/{self.obj.__getattribute__(self.obj.sorting_key)}'
[docs] @staticmethod
def process_result(
result,
):
return result['data']
[docs]class Create(epw.FunctionalEndPoint, epw.ObjectRelated, abc.ABC):
method = 'POST'
def __init__(
self,
obj,
access_key: str = None,
):
self.obj = obj
self.access_key = access_key
def __call__(
self,
base_url: str,
access_token: str,
*args, **kwargs
):
args_ = (
base_url.rstrip('/') + self.path + f'?accesskey={self.access_key or access_token}',
)
kwargs_ = {
'data': json.dumps(
{
type(self.obj).__name__: self.obj.data,
},
sort_keys=True,
),
}
return args_, kwargs_
[docs]class Confirm(epw.FunctionalEndPoint, epw.ObjectRelated, abc.ABC):
method = 'POST'
@property
def path(self) -> str:
return '/' + '/'.join(
[
'api',
'v2',
type(self.obj).__name__.lower().rstrip('s') + 's',
'confirm',
str(self.obj.__getattribute__(self.obj.sorting_key)),
]
)
[docs] def process_result(
self,
result,
):
return type(self.obj)(data=result['data'])
def __init__(
self,
obj=None,
response_id: str = None,
response_text: str = None,
):
self.obj = obj
self.response_id = response_id
self.response_text = response_text
def __call__(
self,
base_url: str,
access_token: str,
*args, **kwargs
):
args_ = [
base_url.rstrip('/') + self.path + f'?accesskey={access_token}',
]
kwargs_ = {
'json': {
type(self.obj).__name__: {
"participation": self.response_id,
"custom_answer": self.response_text or '',
},
},
}
return args_, kwargs_
[docs]class Read(Get, abc.ABC):
method = 'POST'
@property
def path(self):
return '/' + '/'.join(
[
'api',
'v2',
type(self.obj).__name__.lower().rstrip('s') + 's',
'read',
str(self.obj.__getattribute__(self.obj.sorting_key)),
]
)
[docs] @staticmethod
def process_result(
result,
):
return result
[docs]class Delete(epw.FunctionalEndPoint, epw.ObjectRelated, abc.ABC):
method = 'DELETE'
def __call__(
self,
base_url: str,
access_token: str,
*args, **kwargs
):
return (
base_url.rstrip('/') + self.path + f'?accesskey={access_token}',
), {
}
[docs]class Attachment(epw.FunctionalEndPoint, epw.ObjectRelated):
"""
Attaches a file to an object if supported.
:param obj: A divera object that supports attachments.
:param file: A file opened in binary read mode (:code:`open('path/to/file.ext', 'rb')`).
:param file_name: A custom file name. The original file name will be used if this one is not set.
:param description: A description for the file.
"""
method = 'POST'
@property
def path(self) -> str:
return f'/api/v2/{type(self.obj).__name__.lower().rstrip("s")}s/attachment/{self.obj.id}'
def __init__(
self,
obj,
file,
file_name: str = None,
description: str = None,
):
super().__init__(
obj=obj,
)
self.file = file
self.file_name = file_name
self.description = description
def __call__(
self,
base_url: str,
access_token: str,
*args, **kwargs
):
data = aiohttp.FormData()
file_name = self.file_name or self.file.name
data.add_field(
name='Attachment[upload]',
value=self.file,
filename=file_name,
content_type=mimetypes.guess_type(file_name)[0],
)
headers = {
'Accept': 'application/json',
}
return (
base_url.rstrip('/') + self.path + f'?accesskey={access_token}',
), {
'headers': headers,
'data': data,
}