MamaCare FastAPI Backend is a Python REST API handling all Africa's Talking webhook callbacks and demo endpoints. USSD Handler (POST /ussd)
# MamaCare 🤱
AI-powered maternal health assistant via 2G — USSD, SMS, Voice, and Airtime through Africa's Talking.
## Stack
| Layer | Tech |
|---|---|
| Frontend | React 18 + Vite (admin dashboard) |
| Backend | NestJS 10 + TypeScript |
| Database | Supabase PostgreSQL |
| ORM | Prisma 5 |
| AI | OpenAI GPT-4o-mini + LangChain RAG |
| Channels | Africa's Talking (USSD, SMS, Voice, Airtime) |
| Monorepo | npm workspaces + Turborepo |
---
## Prerequisites
- Node.js ≥ 18
- A Supabase project (free tier works)
- An Africa's Talking account (sandbox for dev)
- An OpenAI API key
---
## 1. Clone and install
```bash
git clone mamacare
cd mamacare
npm install --legacy-peer-deps
```
## 2. Environment variables
```bash
cp .env.example .env
```
Fill in `.env`:
```env
# From Supabase → Project Settings → Database → Connection string
DATABASE_URL="postgresql://postgres.[ref]:[password]@aws-0-eu-central-1.pooler.supabase.com:6543/postgres?pgbouncer=true"
DIRECT_URL="postgresql://postgres.[ref]:[password]@aws-0-eu-central-1.pooler.supabase.com:5432/postgres"
# From Africa's Talking dashboard (use "sandbox" username for testing)
AT_API_KEY="your_key"
AT_USERNAME="sandbox"
AT_SENDER_ID="MamaCare"
# From OpenAI
OPENAI_API_KEY="sk-..."
```
> **Note**: `DATABASE_URL` uses the connection pooler (port 6543) for the app.
> `DIRECT_URL` uses the direct connection (port 5432) for Prisma migrations.
## 3. Set up the database
```bash
# Generate Prisma client
npm run db:generate
# Run migrations (creates all tables)
npm run db:migrate
# Seed with facilities and demo data
cd apps/api && npm run db:seed
```
## 4. Run in development
```bash
# From the root — starts both NestJS (port 3000) and React (port 5173)
npm run dev
```
Or individually:
```bash
# API only
cd apps/api && npm run dev
# Web only
cd apps/web && npm run dev
```
---
## Africa's Talking Sandbox Testing
1. Log in to
simulator.africastalking.com
2. Set your webhook URLs to your local tunnel (use …