{"id":32483812,"url":"https://github.com/sajanv88/multi-tenant-fast-api-demo","last_synced_at":"2026-05-18T05:48:26.377Z","repository":{"id":315536910,"uuid":"1059902593","full_name":"sajanv88/multi-tenant-fast-api-demo","owner":"sajanv88","description":"A demonstration project showcasing the basics of multi-tenancy architecture using Beanie ODM and MongoDB. This educational example implements database-per-tenant isolation to show how tenant data can be separated in different MongoDB databases.","archived":false,"fork":false,"pushed_at":"2025-09-19T14:06:04.000Z","size":38,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-10-09T23:50:33.759Z","etag":null,"topics":["beanie-odm","fastapi","pymongo"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/sajanv88.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2025-09-19T05:41:30.000Z","updated_at":"2025-09-19T14:06:44.000Z","dependencies_parsed_at":"2025-09-19T07:40:46.617Z","dependency_job_id":"7c1e142c-b8cb-40b9-8e4d-b8843336c0f9","html_url":"https://github.com/sajanv88/multi-tenant-fast-api-demo","commit_stats":null,"previous_names":["sajanv88/multi-tenant-fast-api-demo"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/sajanv88/multi-tenant-fast-api-demo","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sajanv88%2Fmulti-tenant-fast-api-demo","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sajanv88%2Fmulti-tenant-fast-api-demo/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sajanv88%2Fmulti-tenant-fast-api-demo/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sajanv88%2Fmulti-tenant-fast-api-demo/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/sajanv88","download_url":"https://codeload.github.com/sajanv88/multi-tenant-fast-api-demo/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sajanv88%2Fmulti-tenant-fast-api-demo/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":281211349,"owners_count":26462074,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-10-27T02:00:05.855Z","response_time":61,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["beanie-odm","fastapi","pymongo"],"created_at":"2025-10-27T03:38:57.677Z","updated_at":"2025-10-27T03:39:01.077Z","avatar_url":"https://github.com/sajanv88.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Multi-Tenant FastAPI Todo App with Beanie \u0026 MongoDB\n\n[![Python](https://img.shields.io/badge/Python-3.11+-blue.svg)](https://www.python.org/downloads/)\n[![FastAPI](https://img.shields.io/badge/FastAPI-0.104+-green.svg)](https://fastapi.tiangolo.com/)\n[![MongoDB](https://img.shields.io/badge/MongoDB-6.0+-green.svg)](https://www.mongodb.com/)\n[![Beanie](https://img.shields.io/badge/Beanie-ODM-orange.svg)](https://beanie-odm.dev/)\n\nA **demonstration project** showcasing the basics of **multi-tenancy** architecture using [Beanie ODM](https://beanie-odm.dev/) and MongoDB. This educational example implements **database-per-tenant** isolation to show how tenant data can be separated in different MongoDB databases.\n\n## 🚀 Key Features\n\n- **🏢 Multi-Tenancy Demo**: Basic data isolation with separate databases per tenant\n- **⚡ FastAPI**: Modern, high-performance async Python web framework  \n- **🍃 Beanie ODM**: Elegant async MongoDB ODM built on Pydantic\n- **📋 Simple CRUD**: Basic operations for todos and users\n- **🔒 Tenant Middleware**: Simple tenant detection via headers\n- **📊 MongoDB**: NoSQL database with async operations\n- **🛠️ uv**: Lightning-fast Python package manager\n- **📚 Educational**: Great starting point for learning multi-tenancy concepts Multi-Tenant FastAPI Todo App with Beanie \u0026 MongoDB \n\nA simple, production-style FastAPI application demonstrating multi-tenancy using [Beanie ODM](https://beanie-odm.dev/) and MongoDB. Each tenant’s data is isolated in its own database, and the app provides basic user and todo management APIs.\n\n## Features\n\n- **Multi-Tenancy:** Isolates data per tenant using the `X-Tenant-ID` header.\n- **FastAPI:** Modern, async Python web framework.\n- **Beanie ODM:** Async MongoDB models with Pydantic.\n- **Todo \u0026 User APIs:** CRUD endpoints for todos and users.\n- **MongoDB:** Each tenant gets a separate database.\n- **uv:** Project/dependency management ([uv](https://github.com/astral-sh/uv)).\n\n## 🏗️ Basic Multi-Tenancy Architecture\n\nThis demo application shows a simple **database-per-tenant** pattern:\n\n```\n┌─────────────┐    ┌──────────────────┐    ┌─────────────────────┐\n│   Client    │───▶│   FastAPI App    │───▶│   MongoDB Cluster   │\n│             │    │                  │    │                     │\n│ X-Tenant-ID │    │ Tenant Middleware│    │ ┌─────────────────┐ │\n│   Header    │    │                  │    │ │ tenant_123_db   │ │\n└─────────────┘    │ Dynamic Database │    │ ├─────────────────┤ │\n                   │    Selection     │    │ │ tenant_456_db   │ │\n                   └──────────────────┘    │ ├─────────────────┤ │\n                                           │ │ tenant_789_db   │ │\n                                           │ └─────────────────┘ │\n                                           └─────────────────────┘\n```\n\n### How the Demo Works\n\n1. **Tenant Identification**: Each request includes an `X-Tenant-ID` header (no validation in this demo)\n2. **Middleware Processing**: Simple middleware extracts the tenant ID\n3. **Database Selection**: Beanie connects to tenant-specific database (`tenant_{id}_db`)\n4. **Basic Data Isolation**: Operations are scoped to the tenant's database\n5. **Auto-Creation**: New tenant databases are created automatically\n\n\u003e **⚠️ Note**: This is a basic demonstration. Production apps need authentication, validation, error handling, and security measures.\n\n## 📁 Project Structure\n\n```\nmulti-tenant-fast-api-demo/\n├── app/\n│   ├── __init__.py\n│   ├── config.py              # Application configuration\n│   ├── api/                   # API endpoints\n│   │   ├── __init__.py\n│   │   ├── tenant_endpoint.py # Tenant management APIs\n│   │   ├── todo_endpoint.py   # Todo CRUD operations\n│   │   └── user_endpoint.py   # User management APIs\n│   ├── core/                  # Core application logic\n│   │   ├── __init__.py\n│   │   ├── database.py        # MongoDB connection \u0026 Beanie setup\n│   │   └── tenant_middleware.py # Multi-tenant middleware\n│   └── models/                # Beanie ODM models\n│       ├── __init__.py\n│       ├── app_base.py        # Base model with tenant isolation\n│       ├── tenant.py          # Tenant model\n│       ├── todo.py            # Todo model\n│       └── user.py            # User model\n├── pyproject.toml             # Project dependencies (uv)\n├── uv.lock                    # Locked dependencies\n└── README.md\n```\n\n## 🚀 Quick Start\n\n### Prerequisites\n\n- Python 3.13+\n- MongoDB (running locally or remote)\n- [uv](https://github.com/astral-sh/uv) package manager\n\n### Installation \u0026 Setup\n\n1. **Clone the repository:**\n   ```bash\n   git clone https://github.com/sajanv88/multi-tenant-fast-api-demo.git\n   cd multi-tenant-fast-api-demo\n   ```\n\n2. **Install dependencies using uv:**\n   ```bash\n   uv pip install .\n   ```\n\n3. **Set up MongoDB:**\n   - **Local MongoDB**: Ensure MongoDB is running on `mongodb://localhost:27017`\n   - **Remote MongoDB**: Set the `MONGO_URI` environment variable\n   ```bash\n   export MONGO_URI=\"mongodb://your-mongodb-uri\"\n   ```\n\n4. **Run the application:**\n   ```bash\n   uv run fastapi dev app\n   ```\n\n5. **Access the API:**\n   - **Swagger UI**: [http://localhost:8000/docs](http://localhost:8000/docs)\n   - **ReDoc**: [http://localhost:8000/redoc](http://localhost:8000/redoc)\n\n## 🏢 Multi-Tenancy Demo\n\n### Understanding the Basic Isolation\n\nEvery API request **should** include the `X-Tenant-ID` header. This demo uses this ID to determine which database to use for data storage and retrieval.\n\n\u003e **⚠️ Demo Limitation**: This example doesn't validate tenant IDs or implement authentication and host access permissions - any string can be used as a tenant ID.\n\n```bash\n# Example: Creating a tenant as a host\ncurl -X POST \"http://localhost:8000/api/tenants/\" \\\n  -H \"Content-Type: application/json\" \\\n  -d '{\"name\": \"Acme Corporation\" }'\n```\n\n### Simple Demo Walkthrough\n\n#### 1. Create Two Different Demo Tenants\n\n**Tenant 1: Company ABC**\n```bash\ncurl -X POST \"http://localhost:8000/api/tenants/\" \\\n  -H \"Content-Type: application/json\" \\\n  -d '{\"name\": \"Company ABC\" }'\n```\n\n**Tenant 2: Company XYZ**\n```bash\ncurl -X POST \"http://localhost:8000/api/tenants/\" \\\n  -H \"Content-Type: application/json\" \\\n  -d '{\"name\": \"Company XYZ\" }'\n```\n\n#### 2. Create Users for Each Tenant\n\n**User for Company ABC:**\n```bash\ncurl -X POST \"http://localhost:8000/api/users/\" \\\n  -H \"Content-Type: application/json\" \\\n  -H \"X-Tenant-ID: company-abc-123\" \\\n  -d '{\"name\": \"Alice Smith\", \"email\": \"alice@companyabc.com\"}'\n```\n\n**User for Company XYZ:**\n```bash\ncurl -X POST \"http://localhost:8000/api/users/\" \\\n  -H \"Content-Type: application/json\" \\\n  -H \"X-Tenant-ID: company-xyz-456\" \\\n  -d '{\"name\": \"Bob Johnson\", \"email\": \"bob@companyxyz.com\"}'\n```\n\n#### 3. Create Todos for Each Tenant\n\n**Todo for Company ABC:**\n```bash\ncurl -X POST \"http://localhost:8000/api/todos/\" \\\n  -H \"Content-Type: application/json\" \\\n  -H \"X-Tenant-ID: company-abc-123\" \\\n  -d '{\"title\": \"Implement new feature\", \"description\": \"Add user authentication\", \"completed\": false}'\n```\n\n**Todo for Company XYZ:**\n```bash\ncurl -X POST \"http://localhost:8000/api/todos/\" \\\n  -H \"Content-Type: application/json\" \\\n  -H \"X-Tenant-ID: company-xyz-456\" \\\n  -d '{\"title\": \"Review code\", \"description\": \"Review pull request #123\", \"completed\": false}'\n```\n\n#### 4. Verify Data Isolation\n\n**List todos for Company ABC (should only see ABC's todos):**\n```bash\ncurl -X GET \"http://localhost:8000/api/todos/\" \\\n  -H \"X-Tenant-ID: company-abc-123\"\n```\n\n**List todos for Company XYZ (should only see XYZ's todos):**\n```bash\ncurl -X GET \"http://localhost:8000/api/todos/\" \\\n  -H \"X-Tenant-ID: company-xyz-456\"\n```\n\n\u003e **🔒 Basic Data Isolation**: Each tenant will only see their own data, demonstrating the core concept of multi-tenancy!\n\n## 📚 Basic Endpoint Overview\n\n### Tenant Management\n| Method | Endpoint | Description |\n|--------|----------|-------------|\n| `GET` | `/api/tenants/` | List all tenants |\n| `POST` | `/api/tenants/` | Create a new tenant |\n| `GET` | `/api/tenants/{tenant_id}` | Get current tenant info |\n\n### User Management  \n| Method | Endpoint | Description |\n|--------|----------|-------------|\n| `GET` | `/api/users/` | List all users (tenant-scoped) |\n| `POST` | `/api/users/` | Create a new user |\n| `GET` | `/api/users/{user_id}` | Get user by ID |\n\n### Todo Management\n| Method | Endpoint | Description |\n|--------|----------|-------------|\n| `GET` | `/api/todos/` | List all todos (tenant-scoped) |\n| `POST` | `/api/todos/` | Create a new todo |\n| `GET` | `/api/todos/{todo_id}` | Get todo by ID |\n| `PUT` | `/api/todos/{todo_id}` | Update todo |\n| `DELETE` | `/api/todos/{todo_id}` | Delete todo |\n\n\u003e **📝 Note**: All endpoints in this demo automatically scope data to the tenant specified in the `X-Tenant-ID` header (no validation performed) excepts Tenant endpoint.\n\n## Lets understand the basic important concept\n   The most important concept in Multitenancy is `Host` vs `Tenants`\n\n   - The host is responsible for owning and overseeing the management of the SaaS application’s system.\n   - A tenant refers to a paying customer of the SaaS application who utilizes the service.\n\n\n## 🗄️ Simple Database Models\n\n### Basic Model Structure\n\nThis demo uses simple **Beanie ODM** models to show tenant isolation: Refer `models` folder.\n\n\n## ⚙️ Basic Configuration\n\n### Environment Variables\n\n| Variable | Default | Description |\n|----------|---------|-------------|\n| `MONGO_URI` | `mongodb://localhost:27017` | MongoDB connection string |\n\n### Example `.env` file:\n```bash\nMONGO_URI=mongodb://localhost:27017\n\n```\n\n## 🧪 Testing the Demo\n\nYou can test the basic multi-tenancy concept using:\n\n- **Swagger UI**: [http://localhost:8000/docs](http://localhost:8000/docs) - Don't forget to add the `X-Tenant-ID` header!\n- **curl**: See the examples above\n- **Postman**: Create requests with different `X-Tenant-ID` headers\n- **Python requests**:\n\n```python\nimport requests\n\n# Demo: Two different tenant IDs (can be any string in this demo)\nheaders_tenant_1 = {\"X-Tenant-ID\": \"demo-tenant-1\"}\nheaders_tenant_2 = {\"X-Tenant-ID\": \"demo-tenant-2\"}\n\n# Create todo for demo tenant 1\nrequests.post(\n    \"http://localhost:8000/api/todos/\",\n    json={\"title\": \"Tenant 1 Todo\", \"description\": \"Only visible to tenant 1\"},\n    headers=headers_tenant_1\n)\n\n# Create todo for demo tenant 2  \nrequests.post(\n    \"http://localhost:8000/api/todos/\",\n    json={\"title\": \"Tenant 2 Todo\", \"description\": \"Only visible to tenant 2\"},\n    headers=headers_tenant_2\n)\n\n# Each tenant will only see their own todos (basic isolation demo)\ntodos_tenant_1 = requests.get(\"http://localhost:8000/api/todos/\", headers=headers_tenant_1)\ntodos_tenant_2 = requests.get(\"http://localhost:8000/api/todos/\", headers=headers_tenant_2)\n```\n\n## ⚠️ What This Demo Doesn't Include (Production Requirements)\n\nThis is a **basic educational demo**. For production use, you would need to add:\n\n### 🔐 Security \u0026 Authentication\n- **Tenant Authentication**: Verify that users belong to the tenant they claim\n- **API Authentication**: JWT tokens, API keys, or OAuth2\n- **Tenant ID Validation**: Ensure tenant IDs are valid and authorized\n- **Rate Limiting**: Prevent abuse and ensure fair usage\n\n### 🛡️ Data Protection\n- **Input Validation**: Comprehensive request validation and sanitization\n- **Data Encryption**: Encrypt sensitive data at rest and in transit\n- **Audit Logging**: Track all tenant operations for compliance\n\n### 🚀 Performance \u0026 Reliability\n- **Connection Pooling**: Efficient database connection management\n- **Caching Strategy**: Redis or similar for improved performance\n- **Error Handling**: Comprehensive error handling and user-friendly responses\n- **Health Checks**: Monitoring and alerting for system health\n\n### 📊 Operations \u0026 Monitoring\n- **Logging**: Structured logging with tenant context\n- **Metrics**: Tenant-specific performance metrics\n- **Backup \u0026 Recovery**: Tenant-aware backup strategies\n- **Database Migrations**: Safe schema changes across tenant databases\n\n### 🏗️ Architecture Improvements\n- **Tenant Onboarding**: Automated tenant provisioning\n- **Resource Limits**: Per-tenant resource quotas and limits\n- **Load Balancing**: Distribute load across multiple instances\n- **Circuit Breakers**: Fault tolerance patterns\n\n## 📚 Learning Resources\n\nThis demo is great for learning the basics! To build production multi-tenant apps, study:\n\n- [FastAPI Documentation](https://fastapi.tiangolo.com/)\n- [Beanie ODM Documentation](https://beanie-odm.dev/)\n- [MongoDB Documentation](https://docs.mongodb.com/)\n- [Multi-Tenancy](https://en.wikipedia.org/wiki/Multitenancy)\n\n## 🤝 Contributing\n\nThis is a learning project! Feel free to:\n\n1. Fork the repository\n2. Add features or improvements (`git checkout -b feature/improvement`)\n3. Add better examples or documentation\n4. Submit a Pull Request with your enhancements\n\nIdeas for contributions:\n- Add authentication examples\n- Implement tenant validation\n- Add more comprehensive error handling\n- Create Docker setup\n- Add unit tests\n\n## 📄 License\n\nMIT License - perfect for learning and experimenting with multi-tenancy concepts!\n\n---\n\n\n**Happy learning! 🎉**\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsajanv88%2Fmulti-tenant-fast-api-demo","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fsajanv88%2Fmulti-tenant-fast-api-demo","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsajanv88%2Fmulti-tenant-fast-api-demo/lists"}