Thanks to visit codestin.com
Credit goes to github.com

Skip to content

jhumigas/e-commerce-allocation

Repository files navigation

Architecture Patterns with Python

This repository is a showcase of architectural patterns widely used in industrial projects.

We start from a simple e-commerce use case:

the business decides to implement an exciting new way of allocating stock. Instead of just considering goods available in the warehouse, we will treat the goods on ships as real stock and part of our inventory, just with slightly longer lead times. Fewer goods will appear to be out of stock, we’ll sell more, and the business can save money by keeping lower inventory in the domestic warehouse.

📖 Based on: Cosmic Python book

Introduction

For that purpose, we start with a simple architecture with:

  • domain model: Contains the core model of our domain (with just order lines and batches). Here we define value objects and entities to structure the concepts we work with
  • repository: This layer enables interaction with our storage. We also implement an ORM to bridge our app with our database
  • service layer: This is the part that orchestrates the steps when we have to perform operations like creating batch of products, allocations, etc

Then to have the most consistent interactions with our database, we introduce:

  • unit of work: This helps provide an abstraction over atomic operations
  • aggregates: Evolution of our models so that we can have concurrent operations given a cluster of associated objects

We then evolve our application so that it becomes a message processor, easier to integrate in an architecture with microservices. We introduce:

  • Events: Broadcast by an actor to all interested listeners. Events capture facts
  • Commands: Instructions sent by one part of a system to another. Commands capture intent
  • Command-Query Responsibility Segregation: Basically, we start from the insight that most users are not going to buy, but just browse the product. In our application we need to separate read and write queries, so we introduce a module for views only used to read our products

Prerequisites

Make sure you have:

  • uv: Python package and project manager (instructions)
  • Docker or a docker container manager (use colima for macOS)
  • dbeaver optional database tool to manage your database

The tech stack used:

Setup local env

make start-dev

This will spin up the dev environment in docker, and run a FastAPI locally that connects to docker. Head to http://127.0.0.1:8000/docs for the swagger documentation, and perform some tests.

You can stop the dev env with:

make stop-dev

Run tests

To run all tests, you can use:

make tests

Architecture

Component Diagram

Project structure

.
├── docker-compose.yml
├── Dockerfile
├── Makefile       <-- Commands to build, test and run locally the project
├── pyproject.toml <-- Build configuration file used for build and packaging tools
├── README.md
├── src
│   └── allocation
│       ├── __init__.py
│       ├── entrypoints                 <-- Main script to run the application
│       │   ├── fast_app.py             <-- Entrypoint to run a REST API
│       │   └── eventconsumer.py        <-- Entrypoint to run an event consumer
│       ├── service_layer               <-- Orchestration layer
│       │   ├── __init__.py
│       │   ├── handlers.py             <-- Set of handlers to process commands and events
│       │   ├── messagebus.py           <-- Orchestrator class that processes events and commands then handles persistence
│       │   └── unit_of_work.py         <-- Manage context over atomic operations to the database
│       ├── adapters
│       │   ├── __init__.py
│       │   ├── email.py                <-- Email module to send email when needed
│       │   ├── notifications.py        <-- Notification interface and classes used to produce notifications when needed
│       │   ├── orm.py                  <-- Actual definition of database tables and mappings to our objects
│       │   ├── eventpublisher.py       <-- Event publisher
│       │   └── repository.py           <-- Actual layer to handle persistence
│       ├── domain
│       │   ├── __init__.py
│       │   ├── commands.py             <-- Command definitions
│       │   ├── events.py               <-- Event definitions
│       │   └── model.py                <-- Model definitions
│       ├── bootstrap.py                <-- Dependencies initialization and bootstrapping
│       ├── config.py
│       └── logger.py
├── tests
│   ├── __init__.py
│   ├── conftest.py
│   ├── e2e
│   ├── integration
│   └── unit
└── uv.lock

References

About

An e-commerce project to explore architecture patterns in python with pulsar and FastAPI

Topics

Resources

Stars

Watchers

Forks