MealOS
by naga-pavan12
README.md
# MealOS
Cross-server Swiggy meal intelligence — plan, order, and manage meals across Food, Instamart, and Dineout from a single Claude Desktop conversation.
**Verified working:** placed a live Swiggy order entirely through Claude Desktop chat.
## What it does
MealOS is a local MCP server that gives Claude Desktop a unified meal planning brain. Instead of juggling three separate Swiggy apps, you tell Claude what you want and it:
- Plans 21 meals (breakfast/lunch/dinner × 7 days) routing each to the right Swiggy service
- **Cook at home** → builds an Instamart grocery cart, skipping what's already in your fridge
- **Order in** → finds a restaurant on Swiggy Food, builds a delivery cart, places the order
- **Dine out** → finds a free table reservation on Dineout for Friday/Saturday evenings
- Tracks your weekly budget split across all three modes
- Always asks for confirmation before placing any order or booking
## Architecture
```
Claude Desktop (orchestrator)
│
└── mealos MCP server (local stdio)
├── State tools → profile, fridge, weekly plan (~/.mealos/state.json)
├── Food proxy → 14 tools via https://mcp.swiggy.com/food
├── Instamart proxy → 13 tools via https://mcp.swiggy.com/im
└── Dineout proxy → 8 tools via https://mcp.swiggy.com/dineout
```
Claude Desktop connects to a single local MCP server. That server proxies all 35 Swiggy tools internally using a stored OAuth token — no remote MCP config needed.
## Live Order Flow (what actually happens)
```
You: "Order chicken biryani for dinner"
Claude → mealos: get_addresses → your Hyderabad address
Claude → mealos: search_restaurants → finds open biryani places near you
Claude → mealos: get_restaurant_menu → browses Chaitanya Food Court
Claude → mealos: search_menu → finds Chicken Dum Biryani, shows sizes
You: "Family size"
Claude → mealos: update_food_cart → adds item (menu_item_id + quantity)
Claude → mealos: get_food_cart → shows total, delivery fee, coupon applied
Claude: "Cart total ₹426. Place order?"
You: "Yes"
Claude → mealos: place_food_order → order placed ✅
→ confirmation SMS on your phone
```
Total time: ~2 minutes. No app switching.
> **Note on cart visibility:** The MCP API uses a separate device session (`deviceId: im-mcp-server`) from the Swiggy app. Cart won't show in the app, but placed orders appear in your order history.
## MealOS State Tools
| Tool | Description |
|------|-------------|
| `mealos_get_context` | Full planning context: profile + fridge + plan + constraints. Call at session start. |
| `mealos_get_profile` / `mealos_set_profile` | Read/write preferences: budget, dietary, cook/dine days, location |
| `mealos_get_fridge` / `mealos_update_fridge` | Read/write pantry inventory — Instamart skips items already stocked |
| `mealos_get_plan` / `mealos_save_plan` | Read/write the current weekly plan |
| `mealos_update_meal_status` | Mark a meal as confirmed / ordered / skipped |
## Swiggy Tools (proxied)
All 35 tools accessible through the single mealos server:
**Food (14):** `get_addresses`, `search_restaurants`, `get_restaurant_menu`, `search_menu`, `update_food_cart`, `get_food_cart`, `flush_food_cart`, `fetch_food_coupons`, `apply_food_coupon`, `place_food_order`, `get_food_orders`, `get_food_order_details`, `track_food_order`, `report_error`
**Instamart (13):** `search_products`, `your_go_to_items`, `update_cart`, `get_cart`, `clear_cart`, `checkout`, `get_orders`, `get_order_details`, `track_order`, `create_address`, `delete_address`
**Dineout (8):** `get_saved_locations`, `search_restaurants_dineout`, `get_restaurant_details`, `get_available_slots`, `book_table`, `get_booking_status`
## Built-in Prompts
Use these from the Claude Desktop prompt picker (`/` in chat):
- **`plan_week`** — Generate a full weekly meal plan across all three Swiggy services
- **`quick_order`** — Place a food delivery order right now
- **`restock_groceries`** — Restock the fridge via Instamart
- **`book_dinner`** — Find and book a free restaurant table for dinner
## Setup
### Prerequisites
- [Claude Desktop](https://claude.ai/download)
- Node.js 18+
- A Swiggy account with Builders Club API access
### 1. Clone and install
```bash
git clone https://github.com/naga-pavan12/mealOS.git
cd mealOS
npm install
```
### 2. Authenticate with Swiggy
```bash
npx tsx src/auth-cli.ts
```
This opens your browser for Swiggy OAuth login. Token saves to `~/.mealos/auth.json`. Only needed once — token auto-refreshes.
### 3. Build and deploy the MCP server
```bash
npm run build
mkdir -p ~/.mealos
cp dist/mcp-server.mjs ~/.mealos/mcp-server.mjs
```
> **Why `~/.mealos/`?** Claude Desktop on macOS sandboxes spawned processes and blocks file reads from `~/Downloads`. The bundle must live outside Downloads.
### 4. Configure Claude Desktop
Edit `~/Library/Application Support/Claude/claude_desktop_config.json`:
```json
{
"mcpServers": {
"mealos": {
"command": "/opt/homebrew/bin/node",
"args": ["/Users/YOUR_USERNAME/.mealos/mcp-server.mjs"]
}
}
}
```
### 5. Restart Claude Desktop
mealos should appear as connected under Settings → Developer. You'll see 39 tools available.
### 6. Set up your profile (first time)
Tell Claude:
> "Set up my MealOS profile. Budget ₹3000/week, non-veg, household of 1, cook on Mon/Wed/Sat, dine out Fri/Sat. I'm in [your city]."
Then add your fridge:
> "Update my fridge: I have 500g chicken, 1kg rice, 4 eggs, some garlic."
## State storage
All state is stored locally — no cloud sync, no external database.
```
~/.mealos/
├── mcp-server.mjs ← compiled bundle (from dist/)
├── state.json ← profile, fridge inventory, weekly plan
├── auth.json ← Swiggy OAuth token (chmod 0600)
└── registration.json ← OAuth client ID
```
## Swiggy Constraints
Key limits baked into the planning rules:
| Constraint | Limit |
|------------|-------|
| Cart cap | ₹1000 per order (Food + Instamart) |
| Instamart minimum | ₹99 |
| Payment method | COD only (Food, v1) |
| Dineout bookings | Free only (`isFree=true`, `bookingPrice=0`) |
| Confirmation | Required before every order and booking |
| Order retry | Not idempotent — check order history before retrying |
## Development
```bash
npm run build # bundle src/mcp-server.ts → dist/mcp-server.mjs
npm run typecheck # type-check without emitting
npx tsx src/auth-cli.ts # re-authenticate with Swiggy
```
After any code change: `npm run build` → `cp dist/mcp-server.mjs ~/.mealos/` → restart Claude Desktop.