A modern, mobile-first life tracking app built with React and Supabase.
- Stats Tracking: Log numbers, durations, amounts, and text notes
- Amount Totals: Automatically sum up amount-type stats with the same unit and display as totals
- Amount Formatting: Choose between US (K, M, B) and Indian (K, L, Cr) number formatting
- Habit Tracking: Create habits with custom schedules and track daily completion
- Todo Management: Apple Reminders-style todo system with drag-and-drop functionality
- Focus Timer: Pomodoro-style timer with automatic logging
- Analytics: Visualize your data with charts and insights
- Quick Log: Fast entry for multiple stats at once
- AI Assistant: Personal AI coach with access to your data for insights and guidance
- Dark Mode: Automatic theme switching
- Frontend: React 19, Vite, Tailwind CSS
- Backend: Supabase (PostgreSQL, Auth, Real-time)
- Charts: Recharts
- Icons: Lucide React
- Animations: Framer Motion
- Clone the repository
- Install dependencies:
npm install - Copy
env.exampleto.env.localand fill in your credentials:cp env.example .env.local
- Add your Supabase URL and anon key
- For AI assistant feature, see AI Chat Setup below
- Set up your Supabase database with the required tables (see Database Schema below)
- Run the migrations in your Supabase SQL editor:
- Copy and run the SQL from
migration_add_amount_type.sqlto add the 'amount' type - Copy and run the SQL from
migration_add_user_preferences.sqlto add user preferences - Copy and run the SQL from
migration_add_todos.sqlto add the todos table
- Copy and run the SQL from
- Run the development server:
npm run dev
This app is configured with Capacitor for native mobile development on both Android and iOS.
- Install Android Studio from https://developer.android.com/studio
- Install the Android SDK
- Set up an Android Virtual Device (AVD) or connect a physical Android device
- Build the web app:
npm run cap:build - Open in Android Studio:
npm run cap:open - Run on device/emulator:
npm run cap:run
npm run cap:build- Build web app and sync with Androidnpm run cap:sync- Sync web assets with Android projectnpm run cap:open- Open Android project in Android Studionpm run cap:run- Run app on connected device/emulator
- macOS: iOS development requires macOS
- Xcode: Install the latest version from the Mac App Store
- CocoaPods: Install via Homebrew:
brew install cocoapods
- Build the web app:
npm run cap:build:ios - Open in Xcode:
npm run cap:open:ios - Run on simulator/device:
npm run cap:run:ios
npm run cap:build:ios- Build web app and sync with iOSnpm run cap:sync:ios- Sync web assets with iOS projectnpm run cap:open:ios- Open iOS project in Xcodenpm run cap:run:ios- Run app on simulator/device
For convenience, you can use the provided development scripts:
# Android
./scripts/android-dev.sh build
./scripts/android-dev.sh open
./scripts/android-dev.sh run
./scripts/android-dev.sh full
# iOS
./scripts/build-ios.sh- Make changes to your React app
- Build and sync:
npm run cap:build(Android) ornpm run cap:build:ios(iOS) - Test on device/emulator/simulator
For detailed iOS setup instructions, see IOS_SETUP.md.
The app uses the following Supabase tables:
-- Create the enum type for stat types
CREATE TYPE stat_type AS ENUM ('number', 'duration', 'text', 'amount');
CREATE TABLE stats (
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
user_id UUID REFERENCES auth.users(id) ON DELETE CASCADE,
name TEXT NOT NULL,
type stat_type NOT NULL,
unit TEXT,
color TEXT,
goal_value NUMERIC,
icon TEXT,
pinned BOOLEAN DEFAULT false,
inserted_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);CREATE TABLE entries (
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
user_id UUID REFERENCES auth.users(id) ON DELETE CASCADE,
stat_id UUID REFERENCES stats(id) ON DELETE CASCADE,
day DATE NOT NULL,
value NUMERIC,
note TEXT,
source TEXT,
inserted_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
UNIQUE(user_id, stat_id, day)
);CREATE TABLE habits (
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
user_id UUID REFERENCES auth.users(id) ON DELETE CASCADE,
name TEXT NOT NULL,
icon TEXT,
color TEXT,
days_of_week INTEGER[] DEFAULT '{0,1,2,3,4,5,6}',
inserted_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);CREATE TABLE habit_checkins (
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
user_id UUID REFERENCES auth.users(id) ON DELETE CASCADE,
habit_id UUID REFERENCES habits(id) ON DELETE CASCADE,
day DATE NOT NULL,
done BOOLEAN DEFAULT false,
inserted_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
UNIQUE(user_id, habit_id, day)
);CREATE TABLE user_preferences (
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
user_id UUID REFERENCES auth.users(id) ON DELETE CASCADE UNIQUE,
amount_format VARCHAR(10) DEFAULT 'US' CHECK (amount_format IN ('US', 'IN')),
inserted_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);CREATE TABLE todos (
id UUID DEFAULT gen_random_uuid() PRIMARY KEY,
user_id UUID REFERENCES auth.users(id) ON DELETE CASCADE,
title TEXT NOT NULL,
completed BOOLEAN DEFAULT false,
due_date DATE,
priority INTEGER DEFAULT 0 CHECK (priority IN (0, 1, 2)), -- 0=normal, 1=high, 2=urgent
notes TEXT,
order_index INTEGER DEFAULT 0,
inserted_at TIMESTAMP WITH TIME ZONE DEFAULT NOW(),
updated_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);Enable RLS on all tables and add policies:
ALTER TABLE stats ENABLE ROW LEVEL SECURITY;
ALTER TABLE entries ENABLE ROW LEVEL SECURITY;
ALTER TABLE habits ENABLE ROW LEVEL SECURITY;
ALTER TABLE habit_checkins ENABLE ROW LEVEL SECURITY;
ALTER TABLE user_preferences ENABLE ROW LEVEL SECURITY;
-- Example policy for stats table
CREATE POLICY "Users can view own stats" ON stats
FOR SELECT USING (auth.uid() = user_id);
CREATE POLICY "Users can insert own stats" ON stats
FOR INSERT WITH CHECK (auth.uid() = user_id);
CREATE POLICY "Users can update own stats" ON stats
FOR UPDATE USING (auth.uid() = user_id);
CREATE POLICY "Users can delete own stats" ON stats
FOR DELETE USING (auth.uid() = user_id);
-- Policies for user_preferences table
CREATE POLICY "Users can view own preferences" ON user_preferences
FOR SELECT USING (auth.uid() = user_id);
CREATE POLICY "Users can insert own preferences" ON user_preferences
FOR INSERT WITH CHECK (auth.uid() = user_id);
CREATE POLICY "Users can update own preferences" ON user_preferences
FOR UPDATE USING (auth.uid() = user_id);The app includes an AI assistant powered by OpenAI's GPT-4 that can:
- Analyze your data: Get insights about your habits, stats, and productivity trends
- Provide recommendations: Receive personalized suggestions for improvement
- Answer questions: Ask about your progress, goals, and routines
- Quick interactions: Use pre-defined quick messages for common queries
The AI assistant has access to your:
- Stats and their recent values
- Habits and completion rates
- Todo items and their status
- User preferences and settings
It uses this data to provide personalized insights and recommendations to help you on your life tracking journey.
The AI chat feature is now handled by Supabase Edge Functions for better security and performance.
- Install Supabase CLI:
npm install -g supabase - Login to Supabase:
supabase login - Link your project:
supabase link --project-ref YOUR_PROJECT_ID - Set your OpenAI API key:
export OPENAI_API_KEY=your-key-here - Run the deployment script:
./scripts/deploy-ai-chat.sh
For detailed setup instructions, see SUPABASE_AI_SETUP.md
- API Key Protection: OpenAI API key is stored securely in Supabase
- User Authentication: All requests are authenticated
- Rate Limiting: 10 requests per minute per user
- Input Validation: Message length and content validation
- Timeout Protection: 30-second timeout prevents hanging requests
Your data is sent to OpenAI for processing but is not stored by OpenAI. The conversation history is only kept in your browser session and is not persisted.
MIT