The three runbooks
§ 00New Features
Newest first.
2026-08-19 — Deal Room: real, watermarked PDF downloads
The pre-existing "Allow download" toggles never actually worked — the only Content-Disposition header in the system sat on the route the PDF.js viewer fetches via XHR, which the browser never sees. There's now a distinct /api/doc/:doc_id/download route the viewer's real ⬇ Download button navigates to, gated by a single room-level setting (Edit Room → Download allowed), watermarking the viewer's email + date into the actual PDF bytes server-side (not just the on-screen overlay), and logging every download to the room's Views tab.
First production use: the Wells Fargo deal room, enabled at their request. Full detail in the Deal Room runbook and admin/dr/DEAL_ROOM_MODEL.md §6b.
2026-08-19 — Investor Qualification Questionnaire
A public, ungated 10-question form at /finance/qualify/ that scores every submission deterministically against a fixed 100-point rubric (proven capacity, check-size fit, decision-maker access, 90-day timeline, sector fit, structure understanding, transaction history, diligence clarity) and tiers it — Chairman (80–100), IR/Diligence (65–79), Nurture (50–64), Automated (<50). Built to stop "I'm interested" submissions from consuming data-room access and management time before anyone has confirmed they can actually close.
- Notification: only Chairman and IR/Diligence tiers email Shannon + the Architect immediately. Everything else lands silently in the admin queue.
- Two scores, never blended: the qualification score (the rubric above) is stored separately from form-guard's generic spam/bot risk score — a submission can be low-risk but low-qualification, or vice versa.
- Admin surface:
admin/js/tabs/investor-qualifications.js, under the Finance tab group.master_admin+scoped tofinance— same tier as the deal-room admin surface, not looser. List + detail view (score breakdown, the two comparable-deals card, review status/notes). - AI dossier — on-demand only, never automatic. An admin clicks "Run Dossier" to have Claude web-search-verify the entity's legitimacy and the two claimed comparable deals. Writes
verified / unverified / contradictedfindings per claim; never mutates the score or tier — it's a separate human-judgment artifact, not a scoring input. - Schema:
investor_qualifications(own table — seeschema/investor-qualification-v1.sql), notform_submissions.
2026-08-13 — Deal Room sessions last 90 days
Viewer sessions went from 24 hours to 90 days; manual grant links from 1 hour to 7 days (up to 30). A counterparty working through weeks of diligence no longer requests a fresh code every morning.
2026-08-13 — Manual Access Grant
For a recipient whose own email security quarantines the access code — common at banks. After verifying identity out-of-band, an admin issues a single-use link containing no code at all. Used successfully for a Wells Fargo contact whose bank filtered every OTP.
Check the Access-code attempts log first. If it shows masked_not_allowed rather than sent, no code was ever sent and the real problem is the allow-list — a grant won't fix that. That exact misdiagnosis happened; the recipient simply wasn't on the room's recipient list.
2026-08-13 — /finance/api/verify hardened
The investor verification endpoint now runs the shared form guard: length caps, email validation, rate limits, risk scoring and the review queue. Previously it validated presence only, and raw values reached a Teams card that renders markdown.
§ 01The investor journey
One path from cold visitor to executed subscription. Each step raises an access level, and every level is checked server-side on every request — never in the browser.
§ 02Access levels
One ladder, used everywhere access is checked. An investor resolves to exactly one row regardless of whether they arrived via the finance gate or CF Access.
| Level | Meaning | Typically unlocks |
|---|---|---|
| L0 | Public | Thesis, access page, public decks |
| L1 | NDA signed | Portal, Intelligence Hub, Tier 1 documents |
| L2 | Qualified | Broader diligence material |
| L3 | Accredited | Cornerstone Preferred — required for the equity round |
| L4 | Lead / institutional | Cap table, pipeline, deployment finance |
| L5 | Closing | Execution documents |
| L6 | Post-close | Ongoing reporting |
| L7 | Trustee / bondholder | Bond programme material |
| L8 | Board | Board-level material |
| L9 | Architect | Everything |
Managed at /admin/investors/. Every promotion and demotion writes a grant-history row with who, when and why.
§ 03The gate
Access is a server-side session, not a browser flag. Everything below is enforced in functions/api/finance/[[path]].js.
How someone gets in
- They request access — email entered at /finance/verify/.
- A one-time code is emailed (Resend, DKIM-signed).
- They verify; a server-side session is created.
- An admin grants an access level. This is a human decision — nothing auto-promotes on verification alone.
Rate limits, all in rlOverGate: code requests capped 6/hour per email and 20/hour per IP; verification attempts 10 per 10 min per email and 20 per 10 min per IP.
§ 04What's behind it
The surfaces
| Path | What it is |
|---|---|
/finance/ | Hub. Capital architecture, links to everything else. |
/finance/thesis/ | Public, no NDA. The investment argument. |
/finance/portal/ | Logged-in home. Rounds, compliance status, updates. |
/finance/intelligence/ | Multi-module diligence hub — technology, IP, operating model, valuation. |
/finance/data-room/ | Document library. View-only, watermarked, logged. |
/finance/ppm/ | Private Placement Memorandum — index, condensed, full, viewer. |
/finance/urvs/ | Urban Reserve Valuation Standard + scenario analysis. |
/finance/portal/rounds/ | CLN · Cornerstone · Master Trust (stub). |
ADeal Room tiers
Canon §3.4.2. Document tier and investor level are two separate checks — both must pass.
| Tier | Requires | Contains |
|---|---|---|
| T0 Public | Nothing — shown pre-OTP | Pitch deck, market thesis |
| T1 Confidential | OTP + NDA | CSA terms, regulatory, technical summary, ESG, risk |
| T2 Vault | OTP + NDA + per-document grant | Financial model, capital structure, unsigned pipeline |
Full operating detail is in the Deal Room runbook. That book is task-oriented; this one just places it in the wider picture.
BPPM
The offering document for the Cornerstone Preferred raise. Four surfaces: an index with all ten Parts, a condensed 5-page summary, the complete document, and an in-portal viewer that wraps it in a sandboxed iframe with ?s=part-N deep-linking.
carbotura.com/finance/ppm/* shows "Temporarily Unavailable" on purpose. That holding page is intentional and stays until the Architect explicitly removes it. Removal replaces it with an auth system — not with raw public access.
§ 05Compliance rules
This is a live securities offering. These constraints are legal, not stylistic.
- Rule 506(c). General solicitation is permitted, but every investor must be verified accredited — self-certification alone is not enough for the equity round. That's why L3 exists as a distinct level.
- Permanent exclusions. Vendor identities, the full FMEA, and URVS-2026 methodology inputs are never disclosed at any tier. No override exists. Don't add one.
- URVS methodology. Summary and outputs may be disclosed under executed NDA, deal-room-gated, with the §3.4.1 legend. Formulas, model, proprietary inputs and calibration never are.
- Third-party firms. No named professional-service firms in investor-facing content — generic descriptors only. Aon plc is the sole permitted named firm, as Insurance Broker of Record.
- Deal-room access logs are the disclosure register. There is no separate register to maintain; the logs are it. That's why view logging must never be disabled.
- Canon governs the numbers. Royalty mechanics, fee structures and per-ton figures come from
carbotura-commercial-canon. Never hand-edit a figure in a finance page — check canon first.
§ 06Operating it
Routine tasks and where they live
| Task | Where |
|---|---|
| Grant or change an access level | /admin/investors/ — audited, reversible |
| Create a deal room, attach documents, mint a share link | /admin/dr/ — see its runbook |
| Recipient didn't get their code | Room → Access-code attempts. Read it before resending. |
| Recipient's email security blocks codes | Manual Access Grant — after out-of-band identity check |
| Review who still has access | Room → Attendees. Do this ~90-daily; nothing prompts you. |
| An access request from the public form | /admin/queue/ if it was held |
Diagnosing "I can't get in"
- Check Access-code attempts.
sentmeans it left us — their side is filtering.masked_not_allowedmeans we never sent it and the allow-list is the problem. These need completely different fixes. - Check their screening status. Must be clear, not pending or blocked.
- Check both allow-lists. Room recipient list and the specific link's list — a link minted for one person doesn't work for another.
- Check their level against the document tiers. If every document is T2 and they cap at T1, they'll see an empty room rather than an error.
§ 07Known traps
| Trap | What happens | What to do |
|---|---|---|
| Masked ≠ delivery failure | An address not on the allow-list gets no code and no error, by design. Looks identical to a mail problem. | Read Access-code attempts before resending or issuing a grant. |
| Duplicate share links | Retry loops leave several live links on one room — each is a working front door. | Revoke stale links during the access review. |
| Approving a queued submission | Approve writes to live Attio. It is not a "mark as read". | Judge legitimacy first; reject deletes. |
| Editing figures by hand | Royalty and fee figures are canon-governed; a hand edit silently diverges from the model. | Check carbotura-commercial-canon; flag for a model rerun. |
| PPM holding page | Looks like a broken deploy. It isn't — it's deliberate. | Leave it until the Architect says otherwise. |
| 90-day sessions | Access now persists far longer than most people assume. | Revoke on deal death or personnel change; don't wait for expiry. |