# Module Database Source Audit This audit maps module data sources and highlights table/source risks for Stage 1 SaaS. It uses migrations, the base schema, route map, and project docs. It does not directly query a live database. ## Cross-Cutting Findings 1. Multi-tenant strategy is in transition. Newer SaaS tables use `business_id`, older Cabinet Builder tables use `tenant_id`, and some legacy operational tables need verified business scoping. 2. RLS exists as migration `20260701_data_authorization_rls.sql`, but current project state says it is dormant until `SET LOCAL app.business_id` pre-handler wiring exists. 3. Several docs conflict on auth and response format. Older `API_OVERVIEW.md` says localStorage/plain JSON, while newer route docs and decisions say httpOnly cookies and response envelopes. Treat this as a launch audit item. 4. Dev Centre completion values are not sourced from live module health or database relationships. 5. Fresh customer onboarding depends on correct seed data for `module_settings`, `record_number_settings`, PDF templates, price lists, invoice profiles, and business settings. ## Source Table Map | Module | Reads from | Writes to | Correct source? | Relationship concerns | Mock/stale/wrong source risk | |---|---|---|---|---|---| | Customers | `customers`, `contacts`, `customer_addresses`, `customer_notes`, `customer_activities` | same | Yes | Must link customer to enquiries, quotes, projects, invoices | Duplicate customer detection absent | | Contacts | `contacts`, `contact_price_lists` | same | Yes | Customer/contact split can confuse onboarding | Sidebar disabled but routes exist | | Enquiries | `enquiries`, `enquiry_files`, `enquiry_notes`, `email_intake_logs` | same; creates projects on conversion | Yes | Must preserve enquiry-to-project lineage | Conversion flow must be retested | | Quotes | `quotes`, `quote_line_items`, `quote_payment_schedule_steps`, `quote_events`, customers/contacts/pricelist | same; creates invoices | Yes | State compliance data and template defaults must align | Legal terms/defaults risk | | Projects | `projects`, `project_notes`, `project_files`, `project_update_log`, drawings | same | Yes | Parent to jobs/quotes/invoices must be complete | OneDrive path mismatch | | Jobs | `jobs`, `job_tasks`, `job_notes`, `job_files`, `job_schedules`, projects | same | Yes | Stage labels must match SaaS 14-stage workflow | Legacy 12-stage references | | Invoices | `invoices`, `invoice_line_items`, `invoice_profiles`, `invoice_profile_steps`, quotes/projects/jobs | same | Yes | Xero IDs/status sync must be tenant-scoped | Payment state depends on Xero sync | | Pricelist | `price_lists`, `price_list_items`, pricing rules, import batches/actions | same | Yes | Quote pricing and PO links depend on codes/UOM/GST | New-customer starter data missing | | Xero | `integration_connections`, `integration_sync_logs`, `xero_accounts_cache`, `xero_contacts_cache`, `xero_invoices_cache`, `xero_tax_rates_cache` | same | Yes in design | OAuth tokens must be per business | Scopes/env blocker | | Email Intake | `email_intake_logs`, settings, filters, trusted senders | same; creates enquiries/project updates | Yes in design | Must link to tenant records only | Staging OpenAI key missing; failure modes | | Production Planner | `production_*`, jobs, routing, resources, manual entries | same | Mostly | Needs routing setup before useful | Stage 2; not launch-critical | | Scheduler/Dispatch | `schedule_blocks`, `production_schedule_entries`, jobs | same | Legacy/unclear | Overlaps Production Planner | Park or replace to avoid duplicate workflow | | Inventory | `stock_master`, `stock_transactions`, `stock_kits`, `stock_kit_items`, `stock_remnants`, suppliers | same | Yes | PO receiving to stock must be verified | Stale module-level user bug noted historically | | Purchase Orders | `po_master`, `po_line_items`, `suppliers`, stock/pricelist refs | same | Yes | Receiving should update inventory | Verify `stock_id` and transaction write path | | Time Cards | `time_cards`, `time_card_entries`, `staff`, hour templates | same | Yes | Labour cost feeds financials/capacity later | Stage 2 | | Dev Centre | `dev_log_items`, `dev_module_status`, revisions, improvements, debt, feedback | same | Yes for internal planning | No live readiness calculation | Manual percentages stale | | SaaS Admin | `businesses`, `subscriptions`, tenant provisioning artifacts | same plus new tenant DB/schema | Yes in design | Must seed all required setup tables | Staging only; destructive drop endpoint | | Tradify Importer | `tradify_import_*` plus customers/jobs/quotes/invoices/projects | writes many operational tables | Yes in design | Must dedupe customers and preserve import rollback links | Needs customer CSV guide and tenant write tests | | Financials | `financial_snapshots`, `forecast_*`, `manual_cost_entries`, `regular_expenses`, `project_back_costings`, Xero cache, invoices/PO/time cards | same | Yes but broad | Xero scopes and report access required | Stage 2; route status staging | | PDF Templates | `pdf_templates`, `legal_terms`, business logo/details, quote/invoice data | same | Yes in design | Defaults must match state compliance | Route status missing/unknown; legal blocker | | Settings | `module_settings`, `record_number_settings`, `record_number_preferences`, `businesses`, `staff`, sidebar prefs/groups | same | Yes | Must seed per business | Onboarding wizard missing | | Portal | `portal_users`, customer/job/quote/invoice records | portal users and auth tokens | Yes in design | Customer data scoping is high risk | Stage 2 | | WHS/Training | `whs_*`, `training_modules`, `training_records`, staff | same | Yes | Template library needed for SaaS | Stage 2 | | Cabinet Builder/Mozaik/CNC | `cabinet_builder_*`, `mozaik_*`, `cnc_*` | same/files | Mixed | Separate `tenant_id` conflicts with main `business_id` model | Later-stage tenant model risk | | Team Notes | `team_note_pages`, `team_notes` | same | Yes | Links to jobs/quotes/projects | Stage 1.5 | | Communications/SMS | `communications`, SMS-related fields | same | Yes | Twilio config must be per tenant if enabled | Stage 1.5 | ## Tables That Need Tenant Isolation Verification Priority Stage 1 tables: - `users`, `businesses`, `module_settings` - `customers`, `contacts`, `customer_addresses`, `customer_notes` - `enquiries`, `enquiry_files`, `enquiry_notes` - `quotes`, `quote_line_items`, `quote_payment_schedule_steps` - `projects`, `project_files`, `project_notes`, `project_update_log` - `jobs`, `job_tasks`, `job_notes`, `job_schedules` - `invoices`, `invoice_line_items`, `invoice_profiles` - `price_lists`, `price_list_items`, `contact_price_lists` - `integration_connections`, `xero_*_cache` - `pdf_templates`, `legal_terms` - `tradify_import_*` ## Duplicate / Orphan / Wrong-Source Risks | Risk | Why it matters | Recommendation | |---|---|---| | `business_id` vs `tenant_id` | Cabinet Builder uses a separate tenant model from SaaS business scope | Do not rely on Cabinet Builder for Stage 1 SaaS until mapped | | Dormant RLS | Migration exists but does not enforce without session variable wiring | Add tenant isolation smoke tests before first customer | | Scheduler vs Production Planner | Duplicate scheduling workflows can confuse users | Park Scheduler/Dispatch unless required | | Dev Centre module status | Manual source can mislead launch decisions | Add launch readiness fields and calculated checks | | PDF legal terms/defaults | Wrong default clauses create legal exposure | Make PDF compliance a Stage 1 blocker | | Tradify import writes many tables | Bad import could pollute a new tenant | Use preview/confirm/rollback and test in throwaway tenant | ## Stage 1 Database Gate Before first paying customer, prove these with a throwaway tenant: 1. Create business/admin user. 2. Create customer/contact/enquiry. 3. Convert or create project. 4. Create quote from pricelist item. 5. Generate compliant PDF for customer state. 6. Accept quote and create job/deposit invoice. 7. Push invoice to Xero draft, or mark Xero setup as BoundHQ-managed manual step. 8. Confirm another tenant cannot read any of the above.