Habit Tracker

Habit Tracker

A modern, fast, and responsive habit tracking web application built with Next.js and deployed on Cloudflare.

Tech Stack

Category

Technology

Framework

Next.js (App Router)

Deployment

Cloudflare Workers/Pages (via OpenNext @opennextjs/cloudflare)

Database

Neon Serverless PostgreSQL

ORM

Drizzle ORM

Styling

Tailwind CSS v4 + Vanilla CSS

Push Notifications

ntfy.sh

Features

📅 Habit Tracking

Log daily habits as:

✅ Done

⏭️ Skip

❌ Miss

📊 Statistics & Streaks

Track your progress with:

Current streaks

Perfect streaks

Completion rates

Weekly rhythm

Consistency heatmaps

🔔 Push Notifications

Receive scheduled reminders via ntfy with actionable lock-screen buttons such as:

✓ Done

Skip today

Development

  1. Install Dependencies

npm install

  1. Configure Environment Variables

Copy the example environment file and configure it with your database and notification settings.

cp .env.example .env

Required values:

DATABASE_URL (Neon)

ntfy server configuration

  1. Set Up the Database

Push the schema directly:

npm run db:push

Or generate migrations:

npm run db:generate

  1. Start the Development Server

npm run dev

  1. Preview with Cloudflare

npm run preview

Deployment

The application is hosted on Cloudflare Workers/Pages.

Deploy using:

npm run deploy

Cloudflare Access (Zero Trust)

The deployed application is protected behind Cloudflare Access using two primary policies:

Policy

Purpose

allow-my-email

Restricts web access to your authenticated email address.

allow-api

Allows scheduled cron jobs, programmatic requests, and background habit actions to bypass interactive authentication at the Cloudflare edge.

Maintenance Notes

CSS & Charts (.chart-bar)

The statistics page uses CSS-based bar charts (e.g. WeekdayBars and MonthlyChart).

Important (Mobile Safari):

Safari has a flexbox quirk where .flex-col containers inside a flex row won't expand vertically unless they explicitly include h-full.

Without h-full:

Column height collapses to the text height.

.chart-bar elements render with a height of 0.

Bar charts appear invisible.

Always apply h-full to expanding .flex-col elements inside flex rows.

Push Notifications (src/lib/notifications.ts)

The notification implementation is optimized for the iOS ntfy app.

Markdown

Markdown is intentionally avoided.

iOS ntfy renders Markdown literally (e.g. bold displays with asterisks).

Emojis

Instead of embedding emojis directly into notification titles, a single emoji tag is supplied, for example:

trophy

fire

sparkles

seedling

ntfy automatically converts the tag into the corresponding emoji in the iOS notification banner.

Action Buttons

Notifications include secure http actions that allow users to:

Mark a habit as Done

Skip the current day

These actions include authentication headers so they continue to work even when the /api/habit-action endpoint is protected by Cloudflare Access.

Statistics Page Design

The statistics dashboard intentionally minimizes visual clutter:

Inline emojis have been removed from StatTile components.

Achievement milestone emojis have also been removed.

Emojis are primarily reserved for push notifications to keep notification banners engaging without overwhelming the dashboard UI.