HTTPSerializers
is a work in progress Python library
trying to help APIs replying correctly to the Accept
HTTP header.
It combines a raw response, like:
{
"users": []
}
with an OpenAPI description of the API to generate an appropriate
response, like (if the Accept
header contains
application/hal+json
):
{
"_links": {
"self": {
"href": "http://example.com/api/book/hal-cookbook"
}
},
"users": [],
}
The API:
from httpserializer import serialize
def your_handler(request):
...
return serialize(
message,
accept_header=request.header['Accept']
api_root=request.config["api_root"],
path=request.path,
schema=openapi_schema)
You give the response message, the accept header, the OpenAPI spec to the httpserializers.serialize function and you'll get an appropriate representation.
Idea is to handle at least those types:
- JSON-LD.
- HAL.
- Plain old JSON (no transformation of the document).
- Plain old HTML, just in case you're on a web browser.
- Plain text (as Markdown).
- JSON-home, autogenerated from OpenAPI spec.
OpenAPI can't really describe HATEOAS (Issue #577, so you're more or less damned from the beginning.
You can still give URLs in responses, it's always a good start, but
It'll probably be hard to properly describe actions near to them in
the responses like HTML have <form>
to properly describe the
expected content of a POST body.
Anyway, having a fully HATEOAS implementation will not prevent a
client from hardcoding many URL, so it's not the unique ultimate
solution, if at least they follow the next
links, eventually other
IANA
link relation names, it's a good start.
Imagine a simple document describing an article, having a title, a body, and a link to its comments, you can describe it using simple Python:
>>> from httpserializers import serialize
>>> import requests
>>> schema = requests.get("https://petstore3.swagger.io/api/v3/openapi.json").json()
>>> content_type, response = serialize({"id": 1,"name": "Jessica Right","tag": "pet"},
... "http://127.0.0.1:5000/",
... "/pet/{petId}",
... spec)