5.2 KiB
Microservices example
This repository needs to be used as a template for all microservices that we are going to have in our project. For any questions, please ask AK (@notmewhyitsalwaysme)
Core principals:
- KISS - Keep It Simple
- DRY - Don't Repeat Yourself
- Camell case only
- LONG NAME OF VARIABLE OK, AS FAR AS IT DESCRIBES WHAT THE VARIABLE IS USED FOR
- DO. NOT. USE. NAMES. SUCH. AS. "a, b, c, d, s" OR SOMETHING LIKE THAT YOUR STUPID BRAIN SUGGESTS
- Principals 4 and 5 don't override each other. Truth is somewhere in the middle as always.
- If you unsure how it's needed to be - ask others.
- DO NOT drop_tables()
Folder structure:
microservice_name/ │ ├── main.py # Entry point for your FastAPI application │ ├── requirements.txt # Python dependencies ├── Dockerfile.txt # Docker containerfile ├── README.md # Project documentation ├── .gitignore # Define what to ignore during version control │ ├── app/ # Application directory │ ├── init.py # Initialize the app package │ ├── api/ # API endpoints │ │ ├── init.py # Initialize the api package │ │ ├── v1/ # Versioned API endpoints │ │ │ ├── init.py │ │ │ ├── endpoints.py # Define API routes and handlers │ │ │ └── dependencies.py # Dependency injection │ ├── core/ # Core functionality │ │ ├── init.py │ │ ├── config.py # Application configurations │ │ ├── security.py # Security related utilities │ │ └── ... │ ├── db/ # Database related files │ │ ├── init.py │ │ ├── session.py # Database session handling │ │ └── migrations/ # Database migrations │ ├── services/ # Business logic layer │ │ ├── init.py │ │ ├── user_service.py # Example service │ │ └── ... │ ├── repositories/ # database logic layer │ │ ├── init.py │ │ ├── user_repository.py # Example service │ │ └── ... │ ├── utils/ # Utility functions │ │ ├── init.py │ │ └── ... │ └── schemas/ # Utility functions │ ├── init.py │ ├── pydantic_schema.py │ └── ... │ └── tests/ # Test directory ├── init.py ├── conftest.py # Test fixtures ├── test_main.py # Tests for main module └── test_api/ # API endpoint tests ├── init.py ├── test_v1/ # Versioned API endpoint tests │ ├── init.py │ ├── test_endpoints.py │ └── test_models.py └── ...
Some explainig:
-
The endpoint.py file consists of all your endpoints for your microservice.
-
The dependencies.py file is responsible for adding methods that inject dependencies, like the service layer or repository layer.
def get_users_repository(db=Depends(Database)) -> GenericRepository: return GenericRepository(db) def get_users_service(repository=Depends(get_users_repository)) -> GenericService: return GenericService(repository) -
The services.py communicates with the repository layer that already has a repository instance injected into the service instance at the endpoint.py file
class UserService: def __init__(self, repository): self.repository = repository async def create_user(self, user_data:UserBaseModel): return await self.repository.create_user(user_data) async def read_users(self): return await self.repository.get_all_users() async def read_user_by_email(self, user_email: str): return await self.repository.get_user_by_email(user_email) async def update_user(self, user_id, user_data: UserBaseModel): return await self.repository.update_user(user_id, user_data) async def delete_user(self, user_id: int): return await self.repository.delete_user(user_id) -
The repository.py file is responsible for managing all database operations. The db instance was injected again on the dependency layer.
class UserRepository: def __init__(self, db): self.db = db async def get_all_users(self): ... async def get_user_by_email(self, user_email): ... async def delete_user(self, user_id): ... async def create_user(self, user_data): ... async def update_user(self, user_id, user_data): ... -
Utils store utility functions used throughout the application.
-
Tests holds test files for unit and integration testing.
-
Core contains core functionality such as application configurations and security utilities.
-
The database.py and models.py contains your sqlalchemy models