The platform uses Cloudflare D1 (edge SQLite) for all structured data. Schema is defined in db/schema.sql, seed data in db/seed.sql, and incremental changes in db/migrations/.
db/migrations/ is forward-only — wrangler auto-applies every .sql file there in alphabetical order. Manual rollbacks live in db/rollbacks/ and are never auto-applied; see Database Migrations → Rollbacks .
Table Purpose usersAuthenticated users (auto-created on first login). Auth-only: id, email, name, picture, job_title, pronunciation, access_level, template IDs tool_permissionsPer-tool, per-access-level permission grants org_settingsOrganisation-level key-value settings (timezone, holiday_state) user_preferencesPer-user preference overrides (timezone, holiday_state) squadsTeam groupings derived from people.squad column during Productive sync sidebar_favoritesPer-user pinned sidebar items daily_quotesRotating quotes shown on dashboard historyAudit trail of changes across all resource types notesFreeform notes attached to any resource (company, contact, deal, project, etc)
Table Purpose peopleSource of truth for all employee/HR data. Synced from Productive, enriched via Xero. Includes pronunciation (phonetic name guide, propagated from the linked user). manager_id drives data scoping hierarchy person_linkedin_activitiesLinkedIn activity snapshots for people person_change_alertsAlerts when LinkedIn/external data indicates a change
Table Purpose onboarding_templatesNamed onboarding templates assigned to users scorecard_templatesNamed scorecard templates assigned to users scorecard_template_itemsChecklist items belonging to a scorecard template review_templatesNamed KPI templates for performance reviews review_template_itemsKPI items per review template (area, label, is_mandatory, sort_order) template_profilesNamed role bundles that group one onboarding + one scorecard + one review template
Table Purpose onboarding_phases5 phases with name, description, sort order onboarding_itemsChecklist items within phases (linked to a template; tpl-onb-common = shown to all users) onboarding_progressPer-user completion state for each item. person_id links to people
Table Purpose objectivesBusiness objectives with category (financial/customer/operational/people) prioritiesCurrent priorities linked to an objective, with is_active flag kpi_definitionsKPI definitions linked to a priority, scoped by access_level
Table Purpose scorecardsScorecard header (squad, week, type, period_key, notes, scorecard_template_id). person_id links to people scorecard_scoresIndividual score items (status, note) scorecard_kpisKPI entries (text, target, actual, status, kpi_definition_id) scorecard_metricsFinancial metrics (billable, utilisation, revenue, profit)
Table Purpose review_cyclesReview periods (quarterly/annual) with draft/open/closed lifecycle reviewsOne per person per cycle; status workflow, KPI pass/fail, self-assessment, salary decision review_kpi_ratingsSnapshot of template items with 3-tier ratings (needs_urgent_work/achieving/exceeding) review_goalsSMART goals (goal, success measures, support needed, completion status) feedback_requests360 feedback assignments with pending/submitted/declined status feedback_responsesStructured 5-area feedback with ratings and comments review_questionsCentral question bank for reviews and feedback report_snapshotsCached performance reporting data snapshots
Table Purpose announcementsTitle, content, category (process/team/client/company), attachment URL/name, author announcement_readsRead receipts per user per announcement announcement_distributionsDistribution tracking: channel (slack/google_calendar/email), status, external_id, error
Table Purpose calendar_settingsPer-user calendar display and sync settings eventsTeam events with voting, categories, and scheduling event_votesPer-user votes on event proposals
Table Purpose connectionsOrg-level OAuth/API tokens for external services (Xero, Slack, Productive). Tokens are AES-GCM encrypted user_connectionsPer-user OAuth tokens for personal integrations (Google, GitHub, etc)
Table Purpose leave_typesCached from Xero PayItems (leave type ID, name, is_paid) leave_balancesPer-person leave balances cached from Xero (1hr TTL) leave_requestsLeave requests with status, dates, approval chain, external integration IDs
Table Purpose public_holidaysCached Australian public holidays from Nager.Date API (24hr TTL)
Table Purpose pay_summariesCached pay template info from Xero (annual salary, earnings YTD, next pay date). PK is person_id payslipsCached payslip summaries from Xero
Table Purpose documentsEmployee documents (contracts, policies, certificates) with type, file URL, expiry tracking
Table Purpose companiesCompany records with industry, domain, logo, pronunciation, Productive/Stripe IDs, parent company hierarchy contactsIndividual contacts linked to a company with role, email, phone, pronunciation, LinkedIn, is_primary flag contact_communicationsCommunication history with contacts (emails, calls, meetings) contact_relationship_profilesAI-enriched relationship context per contact contact_life_eventsKey dates and life events for relationship nurturing contact_partnersContact-to-contact partner/relationship links
Table Purpose dealsSales pipeline deals with stage, value, probability, company, close date deal_pipeline_templatesNamed pipeline configurations deal_pipeline_stagesOrdered stages within a pipeline template deal_participantsTeam members assigned to a deal deal_contact_linksContacts associated with a deal deal_research_briefsAI-generated research context for deals deal_project_linksLinks between won deals and resulting projects
Table Purpose contractsService contracts with terms, value, renewal dates, signing status contract_templatesReusable contract templates contract_signersSigners on a contract with status tracking
Table Purpose proposalsClient proposals with status, approval chain, pricing proposal_templatesReusable proposal templates proposal_template_pagesPage content within proposal templates proposal_pagesPage content within individual proposals proposal_pricing_sectionsPricing sections with subtotals proposal_pricing_itemsIndividual line items within pricing sections proposal_approvalsInternal approval workflow entries proposal_team_membersTeam members presented on a proposal proposal_signersExternal signers with signing status proposal_viewsAnalytics: when a proposal was viewed by the client proposal_slide_viewsAnalytics: per-slide view tracking
Table Purpose recruitment_jobsJob postings with title, department, status, salary range, remote policy recruitment_candidatesCandidate profiles with contact info, pronunciation, source, LinkedIn, resume recruitment_applicationsApplications linking candidates to jobs with stage tracking recruitment_application_stage_historyAudit trail of stage transitions recruitment_pipeline_templatesNamed pipeline configurations for hiring recruitment_pipeline_stagesOrdered stages within a pipeline template recruitment_hiring_teamTeam members assigned to a job recruitment_job_requirementsSkills/requirements for a job posting recruitment_consentsCandidate GDPR/privacy consent records recruitment_interviewsScheduled interviews with type, date, location, feedback recruitment_interview_participantsInterviewers assigned to an interview recruitment_evaluationsPost-interview evaluations by team members recruitment_evaluation_scoresScores per criterion within an evaluation recruitment_scorecard_templatesEvaluation criteria templates for jobs recruitment_scorecard_criteriaIndividual criteria within a scorecard template recruitment_email_templatesEmail templates for candidate communication recruitment_stage_email_rulesAuto-send email rules triggered by stage transitions recruitment_communicationsSent emails and messages to candidates
Table Purpose projectsClient projects with company, owner, delivery manager, squad, SLA policy, type, auto-ticket config project_membersTeam members assigned to a project with role project_goalsOKR-style goals within a project project_decisionsKey decisions recorded on a project with context and outcome project_ai_summariesAI-generated project summaries cached per project project_reportsPeriodic project status reports with metrics and narrative project_report_settingsPer-project report configuration (frequency, recipients, sections) project_setup_templatesReusable project setup templates with phases and tasks project_setup_template_phasesPhase definitions within a setup template project_setup_template_tasksTask definitions within a setup template phase tasksTask/issue tracking scoped to any resource. Includes stage, priority, estimate, approval fields task_resourcesResource allocations within a task (compute, budget, team) task_slaSLA tracking per task — response/resolution deadlines, breach flags task_todosOrdered checklist items within a task task_watchersUsers watching a task for notifications sprintsTime-boxed iterations within a project
Table Purpose roadmapsNamed roadmaps with description and date range roadmap_itemsIndividual items on a roadmap with status, dates, owner
Table Purpose budgetsProject budgets with type (fixed/time_and_materials), total, billing details budget_line_itemsLine items within a budget (service, quantity, rate, amount) invoicesInvoices with status, amounts, payment terms, Xero sync tracking invoice_line_itemsLine items within an invoice invoice_paymentsPayment records against invoices invoice_mapping_rulesRules for mapping time entries to invoice line items
Table Purpose time_entriesManual time entries with project, task, duration, billing status activity_signalsAuto-detected activity signals from connected tools (Memtime-style) auto_time_draftsAI-generated draft time entries from activity signals auto_tracking_preferencesPer-user auto-tracking configuration
Table Purpose allocationsResource bookings linking a user to a project, deal, or recruitment role for a date range user_weekly_schedulesPer-user weekly availability schedules user_resourcing_profilesSkills, rates, and capacity data for resourcing resourcing_suggestionsAI-suggested resource matches for project/role needs
Table Purpose sla_policiesNamed SLA policy definitions with response/resolution targets sla_policy_rulesPriority-based rules within an SLA policy
Table Purpose emailsSynced emails with subject, body, thread tracking, entity matching email_contactsEmail address ↔ contact resolution email_sync_statePer-user email sync cursor/token state inbound_emailsEmails received via the inbound webhook (auto-ticket creation)
Table Purpose pagesRich-text wiki pages with title, content, icon, cover, parent hierarchy page_favouritesPer-user bookmarked pages page_discussionsDiscussion threads on a page page_commentsComments within a page discussion page_versionsVersion history snapshots of page content
Table Purpose meetingsSynced calendar meetings with attendees, transcript, entity matching meeting_attendeesAttendees per meeting meeting_transcriptsMeeting transcript content meeting_action_itemsAction items extracted from meetings
Table Purpose client_profilesClient tier, health score, assigned DM, dashboard settings. FK to companies client_onboarding_templatesTemplates for client onboarding journeys client_onboarding_stagesStages within a client onboarding template client_onboarding_milestonesMilestones within a client onboarding stage client_milestone_progressPer-client progress on onboarding milestones client_health_scoresHistorical health score records per client client_tier_historyTier scoring history for trend tracking client_platform_connectionsOAuth/API credentials for connected platforms (Shopify, Meta Ads, etc) client_metric_snapshotsTime-series key-value metrics (ad_spend, revenue, sessions, etc) client_campaign_snapshotsDenormalised campaign-level metrics for ad platforms client_dashboard_insightsAI-generated weekly analysis with health score and recommendations client_oauth_statesOAuth flow state for client platform connections client_goalsMetric targets with baseline, current value, and tracking client_qbrsQuarterly Business Reviews with AI-generated content and portal visibility client_service_cellsService offering cells within a client relationship client_success_profilesFinancial year, trading periods, channel mix, growth priorities client_winsNotable outcomes linked to projects, goals, or meetings
Table Purpose portal_usersExternal client users with access to the client portal portal_invitationsPending invitations to the client portal
Table Purpose notificationsIn-app notifications with type, title, body, action URL, read/dismissed state notification_preferencesPer-user notification channel preferences notification_typesRegistered notification type definitions notification_delivery_logDelivery tracking per notification per channel push_subscriptionsWeb push subscription endpoints per user
Table Purpose squad_sessions4P squad kickoff/retro sessions squad_actionsAction items from squad sessions squad_leadsSquad leadership assignments squad_notification_configPer-squad notification routing config
Table Purpose action_itemsCentralised action items across all sources (meetings, reviews, squads) action_centre_preferencesPer-user action centre display preferences
Table Purpose custom_field_definitionsUser-defined field schemas per entity type custom_field_valuesField values per entity per custom field definition config_listsNamed configuration lists (dropdown options, categories) config_list_itemsItems within a configuration list service_typesService type definitions for projects and budgets
Table Purpose agent_project_configPer-project agent configuration (enabled features, thresholds) agent_task_metaAgent metadata per task (session_id, status, last run) agent_task_runsIndividual agent execution runs with input/output/duration
Table Purpose relationship_auto_actionsAI-suggested relationship nurturing actions relationship_messagesDrafted/sent relationship messages
Table Purpose lead_scan_logLead scanning activity log
The following tables have been removed during migrations:
Table Reason user_external_idsExternal IDs moved to people table columns (xero_employee_id, productive_id) in Phase 3 squad_membersSquad membership now derived from people.squad column, dropped in Phase 7 leave_request_historyRemoved — leave audit trail now tracked via the history table
The platform migrated from user-centric to people-centric data ownership across 7 phases:
Phase 1 : Employee/HR fields moved from users to people. The users table is now auth-only.
Phase 2 : Added person_id foreign keys to 8 employee data tables. Auth middleware resolves personId on every request.
Phase 3 : Eliminated user_external_ids. External ID lookups read directly from people columns.
Phase 4 : Added getScopedPersonIds() using people.manager_id hierarchy for data scoping.
Phase 5 : Dropped dual-writes. All data queries use person_id. Manager verification uses people.manager_id.
Phase 6 : Migrated payroll and leave balance reads to person_id. Replaced squad_members usage with people.manager_id hierarchy.
Phase 7 : Recreated all 8 data tables to drop user_id columns. person_id is NOT NULL REFERENCES people(id) ON DELETE CASCADE. Dropped squad_members table.
All wrangler commands must run from apps/app/ (where wrangler.toml lives):
# Check pending migrations
npx wrangler d1 migrations list nucleus-db --local
# Apply migrations locally
npx wrangler d1 migrations apply nucleus-db --local
# Apply migrations to production
npx wrangler d1 migrations apply nucleus-db --remote
# Initial local setup (schema + seed)
pnpm db:migrate && pnpm db:seed
db/migrations/ is forward-only. Never drop a *.down.sql (or any other non-forward script) into it — wrangler will auto-apply it as another forward migration. Manual rollbacks live in db/rollbacks/ and are run on demand:
pnpm wrangler d1 execute nucleus-db --remote \
--file=db/rollbacks/<migration-id>.down.sql
See Database Migrations → Rollbacks for the full convention.