Sales CRM & RFP
What progress is a construction sales team trying to make when they open their CRM at 7am?
Pitch-Prompt Deck
Five cards. Five headlines. Five pictures. The meme layer — 80 cents in the dollar.
| Card | Headline | Persuasion | Picture | Problem → Question → Decision |
|---|---|---|---|---|
| Principles | Built for how they sell | Ethos | Outcome Map | Generic CRMs force data entry, teams resist → What if the system learns from their bids? → Answer once, auto-fill forever |
| Performance | 70% auto-fill, empty library | Logos | Value Stream | AI features built but library has zero entries → What unlocks the flywheel? → Process one real RFP to seed the library |
| Platform | App complete, auth broken | Topos | Dependency Map | 49% live, full CRM+RFP modules — can't onboard → Blocked by what? → Identity & Access Tier 0 fix unblocks everything |
| Protocols | Six days wire three algorithms | Kairos | Capability Map | Sales forecasting, compound rate, RFP detection all dormant → Wire or rebuild? → Wire — import, call, render |
| Players | Lost the bid nobody tracked | Pathos | A&ID | Sales teams use 3-5 tools to track one deal → Will they switch? → When they miss a deadline because nobody found last bid's answers |
Demand-Side Jobs
Every feature exists because someone is struggling to make progress. No struggle, no feature. These are the jobs — verified by watching what construction sales teams actually do, not what they say they want.
Job 1: Know Who I'm Dealing With
Situation: A BD manager prepares for a meeting tomorrow with a client they haven't spoken to in 3 months. They need to know: who else from their company is involved, what deals are active, what the last conversation was about.
| Element | Detail |
|---|---|
| Struggling moment | Searching email, spreadsheets, and memory to reconstruct a relationship |
| Current workaround | Email search + notebook + asking colleagues "have you spoken to...?" |
| What progress looks like | Open a contact, see everything — company, linked deals, full activity history |
| Hidden objection | "I don't want to enter data just so a system can show it back to me" |
| Switch trigger | When they lose a deal because they didn't know a colleague already had the relationship |
Features that serve this job:
- Contact CRUD with company linking
- Contact detail page showing all linked entities (deals, ventures, activities)
- Activity timeline per contact (calls, emails, meetings, site visits)
- Company page showing all contacts and all deals
- Search by name, email, company, or tag
- CSV import for bulk onboarding
- Contact status (active/inactive) and tagging
Job 2: See Where Every Deal Stands
Situation: Monday morning. A sales director needs to know: which deals are moving, which are stalled, which need action this week, and what the pipeline is worth.
| Element | Detail |
|---|---|
| Struggling moment | Chasing reps for updates, reconciling spreadsheets, guessing pipeline health |
| Current workaround | Weekly team call + shared Google Sheet + gut feeling |
| What progress looks like | One screen shows every deal, every stage, every value, every next action |
| Hidden objection | "My reps won't update this — I'll end up maintaining it alone" |
| Switch trigger | When a forecast is wrong because a deal silently died 3 weeks ago |
Features that serve this job:
- Deal pipeline with visual kanban (drag-drop between stages)
- Deal stages: Lead, Qualified, Proposal, Negotiation, Won, Lost
- Deal value, probability, expected close date
- Cards/Table/Kanban view toggle
- Pipeline summary (total value, weighted value, deal count per stage)
- Dashboard with pipeline health, overdue activities, upcoming deadlines
- Monthly goals tracking (pipeline value, won revenue)
Job 3: Win More Bids, Waste Less Time
Situation: An RFP lands. The team has 3 weeks to respond. Half the questions have been answered before in previous bids, but nobody can find those answers.
| Element | Detail |
|---|---|
| Struggling moment | Rebuilding proposals from scratch, duplicating effort across bids |
| Current workaround | Copy-paste from old Word docs, hope someone saved the last version |
| What progress looks like | Upload an RFP, auto-fill 70% from past answers, human-review the rest |
| Hidden objection | "AI-generated answers will be generic and need so much editing they're not worth it" |
| Switch trigger | When they miss a deadline because the team spent all their time on formatting, not content |
Features that serve this job:
- RFP venture creation with description, tags, industry
- Venture kanban: Discovery, Qualification, Preparation, Review, Submitted
- Document upload (PDF, DOCX, TXT — max 16MB)
- AI-powered answer auto-fill from approved library
- Answer Library with confidence scoring
- Review Queue for SME approval workflow
- My Queue for personal review assignments
- Analytics dashboard (auto-fill rate, time saved, cost saved per RFP)
Job 4: Never Let a Follow-Up Fall Through
Situation: A site visit happened last Tuesday. Three action items came out of it. By Friday, one has been forgotten, one is assigned to someone who doesn't know about it, and one is waiting on a document nobody has sent.
| Element | Detail |
|---|---|
| Struggling moment | Action items live in meeting notes that nobody re-reads |
| Current workaround | Personal to-do lists, sticky notes, memory |
| What progress looks like | Tasks linked to deals and contacts, with due dates, assignees, and status |
| Hidden objection | "I already have a to-do app — why do I need tasks inside the CRM too?" |
| Switch trigger | When a client says "you promised to send that last week" |
Features that serve this job:
- Task creation with title, description, due date, priority
- Task linking to contacts, deals, ventures
- Task status: Not Started, In Progress, Completed
- Overdue task highlighting
- Calendar view for deadlines and follow-ups
Job 5: Link People, Places, and Projects
Situation: A solar installation project involves a property owner, an EPC contractor, two subcontractors, and a financier. The project ties to a specific warehouse address. Three separate bids have been submitted over 18 months as the scope changed.
| Element | Detail |
|---|---|
| Struggling moment | Relationships between entities exist in the salesperson's head, not the system |
| Current workaround | Notes fields, custom tags, "see deal X for context" comments |
| What progress looks like | A venture page showing: the property, all linked companies (with roles), all deals, all contacts |
| Hidden objection | "Our deals are simple enough — we don't need all this linking" |
| Switch trigger | When a new hire joins and can't understand any deal without 30 minutes of verbal context |
Features that serve this job:
- Venture entity linking property + companies + deals + contacts
- Multi-company deals with roles (Client, JV Partner, Subcontractor, Consultant)
- Property registry with address, GPS, site type, status
- Venture-to-deal relationship (multiple bids per project)
- Activity logging against any entity (contact, deal, venture, property)
Awareness Levels
Where the buyer sits determines what we build next.
| Level | They Know | What We Need to Show | Feature Priority |
|---|---|---|---|
| Unaware | Using spreadsheets, don't see the problem | The cost of lost deals and duplicated effort | Marketing, not product |
| Problem Aware | "We lose track of deals" | Name their pain back to them | Dashboard, pipeline view |
| Solution Aware | CRMs exist, tried Salesforce/HubSpot | Why construction needs a vertical CRM | Property registry, RFP workflow |
| Product Aware | Know this tool, not convinced | Remove the hidden objection (adoption, data entry) | CSV import, auto-fill, clean UX |
| Most Aware | Ready to switch | Reduce friction to zero | Onboarding wizard, data migration |
Validation Stack
| Test | Evidence | Status |
|---|---|---|
| Problem exists | Construction teams use 3-5 tools (CRM + spreadsheets + email + file shares + notebooks) to track one deal | Validated — observed in solar, telecom, and construction |
| People pay | App live at dreamineering.com/dashboard with real contacts and deals | Early signal — internal use, needs external pilots |
| You can deliver | CRM + RFP modules functional with auth, CRUD, kanban, AI auto-fill | Validated — prototype running |
| Unit economics | SaaS at $30-80/seat/month vs Salesforce at $75-300 | Unvalidated — need pricing tests |
Kill signal: If users create contacts but never create deals, the CRM is a rolodex, not a sales tool. Deal creation is the activation metric.
Domain Model
CONTACTS ←→ COMPANIES
↕ ↕
VENTURES ←→ DEALS (Bids)
↕ ↕
PROPERTIES DOCUMENTS
| Entity | What It Represents | Key Fields |
|---|---|---|
| Contact | A person you do business with | Name, role, company, phone, email, tags, status |
| Company | An organisation (client, subcontractor, supplier) | Name, type, industry, ABN/tax ID, address |
| Property | A physical site or address where work happens | Address, GPS, site type, status, photos |
| Venture | A project or job that ties people, places, and bids | Name, property, client company, stage, value |
| Deal | A bid, tender, or commercial opportunity | Venture link, value, stage, due date, probability |
| Activity | Any interaction (call, email, meeting, site visit) | Type, date, contacts, notes, linked entity |
| Document | Proposals, RFPs, contracts, drawings | File, version, type, linked deal/venture |
Relationships
| From | To | Cardinality | Example |
|---|---|---|---|
| Contact | Company | Many-to-many | One person works for multiple companies over time |
| Venture | Property | Many-to-one | One property can have multiple project phases |
| Venture | Company | Many-to-many | Client, main contractor, subcontractors all linked |
| Deal | Venture | Many-to-one | Multiple bids submitted for one project |
| Deal | Contact | Many-to-many | Decision-makers, procurement, technical reviewers |
| Activity | Any entity | Polymorphic | A site visit logs against contact, property, and venture |
RFP Workflow
The tender cycle is the heartbeat of construction sales.
TENDER NOTICE
↓
GO/NO-GO DECISION (scored checklist)
↓
BID PREPARATION (document assembly, pricing, team allocation)
↓
SUBMISSION (version-locked, timestamped)
↓
EVALUATION PERIOD (track questions, site visits, presentations)
↓
AWARD / LOSS (win/loss analysis, feedback capture)
↓
HANDOVER TO DELIVERY (venture transitions to In Progress)
Go/No-Go Checklist
Every RFP runs through a qualification gate before committing resources.
| Criteria | Question | Weight |
|---|---|---|
| Relationship | Do we know the decision-maker? | High |
| Capability | Have we done this type of work before? | High |
| Capacity | Do we have the team available? | High |
| Competition | How many competitors are bidding? | Medium |
| Margin | Can we hit target margin at competitive price? | High |
| Location | Is the site in our operating area? | Medium |
| Terms | Are contract terms acceptable? | Medium |
| Timeline | Can we meet the submission deadline? | High |
Score: 70%+ = Go. 50-70% = Review. Below 50% = No-Go.
Competitive Position
| Capability | Salesforce | HubSpot | Pipedrive | This CRM |
|---|---|---|---|---|
| Contact/Company management | Yes | Yes | Yes | Yes |
| Visual pipeline | Yes | Yes | Yes | Yes |
| Property/site registry | No (custom objects) | No | No | Native |
| Multi-company deals | Yes (complex setup) | Limited | No | Native |
| RFP/tender workflow | No (add-on) | No | No | Native |
| AI answer auto-fill | No | No | No | Native |
| Go/No-Go scoring | No | No | No | Planned |
| Document versioning per bid | No (add-on) | Limited | No | Planned |
| Map view of properties | No | No | No | Planned |
| Construction-aware stages | Custom config needed | Custom config needed | Custom config needed | Default |
| Price per seat/month | $75-300 | $0-150 | $15-100 | Target: $30-80 |
The gap: Generic CRMs can be configured for construction. None are designed for it. Configuration tax compounds — every new hire needs setup, every report needs custom fields, every integration needs mapping.
Feature / Function / Outcome
Every row maps a feature to the function it performs, the outcome the user experiences, the job it serves, and delivery state. Reviewed 2026-02-18.
| # | Feature | Function | Outcome | Job | State |
|---|---|---|---|---|---|
| 1 | Contact list | Browse, search, filter contacts | Find the right person in seconds | Job 1 | Live — 23 contacts, table/grid, search, pagination |
| 2 | Contact detail | View profile, linked ventures, linked deals | See full relationship context before a meeting | Job 1 | Live — breadcrumbs, contact info, linked RFP ventures with roles, linked deals section |
| 3 | Contact create | Add new contact with company | Capture a new relationship immediately | Job 1 | Live — /crm/contacts/new |
| 4 | Company pages | View company with all contacts and deals | Understand an organisation's full engagement | Job 1, 5 | Gap — company as contact field, no standalone entity pages |
| 5 | Deal pipeline | Visual kanban of all deals by stage | See where every deal stands at a glance | Job 2 | Live — 4 stages, drag-drop, cards/table/kanban toggle |
| 6 | Deal create | Create new deal with value and stage | Capture a new opportunity immediately | Job 2 | Live — /crm/deals/new |
| 7 | Deal detail | View deal with stakeholders, linked RFP, activity timeline | Understand everything about an opportunity | Job 2 | Live — stage, value, probability, close date, deal type, stakeholder management, linked RFP venture, activity timeline |
| 8 | Deal stakeholders | Add contacts as stakeholders with buying roles | Map the buying committee | Job 2, 5 | Live — "Add Stakeholder" button, buying committee framing |
| 9 | Dashboard | Summary cards and pipeline overview | Know what needs attention today | Job 2 | Live — pipeline summary, goals, quick actions |
| 10 | Monthly goals | Track pipeline and won revenue targets | Know if you're on track this month | Job 2 | Live — $100K pipeline, $50K won targets |
| 11 | Venture kanban | Visual board of RFP projects by stage | Track every bid from discovery to submission | Job 3 | Live — 5 stages, 3 ventures, drag-drop |
| 12 | Venture detail | View RFP questions, linked deal, linked contacts | Full picture of a bid in one page | Job 3, 5 | Live — 10 questions table, linked deal, linked contacts with stakeholder roles/influence, AI buttons |
| 13 | Venture create | Create new RFP venture | Start tracking a new bid | Job 3 | Live — /rfp/ventures/new |
| 14 | Venture-deal link | Bidirectional link between RFP venture and CRM deal | One project, one deal, full picture | Job 5 | Live — linked from both venture detail and deal detail, with Unlink button |
| 15 | Stakeholder roles | Assign roles and influence to linked contacts | Know who decides, who influences, who blocks | Job 5 | Live — Economic Buyer role, high/medium influence levels, description field |
| 16 | RFP questions | Manage Q&A per venture with category/priority/status | Structure the RFP response | Job 3 | Live — 10 questions, Add Question button, category/priority/status columns |
| 17 | Answer detail | Review AI answer or write manual answer | Build the answer library one question at a time | Job 3 | Live — answer review page, manual write with save, min 10 chars |
| 18 | AI Loop | Run AI-powered answer generation across venture questions | Auto-generate draft answers | Job 3 | Built — "Run AI Loop" button on venture detail |
| 19 | Deck generation | Generate presentation deck from answered questions | Turn answers into a deliverable | Job 3 | Built — "Answer some questions first to generate a deck" |
| 20 | Document upload | Upload PDF, DOCX, TXT to ventures | Attach RFP documents to the right project | Job 3 | Live — UploadThing, PDF/DOCX 16MB, TXT 4MB |
| 21 | AI auto-fill | Auto-populate RFP answers from library | Cut 70% of RFP response time | Job 3 | Live — 70% auto-fill rate reported |
| 22 | Answer library | Store approved answers for reuse | Never write the same answer twice | Job 3 | Built — page with confidence scoring, empty state |
| 23 | Review queue | SME approval workflow for answers | Ensure answer quality before auto-fill | Job 3 | Built — review queue + my queue, confidence tiers (40-80%) |
| 24 | RFP analytics | Track time saved, cost saved, fill rate, compound growth | Prove the ROI of the RFP tool | Job 3 | Live — auto-fill rate, approval rate, compound rate, library size, confidence distribution, $1,150/RFP, 20h saved |
| 25 | Task management | Create, assign, track tasks | Never let a follow-up fall through | Job 4 | Partial — page exists, create flow, status cards, empty state |
| 26 | Calendar | View deadlines and follow-ups by date | See the week ahead | Job 4 | Partial — nav link exists |
| 27 | Activity timeline | Log calls, emails, meetings, visits per deal | Build an interaction history | Job 1, 4 | Built — timeline on deal detail with "Log First Activity" button, empty state |
| 28 | CSV import | Bulk import contacts from spreadsheet | Onboard existing contacts in minutes | Job 1 | Not verified |
| 29 | Global search | Search across contacts, deals, ventures | Find anything from one search box | All | Partial — contact search works |
| 30 | Property registry | Track physical sites as standalone entities | Link projects to real-world locations | Job 5 | Partial — address data exists on contacts/ventures, no standalone entity |
| 31 | Go/No-Go scoring | Qualification checklist for RFP decisions | Stop wasting time on unwinnable bids | Job 3 | Gap — qualification stage exists in kanban, no scoring UI |
| 32 | Auth | Sign-in, sign-up, user management | Secure access per user | All | Live — Clerk auth, theme toggle |
| 33 | Navigation | App-wide sidebar and top nav with breadcrumbs | Move between modules without friction | All | Live — 6 modules, breadcrumbs on detail pages |
| 34 | RFP assignments | Assign reviewers to answer queues | Distribute review work across team | Job 3 | Gap — nav link exists, redirects to dashboard |
| 35 | Insights | Analytics and forecasts | Make data-driven decisions | Job 2 | Stub — nav only |
| 36 | Plans | Team plans and task tracking | Coordinate team activity | Job 4 | Stub — nav only |
| 37 | Agents | AI agent registry and workflows | Automate repetitive sales tasks | Job 3 | Stub — nav only |
| 38 | Sales Forecasting | Predict deal close probability by month with confidence | Know which deals will close and when | Job 2 | Dormant — algorithm built in agency lib (sales-forecasting/), page exists at /insights/forecast, not wired |
| 39 | Compound Rate | Track answer library growth rate and compounding curve | Prove the RFP tool compounds in value over time | Job 3 | Dormant — algorithm built (compound-rate-tracking/), analytics page renders placeholder, not wired |
| 40 | RFP Type Detection | Auto-classify uploaded documents by type | Skip manual tagging on every upload | Job 3 | Dormant — algorithm built (rfp-type-detection/), upload flow exists, not wired |
| 41 | Payments | Accept subscription payments via Stripe | Get paid for the product | All | Partial — Stripe backend (Phase 10.1) complete, webhook handlers pending, no production payment flow |
Delivery Summary
| State | Count | % | Meaning |
|---|---|---|---|
| Live | 20 | 49% | Functional, verified with real data |
| Built | 6 | 15% | UI exists, needs data or first use |
| Dormant | 3 | 7% | Algorithm built in agency lib, not wired to UI |
| Partial | 5 | 12% | Page exists, core function incomplete |
| Gap | 2 | 5% | In PRD spec, not yet built |
| Stub | 3 | 7% | Nav link only |
| Not verified | 1 | 2% | May exist, needs testing |
| Total | 41 | — | +4 wiring jobs (3 dormant algos + 1 payment) |
Success Criteria
Functional
| # | Criterion | Verification | Job Served |
|---|---|---|---|
| F1 | Create a contact and link to a company in under 30 seconds | Timed test | Job 1 |
| F2 | Contact detail shows all linked deals, ventures, and activities | Walkthrough | Job 1 |
| F3 | Move a deal through all pipeline stages via drag-drop | Walkthrough | Job 2 |
| F4 | Dashboard accurately reflects pipeline value and deal count | Data verification | Job 2 |
| F5 | Upload an RFP and receive auto-filled answers within 60 seconds | Timed test | Job 3 |
| F6 | SME can review and approve an answer in the Review Queue | Walkthrough | Job 3 |
| F7 | Create a task linked to a deal with due date and assignee | End-to-end test | Job 4 |
| F8 | Create a venture linking property, company, contacts, and deals | End-to-end test | Job 5 |
| F9 | Import 500 contacts from CSV without errors | Bulk import test | Job 1 |
| F10 | Search finds results across all entity types in under 2 seconds | Performance test | All |
Non-Functional
| # | Criterion | Threshold |
|---|---|---|
| NF1 | Page load time | Under 2 seconds on 4G |
| NF2 | Search response | Under 500ms for 10K records |
| NF3 | Concurrent users | 50 simultaneous without degradation |
| NF4 | Mobile responsive | Fully usable at 375px viewport |
| NF5 | Uptime | 99.5% monthly |
Business Dev
This PRD wins only if it closes the loop from operations pain to recurring revenue.
| Layer | Decision | Initial Assumption | Evidence to Collect |
|---|---|---|---|
| ICP | Who buys first? | Construction and solar EPC teams with active RFP volume and spreadsheet pain | 15 interviews, 5 qualified pilots |
| Offer | What do we sell? | "Win more bids with less admin" workflow bundle (CRM + RFP loop) | Pilot users process at least one real RFP |
| Pricing | How do we charge? | Seat-based + workflow tier ($30-80/seat baseline) | Willingness-to-pay interviews + pilot conversion |
| Channel | How do we reach them? | Founder-led outbound + industry referrals + case-study content | 10 qualified demos/month pipeline |
| Conversion | What proves value? | First approved answer in library within 7 days | Activation rate > 60% in pilots |
| Retention | Why do they stay? | Compounding answer library + weekly deal workflow dependency | Weekly active usage in CRM and RFP modules |
Pilot Proof Pack
Each pilot must produce:
- Before/after bid cycle time.
- Auto-fill percentage with quality acceptance rate.
- Deal progression and revenue impact.
- User quote from sales lead or bid manager.
Commissioning
Deep review against live app at dreamineering.com on 2026-02-18. Inspected: dashboard, CRM overview, contacts list, contact detail, deals list, deal detail, tasks, RFP overview, ventures list, venture detail, answer detail, answer library, review queue, my queue, analytics.
BLOCKER: Auth Broken — Infinite Redirect Loop (2026-02-24)
Status: App completely inaccessible. No feature can be commissioned until this is fixed.
Symptom: Navigate to /dashboard → blank page. URL alternates between /dashboard and /sign-in?error=admin_access_required every ~400ms indefinitely.
Root cause from Vercel logs:
- Clerk auth succeeds — userId
user_36MjIJRckjpXRqdOHaZcgMpFjzEauthenticates, organisation found, context validated - User-Role database query fails — PostgreSQL 22P02 (invalid text representation). A Clerk userId string (
user_36MjIJ...) is being cast to a UUID column where it can't fit - Feature access denied — dashboard read blocked because role lookup returned an error
- Redirect to
/sign-in?error=admin_access_required— but Clerk sees user IS authenticated →afterSignInUrl: "/dashboard"→ redirect back → loop
The fix: The User-Role query (added during multi-tenancy work) is using the Clerk userId (string with user_ prefix) instead of the systemUserId (valid UUID f388dbc7-cb98-41ee-9708-d6f5d2c54fe0). The ClerkAuthAdapter already maps these correctly — the role query downstream is passing the wrong field.
Evidence: Vercel production logs, request ID dx89j-1771901662057-8dbab5d4899c, 2026-02-24 15:54:22 NZST. 789 warnings + 789 errors in 30 minutes from the redirect loop.
Regression: Auth was previously working (PRD row #32 marked "Live — Clerk auth" on 2026-02-18). Multi-tenancy changes introduced the role check that breaks it.
| Component | Schema | API | UI | Tests | Status | Notes |
|---|---|---|---|---|---|---|
| Dashboard | Done | Done | Done | Pending | 85% | Section cards, quick actions, 6-module nav |
| Contact CRUD | Done | Done | Done | Pending | 85% | 23 contacts, table/grid, search, filters, pagination, edit |
| Contact Detail | Done | Done | Done | Pending | 80% | Breadcrumbs, contact info, linked RFP ventures with roles/influence, linked deals section |
| Company CRUD | Partial | Partial | Partial | Pending | 25% | Company as contact field only, no standalone entity pages |
| Property Data | Partial | Partial | Partial | Pending | 30% | Address on contacts + ventures, not a standalone entity |
| Venture Board | Done | Done | Done | Pending | 85% | 5-stage kanban, 3 ventures, drag-drop, cards/kanban toggle |
| Venture Detail | Done | Done | Done | Pending | 85% | Questions table, linked deal, linked contacts with roles, AI Loop, deck gen |
| RFP Questions | Done | Done | Done | Pending | 80% | 10 questions per venture, category/priority/status, add question |
| Answer Detail | Done | Done | Done | Pending | 70% | Review page, manual write, min 10 chars, no AI answers yet |
| Deal Pipeline | Done | Done | Done | Pending | 85% | 4-stage kanban, cards/table/kanban, drag-drop, 1 live deal |
| Deal Detail | Done | Done | Done | Pending | 80% | Stage, value, probability, close date, type, stakeholders, linked RFP, activity timeline |
| Stakeholders | Done | Done | Done | Pending | 75% | Add stakeholder on deals + ventures, Economic Buyer role, influence levels |
| Venture-Deal Link | Done | Done | Done | Pending | 90% | Bidirectional — visible from both venture and deal detail, Unlink button |
| Activity Timeline | Partial | Partial | Done | Pending | 40% | UI on deal detail with "Log First Activity", empty state, needs first use |
| Task Management | Partial | Partial | Done | Pending | 35% | Page, status cards, create flow, empty state |
| Document Upload | Done | Done | Done | Pending | 70% | UploadThing configured (PDF/DOCX 16MB, TXT 4MB) |
| AI Auto-fill | Done | Done | Done | Pending | 65% | 70% rate displayed, AI Loop button, needs answer library data |
| AI Deck Gen | Partial | Partial | Done | Pending | 40% | Button exists, requires answered questions first |
| Answer Library | Done | Done | Done | Pending | 50% | Page, confidence tiers, empty — needs first approved answers |
| Review Queue | Done | Done | Done | Pending | 55% | Queue page, my queue, confidence filtering (40-80%) |
| RFP Analytics | Done | Done | Done | Pending | 70% | Auto-fill rate, approval rate, compound rate, library size, confidence dist, value metrics |
| Auth | Done | Done | BROKEN | Pending | 0% | REGRESSION — Infinite redirect loop after multi-tenancy. PostgreSQL 22P02 on User-Role query. See blocker above. |
| Navigation | Done | Done | Done | Pending | 90% | 6 top-level modules, sidebar per module, breadcrumbs on detail pages |
| Assignments | Pending | Pending | Pending | Pending | 0% | Nav link redirects to dashboard |
| Calendar | Partial | Pending | Partial | Pending | 15% | Nav link exists |
| Global Search | Partial | Partial | Partial | Pending | 30% | Contact search works |
| Insights | Pending | Pending | Pending | Pending | 0% | Stub |
| Plans | Pending | Pending | Pending | Pending | 0% | Stub |
| Agents | Pending | Pending | Pending | Pending | 0% | Stub |
| Sales Forecasting | Done | Partial | Partial | Pending | 30% | Algorithm built, page exists, server action not wired — Sprint 0 |
| Compound Rate | Done | Partial | Partial | Pending | 30% | Algorithm built, analytics page renders placeholder — Sprint 0 |
| RFP Type Detection | Done | Pending | Pending | Pending | 15% | Algorithm built, upload flow exists, not integrated — Sprint 0 |
| Stripe Payments | Done | Partial | Pending | Pending | 20% | Backend complete (Phase 10.1), webhooks pending — Sprint 0 |
Quality Assessment
| Dimension | Rating | Evidence |
|---|---|---|
| Data model | Strong | Contacts, deals, ventures, questions, answers, stakeholders — all relational, all linked |
| Entity linking | Strong | Venture-deal bidirectional, contact-venture with roles, contact on deal detail |
| CRM core | Solid | Contact CRUD, deal pipeline, kanban views, detail pages all functional |
| RFP core | Solid | Venture lifecycle, question management, answer workflow, analytics |
| AI features | Early | Auto-fill rate reported, AI Loop button, but answer library empty — needs first real RFP |
| Information architecture | Clean | Consistent sidebar nav, breadcrumbs, module separation, back links |
| Empty states | Good | Every empty state has guidance text and action button |
| Data density | Low | 23 contacts, 1 deal, 3 ventures, 0 tasks, 0 activities — needs real usage |
Gap Analysis
| Priority | Gap | Job Blocked | Effort |
|---|---|---|---|
| High | Company entity — no standalone company pages, can't see all contacts/deals per org | Job 1, Job 5 | Medium |
| High | Activity logging — timeline UI exists but no activities logged, needs friction-free entry | Job 1, Job 4 | Small |
| High | Answer library seeding — AI features exist but library is empty, blocking the auto-fill flywheel | Job 3 | Medium |
| Medium | Property entity — address data scattered across contacts/ventures, no standalone registry | Job 5 | Medium |
| Medium | Go/No-Go scoring — qualification stage exists in kanban but no scoring checklist UI | Job 3 | Medium |
| Medium | Task linking — tasks exist but unclear if they link to deals/contacts/ventures | Job 4 | Small |
| Medium | Assignments page — nav link exists, redirects to dashboard | Job 3 | Small |
| Low | CSV import — not verified | Job 1 | Small |
| Low | Cross-entity search — only contact search verified | All | Medium |
| Low | Calendar — nav link, no content | Job 4 | Medium |
Shape Up
| Stage | Status | Output |
|---|---|---|
| Napkin | Done | Domain model, JTBD analysis, competitive gap |
| Mock-up | Done | Live app — CRM + RFP modules functional with real data |
| Market | In progress | This PRD + internal use (23 contacts, 1 deal, 3 ventures) |
| Build | In progress | 54% Live, 16% Built, 11% Partial — core loop works |
| Demand | Not started | Pilot with one construction/solar EPC company |
Appetite: 6-week cycle. Next cycle: seed the answer library (unlock the AI flywheel), add company entity, make activity logging frictionless. Following cycle: Go/No-Go scoring, property registry.
Next Steps
1. Seed the answer library — process one real RFP to populate answers and prove the auto-fill loop
2. Add company entity — standalone pages showing all contacts and deals per organisation
3. Make activity logging frictionless — quick-log from deal detail, contact detail, venture detail
4. Pilot with one real construction sales team tracking real deals
5. Validate: do they create deals (activation) and return weekly (retention)?
Smallest move: Process one real RFP through the full cycle — upload document, answer 10 questions, approve answers to library, run a second RFP to see auto-fill work. That proves the flywheel.
Kill signal: If users create contacts but never create deals, the CRM is a rolodex. If they create ventures but never answer questions, the RFP tool is a project board. The activation metric is: first answer approved to library within 7 days.
Engineering Brief
Cycle focus: Wire intelligence, then prove the flywheel spins.
Three algorithms and a payment flow sit dormant in the agency lib. The UI surfaces exist. The wiring is 1-2 days each. This is the highest-leverage work before the kill date — it turns "we built a CRM" into "our platform predicts and compounds."
Sprint 0: Wire Dormant Algorithms (Critical — kill date 2026-03-24)
Why: 9 algorithms × 0 UI = 0 value. Three of these algorithms directly serve the Sales CRM product. The pages exist. The algorithms exist. The work is pure wiring — import function, call it with real data, render the result.
What to wire:
-
Sales Forecasting → Forecast Accuracy page (1 day)
- Algorithm:
libs/agency/src/lib/algorithms/sales-forecasting/— exportscalculateSalesForecast(input): SalesForecastResult - Target:
/insights/forecast/page —ForecastDashboardcomponent already renders, callsgetForecastDataAction - Wire: Fetch deals from repo → map to
ForecastDeal[](id, amount, probability, stage, closeDate) → callcalculateSalesForecast({ deals, monthRange, config })→ return typed result - Outcome: Live monthly forecast with confidence scores, pipeline health assessment, recommendations
- Algorithm:
-
Compound Rate Tracking → RFP Analytics (1 day)
- Algorithm:
libs/agency/src/lib/algorithms/compound-rate-tracking/— exportscalculateCompoundRate(snapshots): CompoundRateResult - Target:
/rfp/analytics/page — already rendersanalytics?.compoundRate?.formattedplaceholder - Wire: Fetch snapshots from
outcomeMeasurementRepository.findByMetricCode('RFP_AUTO_FILL_RATE')→ callcalculateCompoundRate(snapshots)→ map to existingcompoundRateinterface - Helpers:
formatCompoundRate()→ "+2.1%/week",getTrendIndicator()→ "↑" - Outcome: Live compound growth rate, trend indicator, weeks-to-target projection
- Algorithm:
-
RFP Type Detection → Upload flow (2 days)
- Algorithm:
libs/agency/src/lib/algorithms/rfp-type-detection/— document type classification - Target: Document upload flow on venture detail
- Wire: After upload, run type detection → auto-tag document type → skip manual classification
- Outcome: Documents auto-classified on upload
- Algorithm:
-
Stripe Webhooks → Production payments (2 days)
- Current: Backend complete (Phase 10.1), webhook handlers pending
- Wire:
payment_intent.succeeded,subscription.created,subscription.updated,subscription.deleted - Outcome: End-to-end payment flow works in production
Acceptance test: Open /insights/forecast → see monthly deal predictions from real CRM data. Open /rfp/analytics → see compound rate with trend arrow and weeks-to-target. Upload a document → type auto-detected. Complete a Stripe checkout → subscription active.
Total effort: ~6 days. This is CONNECT work — no new algorithms, no new UI components, no new schemas.
Sprint 1: Seed the Answer Library (High — unlocks everything)
Why: The RFP module's value proposition is "answer once, auto-fill forever." Until the library has approved answers, auto-fill returns nothing. Every other RFP feature (confidence scoring, compound growth, analytics) is waiting on this.
What to build/fix:
-
AI Loop end-to-end — Currently the "Run AI Loop" button exists on venture detail. Verify it actually generates draft answers for all 10 questions. If it does, the output should appear on each answer detail page (
/rfp/answers/{id}) as a reviewable draft. Currently answer pages show "No answers found for this question." Fix the pipeline: AI generates → draft appears → SME reviews → approves → answer enters library. -
Answer approval flow — On the answer detail page, after an AI-generated or manual answer exists, the SME needs: (a) Edit the answer, (b) Set confidence level, (c) Approve to library. Currently there's a manual write box and Save button but no Approve action that graduates the answer to the library.
-
Library population verification — After approval, the answer should appear in
/rfp/librarywith its confidence score, question category, and source venture. Currently the library page shows "No Approved Answers Yet." Verify the data flow: answer approved → appears in library → available for auto-fill on next venture. -
Auto-fill proof — Create a second test venture with similar questions. Run AI Loop. Verify it pulls from the approved library and pre-fills answers. This is the moment the flywheel proves itself.
Acceptance test: Create venture A → answer 10 questions → approve all to library → create venture B with overlapping questions → run AI Loop → at least 5 answers auto-filled from library. Library page shows 10 approved answers with confidence scores.
Sprint 2: Company Entity (High — Job 1 + Job 5)
Why: "Show me everything with ABC Corp" is the most basic CRM question. Currently companies exist only as a text field on contacts. A sales director can't see: all contacts at a company, all deals with that company, all ventures involving them, total pipeline value per company.
What to build:
-
Company table — New entity:
companieswith fields:name,type(Client, Contractor, Subcontractor, Supplier, Consultant),industry,abn,website,address,phone,created_at. -
Company detail page (
/crm/companies/{id}) — Shows: company info, all linked contacts (with roles), all linked deals (with stage/value), all linked ventures. Summary stats: total pipeline value, active deals count, contact count. -
Company list page (
/crm/companies) — Table with search, filter by type, sort by name/deal count/pipeline value. Add to CRM sidebar nav between Contacts and Deals. -
Contact-company relationship — Migrate the existing company text field on contacts to a foreign key. Contacts link to company records. A contact can belong to one company (with optional role/title at that company).
-
Deal-company linking — When a contact is added as a stakeholder on a deal, their company is implicitly linked. Company detail page shows all deals where any of its contacts are stakeholders.
Acceptance test: Create company "ABC Corp" (type: Client) → link 3 existing contacts to it → create a deal with one of those contacts as stakeholder → company detail page shows all 3 contacts and the deal with pipeline value.
Sprint 3: Activity Logging (High — Job 1 + Job 4)
Why: The activity timeline UI exists on deal detail ("Log First Activity") but has zero entries across the entire system. Without activity history, the CRM can't answer "when did we last talk to them?" or "what happened at the site visit?" — which is the core of Job 1.
What to build:
-
Quick-log modal — A lightweight modal (not a full page) triggered from: deal detail, contact detail, venture detail, and the activities list page. Fields: type (Call, Email, Meeting, Site Visit, Note), date (defaults to now), description (free text), linked contacts (multi-select), linked deal (optional), linked venture (optional).
-
Activity creation API —
POST /api/activitieswith:type,date,description,contact_ids[],deal_id,venture_id. All linking fields optional except at least one contact or one deal. -
Activity timeline rendering — On deal detail: show activities in reverse chronological order with type icon, date, description, linked contacts. On contact detail: show all activities involving that contact. Filter by type.
-
Activity list page (
/crm/activities) — Currently shows "No recent activity." Populate from the activities table. Show all activities across all entities, sortable by date, filterable by type. -
Activity count on overview — The CRM overview shows "Total Activities" card. Wire this to the actual count.
Acceptance test: From deal detail, click "Log First Activity" → modal opens → log a "Site Visit" with date, description, and linked contact → activity appears in deal timeline → same activity appears on contact detail page → CRM overview shows "1" in Total Activities card.
Sprint 4: Data Quality (Medium — all jobs)
Why: The system has 23 contacts but 1 deal at $0 value, 3 ventures all in Discovery, 0 tasks, 0 activities. The architecture works but the data doesn't tell a story. A pilot user seeing this will think "nobody uses this."
What to do:
-
Populate the Solar deal — The "Commercial Solar Installation - ABC Corp Warehouse" deal has $0 value, no probability, no close date. Set realistic values: $150,000 value, 60% probability, close date 3 months out. This makes the pipeline dashboard meaningful.
-
Move ventures through stages — All 3 ventures sit in Discovery. Move the Solar venture to Preparation (it has 10 questions defined). Move "Test Project Alpha" to Qualification. Leave Dreamineering in Discovery. This makes the kanban board tell a story.
-
Add stakeholders to the deal — The deal has 0 stakeholders even though the venture has 1 linked contact. Add Matt Mischewski as a stakeholder on the deal too, with "Economic Buyer" role. This validates the stakeholder flow from deal side.
-
Log 3-5 activities — Create realistic activities: initial call, site visit, proposal discussion. This populates the activity timeline and proves the logging flow.
-
Create 2-3 tasks — "Send revised proposal by Friday," "Schedule site inspection," "Follow up on financing options." Link to the deal. This populates the task board.
Acceptance test: Dashboard shows: pipeline value > $0, at least 2 deals across different stages, recent activity entries. A new user opening the app sees a system in use, not an empty shell.
Not This Cycle
These are real gaps but don't block the flywheel:
- Property entity — Address data exists on contacts/ventures. Standalone entity is nice-to-have until there are 10+ properties.
- Go/No-Go scoring — Qualification stage exists in kanban. Scoring checklist adds value at scale, not at 3 ventures.
- Assignments page — Nav link redirects to dashboard. Matters when there are multiple reviewers.
- Calendar — Important for daily use but doesn't prove the core value loop.
- Cross-entity search — Contact search works. Expand when there's enough data to search.
- Insights/Plans/Agents — Stub modules. Don't start until CRM + RFP core is proven with real usage.
Definition of Done (This Cycle)
1. Answer library has 10+ approved answers with confidence scores
2. Auto-fill works: venture B pulls answers from venture A's approved library
3. Company entity exists with detail pages showing linked contacts/deals
4. Activity timeline has real entries visible from deal + contact detail
5. Pipeline dashboard shows realistic values ($100K+)
6. One real external user can track a deal from lead to proposal using this tool
North Star Metric
Win Rate > 30% (currently 22%)
This is the ONE metric this PRD exists to move. Everything else — contacts, pipelines, auto-fill rates, answer libraries — is secondary. If win rate doesn't move, the tool is busy work.
Mycelium Capability
The Sales CRM & RFP is a demand-driven sales capability. Currently built for construction and solar, but the RFP workflow, answer library, and confidence scoring patterns apply to any industry with competitive bidding — real estate, consulting, government contracting.
Currently Growing In: stackmates
Production Audit — 2026-02-24
Verified against dreamineering.com (authenticated session). The app routes exist, navigation is correct, but the core data pipeline is broken.
Route Status
| Route | Page | Status | Error |
|---|---|---|---|
/rfp | Overview | PASS | Stats render (70% auto-fill, 83% time saved, $1,150/RFP) |
/rfp/ventures | Ventures | FAIL | Operation failed — ventures list query fails |
/rfp/ventures/new | Create Venture | WARN | Form renders but industry dropdown missing Construction/Infrastructure |
/rfp/library | Answer Library | FAIL | You don't have permission to read rfp_answer |
/rfp/review | Review Queue | FAIL | You don't have permission to read rfp_answer |
/rfp/my-queue | My Queue | PASS | Empty state renders correctly |
/rfp/analytics | Analytics | PASS | Metrics, confidence distribution, estimated value render |
/rfp/assignments | Assignments | FAIL | Failed to fetch agents — SME list query fails |
/crm | CRM Overview | WARN | "Some Data Unavailable" warning. Pipeline stages render at 0 deals |
Blocking Issues
- Convex
rfp_answerpermissions — Answer Library and Review Queue both fail with the same auth error. This blocks the entire auto-fill pipeline (Job 3). Root cause: table-level read permission not granted to authenticated user role. - Ventures query failure — Generic "Operation failed" on ventures list. Blocks creating and managing RFP projects. May be a separate Convex function error or the same permissions issue.
- Agents fetch failure — Assignments page can't load SMEs. Blocks the review/approval workflow.
Data Issues
- Industry dropdown mismatch — Create Venture offers: Technology, Healthcare, Finance, Education, Manufacturing, Retail, Services, Other. Missing: Construction, Infrastructure, Energy, Solar — the verticals this PRD explicitly targets. AI response tailoring won't match the target market.
What Works
- Dashboard routing and navigation structure is correct
- RFP Overview renders with stats (though likely hardcoded/seed data)
- Analytics page renders metrics and confidence distribution
- My Queue renders empty state with correct links
- Create Venture form is functional (fields, validation, dropdown)
- CRM Overview renders pipeline stages (Lead/Qualified/Proposal/Negotiation) and monthly goals
- Clerk auth is working (user is authenticated, avatar renders)
Against Definition of Done
| Criterion | Status | Evidence |
|---|---|---|
| 10+ approved answers with confidence scores | BLOCKED | Can't read rfp_answer table |
| Auto-fill works across ventures | BLOCKED | Can't load ventures or answer library |
| Company entity with linked contacts/deals | NOT VERIFIED | CRM data unavailable warning |
| Activity timeline with real entries | EMPTY | "No recent activity" on CRM overview |
| Pipeline dashboard shows $100K+ | FAIL | Shows 0 deals, $0 pipeline value |
| External user can track lead to proposal | BLOCKED | Core data queries failing |
Next Actions (Engineering)
- Fix Convex table permissions for
rfp_answer— unblocks 3 pages - Debug ventures list query — separate from permissions, returns generic error
- Fix agents fetch for assignments page
- Add Construction, Infrastructure, Energy, Solar to industry dropdown
- Seed or create real venture data to validate the full loop
Context
- Jobs To Be Done — Demand-side thinking: what progress, not what features
- Validate Demand — Awareness levels and kill signals
- JTBD Interviews — Extract real jobs from real people
- Shape Up — Fixed time, variable scope
- CRM Software — Generic CRM feature baseline
- Sales Pipeline — Pipeline management patterns
- Sales Support — Sales enablement and intelligence
- Vertical SaaS — The vertical software playbook
- Construction Industry — Domain context
- Solar Industry — Parallel vertical with RFP-driven sales
- Phygital Mycelium — The capability catalogue