A personalized diet management tool for tracking elimination diets, IgG food intolerance test results, and meal planning.
A personalized diet management platform that helps users create, customize, and manage meal plans based on their dietary needs, food allergies, and preferences.
Meal Plans:
- Can be builtin (system-owned templates), published by users, or user-owned (personal plans that appear in their dashboard)
- Mixable and matchable containers of per-day/week food options
- Examples: Celiac, Gluten-Free, Paleo, Vegetarian, Vegan, Atkins, Intermittent Fasting
Food Preferences:
- Metadata that tracks user-specific dietary requirements
- Includes allergies, intolerances, dietary restrictions, and lifestyle choices
- Used to filter meal plans and ensure safe food options (e.g., "user is allergic to nuts, so no meal plans should include nuts")
Food Options:
- Individual meals with configurable variables
- Example: A ham and cheese omelet can have variables for:
- Number of eggs (e.g., 2)
- Quantity of ham (e.g., 100g)
- Quantity of cheese (e.g., 1 slice)
- Variables have specified values in meal plans, but users can easily update them
Support Documents:
- Users can upload PDFs, text files, or markdown files with food preferences/allergies
- Documents are stored as base64 in the database (no object storage needed for small projects)
- Personalized Meal Plans: Create custom plans or choose from premade templates
- Food Preference Management: Upload documents or enter freeform text about allergies and dietary restrictions
- IgG Test Tracking: Track food intolerance test results (High, Borderline, Normal reactivity)
- Meal Planning: Plan meals with safe options, add custom options dynamically
- Reintroduction Challenges: Track food challenge testing during reintroduction phases
- Week View Calendar: Monday-first week view with meal planning interface
- Meal Plan Expansion: View detailed phase information, meal days, and options when expanding meal plans
- Smart Meal Option Selection: Add meal options from active meal plans filtered by day of week and phase, with fuzzy search
- Meal Memory: Remembers recently added food items, ordered by recency and usage count
- Custom Meal Options: Add custom meal options for specific days with support for variables
- Meal Copy Shortcuts: Copy meals from yesterday or last week (for same meal type or entire day)
- User Avatar Caching: Profile images cached in localStorage with TTL to handle rate limiting
- Theme Support: Light/dark/system theme with persistence
- Meal Plan Import/Export: JSON format for sharing and backing up meal plans. Imported meal plans are automatically published to the public library.
- Public Meal Plan Library: Browse all available meal plans with tabbed interface (Your meal plans / All meal plans)
- Template Management: Delete unused meal plan templates from the public library (owners and admins only)
- Real-time Updates: Meal plan changes (add/enable/disable/remove) update the UI without page reload
- Framework: Astro (SSR mode)
- Auth: Auth.js (
@auth/core) with Google OAuth - Database: SQLite (
better-sqlite3) - ORM: Drizzle ORM
- UI: Tailwind CSS + shadcn/ui (React components)
- Deploy: Coolify-ready
- Node.js 18+ installed
- npm or yarn package manager
- Install dependencies:
npm install-
Set up environment variables:
Create a
.envfile in the project root with the following variables:AUTH_SECRET=your-secret-key-here-change-in-production AUTH_URL=https://your-domain.com # Required in production (e.g., https://diet.simi.pw) GOOGLE_CLIENT_ID=your-google-client-id GOOGLE_CLIENT_SECRET=your-google-client-secret ADMIN_EMAILS=admin1@example.com,admin2@example.com DAILY_SIGNUP_LIMIT=15
AUTH_SECRET:
- This is a secret key used by Auth.js to encrypt session tokens and cookies
- Generate a secure random string (at least 32 characters)
- You can generate one using:
Or use an online generator: https://generate-secret.vercel.app/32
openssl rand -base64 32
- Important: Use a different secret for production!
AUTH_URL:
- IMPORTANT: If deploying on Coolify, DO NOT set
AUTH_URLin environment variables - Coolify may URL-encode this variable, which causes Auth.js to fail
- The app automatically uses
COOLIFY_URL(Coolify's predefined variable) instead - For other platforms: Set to the full URL of your application (e.g.,
https://diet.simi.pw) - Used by Auth.js to generate callback URLs for OAuth providers
- Can be omitted in development (localhost)
- Example (non-Coolify):
AUTH_URL=https://diet.simi.pw
ADMIN_EMAILS:
- Comma-separated list of email addresses that have admin access
- Admins can approve/reject user signups via the Admin panel
- Admins are automatically approved on signup
- Example:
ADMIN_EMAILS=admin@example.com,another@example.com
DAILY_SIGNUP_LIMIT:
- Maximum number of unique email addresses that can sign up per day
- Default: 15 if not specified
- Helps prevent spam/DDoS attacks
- Example:
DAILY_SIGNUP_LIMIT=15
Google OAuth Setup:
To get
GOOGLE_CLIENT_IDandGOOGLE_CLIENT_SECRET:- Go to Google Cloud Console
- Create a new project or select an existing one
- Enable the Google+ API:
- Navigate to "APIs & Services" > "Library"
- Search for "Google+ API" and enable it
- Create OAuth 2.0 credentials:
- Go to "APIs & Services" > "Credentials"
- Click "Create Credentials" > "OAuth client ID"
- If prompted, configure the OAuth consent screen first:
- Choose "External" user type
- Fill in app name, user support email, developer contact
- Add your email to test users (for development)
- Select "Web application" as the application type
- Add authorized redirect URIs:
- For local dev:
http://localhost:4321/api/auth/callback/google - For production:
https://yourdomain.com/api/auth/callback/google
- For local dev:
- Click "Create"
- Copy the Client ID and Client Secret to your
.envfile
-
Start the application:
The easiest way to start the app is to use the automated startup script:
npm run start
This command automatically:
- Installs dependencies (
npm install- idempotent) - Syncs database schema (
drizzle-kit push- idempotent) - Seeds the database (
npm run db:seed- idempotent) - Starts the Astro dev server with hot-reload
The app will be available at
http://localhost:4321Note: If you make schema changes, simply stop the server (Ctrl+C) and restart with
npm run start. The schema will be automatically synced on restart.Alternative: If you've already run setup and just want to start the dev server:
npm run dev
Manual setup (if needed):
npm run db:setup
This runs all setup steps manually:
npm installnpx drizzle-kit push(syncs schema)npm run db:seed(creates initial data)
The seed script creates:
- 16 builtin meal plan templates (Low-FODMAP, Mediterranean, Keto, Paleo, Vegetarian, Vegan, etc.)
- Templates are stored in the global library and can be added to user libraries
Login:
- Use Google OAuth with your Google account
Production build:
- Installs dependencies (
npm run build
npm run preview| Command | Action |
|---|---|
npm run start |
Recommended: Full setup + dev server (install, sync schema, seed, dev) |
npm run dev |
Starts Astro dev server only (assumes setup already done) |
npm run build |
Builds production site to ./dist |
npm run preview |
Preview production build locally |
npm run db:setup |
Manual setup: install + sync schema + seed |
npm run db:seed |
Seeds database with initial data (idempotent) |
npm run db:push |
Sync schema changes to database (idempotent) |
npx drizzle-kit generate |
Generate database migrations (usually not needed, push syncs directly) |
npx drizzle-kit push |
Sync schema to database (idempotent) |
/
├── src/
│ ├── components/ # React components (shadcn/ui)
│ ├── db/ # Database schema and seed script
│ ├── layouts/ # Astro layouts
│ ├── lib/ # Utility functions
│ ├── middleware.ts # Auth middleware
│ └── pages/ # Astro pages and API routes
├── auth.config.ts # Auth.js configuration
├── drizzle.config.ts # Drizzle ORM configuration
└── .env # Environment variables (not in git)
The application uses SQLite (local.db) for local development. The database schema includes:
- Users & Auth: User accounts, sessions (Auth.js)
- IgG Profiles: Food intolerance test results
- Diet Plans: User's diet plans with phases
- Meal Planning: Days, meals, and meal options
- Reintroduction Challenges: Food challenge tracking
- Food Preferences: User allergies, intolerances, dietary restrictions
- Support Documents: Uploaded PDFs/txt/md files stored as base64
- Meal Option Variables: Configurable parameters for meal options (e.g., number of eggs, quantity of ham)
- Meal Plan Templates: Builtin/premade plans that users can select (Celiac, Gluten-Free, Paleo, etc.)
- Templates: Builtin or user-created meal plan templates
- User Plans: Personalized meal plans created from templates or from scratch
- Phases: Elimination, Reintroduction, or Personalization phases within a plan
- Meal Days: Days of the week or numbered days
- Meals: Breakfast, Lunch, Dinner, Snacks
- Meal Options: Individual food options with optional variables
- User uploads documents or enters freeform text
- Documents stored as base64 in database
- Preferences used to filter meal plans and ensure safe options
To create a custom meal plan using an LLM (ChatGPT, Gemini, etc.):
- (Optional) Add text files or freeform text to your food preferences
- Click the "Copy LLM Prompt" button to copy a prompt with your preferences and the meal plan JSON schema
- Go to your favourite LLM chat: Gemini, ChatGPT, etc.
- Paste the prompt
- Add your instructions for what kind of meal plan you're trying to create
- Copy the JSON response from the LLM
- Click "Import meal plan JSON" and paste the JSON to add it to your library
Note: Imported meal plans are automatically published to the public library, making them available to all users. You can delete your own unused templates from the "All meal plans" tab.
Meal Plans:
GET /api/meal-plans/templates- List available meal plan templates (includes usage info and delete permissions)GET /api/meal-plans/list- List user's meal plansPOST /api/meal-plans/create- Create a new personalized meal planPOST /api/meal-plans/create-from-template- Create plan from templatePOST /api/meal-plans/toggle- Enable/disable a meal planPOST /api/meal-plans/delete- Remove a meal plan from user's libraryDELETE /api/meal-plans/delete-template?templateId=...- Delete a template from the public library (owners and admins only, unused templates only)GET /api/meal-plans/export?planId=...- Export meal plan as JSONPOST /api/meal-plans/import- Import meal plan from JSON (automatically publishes to public library)GET /api/meal-plans/schema- Get JSON schema for meal plans
Preferences:
GET /api/preferences/get- Get user preferences (theme, week start day)POST /api/preferences/update- Update user preferencesPOST /api/preferences/documents- Upload food preferences documentPOST /api/preferences/text- Save food preferences as textGET /api/preferences/llm-prompt- Get LLM prompt with JSON schema and user preferences for meal plan generation
Meals:
GET /api/meals/selections?weekStart=...- Get meal selections for a weekPOST /api/meals/add-option- Add meal option (existing or custom) for a specific date/meal typePOST /api/meals/remove- Remove a meal selectionGET /api/meals/memory?mealType=...- Get meal memory (recently added items) for a meal typePOST /api/meals/select- Save meal selections for a specific date (legacy)POST /api/meals/options- Add custom meal option (legacy, use/api/meals/add-option)
- Starting the app: Use
npm run startfor automatic setup. It handles all prerequisites idempotently. - Schema changes: After modifying
src/db/schema.ts, restart withnpm run startto automatically sync the schema. - Idempotent operations: All setup steps are idempotent:
npm install- Only installs missing packagesdrizzle-kit push- Only syncs schema changesdb:seed- Checks for existing data and skips if found (non-destructive)
- Database migrations are managed with Drizzle Kit (using
pushmode, not migrations) - The seed script creates 16 builtin meal plan templates (not user-specific data)
- Meal Option Selection: The
AddMealOptionDialogcomponent:- Filters options from active meal plans based on day of week (0=Sunday, 1=Monday, ..., 6=Saturday, null=all days)
- Calculates current phase from plan start date and current date
- Respects applicable weeks (if specified in meal plan)
- Shows meal memory (recently added items) when search is empty
- Deduplicates items between memory and meal plan options
- Hides already-selected items for the current day/meal type
- Meal Memory: Tracks recently added food items, ordered by recency (70%) and usage count (30%)
- Real-time Updates: Meal plan changes trigger custom events that update
WeekViewwithout page reload - User Avatar: Profile images are cached in localStorage with a 24-hour TTL to handle rate limiting. Falls back to user initials if image fails to load.
- Theme: Theme preference (light/dark/system) is persisted in user preferences and localStorage
- Confirmation Dialogs: Uses shadcn/ui AlertDialog for destructive actions (e.g., removing meal plans)
ISC