Skip to content

The repository is a project template for REST microservice built using FastAPI (Python).

License

Notifications You must be signed in to change notification settings

beaver-infra/template-py-rest-microservice

Repository files navigation

Template Python REST Microservice

Pylint CodeQL License

The repository is a project template for REST microservice built using FastAPI (Python). The latest version supports Python 3.8 and above.

Prerequisite

Required

Optional

Features

List of features that comes with default template

  • Use FastAPI as base framework to build the REST API.
  • Use Poetry as a tool for dependency management and packaging in Python.
  • Predefined project scaffolding like files and directories, event handlings, routers, middlewares etc.
  • Comes with default configurations for hostname, port, environment etc. Each of these configuration can be customize as per microservice needs.
  • Predefined common logger for application logging.
  • Preconfigured special routes /info and /health.
  • Use Docker and Kubernetes aka K8s to make it easy to run the app on container and shift it.
  • Predefined GitHub Actions for workflows for PyLint and CodeQL.

Code Structure

Feel free to modify the layout of the repo as much as you want but the given structure is as follows:

app/
├── __init__.py
├── main.py
├── api.py
├── metadata.py
├── configs/
│   └── development.py
│   └── production.py
│   └── stage.py
├── core/
│   └── common_handlers.py
├── endpoints/
│   └── health.py
│   └── info.py
│   └── router.py
│   └── users.py
├── middlewares/
│   └── validation.py
└── models/
    └── users.py
├── test_main.py
  • __init__.py defines and initializes the app configuration.

  • main.py defines the FastAPI application, adds middleware, includes routers, and creates the Mangum handler.

Setup

Environment Variables

export <Name>=<Value>

For example:
export INSTANCE_ENVIRONMENT="DEVELOPMENT"

⚠️ No space before and after = sign.

Name Purpose Possible Values
INSTANCE_ENVIRONMENT Help to identify system instance type on which the app service is running DEVELOPMENT, STAGE and PRODUCTION

Development

export INSTANCE_ENVIRONMENT="DEVELOPMENT"

Install all dependencies using Pip

python3 -m venv .venv
source .venv/bin/activate

pip3 install -r requirements.txt
pip3 install -r requirements-dev.txt

Run the service

uvicorn "app.main:app" --host="0.0.0.0" --port=3000 --reload

Build & Run the service using Docker

docker build -f Dockerfile.dev -t hegdeashwin3/template-py-rest-microservice .
docker run -d -p 3000:3000 hegdeashwin3/template-py-rest-microservice
docker tag pyrest hegdeashwin3/template-py-rest-microservice:1.1.5
docker push hegdeashwin3/template-py-rest-microservice:1.1.5

Run the tests

pytest

Run the API Docs

http://localhost:<PORT>/api/v1/info

Run the Swagger API Docs

http://localhost:<PORT>/api/v1/docs

Run the lint

Run pylint before committing the changes and ensure code quality at least 9.30/10

pylint --rcfile .pylintrc $(git ls-files '*.py')

Run the formatter

Run black & isort before committing the changes

black app
isort **/*.py

Build & Run the service using K8s single instance (Minikube)

Setup Minikube

brew install minikube

Start Minikube & Verify status

minikube start
minikube status

Create K8s deployment

kubectl apply -f k8s-pyrest-deployment.yaml
kubectl get deployments
kubectl get pods

Create K8s service

kubectl apply -f k8s-pyrest-service.yaml
kubectl get services

Do port forwarding

kubectl port-forward service/pyrest-service 5000:3050

Run the API on browser

http://localhost:5000/api/v1/info

Useful Minikube commands

minikube logs
minikube ip
minikube dashboard

Stage

export INSTANCE_ENVIRONMENT="STAGE"

Install only dependencies (exclude dev-dependencies) using Poetry

poetry install --no-dev

Run the service

uvicorn "app.main:app" --host="<STAGE_HOST_IP>" --port=<STAGE_PORT> --workers 2

Run the Swagger API Docs

http://<STAGE_BASE_URL>:<STAGE_PORT>/api/v1/docss

Production

export INSTANCE_ENVIRONMENT="PRODUCTION"

Install only dependencies (exclude dev-dependencies) using Poetry

poetry install --no-dev

Run the service

gunicorn app.main:app --workers <NO_OF_WORKERS> --worker-class uvicorn.workers.UvicornWorker --bind <PRODUCTION_HOST_IP>:<PRODUCTION_PORT>

E.g. gunicorn app.main:app --workers 4 --worker-class uvicorn.workers.UvicornWorker --bind 127.0.0.1:3000

Run the Swagger API Docs

http://<PRODUCTION_BASE_URL>:<PRODUCTION_PORT>/api/v1/docs

References