Files
solelog/docs/roadmap.md

10 KiB

Insole Production Time Tracker — Rebuild Roadmap & Project Overview

  • Created: 2026-06-17
  • Status: Approved — living project doc; Phase 0 plan written (docs/plans/phase-0-foundation.md)
  • Type: Greenfield rebuild of an inherited app
  • Tracked in git under docs/ (the project's documentation source of truth).

2026-06-17 — Legacy code removed. The inherited Create/Anything export (apps/mobile, apps/web, publisher/) was deleted in a full cleanup. The repo is now a single-service backend (apps/api) plus packages/shared. Reference for the old code is preserved in docs/reference/ and in git history. The sections below describe the codebase as inherited and the rebuild plan; treat references to the legacy apps as historical.


1. Context

The codebase was inherited as an export from the Create / Anything AI platform — a working time-tracking app for insole (orthotic) production, originally built by a friend through a chat-driven workflow. It arrived with no history, no documentation, and no clarity on what was complete or where the backend/data lived.

Reverse-engineering established:

  • It is a two-app monorepo: apps/mobile (Expo/React Native) + apps/web (Next.js 16 backend on Neon Postgres). Plus publisher/ (deploy tooling).
  • It is heavily coupled to the Create platform: "do-not-edit" platform files, patched dependencies, a web-sandbox iframe layer, and ~80 dependencies for what is functionally a stopwatch.
  • Auth is better-auth (email+password, argon2 hashes, bearer tokens for mobile, cookies for web), but the core flow does not actually require login.
  • The data and accounts are not ours. Users, password hashes, and all task/time data live in the platform's managed Neon Postgres, bound to the friend's Create account/organization. This repo contains only the code and an ANYTHING_PROJECT_TOKEN — no database credentials. Nothing runs locally and no database is reachable from this code.

Work already done this session (committed):

  • Git repository initialised; baseline + doc corrections committed.
  • Found and fixed /api/logs — it was both git-ignored (an over-broad logs rule) and broken at runtime (missing its import sql). That route is History + Stop&Save.
  • Wrote a reverse-engineered schema.sql (no migration shipped).
  • Installed dependencies (~1.7 GiB) and confirmed Docker is available.

The existing code is treated as a working reference / seed, not the foundation.

2. Vision

A multi-user, backend-driven shop-floor time-tracking system. The phone is one of several clients, not the source of truth.

A worker, on their own phone with their own account, logs in → goes to a workbench → scans it (QR) or selects manually → picks the activity → times the work → ends it → it is saved → repeats. Because the backend is the source of truth:

  • An active session lives server-side, so if the phone dies the worker can end or log the work from a computer instead.
  • There is a manual-entry fallback wherever something can fail.
  • An admin panel shows live who-is-working-on-what, generates reports, and manages users and activities.

Goals: it must genuinely work in the workshop (reliability, no data loss) and serve as a learning vehicle the owner extends himself.

3. Decisions (resolved during brainstorming)

# Decision Choice
1 Purpose Real workshop tool and a learning vehicle
2 Platform relationship Clean break from Create/Anything
3 Hosting Dockerized stack; runs locally now, portable to any cloud later
4 Build strategy Greenfield rebuild, porting only the good parts
5 Backend topology Dedicated backend service (Option A): single owner of auth + DB; UIs are interchangeable clients
6 Auth better-auth (don't hand-roll security for real use)
7 Database SQLite (small userbase; one file, easy backup/Docker)
8 Language TypeScript everywhere so types flow end-to-end

4. Architecture

┌─────────────┐     ┌─────────────┐
│ Mobile app  │     │ Admin web   │     clients — UI only, no DB access
│ (Expo/RN)   │     │ (React SPA) │
└──────┬──────┘     └──────┬──────┘
       │ HTTP (Bearer)     │ HTTP (cookie/Bearer)
       └─────────┬─────────┘
                 ▼
        ┌──────────────────┐
        │  Backend service │   the ONLY thing that touches auth + DB
        │  better-auth +   │
        │  business logic  │
        └────────┬─────────┘
                 ▼
            ┌─────────┐
            │ SQLite  │   single file on a Docker volume
            └─────────┘

Auth flow

  • Mobile — native email+password screen → POST /api/auth/sign-in/email → backend returns a bearer token → stored in Expo SecureStore → sent as Authorization: Bearer <token> on every request. (Drops the current app's embedded login WebView.)
  • Admin — standard better-auth session cookies.
  • Backend — mounts better-auth, owns all DB access, enforces roles.
Layer Pick Notable alternative
Backend framework Hono Fastify
Auth better-auth
DB access + migrations Drizzle ORM Kysely / Prisma
Database SQLite libsql/Turso (if cloud later)
Admin UI Vite + React (SPA) Next.js (if SSR wanted)
Mobile Expo / React Native
Shared contracts packages/shared (TS types + zod)

6. Monorepo shape

apps/
  mobile/      Expo worker app          (client)
  admin/       Vite + React panel       (client)
  api/         Hono + better-auth + Drizzle + SQLite   (backend service)
packages/
  shared/      TS types + zod schemas   (API contracts)
docker-compose.yml + Dockerfiles

7. Data model

Server-authoritative; an open session (end_time null) is "active work".

  • users — id, email, name, password hash (better-auth managed), role (worker | admin)
  • workbenches — id, name, qr_code (seeded / hardcoded for now)
  • activities — id, name, insole_types[] (subset of Kurk | Berk | 3D)
  • sessions — id, user_id, activity_id, workbench_id, insole_type, pair_count, start_time, end_time (null = running), status (active | completed | discarded), source (app | manual), notes, created_at

(better-auth also creates its own session/account/verification tables; those are distinct from the domain sessions table above — naming to be disambiguated in Phase 0, e.g. work_sessions.)

8. Port vs. leave behind

Port (the good parts): the data model, the API route logic, the screen flows/UX, the CSV export logic, the Dutch UI strings, and the lessons captured in the current code's comments (Android font/freeze fixes, SecureStore quirks).

Leave behind: the __create plumbing, the web-sandbox iframe layer, analytics / Sentry / anything-menu, the patched dependencies, and the ~60 unused libraries (ads, IAP, maps, 3D, audio, calendar, contacts, sensors, …).

9. Phased roadmap

Each phase keeps the system working and is its own spec → plan → build cycle.

  • Phase 0 — Foundation. Greenfield monorepo; dockerized Hono backend with better-auth
    • Drizzle + SQLite; docker compose up brings it up; health check + one auth round-trip proven end-to-end. Done when: a client can sign in against the containerised backend and the token authorises a protected call.
  • Phase 1 — Worker timing. Activities + server-authoritative work-sessions (open/close) + history + CSV export in the backend; mobile app rebuilt to use it. Done when: a worker can pick an activity, start/stop a server-side session, and see history; CSV exports.
  • Phase 2 — Accounts & roles. Worker/admin roles, admin-creates-users, per-user data scoping. Done when: workers see only their own sessions; an admin account exists.
  • Phase 3 — Admin panel. The React admin app: live active-work view, reports/export, user management, manual entry/edit (the fallback). Done when: an admin can see who's working now, manage users, and hand-correct a session.
  • Phase 4 — Workbench scanning. QR at the bench → select workbench/activity, with manual selection fallback. Done when: scanning a bench QR pre-fills the session.
  • Phase 5 — Polish & deploy. Reporting niceties, dependency slimming, push the container to a chosen cloud host.

10. Open questions & assumptions (confirm as we go)

  • Scanning = QR codes on benches, read by the phone camera (no special hardware), always with manual fallback. (Assumption.)
  • Start fresh, no data migration. Assumes no live workshop data/users worth preserving in the friend's platform instance. If there are, they must be exported from the friend's Create account — unreachable from this repo.
  • Workbench↔activity mapping is hardcoded/seeded for now; real mapping TBD with the friend.
  • Deployment host is deferred (Phase 5); the dockerized stack keeps options open.
  • Domain term: "insole" / orthotic; Dutch UI (Type zool, handeling, aantal zolen, etc.).

11. Risks

  • Greenfield is more work than evolving in place — mitigated by porting proven logic and keeping the old code as a running reference.
  • SQLite is single-writer / single-instance — fine at this scale; swap to Postgres/libsql is a config change via Drizzle/better-auth if ever needed.
  • Offline on the shop floor — the friend hit connectivity issues. Backend-as-source- of-truth assumes reachable network; true offline-first is explicitly out of scope for now (revisit if it bites).

12. Next step

Brainstorm Phase 0 in detail, then hand it to the writing-plans skill for an implementation plan. No code before that plan exists.