NOTE: This is still under construction and probably very buggy!
A powerful, feature-rich todo and project management application built with Next.js, TypeScript, and Tailwind CSS. Features multiple views, smart input detection, sprint planning, and comprehensive storage options.
Live app: marcelerz.github.io/doit
- β State-based Todo System - Active, Completed, Archived, Deleted states with full timestamp tracking
- β Smart Input - Natural language parsing with auto-detection of dates, people, projects, and priorities
- β Multiple Views - Todos, Kanban, Gantt, Calendar, Notes, People, Projects, Sprints, Reviews, Statistics and Time Reports, each switchable off in settings
- β People & Projects - Full entity management with assignments and mentions
- β Sprint Planning - Scrum-style sprint management with Kanban integration
- β Notes & Reviews - Rich-text notes with action items, and 1:1 review documents
- β Comments & Activity - Full history tracking on todos, notes, people, and projects
- β Time Tracking - Start/stop timers and manual entries, reported per project and person
- Flexible filtering by any metadata (people, projects, tags, priorities, etc.)
- Multiple sort options and grouping (by project, priority, due date, sprint)
- Batch operations on multiple todos
- Saved view presets
- Customizable workflow states (Backlog, To Do, In Progress, Review, Completed, Archived)
- Drag-and-drop between states
- Configurable state transitions
- Multiple board views for different workflows
- Sprint filtering
- Timeline visualization of tasks
- Three scheduling techniques:
- Sequential - Simple task-to-task with context switching
- Pomodoro - 25/5/15 work/break cycles with notifications
- Flow - Extended focus sessions (52/17 method, Ultradian rhythm)
- Customizable time blocks (meetings, lunch, breaks)
- Audio notifications with ambient sounds
- Monthly calendar with task indicators
- Click to view and edit tasks for any day
- Pomodoro timer with configurable work/break intervals
- Flow mode for extended focus sessions
- Ambient sounds for concentration
- Task queue management
- Task completion trends
- Time tracking reports
- Sprint velocity metrics
The app automatically detects and parses:
- Dates - "tomorrow", "next Friday", "in 2 weeks", "eod", "bow" (beginning of week)
- Recurring - "every monday", "every 2 weeks", "every first friday"
- People - Auto-detects names, or use
@personfor assignment,$personfor source - Projects - Auto-detects "on ProjectName", "for ProjectName", or use
%project - Priorities - Auto-detects "urgent", "high priority", or use
!!priority - Tags - Use
#tagfor tagging
- Automatic IndexedDB with localStorage fallback
- Safari Private Mode compatible
- Automatic Migration from localStorage to IndexedDB
- Backup & Restore with JSON export/import
- Data Versioning with automatic migrations
- Node.js 20+ (required by Next.js 16)
- npm
# Clone the repository
git clone https://github.com/marcelerz/doit.git
cd doit
# Install dependencies
npm install
# Start development server
npm run devOpen http://localhost:3000 to see the app.
# Build for production
npm run build
# Static export for GitHub Pages. GITHUB_PAGES=true is what switches on
# output: "export" and the /doit base path -- without it this build fails.
GITHUB_PAGES=true npm run build:gh-pagesThe deployed app is a static export with no server: everything runs in the browser and all data stays in the browser's own storage.
The app is published at https://marcelerz.github.io/doit/.
Pushing to main deploys it. .github/workflows/deploy.yml runs typecheck, lint and the unit
tests, then builds and publishes out/ to the gh-pages branch, which GitHub Pages serves.
There is nothing to run by hand.
Two things worth knowing if you build it yourself:
GITHUB_PAGES=truehas to be in the environment. It is what switches onoutput: "export"and the/doitbase path innext.config.ts. Nothing inpackage.jsonor the build script sets it -- only the workflow does -- so a barenpm run build:gh-pagesproduces an ordinary server build with noout/directory and then fails on the next step.- After the export,
scripts/fix-github-pages.jsadds.nojekyll, copiesindex.htmlto404.htmlfor client-side routing, rewrites the web manifest to the/doit/base path, and stamps the version fromversion.jsoninto the service worker so each deploy ships a worker the browser sees as new.
The visual snapshots are macOS baselines and cannot run on the Linux CI runner, so run
npm run test:visual locally before releasing.
# Run unit tests
npm test
# Run tests in watch mode
npm run test:watch
# Run tests with coverage
npm run test:coverage
# Run E2E tests
npm run test:e2e
# Run smoke and visual suites
npm run test:smoke
npm run test:visual
# typecheck + lint + test + smoke + visual
npm run test:all
# the same, with the coverage floors enforced
npm run validatedoit/
βββ src/
β βββ app/ # Next.js App Router pages
β β βββ layout.tsx # Root layout
β β βββ page.tsx # Main app page
β β βββ settings/ # Settings page
β βββ components/
β β βββ views/ # Main views (TodoApp is the container)
β β βββ items/ # List item components
β β βββ overlays/ # Modal/detail views
β β βββ input/ # SmartInput, RichTextEditor
β β βββ shared/ # Reusable components
β β βββ settings/ # Settings tab components
β β βββ providers/ # App-level React providers
β β βββ ServiceWorkerProvider.tsx # PWA service worker
β β βββ StorageInitializer.tsx # Storage initialization
β β βββ ThemeProvider.tsx # Dark/light theme
β βββ hooks/ # React hooks (state management)
β β βββ useTodos.ts # Todo state management
β β βββ usePeople.ts # People management
β β βββ useProjects.ts # Projects management
β β βββ useSprints.ts # Sprint management
β β βββ useSettings.ts # App settings
β βββ models/ # Business logic layer
β β βββ TodoModel.ts # Todo business logic
β β βββ PersonModel.ts # Person business logic
β β βββ ProjectModel.ts # Project business logic
β β βββ SettingsModel.ts # Settings business logic
β βββ storage/ # Storage abstraction
β β βββ storage.ts # IndexedDB/localStorage adapters
β β βββ migrations.ts # Data migrations
β β βββ backup.ts # Backup/restore functionality
β βββ types/ # TypeScript types, one file per domain
β β βββ todo.ts # Todo types and branded TodoId
β β βββ viewRegistry.ts # The single source for the view tabs
β β βββ settings.ts # Settings types
β βββ utils/ # Utility functions
β βββ autoDetection.ts # Smart input detection
β βββ dateUtils.ts # Date parsing
β βββ recurringParser.ts # Recurring pattern parsing
β βββ ganttScheduler.ts # Gantt scheduling algorithms
β βββ notifications.ts # Sound/notification utilities
βββ public/
β βββ sounds/ # Ambient sounds for focus mode
βββ docs/ # Documentation
βββ package.json
The app uses a business logic layer that wraps raw data with computed properties and validation:
// useTodos returns models, so todos[0] is already a TodoModel
const todo = todos[0];
todo.isOverdue; // Computed: is past due date?
todo.dueDateDisplay; // "Today", "Tomorrow", "Dec 15"
todo.canComplete(todos); // Validates dependencies
todo.matchesSearch(q); // Full-text searchAutomatic storage selection with migration:
// Automatic IndexedDB with localStorage fallback
import { loadFromStorage, saveToStorage, waitForStorageInit } from "@/storage/storage";
// Await initialization first, or on an IndexedDB install you read an
// emptied localStorage and persist the fallback over the user's data
await waitForStorageInit();
const data = await loadFromStorage("doit-todos", []);
await saveToStorage("doit-todos", updatedData);Each data domain has its own hook:
useTodos()- ReturnsTodoModel[]with full CRUDusePeople()- ReturnsPersonModel[]with assignmentsuseProjects()- ReturnsProjectModel[]with linkinguseSprints()- Sprint managementuseSettings()- App configuration
- General - Archive retention, auto-delete
- Priorities - Custom priority levels with colors
- Categories - Project categories
- Date/Time - Morning, noon, afternoon, evening times
- Work Hours - Schedule configuration, time blocks
- Gantt - Scheduling technique settings
- Focus - Pomodoro/Flow mode configuration
- Calendar - Calendar display options
- Notes - Note defaults and templates
- Import - Import from Todoist and other CSV exports
- Kanban - Workflow states, transitions, views
- Sprints - Sprint management, default duration
- Auto-Assign - Default metadata for new todos
- Markers - Color customization
- Links - URL pattern detection
- Notifications - Browser notification settings
- Backup - Export/import data
- Storage - IndexedDB/localStorage settings
| Marker | Usage | Example |
|---|---|---|
@ |
Assign person | @john |
$ |
Source person | $sarah |
% |
Project | %website |
!! |
Priority | !!urgent |
# |
Tag | #bug |
- Tailwind CSS 4 - Utility-first styling
- Dark Mode - Automatic system preference detection
- Mobile-First - Fully responsive design
- Custom Theme - Configurable marker colors
- Chrome/Edge (recommended)
- Firefox
- Safari (including Private Mode)
- Mobile browsers
- Framework: Next.js 16 with App Router
- Language: TypeScript 5
- Styling: Tailwind CSS 4
- Date Parsing: chrono-node
- Storage: IndexedDB + localStorage
- Audio: Web Audio API
- Testing: Jest + Playwright
Personal Use License - This software is available for personal, non-commercial use only. Commercial use, redistribution, and derivative works are prohibited. See LICENSE for full details.
This is a personal project under a Personal Use License, which does not permit redistribution or derivative works -- so there is no open contribution process. Bug reports and suggestions are welcome as issues.
Additional documentation is available in the docs/ folder: