TickTrack is a lightweight and modern Progressive Web App ( PWA ) designed to help users track time and manage tasks efficiently.
TickTrack was created as a lightweight productivity application focused on simplicity and performance. The project combines task management, time tracking, document storage, customizable user profiles and a modern light/dark interface inside a Progressive Web App powered by Supabase.
The application demonstrates practical usage of React, TypeScript, Supabase Authentication, PostgreSQL, Storage, Row Level Security (RLS), Progressive Web App technologies and Docker containerization.
- β Create and delete tasks
- π Organize tasks into projects
- β Mark favorite projects
- β Mark favorite tasks
- π Add task descriptions
- π¬ Add comments to tasks
- π€ Display comment authors with avatars
- π Assign due dates to tasks
- π¦ Assign task statuses (To Do, In Progress, Done)
- π― Assign task priorities (Low, Medium, High)
- βοΈ Update task status and priority directly from the task list
- π Filter tasks by status and priority
- π Quickly filter favorite projects and tasks
- π Sort tasks by name, status and priority
- π Task activity timeline
- β±οΈ Built-in task timer
βΆοΈ Start / pause / stop tracking- π Automatic time calculation
- π Dashboard statistics
- π Completion rate tracking
β οΈ Highlight overdue tasks- β±οΈ Total tracked time
- π Tasks due today
- β Tasks completed today
- π Total number of time tracking sessions
- π Average tracked time per task
- π Productivity charts:
- Tracked Time Last 7 Days
- Tasks by Status
- π Upload PDF files directly to tasks
- π±οΈ Drag & drop PDF upload
- π Built-in PDF preview
- π₯ Download uploaded files
- ποΈ Delete attached files
- π Private storage per authenticated user
- βοΈ Files stored in Supabase Storage
- π Monthly calendar view for task deadlines
- π Display tasks assigned to each day
- π΄ Highlight overdue tasks
- β Visual indicators for completed tasks
- π±οΈ Click a day to view scheduled tasks
- βοΈ Update task status and priority directly from the calendar
- π Email authentication with Supabase
- π€ User-specific projects and tasks
- πΌοΈ Custom user avatar
- βοΈ Editable display name
- π Secure password change
- βοΈ Avatar storage in Supabase Storage
- π Light / Dark mode
- πΎ Theme preference saved in localStorage
- π₯οΈ Automatic system theme detection
- π¨ Consistent theme across the entire application
- β¨ Modern UI built with shadcn/ui
- π Toast notifications using Sonner
- π± Responsive layout improvements
- π¦ Installable
- π± Mobile-friendly
- π Offline support
React 19TypeScriptTailwind CSSlocalStorageβ persistent theme preferencesBolt.newβ initial project scaffold and selected UI componentsViteβ as the frontend build toolPWAβ installable app experience with offline supportSupabaseβ Authentication, PostgreSQL and StorageNode.js/npmβ dependency and script managementDockerβ containerized production buildDocker Composeβ simplified local container managementNginxβ production server for the built React applicationCloudflareβ domain management with DNS, SSL and performance optimizationsRechartsβ chart library used for dashboard productivity visualizationsPDF.jsβ in-app PDF preview renderingshadcn/uiβ reusable UI component libraryRadix UIβ accessible component primitivesSonnerβ toast notifications
The initial project structure and a small part of the UI were bootstrapped using Bolt.new.
From the authentication system onwards, the application has been developed independently, including:
- Supabase Authentication
- Database design
- Row Level Security (RLS)
- File upload system
- PDF validation
- Supabase Storage integration
- Task management
- Timer functionality
- Responsive UI improvements
- Bug fixes and further feature development
- Task activity history
Further development included:
- complete UI redesign using shadcn/ui
- responsive landing page
- modern dialog system
- toast notifications
- user profile management
- avatar upload
- password management
- task comments
Bolt.new allows rapid prototyping of UI components and app logic using AI-generated prompts. Hereβs a quick guide to creating effective prompts:
- Be specific β clearly describe the component or feature you want.
- Include context β mention frameworks, libraries, or styling preferences.
- Provide examples β show the desired structure or behavior if possible.
- Iterate β refine your prompt based on the generated output.
Sample prompt
Create a responsive task timer component in React + TypeScript,
with start/stop buttons and a progress bar.
Style it using Tailwind CSS.
The component should display elapsed time in HH:MM:SS format.-
Use plain language first, then add technical details Start with a simple, natural description of what you want, then layer in frameworks, languages, or constraints. This helps the AI understand your intent clearly.
-
Experiment with different phrasings Slightly changing how you word a prompt can produce different outputs. Donβt hesitate to reword or restructure sentences for clarity or creativity.
-
Combine multiple instructions carefully You can include several requirements in one prompt, but keep it readable and organized. Use line breaks, bullet points, or numbered lists if the AI supports it.
-
Specify the audience or user Mention the target users or context, e.g., βDesign this for mobile usersβ or βMake this suitable for beginners.β This ensures the output is tailored appropriately.
-
Include constraints and rules explicitly If there are limitations (design style, length, format, accessibility requirements), state them clearly to avoid undesired outputs.
-
Ask for step-by-step reasoning for complex tasks For multi-step problems or explanations, request that the AI think step by step. Example: βExplain your approach before giving the final code.β
-
Provide examples whenever possible Demonstrate desired outputs with sample code snippets, UI layouts, or text formats to guide the AI toward your expectations.
-
Iterate and refine Donβt expect perfection on the first try. Review outputs, adjust the prompt, and iterate until you get satisfactory results.
-
Use explicit roles or personas For creative tasks, you can assign the AI a role: βYou are a UX designerβ or βYou are an expert in React development.β This often improves relevance and style.
-
Keep prompts concise yet complete Avoid overly long prompts with unnecessary details, but ensure all key requirements are included.
TickTrack follows a client-first architecture powered by Supabase services.
User
β
βΌ
Cloudflare (DNS/CDN)
β
βΌ
Netlify (Frontend Hosting)
β
βΌ
React + Vite (PWA)
β
βΌ
Supabase
ββββββββββββββββββββββ
β Authentication β
β PostgreSQL β
β Storage β
β Row Level Security β
ββββββββββββββββββββββThe frontend communicates directly with Supabase using the official JavaScript SDK. User authentication, database operations and file uploads are secured using Row Level Security (RLS) policies.
Dockerfile
docker-compose.yml
nginx.conf
.dockerignore
src/
βββ components/
β βββ ui/
β β βββ alert-dialog.tsx
β | βββ badge.tsx
β β βββ button.tsx
β β βββ card.tsx
β β βββ dialog.tsx
β β βββ input.tsx
β β βββ select.tsx
β β βββ sonner.tsx
β β βββ textarea.tsx
β β
β βββ AdSense.tsx
β βββ AdSenseVerification.tsx
β βββ Auth.tsx
β βββ Dashboard.tsx
β βββ PasswordReset.tsx
β βββ PdfUpload.tsx
β βββ PriorityBadge.tsx
β βββ ProductivityCharts.tsx
β βββ ProfileDialog.tsx
β βββ ProjectList.tsx
β βββ StatusBadge.tsx
β βββ TaskFilesList.tsx
β βββ TaskComments.tsx
β βββ TaskActivity.tsx
β βββ TaskList.tsx
β βββ ThemeToggle.tsx
β βββ Timer.tsx
β
βββ lib/
β βββ directAuth.ts
β βββ supabase.ts
β βββ taskActivity.ts
β βββ theme.ts
β
βββ App.css
βββ App.tsx
βββ index.css
βββ main.tsx
βββ registerSW.ts
βββ types.ts
βββ vite-env.d.ts
β
βββ supabase/
β
βββ ...
The application is organized into reusable React components with Supabase configuration separated inside the lib directory.
Responsible for:
- displaying project statistics
- calculating task completion rate
- showing overdue task count
- summarizing tracked working time
- showing productivity metrics
- displaying tasks due today
- displaying tasks completed today
- calculating average task time
- calculating total number of time tracking sessions
Responsible for:
- displaying productivity charts
- showing tracked time from the last 7 days
- showing task distribution by status
- visualizing productivity data using Recharts
Responsible for:
- selecting PDF files
- drag & drop uploads
- validating uploaded files
- uploading files to Supabase Storage
- displaying upload status
Responsible for:
- managing user profile
- uploading and removing avatars
- changing display name
- changing account password
- synchronizing profile data with Supabase
Responsible for:
- creating projects
- displaying project list
- selecting active projects
- deleting projects
- marking favorite projects
- quick filtering favorite projects
Responsible for:
- displaying task activity history
- logging task changes
- displaying comments, file and timer events
- chronological activity timeline
Responsible for:
- fetching uploaded files
- displaying task attachments
- previewing PDF files
- downloading files
- deleting uploaded documents
Responsible for:
- displaying task comments
- creating new comments
- deleting comments
- displaying author names and avatars
- synchronizing comments with Supabase
Responsible for:
- creating tasks
- assigning statuses and priorities
- marking favorite tasks
- adding task descriptions
- assigning due dates
- filtering and sorting tasks
- quick filtering favorite tasks
- managing attached files
Responsible for:
- tracking task duration
- start, pause and stop functionality
- displaying elapsed time
Responsible for:
- switching between light and dark mode
- saving user theme preferences
- updating the global application theme
TickTrack allows authenticated users to upload PDF documents directly to individual tasks.
Each uploaded document is:
- linked to a specific task
- isolated per authenticated user
- stored in Supabase Storage
- indexed in PostgreSQL
- protected by Row Level Security (RLS)
- upload PDF files
- automatic validation (PDF only)
- download attachments
- delete attachments
- private storage using Supabase Storage
- metadata stored in Supabase Database
- maximum file size: 10 MB
- safe file name sanitization
- color-coded success and error messages
- automatic input reset after invalid file selection
- drag & drop uploads
- built-in PDF preview
task-files/
user-id/
task-id/
file.pdf
TickTrack protects user data using several Supabase security features:
- Supabase Authentication
- Row Level Security (RLS)
- protected Storage buckets
- authenticated file uploads
- ownership validation
- PDF MIME type validation
- maximum upload size validation
- sanitized file paths for secure storage
- user-specific task isolation
- secure password updates
- avatar ownership validation
- protected avatar storage
- Row Level Security (
RLS) for task comments - comment ownership validation
The production version of TickTrack is deployed using Netlify .
The repository also contains a Docker configuration that allows the production build to be run locally using Docker Compose and Nginx.
Cloudflare is used for:
- custom domain management
- DNS configuration
- automatic SSL certificates
- HTTPS
- performance optimizations
- CDN
The project follows modern React and TypeScript best practices.
Implemented improvements include:
- strict TypeScript configuration
- ESLint integration
- React Hooks dependency validation
- reusable React components
- asynchronous error handling
- client-side file validation
- upload error handling
- reusable upload components
- sanitized storage paths
- strongly typed Supabase responses
- responsive task management interface
- dashboard statistics
- overdue task highlighting
- automated type checking using
npm run typecheck - fixed TypeScript project configuration for successful type checking
- separated productivity charts into a reusable component
- centralized theme management
- persistent user theme preferences
- system color scheme detection
- reusable theme toggle component
- shadcn/ui component architecture
- reusable dialog components
- reusable toast notifications
- path aliases for cleaner imports
- improved responsive layouts
- reusable profile management component
- image upload validation
- reusable task comments component
- strongly typed comment models
These improvements increase maintainability, readability and long-term scalability of the application.
Before running the project locally, make sure you have:
Node.js20+Docker Desktopβ optional, required only for containerized local deploymentnpm10+- a Supabase project
- Supabase Storage bucket named
task-files - Supabase Storage bucket named
avatars - configured
RLSpolicies for Storage buckets
- Clone the repository:
git clone https://github.com/WiolaWysopal/TickTrack.git
cd TickTrack- Install dependencies:
npm install- Run the development server:
npm run dev- Create the environment variables:
cp .env.example .env.publicor manually create:
.env.public
TickTrack can be built and run locally inside a Docker container.
The application uses a multi-stage Docker build:
- Node.js installs dependencies and builds the React/Vite application.
- The generated production files are copied to a lightweight Nginx image.
- Nginx serves the application on port
80inside the container.
Make sure Docker Desktop is installed and running.
Create a .env file containing the required Supabase variables:
VITE_SUPABASE_URL=https://YOUR-PROJECT.supabase.co
VITE_SUPABASE_ANON_KEY=YOUR_PUBLIC_ANON_KEYBuild and start the application:
docker compose up --buildThe application will be available at:
http://localhost:8080
Stop the running containers using:
docker compose downThe Docker setup includes:
- multi-stage production build
- Node.js build environment
- lightweight Nginx production server
- Docker Compose configuration
- React Router fallback handled by Nginx
- Supabase environment variables passed during the build process
Docker is provided as an alternative local deployment method. The production version of TickTrack remains hosted on Netlify.
npm run devβ start the development servernpm run buildβ build the app for productionnpm run previewβ preview the production buildnpm run lintβ lint code with ESLintnpm run typecheckβ run TypeScript type checking
Create a .env.public file in your project/ directory:
VITE_SUPABASE_URL="https://YOUR-PROJECT.supabase.co"
VITE_SUPABASE_ANON_KEY="YOUR_PUBLIC_ANON_KEY"TickTrack stores application data in a Supabase PostgreSQL database. The application uses relational tables linked by foreign keys to manage projects, tasks, tracked work sessions and attached documents.
Stores additional user profile information.
Fields include:
- user id
- display name
- public avatar URL stored in Supabase Storage
- created_at
- updated_at
Stores user-created projects.
Fields include:
- project name
- owner (
user_id) - favorite flag (
is_favorite) - creation timestamp
Stores tasks assigned to projects.
Fields include:
- task name
- associated project (
project_id) - owner (
user_id) - status (
todo,in_progress,done) - favorite flag (
is_favorite) - priority (
low,medium,high) - optional description
- optional due date
- completion timestamp (
completed_at) - creation timestamp
Stores the activity history for each task.
Fields include:
- related task (
task_id) - author (
user_id) - activity type
- description
- metadata (JSON)
- creation timestamp
Stores comments attached to tasks.
Fields include:
- related task (
task_id) - author (
user_id) - comment content
- creation timestamp
- update timestamp
Stores tracked work sessions created by the timer.
Each session contains:
- related task (
task_id) - related project (
project_id) - owner (
user_id) - session start and end time
- tracked duration (seconds)
- creation timestamp
These records are used to calculate:
- total tracked time
- average task time
- average session duration
- number of sessions
- productivity dashboard statistics
- productivity charts
Stores metadata for PDF documents attached to tasks.
Fields include:
- related task (
task_id) - owner (
user_id) - file name
- storage path
- creation timestamp
The task_files table stores metadata only. Uploaded files themselves are stored in Supabase Storage. The actual PDF files are stored in Supabase Storage , while only their metadata is stored in PostgreSQL.
The database uses foreign keys to maintain relationships between entities:
- one user can own multiple projects
- one project can contain multiple tasks
- one task can have multiple time sessions
- one task can have multiple attached PDF files
- one task can have multiple comments
- one profile can reference one avatar stored in Supabase Storage
The project uses GitHub Actions to periodically ping Supabase, preventing the free-tier database from going to sleep.
- Add
.github/workflows/keep-supabase-awake.yml:
name: Keep Supabase Awake
on:
schedule:
- cron: '*/5 * * * *'
jobs:
ping:
runs-on: ubuntu-latest
steps:
- name: Ping Supabase tables
run: |
SUPA_URL="https://YOUR-PROJECT.supabase.co"
SUPA_KEY="YOUR_PUBLIC_ANON_KEY"
for table in tasks users projects; do
echo "Pinging table: $table"
curl -X GET "$SUPA_URL/rest/v1/$table" \
-H "apikey: $SUPA_KEY" \
-H "Authorization: Bearer $SUPA_KEY" \
-H "Accept: application/json"
echo ""
done- You can view the run history in
GitHub β Actions β Keep Supabase Awake.
The application icon ( favicon ) was generated using Craiyon , an AI-powered tool that creates images based on short text prompts. Craiyon uses generative models to produce graphics in various styles, making it easy to generate simple illustrations, icons, or visual concepts. The image used in this project was created specifically for the application and does not depict any real persons or objects.
Planned features include:
- support for additional file types
- Kanban board based on task statuses
- custom task statuses
- task reminders and notifications
- avatar cropping before upload
- profile preferences
- export to PDF
- team collaboration
No installation is required. Simply open the link and sign up to start using the application. The TickTrack app is deployed and available online at:
You can access the full Progressive Web App ( PWA ) in your browser.