The goal of this refactor is to have a clean and lean API that can then share with the public and third-parties.
This change should also enable us switch between different python frameworks and also move to microservices where/when the need be.
We would be sticking with
due to its stability and its robust permission management features.
1. Basic folder structure
To ensure that we still have the current API working whilst developing v2, we’d create a
sub folder - in each app - where most of the work would be done. The
file would maintain its current location in the app’s package.
would be a module that would contain different view files for each package. e.g for the
app, there’s are a lot of views so we’d break them down in such a way that we can have similar views in a file. Then in the __init__py file of the views module, we import all views. For smaller apps e.g
We can have just a single
We would be making use of viewsets with list and detail routes as opposed to APIView. This would help to generate the documentation via
would be explained later.
def create(self, request, **kwargs):
def update(self, request, pk=None, **kwargs):
def retrieve(self, request, pk=None, **kwargs):
def list(self, request, **kwargs):
def destroy(self, request, pk=None, **kwargs):
def register_2fa(self, request, **kwargs):
def activate_user(self, request, **kwargs):
would be in their own package where we can have unit tests (services, models) and integration tests (views)
There would be a
file which would contain code that bridges view-model interaction so the view does not interact with the models directly but via the service class. For example,
there would exist a
class . When a call is made to the create plan endpioint, we pass the data to the PlanService to create the plan and then get a response. i.e
code ommited for brevity
plans_service = PlanService(**args)
result = plan_service.create_plan(**args)
has to interact with models from the
app, it would be done via the
*(We may need to consider using DI here)
.py would contain the serializers of the models in their respective app. The serializers would handle validation for things like data type checking, text length check etc. We can have a number of serializers per model. e.g we can have a
for update and retrieve and a
.py would contain app specific background tasks (via celery)
would contain the router for the package. We would then import the router url in the project level router.py.
.py would contain specific functions that are re-used in the app services. We would rarely have to create this file as most of the work would be done by the Services already. We would most likely use the project level utils file for shared utility code used in multiple services.
Another advantage of using Django Rest Framework is the vast amount of libraries one has available to work with.
. Core API allows us to create a documentation page for our APIs that frontend developers can easily interact with. Here is an example of what it looks like -
It requires little configuration as drf is able to read metadata from serializers and use the model structure create the documentation. It is also customizable.
We would be handling permission with DRF’s default permission handler. We’d create custom permission classes for different types of users, we would also be considering creating permissions on an app basis e.g
Everyone on the team understands DRF
We would be working with the documentation created on