The problems that I want to solve:
There are several __init__.py files: one in each directory or subdirectory. This is what allows importing code from one file into another. For example, in app/main.py you could have a line like: from app.routers import items.
Fastapi-mvc is a developer productivity tool for FastAPI web framework. It is designed to make programming FastAPI applications easier by making assumptions about what every developer needs to get started. It allows you to write less code while accomplishing more.
Welcome to the Ultimate FastAPI tutorial series. This post is part 8. The series is a project-based tutorial where we will build a cooking recipe API. Each post gradually adds more complex functionality, showcasing the capabilities of FastAPI, ending with a realistic, production-ready API.
The best thing about working with FastAPI is that you only need to focus on your APIs, you do not need to worry about documentation and the request & response configuration. I started out by writing my APIs in a single file and creating the database models using the SQLAlchemy ORM. Let's talk about an example API: Create new products.
In this blog post, we will set up a simple FastAPI application from scratch. This can serve as a good starting point for small to medium projects. Generate a base project with Poetry. Install FastAPI, SQLAlchemy and other dependencies. Create the necessary files that will serve as the base of the application
The series is a project-based tutorial where we will build a cooking recipe API. Each post gradually adds more complex functionality, showcasing the capabilities of FastAPI, ending with a realistic, production-ready API. The series is designed to be followed in order, but if you already know FastAPI you can jump to the relevant part.
Harsha already mentioned my project generator but I think it can be helpful for future readers to explain the ideas behind of it.
If you are going to serve your frontend something like yarn or npm. You should not worry about the structure between them. With something like axios or the Javascript's fetch you can easily talk with your backend from anywhere.
When it comes to structuring the backend, if you want to render templates with Jinja, you can have something that is close to MVC Pattern.
your_project
├── __init__.py
├── main.py
├── core
│ ├── models
│ │ ├── database.py
│ │ └── __init__.py
│ ├── schemas
│ │ ├── __init__.py
│ │ └── schema.py
│ └── settings.py
├── tests
│ ├── __init__.py
│ └── v1
│ ├── __init__.py
│ └── test_v1.py
└── v1
├── api.py
├── endpoints
│ ├── endpoint.py
│ └── __init__.py
└── __init__.py
By using __init__
everywhere, we can access the variables from the all over the app, just like Django.
Let's the folders into parts:
It is for your database models, by doing this you can import the same database session or object from v1 and v2.
Schemas are your Pydantic models, we call it schemas because it is actually used for creating OpenAPI schemas since FastAPI is based on OpenAPI specification we use schemas everywhere, from Swagger generation to endpoint's expected request body.
It is for Pydantic's Settings Management which is extremely useful, you can use the same variables without redeclaring it, to see how it could be useful for you check out our documentation for Settings and Environment Variables
This is optional if you are going to render your frontend with Jinja, you can have something close to MVC pattern
It would look something like this if you want to add views.
It is good to have your tests inside your backend folder.
Create them independently by APIRouter, instead of gathering all your APIs inside one file.
You can use absolute import for all your importing since we are using __init__
everywhere, see Python's packaging docs.
So assume you are trying to import v1's endpoint.py from v2, you can simply do
from my_project.v1.endpoints.endpoint import something
The official documentation suggests the below style like Flask blueprints.
.
├── app # "app" is a Python package
│ ├── __init__.py # this file makes "app" a "Python package"
│ ├── main.py # "main" module, e.g. import app.main
│ ├── dependencies.py # "dependencies" module, e.g. import app.dependencies
│ └── routers # "routers" is a "Python subpackage"
│ │ ├── __init__.py # makes "routers" a "Python subpackage"
│ │ ├── items.py # "items" submodule, e.g. import app.routers.items
│ │ └── users.py # "users" submodule, e.g. import app.routers.users
│ └── internal # "internal" is a "Python subpackage"
│ ├── __init__.py # makes "internal" a "Python subpackage"
│ └── admin.py # "admin" submodule, e.g. import app.internal.admin
Taken from the official link, read more at https://fastapi.tiangolo.com/tutorial/bigger-applications/
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With