A minimalist, fast, and user-friendly habit tracking application built with Next.js and Supabase. Focus on consistency, not complexity.
Streaky is a Progressive Web App (PWA) designed for daily habit tracking with extreme simplicity and zero friction. The goal is to make tracking habits as easy as a single tap, encouraging daily consistency without overwhelming users with features.
- β¨ One-tap habit tracking - Mark habits as complete with a single action
- π― Minimal UI - No unnecessary steps or complexity
- β‘ Fast load time - Optimized for quick access
- π± Works offline - Basic offline support via PWA
- π Focus on consistency - Track streaks and build lasting habits
- π Authentication - Google OAuth and email/password login
- π Habit Management - Create, edit, and delete habits
- β Daily Tracking - Mark habits as completed each day
- π₯ Streak Calculation - Track consecutive days of completion
- π Basic Statistics - View completion rates and progress
- π Calendar View - Visual representation of habit completion
- π± PWA Support - Installable on mobile devices
- π¨ Responsive Design - Works seamlessly on desktop and mobile
- Push notifications
- Social features
- Gamification
- Health integrations
- Templates & routines
- Advanced analytics
- React 19 - UI library
- Next.js 16 - React framework with App Router
- TypeScript - Type safety
- TailwindCSS - Utility-first CSS
- shadcn/ui - UI component library
- React Query - Server state management
- Zustand - UI and local state
- Supabase - Backend as a Service
- Authentication (Google OAuth + Email)
- PostgreSQL Database
- Row Level Security (RLS)
- Edge Functions (optional)
- Progressive Web App (PWA) - Installable on mobile devices
- Node.js 18+ and npm/yarn/pnpm
- A Supabase account (sign up here)
- Git
-
Clone the repository
git clone https://github.com/BrayanMQ/streaky-app.git cd streaky-app -
Install dependencies
npm install # or yarn install # or pnpm install
-
Set up environment variables
Copy the example environment file and fill in your Supabase credentials:
cp .env.example .env.local
Then edit
.env.localand replace the placeholder values with your actual Supabase credentials:NEXT_PUBLIC_SUPABASE_URL=your_supabase_project_url NEXT_PUBLIC_SUPABASE_ANON_KEY=your_supabase_anon_key SUPABASE_PROJECT_ID=your_supabase_project_id
How to get your Supabase credentials:
- Go to your Supabase Dashboard
- Select your project (or create a new one)
- Navigate to Settings β API
- Copy the Project URL and paste it as
NEXT_PUBLIC_SUPABASE_URL - Copy the anon public key and paste it as
NEXT_PUBLIC_SUPABASE_ANON_KEY - Copy the Project ID (found in the project URL or Settings β General) and paste it as
SUPABASE_PROJECT_ID
Note: The
NEXT_PUBLIC_prefix is required for these variables to be accessible in both server and client components in Next.js. -
Set up the database
Apply the database migrations using Supabase CLI:
npx supabase db push
This will apply all migrations from
supabase/migrations/in chronological order. The migrations include:habitstable - Stores user habitshabit_logstable - Stores daily completion records- Indexes for query optimization
- Constraints for data validation
- Row Level Security (RLS) policies for data protection
Alternative: You can also run the SQL schema manually in Supabase SQL Editor. See
docs/database-schema.sqlfor the complete schema. -
Generate TypeScript types (Optional but recommended)
After setting up your database schema, generate TypeScript types from your Supabase database:
npm run generate:types
This command uses the
SUPABASE_PROJECT_IDenvironment variable from your.env.localfile to generate type-safe database types intypes/database.ts. Run this command whenever you make changes to your database schema.Note: Make sure you have set
SUPABASE_PROJECT_IDin your.env.localfile before running this command. -
Run the development server
npm run dev # or yarn dev # or pnpm dev
-
Open your browser
Navigate to http://localhost:3000
streaky-app/
βββ app/ # Next.js App Router
β βββ auth/ # Authentication pages
β β βββ login/ # Login page
β β βββ callback/ # OAuth callback
β βββ dashboard/ # Dashboard page
β βββ habits/ # Habits management pages
β βββ globals.css # Global styles
βββ components/ # React components
β βββ HabitCard.tsx
β βββ HabitList.tsx
β βββ AddHabitModal.tsx
β βββ CalendarGrid.tsx
β βββ Header.tsx
β βββ BottomNav.tsx
βββ hooks/ # Custom React hooks
β βββ useHabits.ts
β βββ useHabitLogs.ts
β βββ useAuth.ts
βββ lib/ # Utility functions
β βββ supabaseClient.ts
β βββ auth.ts
β βββ streaks.ts
β βββ stats.ts
βββ store/ # Zustand stores
β βββ ui.ts
β βββ habits.ts
βββ public/ # Static assets
β βββ manifest.json # PWA manifest
β βββ icons/ # App icons
βββ docs/ # Documentation
β βββ context.md # Technical context
βββ issues/ # Development issues/tasks
βββ scripts/ # Utility scripts
npm run dev- Start development servernpm run build- Build for productionnpm run start- Start production servernpm run lint- Run ESLintnpm run generate:types- Generate TypeScript types from Supabase database schema (requiresSUPABASE_PROJECT_IDin.env.local)
-
Create a Supabase project
- Sign up at supabase.com
- Create a new project
-
Configure Authentication
- Go to Authentication β Providers
- Enable Email provider
- Enable Google OAuth (requires OAuth credentials)
-
Set up the database
- Apply migrations using:
npx supabase db push - Or manually run the schema from
docs/database-schema.sqlin SQL Editor - Verify RLS policies are enabled
- Apply migrations using:
-
Get your credentials
- Go to Settings β API
- Copy Project URL and anon key to
.env.local - Make sure to use the
NEXT_PUBLIC_prefix for both variables
Required environment variables:
The project uses NEXT_PUBLIC_ prefixed variables so they work in both Server and Client Components:
NEXT_PUBLIC_SUPABASE_URL=your_supabase_project_url
NEXT_PUBLIC_SUPABASE_ANON_KEY=your_supabase_anon_key
SUPABASE_PROJECT_ID=your_supabase_project_idNote:
SUPABASE_PROJECT_IDis required for thegenerate:typesscript to automatically generate TypeScript types from your Supabase database schema.
Why
NEXT_PUBLIC_? In Next.js, only environment variables prefixed withNEXT_PUBLIC_are exposed to the browser. Since our Supabase client (lib/supabaseClient.ts) is used in both Server and Client Components, we use this prefix to ensure it works everywhere.
Optional (for production):
NEXT_PUBLIC_APP_URL=https://your-domain.comThe Supabase client is configured in lib/supabaseClient.ts and can be used in both Server and Client Components:
// In a Server Component
import { supabase } from '@/lib/supabaseClient'
// In a Client Component
'use client'
import { supabase } from '@/lib/supabaseClient'The client automatically validates that the required environment variables are set and will throw helpful error messages if they're missing.
- TypeScript strict mode enabled
- ESLint configured with Next.js rules
- Prefer functional components with hooks
- Use TypeScript for type safety
- React Query: Use for all server state (API calls, Supabase queries)
- Zustand: Use for UI state (modals, selected items, local preferences)
- Local State: Use
useStatefor component-specific state
The project uses Supabase migrations to manage database schema changes. Migrations are located in supabase/migrations/ and are applied using:
npx supabase db pushMigrations are executed in chronological order based on their timestamp. Each migration is idempotent and can be safely re-run.
20251220100000_create_habits_table.sql- Creates the habits table with indexes and constraints20251220100001_create_habit_logs_table.sql- Creates the habit_logs table with indexes20251220100002_enable_rls.sql- Enables Row Level Security on both tables20251220100003_create_habits_rls_policies.sql- RLS policies for habits table20251220100004_create_habit_logs_rls_policies.sql- RLS policies for habit_logs table
- Technical Context - Full technical documentation
- Supabase Docs - Supabase documentation
- Next.js Docs - Next.js documentation
This project is private and proprietary.
Made with β€οΈ for building better habits