A modern and simple way to create clients for REST like APIs
If you are looking for
dataclass-rest, this is the same project with a new name.We had reworked it a lot, but old code is still available in a separate branch.
Step 1. Install
pip install descanso requests adaptixrequests and adaptix are optional dependencies, but we will use them in quickstart.
Step 2. Declare models
from dataclasses import dataclass
@dataclass
class Todo:
id: int
user_id: int
title: str
completed: boolStep 3. Select serialization library. We recommend using adaptix.
You need to have Loader and Dumper implementations, adaptix.Retort would be fine
Step 4. Configure RestBuilder instance. It is needed to reuse common step during request.
from adaptix import Retort
from descanso import RestBuilder
rest = RestBuilder(
request_body_dumper=Retort(),
response_body_loader=Retort(),
query_param_dumper=Retort(),
)Step 5. Create client class. Use RequestsClient or AiohttpClient
from descanso.http.requests import RequestsClient
class RealClient(RequestsClient):
...Step 6. Declare methods using rest.get/rest.post/rest.delete/rest.patch/rest.put decorators. You can override RestBuilder params if needed.
Type hints are required. Body of method is ignored.
Use any method arguments to format URL.
body argument is sent as request body with json. Other arguments, not used in the URL are passed as query parameters.
from descanso.http.requests import RequestsClient
class RealClient(RequestsClient):
@rest.get("todos/{id}")
def get_todo(self, id: str) -> Todo:
pass
@rest.get("todos")
def list_todos(self, user_id: int | None) -> list[Todo]:
pass
@rest.delete("todos/{id}")
def delete_todo(self, id: int):
pass
@rest.post("todos")
def create_todo(self, body: Todo) -> Todo:
passStep 7. Create client instance and use it.
from requests import Session
client = RealClient(
base_url="https://example.com/api",
session=Session()
)
client.get_todo(5)To use async client instead of sync:
- Install
aiohttp(instead ofrequests) - Change
descanso.http.requests.RequestsClienttodescanso.http.aiohttp.AiohttpClient - All methods will be async, but you can add
asynckeyword to make it more verbose