Skip to main content

Notes And Today Implementation Plan

Purpose

Turn the Notes and Today product spec into an exact implementation map for app routes, shell wiring, Convex modules, and rollout order.

This document is the execution bridge between:

Route Map

Org Shell Additions

  • add Today to the Home group in the org sidebar
  • do not add Notes to the sidebar

Files:

  • apps/app/src/app/[locale]/org/(dashboard)/_components/shell/nav.ts
  • apps/app/src/app/[locale]/_lib/routes/org.ts

Top bar

  • add a Notes launcher beside Calendar
  • keep Today out of the top bar for the first slice

Files:

  • apps/app/src/app/[locale]/org/(dashboard)/_components/shell/topbar.tsx
  • apps/app/src/app/[locale]/org/(dashboard)/_components/shell/notes-quick-view.tsx

Quick-action dock

  • add Add note
  • do not add Open Today

Files:

  • apps/app/src/app/[locale]/org/(dashboard)/_components/shell/quick-action-dock.tsx

Org Routes

today

Public route contract:

  • appRoutes.org.today()

App files:

  • apps/app/src/app/[locale]/org/(dashboard)/today/page.tsx

Responsibilities:

  • render the logged-in user's personal operating view
  • show pinned notes, checklist items, active timer context, and same-day agenda context
  • own lightweight personal checklist interactions

notes

Public route contract:

  • appRoutes.org.notes()

App files:

  • apps/app/src/app/[locale]/org/(dashboard)/notes/page.tsx

Responsibilities:

  • render internal notes with list plus editor behavior
  • support create, edit, archive, and pin flows
  • support personal, client-linked, and project-linked notes
  • accept shell handoff from ?panel=create
  • keep project-linked notes separate from projectUpdates; if a future promote flow is added, it should create a projectUpdate, not repurpose the note row

Convex Module Map

Registered surfaces

  • packages/backend/convex/org/notes.ts
  • packages/backend/convex/org/today.ts

These stay as same-runtime registered family surfaces, matching the current backend naming rules.

App API wrappers

  • apps/app/src/app/[locale]/_lib/convex/api/org/notes.ts
  • apps/app/src/app/[locale]/_lib/convex/api/org/today.ts
  • update apps/app/src/app/[locale]/_lib/convex/api/org/index.ts

Schema changes

Add tables to packages/backend/convex/schema.ts:

  • notes
  • personalChecklistItems

Backend Function Plan

org/notes.ts

Queries

  • getNotesLauncherData Used by the top-bar launcher. Returns pinned and recent note summaries for the current user.
  • getNotesPageData Used by the full Notes route. Returns note list plus visible client and project options.

Mutations

  • createNote
  • updateNote
  • toggleNotePin
  • archiveNote

Notes query shape

getNotesPageData should return:

  • notes
  • clientAccounts
  • projects
  • counts for all, pinned, personal, client, project

org/today.ts

Queries

  • getTodayWorkspace Returns pinned notes plus open and completed checklist items for the current user.

Mutations

  • createPersonalChecklistItem
  • updatePersonalChecklistItem
  • togglePersonalChecklistItem
  • deletePersonalChecklistItem

App Component Plan

notes-launcher.tsx

Pattern to follow:

  • mirror calendar-launcher.tsx
  • use a popover trigger in the top bar
  • show pinned notes first, then recent notes
  • end with Open notes

notes.client.tsx

First-pass composition:

  • PageTopBar
  • count cards or compact stats for Pinned, Personal, Linked, Recent
  • scope filter row
  • left list of notes
  • right editor panel

Key interactions:

  • open note from list
  • create note
  • body-first quick capture
  • pin or unpin
  • archive
  • save changes

Terminology rule:

  • prefer client-linked note and project-linked note in UI copy when a surface also contains projects or updates
  • avoid implying that a project note is the same thing as a project update

Linked note surfaces

  • the client detail notes tab should show both client-linked notes and project-linked notes for that client context
  • the project detail overview should show recent project-linked notes directly in the page instead of only exposing a create action
  • both surfaces should route note opening back through the full Notes workspace instead of inventing a second editor shell

today.client.tsx

First-pass composition:

  • PageTopBar
  • pinned-notes panel
  • personal checklist panel
  • active timer summary panel
  • same-day agenda panel using current calendar utility state

Key interactions:

  • add checklist item
  • edit checklist item title
  • mark done or reopen
  • open note in full Notes route
  • jump to timer route

Localization Keys

Add keys under:

  • organization.shell.*
  • organization.workspaceDock.*
  • organization.notes.*
  • organization.today.*

Update all supported locale dictionaries:

  • apps/app/messages/en.json
  • apps/app/messages/es.json
  • apps/app/messages/fr.json
  • apps/app/messages/it.json

Data Model Decisions For Implementation

notes

Canonical fields:

  • organizationId
  • authorUserId
  • scope: personal | client | project
  • title
  • body
  • bodyPreview
  • clientAccountId?
  • projectId?
  • isPinned
  • pinnedAt?
  • archivedAt?
  • createdAt
  • updatedAt

Rules:

  • notes are author-owned in the first slice
  • project notes should persist both projectId and the resolved clientAccountId
  • scope is the context anchor, not a parallel progress model
  • pinning is per-user because notes are not shared yet
  • archive is soft-delete only in the first slice

personalChecklistItems

Canonical fields:

  • organizationId
  • ownerUserId
  • title
  • status: open | done
  • sortOrder
  • clientAccountId?
  • projectId?
  • completedAt?
  • createdAt
  • updatedAt

Rules:

  • checklist items are private to the owner in the first slice
  • keep the state model intentionally small
  • linked client or project context is optional metadata, not a required workflow branch

Note-Creation UX Decision

Use body-first quick capture.

Implementation rule:

  • title is stored as a real field in the backend
  • when the user does not provide one explicitly, derive it from the first meaningful line of body
  • bodyPreview is derived from normalized body text during create and update

That keeps the list scan-friendly without forcing a title-first form for fast capture.

Validation Plan

After implementation, validate in this order:

  1. pnpm --filter @starter/docs build
  2. pnpm exec convex codegen from packages/backend
  3. pnpm --filter @starter/backend typecheck
  4. pnpm --filter @starter/app typecheck

If the schema and new registered surfaces land cleanly, the routes and shell additions should typecheck without reopening unrelated product areas.