diff --git a/AiBook_Implementation_Plan.md b/AiBook_Implementation_Plan.md index ed14817..9ae7dcd 100644 --- a/AiBook_Implementation_Plan.md +++ b/AiBook_Implementation_Plan.md @@ -1,14 +1,14 @@ --- -title: "AIBook.fun — Implementation Plan" +title: "AiBook.fun — Implementation Plan" type: implementation-plan status: draft owner: Patrick (Product) launch-target: 2026-09-26 -last-updated: 2026-08-26 +last-updated: 2026-08-31 companions: [AiBook_PRD.md, AiBook_Spec.md] --- -# 📚 AIBook.fun — Implementation Plan +# 📚 AiBook.fun — Implementation Plan > **Status: DRAFT.** The schedule below assumes decisions that aren't final yet (see "Do this > week"). Dates, owners, and dollar figures are planning assumptions until signed off. This is a @@ -16,12 +16,11 @@ companions: [AiBook_PRD.md, AiBook_Spec.md] > [Appendix — What changed](#appendix--what-changed-in-this-revision) for how this revision > differs from the prior draft. -**The clock:** today is late August 2026; **launch is 9/26/2026** — roughly **4–5 weeks out**. -Every week counts, and the critical path has little slack. The domain expires **09-05**, so -step one is non-negotiable and immediate. +**The clock:** today is 31 Aug 2026; **launch is 26 Sep 2026**. Domain and price are signed. +Content is the remaining critical path. **The critical path in one line:** -`renew domain + make the pricing decisions → seed the Minimum Lovable Library → freeze copy → no-crypto scrub → submit to Kickstarter → launch 9/26` +`assign MLL authors + D-3 co-authors → write the library → freeze copy → no-crypto scrub → submit to Kickstarter → launch 9/26` --- @@ -31,17 +30,16 @@ Before any copy or build locks, close these. Most are decisions or de-risking, n | # | Task | Owner | Why it's first | |:--|:--|:--|:--| -| 0.1 | **Renew aibook.fun today.** It expires 09-05; launch is 09-26. | Whoever holds the registrar login | It's a chore, not a decision. A lapsed domain 3 weeks before launch is a self-inflicted disaster. | -| 0.2 | **Decide the pricing spine — lifetime *and* royalties together** (D-1 + D-2). | Commercial lead (@GTM) | Both block copy freeze; they're linked (see [Spec §6](AiBook_Spec.md)). | -| 0.3 | **Ratify the North-Star + product-health floors** (activation, submissions, renewal). | Product (@pat) + team | So we measure the right thing from Day 1, not just dollars. | +| 0.1 | **~~Renew aibook.fun~~ Done 2026-08-31.** | Registrar owner | Closed. | +| 0.2 | **~~Pricing spine~~ Done 2026-08-31.** **$47/yr** is the product. No lifetime SKU as an equal. Founding writers on **contract** (v1 authored). | Commercial + Product | Copy freeze unblocked on price. | +| 0.3 | **~~Ratify the North-Star + product-health floors~~ Done 2026-08-29.** Activation 20/35 from access date; campaign waitlist 50/100; post-key submissions 10/25 in 90 days; renewal 40/60 excluding lifetime; curation is an ops SLA, not a launch bar. See PRD §8. | Product (@pat) | Locked. Don't quote 60% renewal publicly. | | 0.4 | **Ratify the Minimum Lovable Library number and assign every workflow an author.** | Product + co-authors | This is the #1 risk; turn it from hope into owned work. | | 0.5 | **Confirm the two unconfirmed co-authors, or cut their verticals from v1** (D-3). | Commercial lead (@GTM) | Scope certainty before outline lock. | | 0.6 | Open the claims register; assign a post-campaign renewal owner. | Product + Commercial | Truth-in-claims gate; don't leave renewal unstaffed. | | 0.7 | Set up the Kickstarter creator account + identity verification. | Campaign lead (@THY) | Long lead time; do it early. | -**✅ Gate 0 — decisions closed.** Pricing spine decided · targets ratified · Minimum Lovable -Library scoped with authors · domain renewed · claims register open. *Until pricing is decided, -don't freeze copy. Until the domain is renewed, don't push anything live.* +**✅ Gate 0 — decisions closed.** **Pricing spine signed ($47/yr; writers on contract)** · **targets ratified (2026-08-29)** · Minimum Lovable +Library scoped with authors · **domain renewed (2026-08-31)** · claims register open. *Until the library has named authors and D-3 is closed, don't treat content as on track. Copy freeze still waits on claims + co-author scope.* --- @@ -53,8 +51,8 @@ campaign around an empty library fails. ### 1A · Content — seed the Minimum Lovable Library (critical path) | Task | Owner | |:--|:--| -| Lock the chapter outline (chapters per vertical, a named owner each) | Co-authors | -| Publish the Workflow Recipe template + 3 filled examples | Product | +| Lock the chapter outline (chapters per vertical, a named owner each). Blank is [`workflows/chapter-structure.md`](workflows/chapter-structure.md) | Co-authors | +| Review and freeze the chapter blank, then 3 filled examples | Product + authors | | **Seed the Minimum Lovable Library to its floor number** (team + co-authors write & test the workflows) | Co-authors + team | | 3 "clone-and-run" kits, each **verified by actually running it** | Dev + QA support | | 2 sample chapters (the backer preview) | Two lead co-authors | @@ -75,7 +73,7 @@ campaign around an empty library fails. | Task | Owner | |:--|:--| | Kickstarter page copy (all sections, 9/26 dates) | Campaign lead + exec co-author | -| **Copy freeze — commercial terms locked** (lifetime/royalties per D-1/D-2) | Commercial lead (sign) | +| **Copy freeze** (price already signed: $47/yr, writers on contract; still freeze claims + NFT scrub) | Commercial lead (sign) | | **No-crypto scrub gate on every asset** (translation table) | Campaign lead (owner) | | Hero video: script → shoot → edit (2–3 min) | Creative lead (@LFG) + co-authors | | Cover design + 3D mockups | Creative lead | diff --git a/AiBook_PRD.md b/AiBook_PRD.md index 09d4f07..4c1f9de 100644 --- a/AiBook_PRD.md +++ b/AiBook_PRD.md @@ -1,13 +1,13 @@ --- -title: "AIBook.fun — Product Requirements Document" +title: "AiBook.fun — Product Requirements Document" type: prd status: draft owner: Patrick (Product) launch-target: 2026-09-26 -last-updated: 2026-08-26 +last-updated: 2026-08-31 --- -# 📚 AIBook.fun — Product Requirements Document +# 📚 AiBook.fun — Product Requirements Document > **Status: DRAFT.** Dollar figures, dates past today, and commercial terms in this > document are planning assumptions, not commitments. Nothing here should be quoted @@ -20,7 +20,7 @@ last-updated: 2026-08-26 ## TL;DR -AIBook.fun is a **crowd-written, practical field guide to using AI agents responsibly at +AiBook.fun is a **crowd-written, practical field guide to using AI agents responsibly at work** — sold as an annual subscription, launched on Kickstarter on **September 26, 2026**. Its unit of content is not a chapter but a **workflow you can actually run**: a documented, tested recipe for getting a real job done with AI, complete with the guardrails. @@ -142,8 +142,9 @@ the structural answer to "how do I know this AI advice isn't hallucinated?" | **Costs** | Model/tool costs where known — honesty about the economics | | **Author & sources** | Who wrote it, when, for which vertical, with citations | -**Chapters** are curated collections of these recipes, one set per vertical: Real Estate · -Financial Advisors · Fractional C-Suite · Higher Ed · Communities · Technology. **Editions** +**Chapters** are substantial essays, one per vertical (Real Estate · Financial Advisors · +Fractional C-Suite · Higher Ed · Communities · Technology), with full Workflow Recipes +**nested in the argument**. See [§5.4](#54-the-reading-surface-locked-2026-08-31). **Editions** refresh annually — which is the honest justification for a *subscription* rather than a one-time purchase: the content genuinely goes stale as AI changes. @@ -160,15 +161,61 @@ post-launch aspiration. Community contribution is **Layer 2** — an experiment we've seeded a library worth subscribing to. ### 5.3 Be honest: v1 is an *authored* book, not yet a *crowd* book -The prior draft's "contributor economy" pays co-authors **15% affiliate commission** — which -is a reward for *referring backers*, not for *writing workflows*. Writing a workflow currently -earns a byline and nothing else. The mechanic that would actually pay contributors — royalties -— is unresolved (see [D-2](#10-open-decisions)). +The prior draft's "contributor economy" pays co-authors **15% affiliate commission**, which +is a reward for *referring backers*, not for *writing workflows*. -So for v1, we state plainly: **the first edition is written by a founding set of co-authors and -the team.** Open community contribution — with a real incentive attached — is the very next -thing we build, and its incentive design ([D-2](#10-open-decisions)) is a **launch-blocking -decision, not a nice-to-have**, because the entire "living book" thesis depends on it. +**Signed 2026-08-31 (D-2):** founding writers are paid **on contract**. v1 is an authored book. +Affiliate referral can still pay for referring backers. It is not how writing is paid. Open +contribution with royalties or bounties waits for Layer 2. + +So we state plainly: **the first edition is written by a founding set of co-authors and the +team.** Layer 2 is the next thing we build, after the library is worth subscribing to. + +--- + +### 5.4 The reading surface (locked 2026-08-31) + +People read **chapters**, not a shelf of detached cards. A chapter is a substantial essay +for one vertical: it argues a way of working, then **nests full workflows inside that +argument** as the proof. + +This is a deliberate break from treating the workflow as the only page. The workflow is +still the unit of *practice* (and of activation). The chapter is the unit of *reading*. + +**Chapter page** +- Title, vertical, edition, authors +- Opening promise (what this chapter is for) plus a **Skip to a Try-it** control — activation + must not require finishing the essay +- Essay body: sections that teach the practice (stakes, constraints, how we work here) +- Nested **Workflow blocks** at the points in the argument they earn — not bunched in an appendix +- End matter: further workflows in this vertical, sources, last updated + +**Nested workflow block** (the recipe, in full — not a teaser) +1. Chrome: recipe ID, version, time, cost +2. Title as the job +3. Problem +4. Actors +5. Setup (tools, sample files, cost) +6. **Safeguards before the steps** so data-handling is read before anyone pastes a client list +7. Method, with real tool output *in* the steps +8. Evidence +9. Try-it (~15 min, sample data, mark complete — fires Activation) +10. Share result (community template; events, not content) +11. Author, sources, last updated + +**Addressability** +- Every workflow has a stable ID (e.g. `RE-01`) and a URL that opens the chapter scrolled to + that block (and a focused/print view of the same block). Campaign samples, clone-and-run + kits, and Workflow-of-the-Week link here — never to an essay with no way in. +- PDF matches this stack: chapter essay + in-place recipes. Print and web must not drift. + +**Non-goals for the reader** +- No chatbot on the chapter page +- No crypto/Web3 language +- Nested recipes are not collapsed “click to reveal” cards that hide the Method + +**Writing drafts** live in [`workflows/chapter-structure.md`](workflows/chapter-structure.md). +Copy that blank into a vertical file (`workflows/real-estate.md`, etc.) when a chapter is assigned. --- @@ -202,8 +249,8 @@ Requirements are grouped by the layer they serve; **most 🔴 items serve the co | ID | Requirement | Pri | |:--|:--|:--| | A-1 | Post-campaign access: a digital key unlocks PDF + web reader for 12 months, renews annually | 🟢 | -| A-2 | Anchor price **$47/yr** *(draft — needs commercial re-sign)* + hardcopy at-cost upcharge | 🔴 | -| A-3 | Lifetime tier — **decision required before copy freeze** (see [D-1](#10-open-decisions)) | 🟡 | +| A-2 | Anchor price **$47/yr** *(signed 2026-08-31)* + hardcopy at-cost upcharge. No lifetime SKU as an equal product. | 🔴 | +| A-3 | Lifetime tier — **not offered as a v1 SKU** (D-1 signed 2026-08-31: $47/yr only). Revisit only as a capped early-bird later, not as an equal product. | 🟢 | | A-4 | Fulfillment ledger: backer ↔ key/upcharge tracked (a spreadsheet is fine for v1) | 🟢 | ### 6.4 The other layers — mostly 🟡 / 🟢 @@ -236,7 +283,7 @@ Requirements are grouped by the layer they serve; **most 🔴 items serve the co | NFR-3 | **Privacy:** no confidential client data in any workflow or campaign asset; track events, not content. | | NFR-4 | **Availability:** landing page up through the campaign; emails on schedule; affiliate tracking live from Day 1 (the 30-day cookie means every hour of Day 1 counts). | | NFR-5 | **Content quality:** every workflow passes the Recipe template + at least one co-author review. | -| NFR-6 | **Domain continuity:** aibook.fun must not lapse (it currently expires 09-05 — see [§9](#9-immediate-next-steps)). | +| NFR-6 | **Domain continuity:** aibook.fun must not lapse (**renewed 2026-08-31**). | | NFR-7 | **Accessibility:** reader and landing page are mobile-readable, targeting WCAG AA. | | NFR-8 | **Cost discipline:** pre-revenue burn stays within the ~$6K budget ([Appendix C](#appendix-c--budget)). | @@ -249,12 +296,18 @@ metrics; those measure the *campaign*, not the *product.* A funded campaign can dead product if nobody activates, renews, or contributes. ### Product health (report these first) -| Metric | Floor | Target | Why it matters | -|:--|:--|:--|:--| -| **Activation** — read 1 workflow + do 1 Try-it in 14 days | 20% | 35% | The North-Star. Is the core loop actually useful? | -| **Workflow submissions** during campaign window | 10 | 25 | Early signal that Layer 2 (contribution) is real | -| **Renewal rate** — year-1 cohort | — | 60% | Is a *subscription* the right model at all? | -| **Curation turnaround** ≤ 10 working days | 80% | 95% | Can we keep quality without becoming the bottleneck? | + +**Ratified 2026-08-29 (Product).** These are the numbers we run. Do not quote the 60% renewal target on Kickstarter or any public surface. + +| Metric | Floor | Target | Clock / notes | Why it matters | +|:--|:--|:--|:--|:--| +| **Activation** — read 1 workflow + finish 1 Try-it | 20% | 35% | **14 days from access-key date, not pledge date.** North-Star. | Is the core loop actually useful? | +| **Contributor waitlist** during the campaign | 50 | 100 | People who *say* they will contribute a workflow. Not written recipes. | Early Layer-2 signal without betting launch on cold-start writing | +| **Workflow submissions** | 10 | 25 | First **90 days after keys go out** | Is paid/open contribution real once the library exists? | +| **Renewal rate** — year-1 **paid** cohort | 40% | 60% | **Exclude lifetime SKUs** from the denominator. 60% is internal. | Is a *subscription* the right model at all? | +| **Curation turnaround** ≤ 10 working days | 80% | 95% | **Ops SLA after Layer 2 is on** — not a launch health bar | Can we keep quality without becoming the bottleneck? | + +Leading indicator before fulfillment: % of the pre-launch list who run the *sample* Try-it. ### Campaign performance (the fundraise) | Metric | Min | Target | Stretch | @@ -279,13 +332,13 @@ dead product if nobody activates, renews, or contributes. ## 9. Immediate next steps **This week — decisions and de-risking (before any copy or build locks):** -1. **Renew aibook.fun today.** It expires 09-05; launch is 09-26. This is a chore, not a - strategic decision — do it now and delete it from the risk list. *(Owner: whoever holds the - registrar login.)* -2. **Resolve the pricing spine together — lifetime ([D-1](#10-open-decisions)) *and* royalties - ([D-2](#10-open-decisions)).** They're linked, and both block copy freeze. -3. **Ratify the North-Star + the product-health floors** (§8) so we're measuring the right - thing from Day 1. +1. **~~Renew aibook.fun~~ Done.** Domain renewed (confirmed 2026-08-31). Launch remains 09-26. +2. **~~Resolve the pricing spine (D-1 / D-2)~~ Done 2026-08-31.** Anchor is **$47/yr**. No + lifetime SKU as an equal product. Founding writers are engaged **on contract** — v1 is an + authored book; open royalties are not the v1 mechanic. Copy freeze is unblocked on price. +3. **~~Ratify the North-Star + the product-health floors~~ Done 2026-08-29.** Locked in §8: + activation 20/35 from access date; campaign waitlist 50/100; post-key submissions 10/25 in + 90 days; renewal 40/60 excluding lifetime; curation SLA not a launch bar. 4. **Ratify the Minimum Lovable Library number and assign every workflow an author** (§5.2). 5. **Confirm the two unconfirmed co-authors** (Higher Ed, Communities) or re-scope those verticals out of v1. @@ -313,8 +366,8 @@ decision-maker has a starting point — but the recommendation is not yet a deci | # | Decision | Recommendation | Blocks | |:--|:--|:--|:--| -| **D-1** | **Lifetime tier — offer it, and at what price?** A ~$97–147 lifetime breaks even against $47/yr in ~2–3 years, which *undercuts the recurring-revenue thesis.* | **Pick a spine.** Keep $47/yr as the anchor. If you want a lifetime option, frame it *only* as a bounded early-bird instrument to capitalize the community fund (capped quantity), not the default SKU. Don't ship recurring + lifetime as equals. | KS copy freeze | -| **D-2** | **Contributor payment — how do people earn for *writing workflows* (not just referring)?** Today the only paid mechanic is affiliate referral. | **Resolve before launch.** This is the engine of the "living book." Decide: royalty pool, per-accepted-workflow bounty, or an explicit "v1 is authored, paid contribution ships in Q1" — but decide, don't leave blank. | The core value prop | +| **D-1** | ~~Lifetime tier~~ **Signed 2026-08-31.** Product price is **$47/yr**. No lifetime SKU as an equal v1 product. | Locked. Don't quote a lifetime price. Hardcopy remains an at-cost upcharge. | — | +| **D-2** | ~~Writer payment~~ **Signed 2026-08-31.** The first set of writers is engaged **on contract**. v1 is an authored book. Affiliate referral can still pay for *referring backers*; it is not how writing is paid. Open contribution + any royalty/bounty is post-v1 (Layer 2), not a launch mechanic. | Locked for v1. Revisit royalties before opening Layer 2. | — | | **D-3** | **Co-author confirmations** (Higher Ed, Communities verticals). | Confirm within the week or cut those verticals from v1 and add post-launch. | Chapter outline, scope | | **D-4** | **Refresh the source-of-truth plan** to the 9/26 dates and re-signed terms (depends on D-1/D-2). | Do after D-1/D-2 land. | Copy freeze | | **D-5** | **Human-first or agent-first for v1?** Writing for human motivation and for machine ingestion are different jobs. | **Human-first.** Build the content format so agents *can* read it later (K-7), but optimize v1 for human learners. Agent onboarding is Layer 4. | Content design | @@ -375,16 +428,17 @@ changes from the prior draft, and the reasoning: funnel are explicitly later layers. 3. **Elevated the content cold-start** to the #1 risk and added the *Minimum Lovable Library* launch gate (§5.2). -4. **Told the truth about incentives** (§5.3): v1 is an authored book; the "contributor - economy" is currently a referral scheme; paid contribution (D-2) is now launch-blocking. -5. **Forced the subscription-vs-lifetime tension** into a real decision (D-1). +4. **Told the truth about incentives** (§5.3). **D-2 signed 2026-08-31:** founding writers on + contract; v1 authored; royalties wait for Layer 2. Affiliate still pays referrals, not writing. +5. **Forced the subscription-vs-lifetime tension** into a real decision. **D-1 signed 2026-08-31:** + **$47/yr** only. No lifetime SKU as an equal v1 product. 6. **Split the validation bar from the funding floor** (§8) so a funded-but-dead outcome can't hide. 7. **Reframed the pitch as utility-first** (§4, §9 hook test) — the buyer wants a workflow, not an ownership philosophy. 8. **Demoted governance to proportionate** (Appendix B), keeping only the NFT-scrub and truth-in-claims as active gates. -9. **Turned the domain "decision" into a same-day chore** (§9). +9. **Turned the domain into a same-day chore** (§9). **Done 2026-08-31:** `aibook.fun` renewed. 10. **Translated the jargon out.** Internal codes, handles, and merge-history are gone from the body; a who's-who / glossary can be maintained separately if the team wants traceability back to the source-of-truth IDs. diff --git a/AiBook_Spec.md b/AiBook_Spec.md index eca52de..f25c0b3 100644 --- a/AiBook_Spec.md +++ b/AiBook_Spec.md @@ -1,14 +1,14 @@ --- -title: "AIBook.fun — Product Specification" +title: "AiBook.fun — Product Specification" type: spec status: draft owner: Patrick (Product) launch-target: 2026-09-26 -last-updated: 2026-08-26 +last-updated: 2026-08-31 companions: [AiBook_PRD.md, AiBook_Implementation_Plan.md] --- -# 📚 AIBook.fun — Product Specification +# 📚 AiBook.fun — Product Specification > **Status: DRAFT.** This spec is the *thinking* behind the product — the vision, the > principles, the model. The [PRD](AiBook_PRD.md) turns it into requirements; the @@ -22,7 +22,7 @@ companions: [AiBook_PRD.md, AiBook_Implementation_Plan.md] ## TL;DR -AIBook.fun is a **living, crowd-written field guide to using AI agents responsibly at work.** +AiBook.fun is a **living, crowd-written field guide to using AI agents responsibly at work.** Its unit of value is a **workflow you can run** — a documented, tested recipe for doing a real job with AI, including the guardrails. It launches as an annual subscription via Kickstarter on **September 26, 2026**. @@ -56,7 +56,8 @@ ambition — but an engine needs one cylinder firing before you add the rest. He Everything else the product wants to be — a contributor economy, a cohort program, an onboarding corpus for AI agents — is a **layer built on top of this loop**, and only worth building once the loop demonstrably works. We measure that with one number, **Activation**: *did -a reader run at least one workflow within 14 days?* (Full metric set in [PRD §8](AiBook_PRD.md).) +a reader run at least one workflow and finish one Try-it within 14 days of getting access +(access key, not pledge)?* Floors/targets ratified 2026-08-29 — full set in [PRD §8](AiBook_PRD.md). ### The product in layers | Layer | What | When | @@ -95,7 +96,7 @@ These are gates, not preferences — a workflow or a claim either clears them or | Actor | Who | Their job | The boundary | |:--|:--|:--|:--| -| **Reader / subscriber** | Practitioners (real estate, financial advisors, fractional execs, higher ed, communities, tech) | Get current, trustworthy AI workflows to apply this week | Pays for access (~$47/yr — *draft*) | +| **Reader / subscriber** | Practitioners (real estate, financial advisors, fractional execs, higher ed, communities, tech) | Get current, trustworthy AI workflows to apply this week | Pays for access (**$47/yr** — signed) | | **Co-author** | Confirmed: three founders across RE/FA, C-suite, and tech. Potential: two more for Higher Ed & Communities | Own a vertical; write and curate its workflows | Content follows the template; curated | | **Curator / editor** | Co-authors + community editors | Keep the quality bar; run the editorial pipeline | Curating ≠ owning the platform | | **Affiliate** | Community, podcast, press | Refer backers; earn commission | Commission rates below | @@ -146,9 +147,11 @@ answer to "how do I know this isn't hallucinated AI advice?" | **Costs** | Model/tool costs where known — honesty about economics | | **Author & sources** | Who, when, which vertical, with citations | -**Chapters** are curated collections of these per vertical. **Editions** refresh annually — +**Chapters** are the reading unit: a substantial essay per vertical, with **full workflows +nested in the argument** (not a table of contents of cards). **Editions** refresh annually — which is the honest justification for a *subscription*: AI moves fast enough that a static book -goes stale, so the value is in staying current. +goes stale, so the value is in staying current. Reading IA locked 2026-08-31; see +[PRD §5.4](AiBook_PRD.md). ### 4.2 Seed the shelf before you sell tickets (the cold-start rule) The value proposition is a rich library. The failure mode is a near-empty one. Crowd-sourced @@ -179,7 +182,7 @@ around and after launch, not gating it: ### 4.4 Digital surface (current state) | Surface | What it is | Status | |:--|:--|:--| -| `aibook.fun` domain | Public home: pitch, sample workflows, affiliate signup, campaign link | Parked — **expires 09-05, renew immediately** | +| `aibook.fun` domain | Public home: pitch, sample workflows, affiliate signup, campaign link | **Renewed 2026-08-31** | | Landing page (built) | A staged proof-of-concept, ready to review and push live | Staged locally, not yet public | | Subscription access | Digital key → PDF + web reader + annual updates | Not built yet (post-campaign) | | Community | Team channel live; cohort spaces not built | Partial | @@ -218,9 +221,9 @@ from the core loop.* | Item | Value | Status | |:--|:--|:--| -| Anchor subscription | $47/yr digital + hardcopy upcharge | **Draft** — needs commercial re-sign for the 9/26 relaunch | -| Lifetime access | Proposed; ~$97–147 one-time *(figures illustrative — do not quote)* | **Open decision** ([D-1](#8-open-decisions)) | -| Contributor royalties | None documented today; current mechanic is affiliate referral only | **Open decision** ([D-2](#8-open-decisions)) | +| Anchor subscription | **$47/yr** digital + hardcopy at-cost upcharge | **Signed 2026-08-31** | +| Lifetime access | Not a v1 SKU | **Signed D-1:** $47/yr only | +| Founding writers | Paid **on contract** (v1 is authored). Affiliate still pays referrals, not writing. | **Signed D-2 2026-08-31.** Royalties/bounties wait for Layer 2. | | Projected revenue | ~$53,600 at 706 backers | Draft planning figure | | Pre-revenue budget | ~$6,000 (ads + KS fees + affiliate fee) | Draft planning figure | | "eBookNFT platform" | A future idea; this book is the first product | Not in scope | @@ -274,8 +277,8 @@ carries a recommendation as a starting point, not a settled answer. | # | Decision | Recommendation | |:--|:--|:--| -| **D-1** | Lifetime tier — offer it, at what price/position? | Keep $47/yr as the anchor; a lifetime option only as a bounded early-bird capitalization play, not the default. | -| **D-2** | Contributor payment — how do people earn for *writing* workflows, not just referring? | **Resolve before launch** — it's the engine of the "living book." Royalty pool, per-workflow bounty, or an explicit "v1 authored, paid contribution in Q1." | +| **D-1** | ~~Lifetime~~ **Signed 2026-08-31:** **$47/yr** only. No lifetime SKU as an equal product. | Locked. | +| **D-2** | ~~Writer pay~~ **Signed 2026-08-31:** founding writers on **contract**. v1 authored. Layer 2 royalties later. | Locked for v1. | | **D-3** | Confirm the two unconfirmed co-authors (Higher Ed, Communities) | Confirm this week, or cut those verticals from v1 and add post-launch. | | **D-4** | Refresh the source-of-truth plan to the 9/26 dates & re-signed terms | Do after D-1/D-2 land. | | **D-5** | Human-first or agent-first for v1? | Human-first. Build the format so agents *can* read it later; optimize v1 for human learners. | diff --git a/README.md b/README.md index 68e8e14..cc82304 100644 --- a/README.md +++ b/README.md @@ -1,15 +1,15 @@ -# 📚 AIBook.fun +# 📚 AiBook.fun **A living, crowd-written field guide to using AI agents responsibly at work.** -AIBook.fun's unit of content isn't a chapter — it's a **workflow you can actually run**: a -documented, tested recipe for getting a real job done with AI, guardrails included. It's written -and kept current by the practitioners who use it, and it launches as an annual subscription, -crowdfunded on Kickstarter. +People read **chapters**. Each chapter is a substantial essay for one vertical, with full +workflows nested in the argument. The workflow is the unit of practice: a documented, tested +recipe for a real job, guardrails included. The first edition is written on contract by founding +authors. It launches as a **$47/yr** subscription, crowdfunded on Kickstarter. -> **Status: planning stage.** This repository holds the product's planning documents. The product -> is not yet live, and everything here is a working draft — figures, dates, and commercial terms -> are planning assumptions, not commitments. Public launch is **targeted for September 26, 2026**. +> **Status: planning + writing.** Planning docs and the chapter blank live here. The product is +> not yet live. **$47/yr** is signed. Domain `aibook.fun` is renewed. Other figures and unsigned +> terms are still planning assumptions, not for public quote. Launch target **26 Sep 2026**. ## The idea in one loop @@ -30,22 +30,23 @@ not read AI theory. ## What's in this repository -This is a documentation and planning repo. Three companion documents define the product: +This is a documentation and writing repo. | Document | What it covers | |:--|:--| -| [Product Requirements (PRD)](AiBook_PRD.md) | What we're building and why — scope, requirements, success metrics, open decisions | -| [Product Specification (Spec)](AiBook_Spec.md) | The thinking behind it — vision, principles, content model, business model | -| [Implementation Plan](AiBook_Implementation_Plan.md) | How and when — the path from now to launch and fulfillment | +| [Product Requirements (PRD)](AiBook_PRD.md) | What we're building and why. Scope, requirements, success metrics, open decisions | +| [Product Specification (Spec)](AiBook_Spec.md) | The thinking behind it. Vision, principles, content model, business model | +| [Implementation Plan](AiBook_Implementation_Plan.md) | How and when. Path from now to launch and fulfillment | +| [Chapter structure](workflows/chapter-structure.md) | The blank chapter for review. Copy it into a vertical file when writing starts | New here? Start with the **[Spec](AiBook_Spec.md)** for the vision, then the **[PRD](AiBook_PRD.md)** -for the specifics. +for the specifics. Writers start at **[chapter structure](workflows/chapter-structure.md)**. ## How it works (the short version) -- **Content:** every entry follows one *Workflow Recipe* template — problem, method (showing the - real tool output), safeguards, evidence, a ~15-minute Try-it, and costs. The template is the - quality guarantee — the structural answer to "how do I know this AI advice isn't made up?" +- **Content:** readers get a chapter essay. Nested in it, every workflow follows one recipe: + problem, actors, setup, safeguards, method (real tool output), evidence, a ~15-minute Try-it, + share, costs, author. Safeguards sit before the steps. The template is the quality guarantee. - **Editions:** the guide refreshes annually — which is why it's a subscription. AI moves fast, and stale advice is worthless. - **Contribution:** the first edition is written by a founding set of co-authors; open community @@ -61,7 +62,7 @@ for the specifics. | Post-launch | Fulfill the first edition; open community contribution | | Later | Cohort learning, annual editions, deeper ecosystem integration | -AIBook.fun is part of the **WeOwnNet** ecosystem. +AiBook.fun is part of the **WeOwnNet** ecosystem. ## License diff --git a/marketing-site/README.md b/marketing-site/README.md index c62f499..a120d65 100644 --- a/marketing-site/README.md +++ b/marketing-site/README.md @@ -1,4 +1,4 @@ -# AIBook.fun Marketing Site +# AiBook.fun Marketing Site Scaffolded for Framer import and Next.js (Cloudflare Pages / DigitalOcean). @@ -33,3 +33,14 @@ Note: Framer Sites don't run Next.js natively. For a live site with routing (A/B - 3 sample tiers shown ($10 / $47yr / $4,888) - No NFT/crypto/Web3 language (Kickstarter compliance scrubbed) - Event tracking only (not content) — PostHog/Cloudflare Analytics slot available + +## Reading demo + +A sample reading environment is wired into this Next.js app (pages router). + +```bash +npm install +npm run dev +``` + +Then open [http://localhost:3000/read](http://localhost:3000/read). One chapter is filled (Real Estate, with nested RE-01 and RE-02). This is a demo, not the live book. diff --git a/marketing-site/components/Authors.jsx b/marketing-site/components/Authors.jsx index c302c08..c4b5d6e 100644 --- a/marketing-site/components/Authors.jsx +++ b/marketing-site/components/Authors.jsx @@ -13,8 +13,8 @@ export default function Authors() { Who’s writing this

Practitioners, one per vertical.

- Each chapter is owned by someone who does the work — not a generalist writing about - it. Names are announced as co-authors confirm. + Each chapter is owned by someone who does that work for a living. Names go up as + co-authors confirm.

{AUTHORS.map((a) => ( diff --git a/marketing-site/components/Book3D.jsx b/marketing-site/components/Book3D.jsx index 193ee74..666e0dd 100644 --- a/marketing-site/components/Book3D.jsx +++ b/marketing-site/components/Book3D.jsx @@ -11,7 +11,7 @@ export default function Book3D() {
- AIBook.fun · Responsible Agentic AI + AiBook.fun · Responsible Agentic AI
The Field Guide @@ -28,7 +28,7 @@ export default function Book3D() { - AIBook.fun + AiBook.fun
{/* Belly band — the classic publisher's wraparound strip for a themed tie-in, rather than redesigning the whole cover around it. */} diff --git a/marketing-site/components/FAQ.jsx b/marketing-site/components/FAQ.jsx index 3259395..46587e3 100644 --- a/marketing-site/components/FAQ.jsx +++ b/marketing-site/components/FAQ.jsx @@ -1,28 +1,28 @@ const QA = [ { q: "Is this AI theory, or something I can actually run?", - a: "Something you run. Every workflow shows the real tool output, lists the real steps, and ends in a ~15-minute Try-it on non-confidential sample data. If you can’t run it, it doesn’t ship.", + a: "Something you run. Every workflow shows the real tool output, lists the real steps, and ends in a ~15-minute Try-it on non-confidential sample data. If you can't run it, it doesn't ship.", open: true, }, { q: "How is this different from a course?", - a: "A course teaches concepts; this is a field guide of tested recipes you apply to your real job this week. It refreshes annually because AI moves fast — stale advice is worthless.", + a: "A course teaches concepts. This is a field guide of tested recipes you apply to your job this week. The recipes get rewritten as the tools change, not left sitting until next year.", }, { - q: "What does “responsible by design” actually mean?", - a: "Every recipe includes data-handling rules, human-oversight steps, failure modes, and escalation paths. They’re part of the template — not an appendix, not an afterthought.", + q: "What does \"responsible by design\" actually mean?", + a: "Every recipe includes data-handling rules, human-oversight steps, failure modes, and escalation paths. They sit in the template above Method, not in a footnote.", }, { q: "Can I contribute a workflow after backing?", - a: "Yes — open contribution opens once the founding library is live. We’re finalizing how contributors get paid (not just a byline) before launch.", + a: "Yes. Open contribution starts once the founding library is live. How contributors get paid is still being finalized before launch.", }, { q: "Why subscribe instead of buy once?", - a: "Because a static AI book is out of date in months. The subscription is what keeps every workflow current — and it’s what funds the practitioners keeping them that way.", + a: "A one-time AI book goes stale in weeks. The $47/yr subscription funds ongoing updates as models and products move, often weekly or monthly.", }, { q: "Why frame this around the American Dream?", - a: "Because for most of the people writing and reading this guide, real fluency with these tools isn’t a slogan — it’s a practical ladder. Nobody in this book inherited their edge; they built it, one real skill at a time. We think this is the next one worth building.", + a: "For most of the people writing and reading this guide, fluency with these tools is a practical ladder. Nobody in this book inherited their edge. They built it, one real skill at a time. We think this is the next one worth building.", }, ]; diff --git a/marketing-site/components/FieldNotes.jsx b/marketing-site/components/FieldNotes.jsx index d7cbe4c..4e01730 100644 --- a/marketing-site/components/FieldNotes.jsx +++ b/marketing-site/components/FieldNotes.jsx @@ -1,18 +1,18 @@ const NOTES = [ { n: "01 / Stays current", - h: "A subscription, not a static book", - p: "AI moves too fast for a book you buy once. Each annual edition is refreshed so the ground you gain here doesn’t erode the moment you look away.", + h: "Rewritten as the tools move", + p: "Models and products change by the week. We update recipes when a step breaks or a better path shows up, often weekly or monthly. The $47/yr subscription is what pays for that work.", }, { n: "02 / Authored, then open", - h: "Written by practitioners first", - p: "The first edition is seeded by co-authors — a real founding library, not an empty shelf. Open, paid contribution opens once it’s worth browsing, so the people who build it get to own a piece of it.", + h: "Co-authors fill it before launch", + p: "Founding writers are on contract. They write and test the first library. Outside contribution opens later, once there is a real catalog to join, not an empty page waiting for strangers.", }, { n: "03 / Responsible by design", - h: "Guardrails in every recipe", - p: "Data handling, human oversight, failure modes, escalation — part of the template on every workflow, never an appendix.", + h: "Safeguards sit above the steps", + p: "Every recipe names what never goes in the prompt, who reviews before anything leaves the building, and when you stop. That block is read before Method.", }, ]; diff --git a/marketing-site/components/Footer.jsx b/marketing-site/components/Footer.jsx index deee82d..4344b35 100644 --- a/marketing-site/components/Footer.jsx +++ b/marketing-site/components/Footer.jsx @@ -5,17 +5,16 @@ export default function Footer() {
- AIBook. + AiBook. fun

- A living, crowd-written field guide to using AI agents responsibly at work. Part - of the WeOwnNet ecosystem. + An authored field guide of runnable AI workflows for work. Part of the WeOwnNet + ecosystem.

A recipe - Contents Preview FAQ
diff --git a/marketing-site/components/Hero.jsx b/marketing-site/components/Hero.jsx index f19627c..1b27596 100644 --- a/marketing-site/components/Hero.jsx +++ b/marketing-site/components/Hero.jsx @@ -27,9 +27,10 @@ export default function Hero() { responsibly at work.

- Not theory. Not hype. A subscription guide of{" "} - tested workflows you can actually run — each with the - real tool output, the guardrails, and a 15-minute exercise so you learn by doing. + A living subscription guide of{" "} + tested workflows you can run. Each one shows the real + tool output, the safeguards, and a 15-minute Try-it. Recipes get updated as the + tools change.

diff --git a/marketing-site/components/Letter.jsx b/marketing-site/components/Letter.jsx index 780501f..1e3e0cb 100644 --- a/marketing-site/components/Letter.jsx +++ b/marketing-site/components/Letter.jsx @@ -4,17 +4,17 @@ export default function Letter() {

A note on why

- Most AI advice is either hype or theory — and neither survives contact with real - work. We’re writing the guide we wish we’d had: workflows that actually run, - with the guardrails built in, kept honest by the people - who use them every day. For a lot of us, mastering these tools isn’t optional - anymore — it’s how you build the life you’re working toward. Fund the first edition, - and you don’t just get the book — you help decide what goes in it. + Most AI advice is hype or theory, and neither survives contact with real work. We are + writing the guide we wish we had: workflows that actually run, with the{" "} + safeguards built in, kept current by the people who use + them every day as the tools move. For a lot of us, fluency with these tools is how you + build the life you are working toward. Fund the first edition and you help decide what + goes in it.

The co-authors - AIBook.fun founding team + AiBook.fun founding team
Real estate · finance · leadership · tech
diff --git a/marketing-site/components/Nav.jsx b/marketing-site/components/Nav.jsx index 00e1d0b..34d4572 100644 --- a/marketing-site/components/Nav.jsx +++ b/marketing-site/components/Nav.jsx @@ -1,12 +1,27 @@ import { useEffect, useRef, useState } from "react"; +import Link from "next/link"; const LINKS = [ { href: "#recipe", label: "A recipe" }, - { href: "#contents", label: "Contents" }, { href: "#letter", label: "Why" }, { href: "#faq", label: "FAQ" }, ]; +function NavItem({ href, label, onClick }) { + if (href.startsWith("/")) { + return ( + + {label} + + ); + } + return ( + + {label} + + ); +} + export default function Nav() { const [scrolled, setScrolled] = useState(false); const [open, setOpen] = useState(false); @@ -39,22 +54,25 @@ export default function Nav() { return (
@@ -40,7 +40,7 @@ export default function Tiers() {
limited · final terms at launch
A named acknowledgment in the guide, a private cohort seat, and a hand in shaping - the first edition — the ground floor of something you helped build. + the first edition.
diff --git a/marketing-site/components/reader/ChapterKit.jsx b/marketing-site/components/reader/ChapterKit.jsx new file mode 100644 index 0000000..911856d --- /dev/null +++ b/marketing-site/components/reader/ChapterKit.jsx @@ -0,0 +1,60 @@ +import { collectChapterKit } from "../../data/sample-chapter"; + +export default function ChapterKit({ recipes }) { + const kit = collectChapterKit(recipes); + if (!kit.tools.length && !kit.files.length) return null; + + return ( +
+

What you need

+

+ {recipes.length} Try-it{recipes.length === 1 ? "" : "s"} on sample data. Nothing + from a live client file. +

+
+
+
Tools
+
+
    + {kit.tools.map((t) => ( +
  • {t}
  • + ))} +
+
+
+
+
Files
+
+
    + {kit.files.map((f) => ( +
  • {f}
  • + ))} +
+
+
+
+
Model
+
+
    + {kit.models.map((m) => ( +
  • {m}
  • + ))} +
+
+
+
+
Try-its
+
+
    + {kit.tryits.map((t) => ( +
  • + {t.id} · {t.time} · {t.cost} +
  • + ))} +
+
+
+
+
+ ); +} diff --git a/marketing-site/components/reader/ChapterOutline.jsx b/marketing-site/components/reader/ChapterOutline.jsx new file mode 100644 index 0000000..d7a8d08 --- /dev/null +++ b/marketing-site/components/reader/ChapterOutline.jsx @@ -0,0 +1,99 @@ +import { useEffect, useMemo, useState } from "react"; + +function OutlineBody({ groups, complete, count, total, active, showTitle }) { + return ( + <> +

+ {count}/{total} Try-its complete +

+ {showTitle ?

In this chapter

: null} + {groups.map((g) => ( +
+

{g.label}

+ +
+ ))} + + ); +} + +export default function ChapterOutline({ + groups, + complete = {}, + count = 0, + total = 0, + variant = "desktop", +}) { + const ids = useMemo( + () => groups.flatMap((g) => g.items.map((item) => item.id)), + [groups] + ); + const [active, setActive] = useState(ids[0] || ""); + + useEffect(() => { + const els = ids.map((id) => document.getElementById(id)).filter(Boolean); + if (!els.length || typeof IntersectionObserver === "undefined") return; + + const observer = new IntersectionObserver( + (entries) => { + const visible = entries + .filter((e) => e.isIntersecting) + .sort((a, b) => a.boundingClientRect.top - b.boundingClientRect.top); + if (visible[0]?.target?.id) setActive(visible[0].target.id); + }, + { rootMargin: "-88px 0px -55% 0px", threshold: [0, 0.1, 0.25, 0.5, 1] } + ); + els.forEach((el) => observer.observe(el)); + return () => observer.disconnect(); + }, [ids]); + + if (variant === "mobile") { + return ( +
+ In this chapter + +
+ ); + } + + return ( + + ); +} diff --git a/marketing-site/components/reader/ReaderCrumbs.jsx b/marketing-site/components/reader/ReaderCrumbs.jsx new file mode 100644 index 0000000..da23560 --- /dev/null +++ b/marketing-site/components/reader/ReaderCrumbs.jsx @@ -0,0 +1,24 @@ +import Link from "next/link"; + +export default function ReaderCrumbs({ items }) { + return ( + + ); +} diff --git a/marketing-site/components/reader/ReaderFooter.jsx b/marketing-site/components/reader/ReaderFooter.jsx new file mode 100644 index 0000000..1c59930 --- /dev/null +++ b/marketing-site/components/reader/ReaderFooter.jsx @@ -0,0 +1,32 @@ +import Link from "next/link"; + +export default function ReaderFooter() { + return ( +
+
+
+
+
+ AiBook. + fun +
+

+ Reading demo. Not the live book. Workflows sit inside a chapter, + not on a shelf of cards. +

+
+
+ Home + Library + Preview +
+
+
+ © 2026 WeOwnAI · MIT-licensed docs · This page is a reading-environment demo. +
+ Activation is stored in this browser only. No chatbot. No live client data. +
+
+
+ ); +} diff --git a/marketing-site/components/reader/ReaderNav.jsx b/marketing-site/components/reader/ReaderNav.jsx new file mode 100644 index 0000000..ec9db7e --- /dev/null +++ b/marketing-site/components/reader/ReaderNav.jsx @@ -0,0 +1,40 @@ +import { useEffect, useState } from "react"; +import Link from "next/link"; + +export default function ReaderNav({ here = "library" }) { + const [scrolled, setScrolled] = useState(false); + + useEffect(() => { + const onScroll = () => setScrolled(window.scrollY > 12); + onScroll(); + window.addEventListener("scroll", onScroll, { passive: true }); + return () => window.removeEventListener("scroll", onScroll); + }, []); + + return ( + + ); +} diff --git a/marketing-site/components/reader/TermOutput.jsx b/marketing-site/components/reader/TermOutput.jsx new file mode 100644 index 0000000..95a5ded --- /dev/null +++ b/marketing-site/components/reader/TermOutput.jsx @@ -0,0 +1,60 @@ +/** Same terminal chrome as the marketing Recipe (.term / .term-bar). */ + +export function TermRE01() { + return ( +
+
+ + + + agent — property-brief · sample dataset (non-confidential) +
+
+        {"$ "}
+        {"brief"}
+        {" --input "}
+        {"sample_listings.csv"}
+        {" --template market-1pager\n\n"}
+        {"✓ redacted 3 fields (owner_name, phone, exact_address)\n✓ 41 comps in radius · median $/sqft computed\n\n"}
+        {"MARKET BRIEF — Maple Heights (sample)\n"}
+        {" · Median list: $420/sqft  (▲ 4.1% QoQ)\n · Days on market: 22  (was 31)\n · Inventory: 1.8 mo — seller-leaning\n · Read: price to comp, expect <2 wks at ask\n\n"}
+        {"# cost this run: $0.03 · model: claude · 2,140 tokens"}
+      
+
+ ); +} + +export function TermRE02() { + return ( +
+
+ + + + agent — listing-copy · sample comps (public facts) +
+
+        {"$ "}
+        {"listing-copy"}
+        {" --input "}
+        {"sample_comps.json"}
+        {" --voice house-voice --out draft.md\n\n"}
+        {"✓ used 6 public comps (no CRM fields present)\n✓ 184 words · reading grade 8\n\n"}
+        {"LISTING DRAFT · 14xx Cedar (sample street, public facts)\n"}
+        {" · Bright corner lot, 3 bed / 2 bath, maple kitchen from 2019.\n · Priced to the block: comps closed $398–$441/sqft in 60 days.\n · No owner name, phone, or showing list in the prompt.\n\n"}
+        {"# cost this run: $0.02 · model: claude · 1,280 tokens"}
+      
+
+ ); +} + +const TERMS = { + "re-01": TermRE01, + "re-02": TermRE02, +}; + +export default function TermOutput({ id }) { + const Cmp = TERMS[id]; + if (!Cmp) return null; + return ; +} diff --git a/marketing-site/components/reader/WorkflowBlock.jsx b/marketing-site/components/reader/WorkflowBlock.jsx new file mode 100644 index 0000000..fb5b83b --- /dev/null +++ b/marketing-site/components/reader/WorkflowBlock.jsx @@ -0,0 +1,262 @@ +import { useState } from "react"; +import Link from "next/link"; +import TermOutput from "./TermOutput"; + +const JUMP = [ + { id: "kit", label: "Kit" }, + { id: "problem", label: "Problem" }, + { id: "actors", label: "Actors" }, + { id: "setup", label: "Setup" }, + { id: "safeguards", label: "Safeguards" }, + { id: "method", label: "Method" }, + { id: "evidence", label: "Evidence" }, + { id: "tryit", label: "Try-it" }, +]; + +function ShieldCheck() { + return ( + + ); +} + +function CheckMark() { + return ( + + ); +} + +async function copyText(text) { + try { + await navigator.clipboard.writeText(text); + return true; + } catch { + try { + const el = document.createElement("textarea"); + el.value = text; + el.setAttribute("readonly", ""); + el.style.position = "fixed"; + el.style.left = "-9999px"; + document.body.appendChild(el); + el.select(); + const ok = document.execCommand("copy"); + el.remove(); + return ok; + } catch { + return false; + } + } +} + + +function WorkflowKit({ recipe }) { + const k = recipe.kit; + if (!k) return null; + const rows = [ + ["You run", k.youRun], + ["Tools", (k.tools || []).join(" · ")], + ["Files", (k.files || []).join(" · ")], + ["Model", k.model], + ["Time", recipe.time], + ["Cost", recipe.cost], + ["You produce", k.artifact], + ].filter(([, v]) => v); + return ( +
+ {rows.map(([label, value]) => ( +
+
{label}
+
{value}
+
+ ))} +
+ ); +} + +function Field({ anchor, name, label, children }) { + return ( +
+

{label}

+
{children}
+
+ ); +} + +export default function WorkflowBlock({ + recipe, + complete = false, + onToggleComplete, + focused = false, + index = 1, + total = 1, +}) { + const [copied, setCopied] = useState(false); + const a = recipe.anchor; + + const onShare = async () => { + const ok = await copyText(recipe.shareBlurb); + if (!ok) return; + setCopied(true); + window.setTimeout(() => setCopied(false), 1800); + }; + + return ( +
+
+ + Workflow {index} of {total} · {recipe.id} · v{recipe.version} · {recipe.time} · {recipe.cost} + + {recipe.vertical} +
+ +
+

+ {recipe.title} +

+ + + + + + + {recipe.problem} {recipe.problemJob} + + + +
    + {recipe.actors.map((line) => ( +
  • {line}
  • + ))} +
+
+ + +
    + {recipe.setup.map((line) => ( +
  • {line}
  • + ))} +
+
+ + + {recipe.safeguards.map((line) => ( +
+ + {line} +
+ ))} +
+ + +
    + {recipe.method.map((step, i) => ( +
  1. +
    + {step.text} + {step.term ? : null} +
    +
  2. + ))} +
+
+ + + {recipe.evidence.map((line) => ( +

+ {line} +

+ ))} +
+ + +

+ About {recipe.tryit.minutes} minutes. {recipe.tryit.sample}{" "} + {recipe.tryit.produce} +

+

+ {recipe.tryit.done}{" "} + + {recipe.tryit.hrefLabel} + +

+

+ ◷ {recipe.tryit.chip} +

+ {onToggleComplete ? ( +
+ +
+ ) : null} +
+ + +

Copy a short result line. Share the outcome, not the recipe text.

+
+ +
+
+ + +
+ Author: {recipe.author} + Sources: {recipe.sources} + Last updated: {recipe.lastUpdated} + {focused ? ( + + + Back to the chapter + + + ) : ( + + Open on paper + + )} +
+
+
+
+ ); +} diff --git a/marketing-site/components/reader/WorkflowRail.jsx b/marketing-site/components/reader/WorkflowRail.jsx new file mode 100644 index 0000000..fa2a641 --- /dev/null +++ b/marketing-site/components/reader/WorkflowRail.jsx @@ -0,0 +1,35 @@ +export default function WorkflowRail({ recipes, complete = {}, total }) { + return ( + + ); +} diff --git a/marketing-site/components/reader/useActivation.js b/marketing-site/components/reader/useActivation.js new file mode 100644 index 0000000..4a93216 --- /dev/null +++ b/marketing-site/components/reader/useActivation.js @@ -0,0 +1,43 @@ +import { useCallback, useEffect, useMemo, useState } from "react"; + +function keyFor(id) { + return `aibook-demo-activation:${id}`; +} + +/** + * Demo-only activation state. Completing a Try-it writes + * localStorage key `aibook-demo-activation:`. + */ +export default function useActivation(ids) { + const list = useMemo(() => ids, [ids.join("|")]); + const [complete, setComplete] = useState(() => + Object.fromEntries(list.map((id) => [id, false])) + ); + + useEffect(() => { + const next = {}; + list.forEach((id) => { + try { + next[id] = window.localStorage.getItem(keyFor(id)) === "1"; + } catch { + next[id] = false; + } + }); + setComplete(next); + }, [list]); + + const toggle = useCallback((id) => { + setComplete((prev) => { + const value = !prev[id]; + try { + window.localStorage.setItem(keyFor(id), value ? "1" : "0"); + } catch { + /* private mode: still toggle in memory */ + } + return { ...prev, [id]: value }; + }); + }, []); + + const count = list.filter((id) => complete[id]).length; + return { complete, toggle, count, total: list.length }; +} diff --git a/marketing-site/data/sample-chapter.js b/marketing-site/data/sample-chapter.js new file mode 100644 index 0000000..66798b4 --- /dev/null +++ b/marketing-site/data/sample-chapter.js @@ -0,0 +1,311 @@ +/** + * Sample chapter + nested recipes for the reading demo. + * Imported by pages under /read. Not a CMS. + */ + +export const LIBRARY = [ + { + num: "01", + name: "Real Estate", + slug: "real-estate", + href: "/read/real-estate", + desc: "Market briefs and listings, without leaking client data", + status: "ready", + }, + { + num: "02", + name: "Financial Advisors", + slug: "financial-advisors", + desc: "Portfolio summaries that stay compliant and reviewed", + status: "coming", + }, + { + num: "03", + name: "Fractional C-Suite", + slug: "fractional-c-suite", + desc: "Board updates and plans with real escalation paths", + status: "coming", + }, + { + num: "04", + name: "Higher Ed", + slug: "higher-ed", + desc: "Course and research workflows with academic integrity", + status: "coming", + }, + { + num: "05", + name: "Communities", + slug: "communities", + desc: "Moderation and programming that respects members", + status: "coming", + }, + { + num: "06", + name: "Technology", + slug: "technology", + desc: "Agent patterns, evals, and the responsible defaults", + status: "coming", + }, +]; + +const RE01 = { + id: "RE-01", + anchor: "re-01", + version: "1.2", + time: "~15 min", + cost: "≈ $0.03", + vertical: "Real Estate", + shortTitle: "Market brief", + title: "Draft a property-market brief with an AI agent without leaking client data.", + problem: + "You need a neighborhood market brief for a client meeting this week. The listing sheet and client notes cannot go into a public model.", + problemJob: + "Job: turn messy local data into a credible one-pager in minutes, safely.", + actors: [ + "Listing agent runs it.", + "Client receives the brief.", + "Model may draft and classify. A human must review before send.", + ], + setup: [ + "Tools: local redaction script (brief CLI), Claude or your usual model.", + "Sample files: sample_listings.csv, market-1pager template.", + "Cost: about $0.03 on the sample run (2,140 tokens).", + ], + safeguards: [ + "Redaction runs on your machine. Raw client data never reaches the model.", + "A human checklist is required before the brief is shared. The checklist is part of the recipe.", + "Stop if identifiers remain after the strip report. Do not prompt until owner_name, phone, and exact_address are gone.", + ], + method: [ + { + text: "Strip identifiers from the source data locally (a provided script does this).", + }, + { + text: "Prompt the agent with the anonymized sample and a fixed brief template.", + term: "re-01", + }, + { + text: "Review the draft against the checklist before anything leaves your machine.", + }, + ], + evidence: [ + "A one-pager brief on Maple Heights (sample), ready for a meeting once a human signs the checklist.", + "Sample metrics from that run: median $420/sqft, 22 days on market, 1.8 months of inventory.", + ], + tryit: { + minutes: 15, + sample: "Use the included sample_listings.csv (no live client file).", + produce: "Produce the market-1pager brief and walk the human checklist.", + done: "Mark complete when you have a brief you would send after review. Completing this is the activation demo.", + href: "/samples/sample_listings.csv", + hrefLabel: "sample_listings.csv", + chip: "cost to try ≈ $0.03", + }, + shareBlurb: + "Ran RE-01 on sample comps. Maple Heights median $420/sqft, 22 DOM.", + author: "Founding library · sample", + sources: "Sample MLS packet (non-confidential); market-1pager template shipped with the recipe.", + lastUpdated: "31 Aug 2026", + kit: { + youRun: "Listing agent", + tools: ["brief CLI (local redaction)", "Claude"], + files: ["sample_listings.csv", "market-1pager template"], + model: "Claude", + artifact: "One-pager market brief", + }, +}; + +const RE02 = { + id: "RE-02", + anchor: "re-02", + version: "1.0", + time: "~12 min", + cost: "≈ $0.02", + vertical: "Real Estate", + shortTitle: "Listing copy", + title: "Rewrite a listing description from public comps without pasting the client address book.", + problem: + "You need listing copy that sounds like this house, not every house on the street. The CRM holds owner notes and the showing list. Those do not go into a public model.", + problemJob: + "Job: draft 180-word listing copy from public facts only, then edit it yourself.", + actors: [ + "Listing agent runs it.", + "The public listing receives the copy.", + "Model drafts. A human edits, files, and posts to MLS.", + ], + setup: [ + "Tools: listing-copy CLI, listing-voice template, Claude or your usual model.", + "Sample files: sample_comps.json (public comps only).", + "Cost: about $0.02 on the sample run (1,280 tokens).", + ], + safeguards: [ + "Prompt only with public listing facts. No CRM export, no showing list, no owner notes.", + "A human edits the draft before it hits MLS. Do not auto-post.", + "Stop if a private note, phone, or exact owner name appears in the draft.", + ], + method: [ + { + text: "Export public comps for the block. Leave the CRM closed.", + }, + { + text: "Run listing-copy against the sample comps and the house-voice template.", + term: "re-02", + }, + { + text: "Edit the draft. Cut anything that could only have come from a private note.", + }, + ], + evidence: [ + "A 184-word listing draft, public facts only, reading grade 8.", + "Comps on the block closed between $398 and $441/sqft in 60 days. The draft prices to that range without naming a client.", + ], + tryit: { + minutes: 12, + sample: "Use the included sample_comps.json (public comps, no address book).", + produce: "Produce a ~180-word listing description and a human edit pass.", + done: "Mark complete when the draft has no private fields. Completing this is the activation demo.", + href: "/samples/sample_comps.json", + hrefLabel: "sample_comps.json", + chip: "cost to try ≈ $0.02", + }, + shareBlurb: + "Ran RE-02 on sample comps. 184-word listing draft, public facts only.", + author: "Founding library · sample", + sources: "Public comps sample packet; listing-voice template shipped with the recipe.", + lastUpdated: "31 Aug 2026", + kit: { + youRun: "Listing agent", + tools: ["listing-copy CLI", "Claude"], + files: ["sample_comps.json", "listing-voice template"], + model: "Claude", + artifact: "180-word listing draft", + }, +}; + +export const RECIPES = [RE01, RE02]; + +export const RECIPES_BY_ID = { + "RE-01": RE01, + "RE-02": RE02, + // Old demo URLs. Displayed ID is RE-01 / RE-02. + "RE-04": RE01, + "RE-05": RE02, +}; + +export const CHAPTER = { + slug: "real-estate", + vertical: "Real Estate", + edition: "2026", + authors: "Founding library · sample", + title: "Work the listing without leaking the client", + promise: + "In this chapter you run two jobs a realtor actually has this week, on sample data, without putting a client file in a public model.", + lastUpdated: "31 Aug 2026", + skip: [ + { id: "RE-01", href: "#re-01", title: "Market brief" }, + { id: "RE-02", href: "#re-02", title: "Listing copy" }, + ], + stakes: { + id: "stakes", + heading: "The stakes", + paragraphs: [ + "A listing that stalls because the market brief is late is a lost weekend. A listing that leaks because you pasted the client sheet into a public model is a lost license. Real estate work runs on both clocks: the showing at 4pm, and the file that must never leave the office.", + "The failure is not that AI sits unused. It is a one-pager that is late, generic, or built from a client name that should not have been in the prompt. Buyers notice fluff. Brokers notice a privacy incident. Neither is recoverable in the same week.", + ], + }, + constraints: { + id: "constraints", + heading: "Constraints you cannot ignore", + paragraphs: [ + "You already work in MLS exports, a CRM, and a phone that rings during the write-up. Done is a brief the client can read in a meeting, with numbers you can stand behind, reviewed by a human. Public models are useful for draft and classify. They are not a filing cabinet.", + "Owner names, phones, exact addresses, and showing lists stay on your machine. Comps, medians, and days on market can travel, once identifiers are stripped. If a field could pick one household out of the block, it does not go in the prompt.", + ], + }, + practice: { + id: "practice", + heading: "How we work here", + paragraphs: [ + "Redact locally. Prompt with a sample or a stripped file. Review against a checklist. Share the artifact, not the workflow text. The first job this week is the neighborhood market brief. Run it on sample comps before you touch a live listing.", + ], + }, + between: { + id: "between", + heading: "The brief is half the meeting", + paragraphs: [ + "The brief gets you into the room with numbers. The other half is the listing copy: public comps, a description that does not sound like every other house on the street, and an address book that never belongs in the prompt. Same rule. Different job.", + ], + }, + further: [ + { id: "RE-01", href: "#re-01", title: "Draft a property-market brief without leaking client data" }, + { id: "RE-02", href: "#re-02", title: "Rewrite a listing description from public comps" }, + { id: "RE-03", title: "Offer-response notes from public remarks (later)", coming: true }, + ], + sources: [ + "Sample MLS packet shipped with this chapter (non-confidential).", + "market-1pager and listing-voice templates in the recipe kit.", + "Local redaction fields: owner_name, phone, exact_address.", + ], +}; + +/** Outline groups for the chapter map. Headings come from the essay objects. */ +export function buildOutline(chapter, recipes) { + return [ + { + label: "Start", + items: [{ id: "need", label: "What you need" }], + }, + { + label: "Essay", + items: [chapter.stakes, chapter.constraints, chapter.practice, chapter.between].map((s) => ({ + id: s.id, + label: s.heading, + })), + }, + { + label: "Workflows", + items: recipes.map((r) => ({ + id: r.anchor, + recipeId: r.id, + label: r.id + " · " + r.shortTitle, + time: r.time, + shortTitle: r.shortTitle, + tools: r.kit && r.kit.tools ? r.kit.tools.join(", ") : "", + })), + }, + { + label: "End", + items: [ + { id: "further", label: "Further workflows" }, + { id: "sources", label: "Sources" }, + ], + }, + ]; +} + +/** Union of recipe kits for the chapter "What you need" strip. */ +export function collectChapterKit(recipes) { + const tools = []; + const files = []; + const models = []; + const add = (arr, value) => { + if (value && !arr.includes(value)) arr.push(value); + }; + recipes.forEach((r) => { + const k = r.kit || {}; + (k.tools || []).forEach((item) => add(tools, item)); + (k.files || []).forEach((item) => add(files, item)); + add(models, k.model); + }); + return { + tools, + files, + models, + tryits: recipes.map((r) => ({ + id: r.id, + time: r.time, + cost: r.cost, + artifact: r.kit && r.kit.artifact, + })), + }; +} diff --git a/marketing-site/next.config.mjs b/marketing-site/next.config.mjs index d3e18fc..847a3f0 100644 --- a/marketing-site/next.config.mjs +++ b/marketing-site/next.config.mjs @@ -1,9 +1,6 @@ /** @type {import('next').NextConfig} */ const nextConfig = { reactStrictMode: true, - // Deploy layer (deploy/docker/Dockerfile) builds the standalone - // output. No runtime behavior change for preview/dev. - output: 'standalone', // A stray package-lock.json sits at the repo root; pin the workspace root here // so Turbopack doesn't infer the wrong one. turbopack: { diff --git a/marketing-site/package.json b/marketing-site/package.json index 9595a6d..9d3de0a 100644 --- a/marketing-site/package.json +++ b/marketing-site/package.json @@ -2,7 +2,7 @@ "name": "aibook-fun-marketing", "version": "1.0.0", "private": true, - "description": "AIBook.fun — pre-launch marketing site (field-guide design)", + "description": "AiBook.fun — pre-launch marketing site (field-guide design)", "license": "MIT", "scripts": { "dev": "next dev -p 3000", diff --git a/marketing-site/pages/index.jsx b/marketing-site/pages/index.jsx index 68c3ab7..5fb1b65 100644 --- a/marketing-site/pages/index.jsx +++ b/marketing-site/pages/index.jsx @@ -18,10 +18,10 @@ export default function Home() { return ( <> - AIBook.fun — a field guide to AI agents at work + AiBook.fun · a field guide to AI agents at work diff --git a/marketing-site/pages/read/index.jsx b/marketing-site/pages/read/index.jsx new file mode 100644 index 0000000..8e1313e --- /dev/null +++ b/marketing-site/pages/read/index.jsx @@ -0,0 +1,56 @@ +import Head from "next/head"; +import Link from "next/link"; +import ReaderNav from "../../components/reader/ReaderNav"; +import ReaderFooter from "../../components/reader/ReaderFooter"; +import { LIBRARY, RECIPES } from "../../data/sample-chapter"; + +export default function ReadLibrary() { + return ( + <> + + Library · AiBook.fun reading demo + + + + + +
+
+
+ Reading demo · not the live book +

Library

+

+ Six verticals for the 2026 edition. +

+
+ {LIBRARY.map((item) => + item.status === "ready" ? ( + + {item.num} + {item.name} + {item.desc} + {RECIPES.length} workflows + + + ) : ( +
+ {item.num} + {item.name} + {item.desc} + Coming +
+ ) + )} +
+
+
+
+ + + ); +} diff --git a/marketing-site/pages/read/real-estate.jsx b/marketing-site/pages/read/real-estate.jsx new file mode 100644 index 0000000..48caebd --- /dev/null +++ b/marketing-site/pages/read/real-estate.jsx @@ -0,0 +1,208 @@ +import { useEffect, useMemo } from "react"; +import Head from "next/head"; +import ReaderNav from "../../components/reader/ReaderNav"; +import ReaderCrumbs from "../../components/reader/ReaderCrumbs"; +import ReaderFooter from "../../components/reader/ReaderFooter"; +import WorkflowBlock from "../../components/reader/WorkflowBlock"; +import ChapterOutline from "../../components/reader/ChapterOutline"; +import WorkflowRail from "../../components/reader/WorkflowRail"; +import ChapterKit from "../../components/reader/ChapterKit"; +import useActivation from "../../components/reader/useActivation"; +import { CHAPTER, RECIPES, buildOutline } from "../../data/sample-chapter"; + +const RECIPE_IDS = RECIPES.map((r) => r.id); +const ESSAY_KEYS = ["stakes", "constraints", "practice"]; + +function Essay({ id, heading, paragraphs }) { + return ( +
+

{heading}

+ {paragraphs.map((p) => ( +

{p}

+ ))} +
+ ); +} + +export default function RealEstateChapter() { + const { complete, toggle, count, total } = useActivation(RECIPE_IDS); + const [first, second] = RECIPES; + const outline = useMemo(() => buildOutline(CHAPTER, RECIPES), []); + const essayGroup = outline.find((g) => g.label === "Essay"); + const workflowGroup = outline.find((g) => g.label === "Workflows"); + + useEffect(() => { + const hash = window.location.hash; + if (!hash) return; + const el = document.getElementById(hash.slice(1)); + if (el) el.scrollIntoView({ behavior: "smooth", block: "start" }); + }, []); + + return ( + <> + + {CHAPTER.title} · AiBook.fun reading demo + + + + + + +
+
+
+ +
+
+ + +
+ Reading demo · not the live book +

+ {CHAPTER.vertical} · {CHAPTER.edition} edition +

+

{CHAPTER.title}

+

{CHAPTER.authors}

+ + + +

{CHAPTER.promise}

+ + + +
+

What's in this chapter

+
+

Essay

+
    + {essayGroup.items.map((item) => ( +
  • + {item.label} +
  • + ))} +
+
+
+

Workflows

+ +
+
+ +
+ Skip to a Try-it + {RECIPES.map((r) => ( + + {r.id} + {r.shortTitle} + + ))} +
+ + {ESSAY_KEYS.map((key) => ( + + ))} + +

+ Workflow 1 of {RECIPES.length} in this chapter +

+ + + + +

+ Workflow 2 of {RECIPES.length} in this chapter +

+ + +
+

Further workflows in this vertical

+
    + {CHAPTER.further.map((item) => ( +
  • + {item.coming ? ( + <> + + {item.id} + {" "} + {item.title} + + ) : ( + <> + + + {item.id} + + {" "} + {item.title} + + )} +
  • + ))} +
+
+ +
+

Sources

+
    + {CHAPTER.sources.map((s) => ( +
  • {s}
  • + ))} +
+

Last updated: {CHAPTER.lastUpdated}

+
+
+ + +
+
+
+ + + ); +} diff --git a/marketing-site/pages/read/recipe/[id].jsx b/marketing-site/pages/read/recipe/[id].jsx new file mode 100644 index 0000000..7da3e80 --- /dev/null +++ b/marketing-site/pages/read/recipe/[id].jsx @@ -0,0 +1,91 @@ +import Head from "next/head"; +import Link from "next/link"; +import { useRouter } from "next/router"; +import ReaderNav from "../../../components/reader/ReaderNav"; +import ReaderCrumbs from "../../../components/reader/ReaderCrumbs"; +import ReaderFooter from "../../../components/reader/ReaderFooter"; +import WorkflowBlock from "../../../components/reader/WorkflowBlock"; +import useActivation from "../../../components/reader/useActivation"; +import { RECIPES, RECIPES_BY_ID } from "../../../data/sample-chapter"; + +export default function RecipeFocus() { + const router = useRouter(); + const raw = typeof router.query.id === "string" ? router.query.id : ""; + const recipe = RECIPES_BY_ID[raw] || RECIPES_BY_ID[raw.toUpperCase()] || null; + const { complete, toggle } = useActivation(recipe ? [recipe.id] : []); + + if (!router.isReady) { + return ( + <> + +
+
+

Loading recipe…

+
+
+ + ); + } + + if (!recipe) { + return ( + <> + + Recipe not in this demo · AiBook.fun + + + +
+
+ Reading demo · not the live book +

This recipe is not in the sample.

+

+ The demo ships two nested workflows, RE-01 and RE-02, inside the Real + Estate chapter. +

+

+ + Back to the chapter + +

+
+
+ + + ); + } + + return ( + <> + + {`${recipe.id} on paper · AiBook.fun reading demo`} + + + + + +
+
+ + Reading demo · not the live book +

Print / focus view

+ r.id === recipe.id) + 1, 1)} + total={RECIPES.length} + complete={!!complete[recipe.id]} + onToggleComplete={toggle} + focused + /> +
+
+ + + ); +} diff --git a/marketing-site/public/samples/sample_comps.json b/marketing-site/public/samples/sample_comps.json new file mode 100644 index 0000000..9382b09 --- /dev/null +++ b/marketing-site/public/samples/sample_comps.json @@ -0,0 +1,19 @@ +{ + "note": "Public comps only. No CRM fields, no owner names, no phones, no showing lists.", + "block": "14xx Cedar (sample street)", + "subject": { + "beds": 3, + "baths": 2, + "sqft": 1320, + "year_kitchen": 2019, + "lot": "corner, public record" + }, + "comps": [ + { "id": "C1", "closed_price_sqft": 398, "dom": 19, "beds": 3, "baths": 2, "closed_days_ago": 18 }, + { "id": "C2", "closed_price_sqft": 441, "dom": 11, "beds": 3, "baths": 2, "closed_days_ago": 27 }, + { "id": "C3", "closed_price_sqft": 412, "dom": 22, "beds": 3, "baths": 2, "closed_days_ago": 41 }, + { "id": "C4", "closed_price_sqft": 425, "dom": 16, "beds": 3, "baths": 3, "closed_days_ago": 9 }, + { "id": "C5", "closed_price_sqft": 405, "dom": 28, "beds": 2, "baths": 2, "closed_days_ago": 55 }, + { "id": "C6", "closed_price_sqft": 433, "dom": 14, "beds": 3, "baths": 2, "closed_days_ago": 33 } + ] +} diff --git a/marketing-site/public/samples/sample_listings.csv b/marketing-site/public/samples/sample_listings.csv new file mode 100644 index 0000000..b49e378 --- /dev/null +++ b/marketing-site/public/samples/sample_listings.csv @@ -0,0 +1,7 @@ +id,neighborhood,list_price,sqft,dom,owner_name,phone,exact_address,beds,baths +MH-01,Maple Heights,504000,1200,18,Jane Client,555-0140,12 Oak Street,3,2 +MH-02,Maple Heights,612000,1450,24,Sam Owner,555-0141,88 Birch Avenue,3,2 +MH-03,Maple Heights,459000,1100,31,R. Patel,555-0142,4 Cedar Court,2,2 +MH-04,Maple Heights,670000,1580,12,Lee Family Trust,555-0143,21 Maple Drive,4,3 +MH-05,Maple Heights,538000,1288,22,A. Gomez,555-0144,9 Pine Lane,3,2 +MH-06,Maple Heights,481000,1140,27,Hidden,555-0145,16 Walnut Place,3,1 diff --git a/marketing-site/styles/globals.css b/marketing-site/styles/globals.css index 16269a3..1aa5dba 100644 --- a/marketing-site/styles/globals.css +++ b/marketing-site/styles/globals.css @@ -1,7 +1,7 @@ @import "tailwindcss"; /* ============================================================ - AIBook.fun — "field guide" design system + AiBook.fun — "field guide" design system Tokens live in @theme so they're available BOTH as CSS vars (var(--color-pine)) and as Tailwind utilities (bg-pine, font-display). ============================================================ */ @@ -104,21 +104,33 @@ h1, h2, h3 { text-wrap: balance; margin: 0; } /* ============ NAV ============ */ .nav { position: sticky; top: 0; z-index: 50; - background: color-mix(in srgb, var(--color-paper) 82%, transparent); - backdrop-filter: blur(14px) saturate(1.3); -webkit-backdrop-filter: blur(14px) saturate(1.3); + background: var(--color-paper); border-bottom: 1px solid transparent; transition: border-color 0.3s, box-shadow 0.3s; } .nav.scrolled { border-bottom-color: var(--color-line); box-shadow: var(--sh-sm); } .nav-in { + position: relative; max-width: var(--wrap); margin: 0 auto; padding: 0 28px; height: 68px; display: flex; align-items: center; justify-content: space-between; gap: 20px; } -.logo { display: flex; align-items: baseline; gap: 2px; font-family: var(--font-display); font-weight: 900; font-size: 21px; letter-spacing: -0.02em; } +.logo { + display: flex; align-items: baseline; gap: 2px; + font-family: var(--font-display); font-weight: 900; font-size: 21px; letter-spacing: -0.02em; + flex: none; position: relative; z-index: 1; +} .logo b { color: var(--color-pine); } .logo .dot { color: var(--color-muted); font-weight: 500; } -.nav-links { display: flex; align-items: center; gap: 30px; font-size: 14.5px; font-weight: 600; color: var(--color-muted); } +.nav-links { + display: flex; align-items: center; gap: 30px; + font-size: 14.5px; font-weight: 600; color: var(--color-muted); + position: absolute; left: 50%; transform: translateX(-50%); +} .nav-links a { transition: color 0.18s; } .nav-links a:hover { color: var(--color-ink); } +.nav-actions { + display: flex; align-items: center; gap: 10px; + flex: none; margin-left: auto; position: relative; z-index: 1; +} .nav-cta { font-size: 14px; padding: 10px 18px; } /* mobile hamburger toggle (hidden on desktop) */ @@ -144,6 +156,7 @@ h1, h2, h3 { text-wrap: balance; margin: 0; } @media (max-width: 860px) { .nav-links { display: none; } + .nav-actions { display: none; } .nav-cta { display: none; } /* CTA moves into the menu */ .nav-toggle { display: inline-flex; } .nav-menu { @@ -281,7 +294,7 @@ h1, h2, h3 { text-wrap: balance; margin: 0; } /* ============ RECIPE (value centerpiece) ============ */ .recipe-head { max-width: 40rem; margin-bottom: 44px; } -.recipe-head h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(2rem, 4.3vw, 3.3rem); letter-spacing: -0.025em; line-height: 1.02; margin: 16px 0 18px; } +.recipe-head h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(2rem, 4.3vw, 3.3rem); letter-spacing: -0.025em; line-height: 1.15; margin: 16px 0 18px; } .recipe-head p { color: var(--color-muted); font-size: 1.08rem; } .recipe { background: var(--color-card); border: 1px solid var(--color-line); border-radius: 20px; box-shadow: var(--sh-lg); overflow: hidden; } .recipe-top { display: flex; align-items: center; justify-content: space-between; gap: 16px; padding: 20px 28px; border-bottom: 1px solid var(--color-line); background: linear-gradient(var(--color-card), var(--color-paper)); } @@ -327,7 +340,7 @@ h1, h2, h3 { text-wrap: balance; margin: 0; } /* ============ CONTENTS (table-of-contents) ============ */ .contents { background: var(--color-paper-2); border-top: 1px solid var(--color-line); border-bottom: 1px solid var(--color-line); } -.contents h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(1.9rem, 4vw, 3rem); letter-spacing: -0.025em; margin: 14px 0 34px; max-width: 20ch; } +.contents h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(1.9rem, 4vw, 3rem); letter-spacing: -0.025em; line-height: 1.2; margin: 14px 0 34px; max-width: 20ch; } .toc { border-top: 1px solid var(--color-line-2); } .toc a { display: grid; grid-template-columns: 52px 1fr auto auto; align-items: center; gap: 20px; padding: 22px 8px; border-bottom: 1px solid var(--color-line); transition: background 0.2s, padding 0.2s; } .toc a:hover { background: var(--color-pine-wash); padding-left: 16px; } @@ -352,7 +365,7 @@ h1, h2, h3 { text-wrap: balance; margin: 0; } @media (max-width: 600px) { .letter-in { padding: 0 20px; } } /* ============ AUTHORS ============ */ -.authors h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(1.9rem, 3.6vw, 2.7rem); letter-spacing: -0.025em; margin: 14px 0 10px; } +.authors h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(1.9rem, 3.6vw, 2.7rem); letter-spacing: -0.025em; line-height: 1.2; margin: 14px 0 10px; } .authors .lede { color: var(--color-muted); max-width: 38rem; margin-bottom: 38px; } .auth-grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 14px; } .auth { background: var(--color-card); border: 1px solid var(--color-line); border-radius: 16px; padding: 24px; box-shadow: var(--sh-sm); transition: box-shadow 0.2s, transform 0.2s; } @@ -372,7 +385,7 @@ h1, h2, h3 { text-wrap: balance; margin: 0; } /* ============ EMAIL CAPTURE ============ */ .capture { background: var(--color-paper-2); border-top: 1px solid var(--color-line); border-bottom: 1px solid var(--color-line); } .capture-in { max-width: 640px; margin: 0 auto; text-align: center; padding: 0 28px; } -.capture h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(2rem, 4vw, 3rem); letter-spacing: -0.025em; line-height: 1.02; margin: 16px 0 14px; } +.capture h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(2rem, 4vw, 3rem); letter-spacing: -0.025em; line-height: 1.15; margin: 16px 0 14px; } .capture p { color: var(--color-muted); font-size: 1.06rem; margin-bottom: 28px; } .capture form { display: flex; gap: 10px; flex-wrap: wrap; justify-content: center; } .capture .fine { font-family: var(--font-mono); font-size: 11.5px; color: var(--color-muted); margin-top: 18px; } @@ -381,7 +394,7 @@ h1, h2, h3 { text-wrap: balance; margin: 0; } /* ============ TIERS PREVIEW ============ */ .tiers-head { display: flex; align-items: flex-end; justify-content: space-between; gap: 20px; flex-wrap: wrap; margin-bottom: 34px; } -.tiers-head h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(1.9rem, 3.6vw, 2.7rem); letter-spacing: -0.025em; margin: 12px 0 0; } +.tiers-head h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(1.9rem, 3.6vw, 2.7rem); letter-spacing: -0.025em; line-height: 1.2; margin: 12px 0 0; } .tiers-note { font-family: var(--font-mono); font-size: 12px; color: var(--color-muted); max-width: 22rem; text-align: right; line-height: 1.6; } .tier-grid { display: grid; grid-template-columns: repeat(3, 1fr); gap: 14px; } .tier { background: var(--color-card); border: 1px solid var(--color-line); border-radius: 18px; padding: 30px 26px; display: flex; flex-direction: column; transition: box-shadow 0.2s, transform 0.2s; } @@ -399,7 +412,7 @@ h1, h2, h3 { text-wrap: balance; margin: 0; } @media (max-width: 820px) { .tier-grid { grid-template-columns: 1fr; } .tiers-note { text-align: left; } } /* ============ FAQ ============ */ -.faq h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(1.9rem, 3.6vw, 2.7rem); letter-spacing: -0.025em; margin-bottom: 34px; } +.faq h2 { font-family: var(--font-display); font-weight: 900; font-size: clamp(1.9rem, 3.6vw, 2.7rem); letter-spacing: -0.025em; line-height: 1.2; margin-bottom: 34px; } .qa { border-top: 1px solid var(--color-line); } .qa details { border-bottom: 1px solid var(--color-line); padding: 6px 0; } .qa summary { cursor: pointer; list-style: none; padding: 20px 0; display: flex; align-items: center; justify-content: space-between; gap: 20px; font-family: var(--font-display); font-weight: 600; font-size: 1.2rem; letter-spacing: -0.02em; } @@ -421,3 +434,446 @@ h1, h2, h3 { text-wrap: balance; margin: 0; } .foot-links a:hover { color: #f7f5f0; } .colophon { padding-top: 26px; font-family: var(--font-mono); font-size: 11.5px; color: #7a7266; letter-spacing: 0.02em; line-height: 1.8; } @media (max-width: 600px) { .foot-in { padding: 48px 20px 40px; } } + +/* ============ READER DEMO ============ */ +/* Layout the landing page does not already have. Reader pages use a wider wrap. + Same tokens, same ~20px cards and 999px pills. Do not restyle the homepage recipe. */ + +.demo-chip { + display: inline-flex; align-items: center; gap: 8px; + font-family: var(--font-mono); font-size: 11px; font-weight: 500; + letter-spacing: 0.12em; text-transform: uppercase; + color: var(--color-amber); + background: rgba(180, 121, 31, 0.08); + border: 1px solid rgba(180, 121, 31, 0.22); + padding: 5px 12px; border-radius: 999px; + margin-bottom: 22px; +} + + +.reader-nav .nav-in, +.reader-footer .foot-in, +.wrap.reader-wide { + max-width: min(1520px, calc(100vw - 40px)); +} + + +.crumbs { + padding: 4px 0 18px; + font-size: 13.5px; +} +.crumbs ol { + display: flex; flex-wrap: wrap; align-items: center; + list-style: none; margin: 0; padding: 0; +} +.crumbs li { display: flex; align-items: center; } +.crumbs-sep { + margin: 0 10px; color: var(--color-muted); font-weight: 400; +} +.crumbs a { color: var(--color-pine); font-weight: 600; } +.crumbs a:hover { color: var(--color-pine-deep); } +.crumbs [aria-current="page"] { color: var(--color-ink); font-weight: 600; } + +.reader-nav .nav-title { + font-size: 14.5px; font-weight: 600; color: var(--color-ink); +} +.reader-nav .nav-title:hover { color: var(--color-pine); } + +.reader-nav .reader-links { gap: 22px; } +.reader-nav .nav-current { + font-size: 14.5px; font-weight: 600; color: var(--color-ink); + max-width: 22ch; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; +} +@media (max-width: 860px) { + .reader-nav .nav-links { + display: flex; align-items: center; gap: 16px; font-size: 13.5px; + } + .reader-nav .nav-cta { + display: inline-flex; font-size: 13px; padding: 8px 14px; + } + .reader-nav .nav-current { display: none; } + .reader-nav .nav-toggle { display: none; } +} + +.chapter-page { padding: 48px 0 96px; } +.chapter-shell { + display: grid; + grid-template-columns: 240px minmax(0, 1fr); + gap: 32px 40px; + align-items: start; +} +@media (min-width: 1080px) { + .chapter-shell { + grid-template-columns: 240px minmax(0, 1fr) 280px; + } +} +.chapter-col { min-width: 0; } +.chapter-kicker { margin: 8px 0 14px; } +.chapter-title { + font-family: var(--font-display); font-weight: 900; + font-size: clamp(2.1rem, 4.6vw, 3.4rem); + letter-spacing: -0.028em; line-height: 1.15; margin: 0 0 12px; + max-width: 22ch; +} +.chapter-by { + font-family: var(--font-mono); font-size: 12.5px; color: var(--color-muted); + letter-spacing: 0.04em; margin-bottom: 20px; +} +.chapter-promise { + font-size: 1.12rem; line-height: 1.62; color: var(--color-ink); margin: 0 0 28px; + max-width: 46rem; +} + +.chapter-outline { + position: sticky; + top: 68px; + z-index: 30; + align-self: start; + background: var(--color-paper); + border-right: 1px solid var(--color-line); + padding: 16px 20px 28px 0; + max-height: calc(100vh - 68px); + overflow-y: auto; +} +.outline-progress { + font-family: var(--font-mono); font-size: 11.5px; color: var(--color-muted); + letter-spacing: 0.04em; margin: 0 0 14px; +} +.outline-heading { + font-family: var(--font-display); font-weight: 600; + font-size: 1.08rem; letter-spacing: -0.02em; margin: 0 0 16px; +} +.outline-group { margin: 0 0 18px; } +.outline-group:last-child { margin-bottom: 0; } +.outline-group-label { margin: 0 0 8px; } +.outline-group ul { list-style: none; margin: 0; padding: 0; } +.outline-group li { margin: 0; } +.outline-group a { + display: flex; align-items: baseline; justify-content: space-between; gap: 8px; + padding: 5px 0 5px 10px; + border-left: 2px solid transparent; + font-size: 13.5px; line-height: 1.35; color: var(--color-muted); +} +.outline-group a:hover { color: var(--color-ink); } +.outline-group a.is-active { + color: var(--color-pine); border-left-color: var(--color-pine); font-weight: 600; +} +.outline-done { + font-family: var(--font-mono); font-size: 12px; color: var(--color-pine); flex: none; +} + + +.chapter-rail { + position: sticky; + top: 84px; + align-self: start; + display: none; +} +@media (min-width: 1080px) { + .chapter-rail { display: block; } +} +.chapter-rail .spec { margin: 0 0 14px; } +.rail-list { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 12px; } +.rail-card { + display: flex; flex-direction: column; gap: 6px; + padding: 16px 18px; + background: var(--color-card); + border: 1px solid var(--color-line); + border-radius: 16px; + box-shadow: var(--sh-sm); + transition: border-color 0.18s, transform 0.14s var(--ease), box-shadow 0.18s; +} +.rail-card:hover { + border-color: var(--color-pine-tint); + transform: translateY(-1px); + box-shadow: var(--sh-md); +} +.rail-card.is-done { border-color: var(--color-pine-tint); background: var(--color-pine-wash); } +.rail-kicker { + font-family: var(--font-mono); font-size: 11px; letter-spacing: 0.1em; + text-transform: uppercase; color: var(--color-pine); +} +.rail-title { + font-family: var(--font-display); font-weight: 600; + font-size: 1.15rem; letter-spacing: -0.02em; line-height: 1.2; + color: var(--color-ink); +} +.rail-meta { + font-family: var(--font-mono); font-size: 12px; color: var(--color-muted); + letter-spacing: 0.02em; +} +.rail-skip { + display: inline-block; margin-top: 16px; + font-family: var(--font-mono); font-size: 12.5px; font-weight: 600; + color: var(--color-pine); +} +.rail-skip:hover { color: var(--color-pine-deep); } + +.chapter-outline-mobile { + margin: 0 0 24px; + padding: 10px 16px 12px; + border: 1px solid var(--color-line); + border-radius: 12px; + background: var(--color-card); +} +.chapter-outline-mobile summary { + cursor: pointer; list-style: none; + font-family: var(--font-display); font-weight: 600; + font-size: 1.05rem; letter-spacing: -0.02em; + padding: 6px 0; +} +.chapter-outline-mobile summary::-webkit-details-marker { display: none; } +.chapter-outline-mobile[open] summary { margin-bottom: 10px; } +.chapter-outline-mobile .outline-progress { margin-top: 4px; } + + +.chapter-kit { + margin: 0 0 28px; + padding: 18px 20px 16px; + background: var(--color-pine-wash); + border: 1px solid var(--color-pine-tint); + border-radius: 16px; +} +.chapter-kit-title { + font-family: var(--font-display); font-weight: 600; + font-size: 1.2rem; letter-spacing: -0.02em; + margin: 0 0 6px; +} +.chapter-kit-lede { + font-size: 14.5px; color: var(--color-muted); + margin: 0 0 16px; +} +.kit-grid { + display: grid; + grid-template-columns: 1fr 1fr; + gap: 14px 28px; + margin: 0; +} +@media (min-width: 900px) { + .kit-grid { grid-template-columns: repeat(4, minmax(0, 1fr)); } +} +@media (max-width: 720px) { + .kit-grid { grid-template-columns: 1fr; } +} +.kit-grid dt { + font-family: var(--font-mono); font-size: 11px; font-weight: 500; + letter-spacing: 0.12em; text-transform: uppercase; + color: var(--color-pine); margin: 0 0 6px; +} +.kit-grid dd { margin: 0; font-size: 14.5px; line-height: 1.4; color: var(--color-ink); } +.kit-grid ul { list-style: none; margin: 0; padding: 0; } +.kit-grid li { margin: 0 0 4px; } +.kit-grid li:last-child { margin-bottom: 0; } + +.workflow-kit { + display: grid; + grid-template-columns: repeat(auto-fit, minmax(132px, 1fr)); + gap: 12px 16px; + margin: 4px 0 8px; + padding: 14px 0 16px; + border-bottom: 1px dashed var(--color-line-2); +} +.workflow-kit dt { + font-family: var(--font-mono); font-size: 11px; font-weight: 500; + letter-spacing: 0.1em; text-transform: uppercase; + color: var(--color-pine); margin: 0 0 4px; +} +.workflow-kit dd { + margin: 0; font-size: 14px; line-height: 1.4; color: var(--color-ink); +} + +.rail-kit { + font-size: 12.5px; line-height: 1.35; color: var(--color-muted); +} +.rail-out { color: var(--color-ink); } + +.chapter-map { + display: grid; + grid-template-columns: 1fr 1fr; + gap: 8px 40px; + margin: 0 0 8px; + padding: 18px 0 6px; + border-top: 1px solid var(--color-line); +} +.chapter-map-title { grid-column: 1 / -1; } +@media (max-width: 720px) { + .chapter-map { grid-template-columns: 1fr; } +} +.chapter-map-title { + font-family: var(--font-display); font-weight: 600; + font-size: 1.2rem; letter-spacing: -0.02em; + margin: 0 0 16px; +} +.chapter-map-block { margin: 0 0 16px; } +.chapter-map-block .spec { margin: 0 0 8px; } +.chapter-map-block ul { margin: 0; padding: 0 0 0 1.1em; } +.chapter-map-block li { margin: 0 0 6px; } +.chapter-map-block a { color: var(--color-pine); font-weight: 600; } +.chapter-map-block a:hover { color: var(--color-pine-deep); } + +.skip-row { + display: flex; flex-wrap: wrap; align-items: center; gap: 10px; + margin: 0 0 48px; padding: 16px 0; + border-top: 1px dashed var(--color-line-2); + border-bottom: 1px dashed var(--color-line-2); +} +.skip-label { + font-family: var(--font-mono); font-size: 11.5px; font-weight: 500; + letter-spacing: 0.12em; text-transform: uppercase; color: var(--color-pine); + margin-right: 4px; +} +.skip-chip { + display: inline-flex; align-items: baseline; gap: 8px; + font-family: var(--font-mono); font-size: 12.5px; color: var(--color-pine); + background: var(--color-pine-wash); border: 1px solid var(--color-pine-tint); + padding: 7px 13px; border-radius: 999px; + transition: background 0.18s, transform 0.14s var(--ease); +} +.skip-chip:hover { background: var(--color-pine-tint); transform: translateY(-1px); } +.skip-chip:focus-visible { outline: 2px solid var(--color-pine); outline-offset: 3px; } +.skip-chip-job { + font-family: var(--font-body); font-size: 13px; font-weight: 600; + color: var(--color-ink); letter-spacing: 0; text-transform: none; +} + +.essay, +.recipe-nested, +.end-matter, +.end-sources, +.recipe-nested .row { + scroll-margin-top: 88px; +} + +.essay { margin: 0 0 36px; max-width: 46rem; } +.essay h2 { + font-family: var(--font-display); font-weight: 600; + font-size: 1.45rem; letter-spacing: -0.02em; line-height: 1.2; + margin: 0 0 12px; +} +.essay p { color: var(--color-ink); margin: 0 0 14px; } +.essay p:last-child { margin-bottom: 0; } + +.workflow-kicker { margin: 8px 0 10px; } + +.recipe-nested { + margin: 0 0 52px; +} +.recipe-nested .step-copy { min-width: 0; flex: 1; } +.recipe-nested .step-copy .term { margin-top: 12px; } +.recipe-nested h4.k { margin: 0; font-weight: 500; } +.recipe-nested .term { + overflow-x: auto; + overflow-y: hidden; +} +.recipe-nested .term pre { overflow-x: auto; } + +.recipe-jump { + display: flex; flex-wrap: wrap; gap: 8px 16px; + margin: 0 0 8px; padding: 0 0 16px; + border-bottom: 1px dashed var(--color-line-2); + font-size: 13.5px; +} +.recipe-jump a { color: var(--color-pine); font-weight: 600; } +.recipe-jump a:hover { color: var(--color-pine-deep); } +.recipe-jump a:focus-visible { outline: 2px solid var(--color-pine); outline-offset: 2px; } + +.plain-list { margin: 0; padding: 0 0 0 1.1em; } +.plain-list li { margin: 0 0 6px; } +.plain-list li:last-child { margin-bottom: 0; } + +.evidence-p { margin: 0 0 10px; } +.evidence-p:last-child { margin-bottom: 0; } +.sub-line { color: var(--color-muted); font-size: 14.5px; margin: 8px 0 12px; } +.inline-sample { + font-family: var(--font-mono); font-size: 13px; color: var(--color-pine); + border-bottom: 1px solid var(--color-pine-tint); +} +.inline-sample:hover { color: var(--color-pine-deep); } + +.tryit-actions { display: flex; flex-wrap: wrap; gap: 10px; margin-top: 14px; } +.tryit-actions .btn { font-size: 14px; padding: 11px 18px; } +.tryit-done { gap: 8px; } +.recipe-record { + display: flex; flex-direction: column; gap: 6px; + font-size: 14.5px; color: var(--color-muted); +} +.recipe-record a { color: var(--color-pine); font-weight: 600; } +.recipe-record a:hover { color: var(--color-pine-deep); } + +.end-matter { + margin-top: 56px; padding-top: 28px; + border-top: 1px solid var(--color-line); +} +.end-sources { margin-top: 32px; } +.end-matter h2, +.end-sources h2 { + font-family: var(--font-display); font-weight: 600; + font-size: 1.35rem; letter-spacing: -0.02em; margin: 0 0 12px; +} +.end-matter h2 + .further-list { margin-bottom: 8px; } +.further-list { margin: 0 0 8px; padding: 0 0 0 1.1em; color: var(--color-ink); } +.further-list li { margin: 0 0 8px; } +.further-list a { color: var(--color-pine); font-weight: 600; } +.chapter-updated { + font-family: var(--font-mono); font-size: 12px; color: var(--color-muted); + letter-spacing: 0.04em; margin-top: 18px; +} + +.library-title { + font-family: var(--font-display); font-weight: 900; + font-size: clamp(1.9rem, 4vw, 3rem); letter-spacing: -0.025em; + line-height: 1.15; margin: 14px 0 16px; + white-space: nowrap; +} +.library-lede { color: var(--color-muted); max-width: 38rem; margin-bottom: 34px; } + +.toc .toc-soon { + display: grid; grid-template-columns: 52px 1fr auto auto; + align-items: center; gap: 20px; padding: 22px 8px; + border-bottom: 1px solid var(--color-line); + color: var(--color-muted); +} +.toc .soon { + font-family: var(--font-mono); font-size: 11px; letter-spacing: 0.12em; + text-transform: uppercase; color: var(--color-muted); + background: var(--color-card); border: 1px solid var(--color-line); + padding: 4px 10px; border-radius: 999px; white-space: nowrap; +} +.reader-library .toc a { + grid-template-columns: 52px 1fr auto auto auto; +} +.toc-count { + font-family: var(--font-mono); font-size: 11.5px; font-weight: 500; + letter-spacing: 0.08em; text-transform: uppercase; + color: var(--color-pine); white-space: nowrap; +} +@media (max-width: 720px) { + .toc .toc-soon .desc { display: none; } + .toc .toc-soon { grid-template-columns: 40px 1fr auto; } + .reader-library .toc a { grid-template-columns: 40px 1fr auto auto; } +} + +.recipe-focus-page { padding: 40px 0 96px; } +.recipe-focus-page .demo-chip { margin-bottom: 12px; } +.recipe-focus-page .recipe { max-width: none; } +.focus-back { + font-family: var(--font-mono); font-size: 13px; color: var(--color-muted); + margin: 0 0 28px; +} +.focus-back a { color: var(--color-pine); font-weight: 600; } + +@media (max-width: 959px) { + .chapter-shell { grid-template-columns: 1fr; gap: 0; } + .chapter-outline { display: none; } + .chapter-rail { display: none; } +} +@media (min-width: 960px) { + .chapter-outline-mobile { display: none; } +} + +@media print { + .reader-nav, .chapter-outline, .chapter-outline-mobile, .chapter-rail, .reader-footer, .skip-row, .tryit-actions, .demo-chip, .recipe-jump { + display: none !important; + } + .recipe-nested { break-inside: avoid; box-shadow: none; } +} diff --git a/workflows/chapter-structure.md b/workflows/chapter-structure.md new file mode 100644 index 0000000..0014586 --- /dev/null +++ b/workflows/chapter-structure.md @@ -0,0 +1,224 @@ +--- +status: draft-for-review +type: chapter-template +edition: 2026 +vertical: # real-estate | financial-advisors | fractional-c-suite | higher-ed | communities | technology +title: "" +authors: [] +recipe_ids: [XX-01, XX-02] +last_updated: 2026-08-31 +--- + +# Chapter structure (for review) + +This is the blank chapter, matching PRD §5.4 (locked 2026-08-31). Review the shape before anyone writes a real vertical. + +**How to use it.** Copy this file to `workflows/[vertical-slug].md` (example: `workflows/real-estate.md`). Replace `XX` with the vertical prefix. Leave this file as the blank. + +**What a chapter is.** A substantial essay for one vertical. Full workflows sit inside the argument, at the point they earn, not in an appendix and not as a stack of cards. + +**What a workflow is.** The unit of practice. Read it, run the Try-it (~15 min), share the result. That Try-it is what counts as activation. + +**Rules that do not move.** +- Skip-to-Try-it at the top. Activation does not wait for the essay. +- Safeguards before Method. Data handling is read before anyone pastes a client list. +- Method shows real tool output, not a description of it. +- Nested recipes stay open. Do not hide Method behind "click to reveal." +- Every recipe has a stable ID and a heading it can link to. +- Every recipe names its kit (who runs it, tools, files, model, time, cost, artifact). The chapter page shows the union at the top and the kit on each nested recipe. +- No chatbot on the page. No crypto or Web3 language. +- PDF must match this stack: essay + in-place recipes. + +**Vertical prefixes** + +| Vertical | Slug | ID prefix | +|:--|:--|:--| +| Real Estate | `real-estate` | `RE` | +| Financial Advisors | `financial-advisors` | `FA` | +| Fractional C-Suite | `fractional-c-suite` | `CS` | +| Higher Ed | `higher-ed` | `HE` | +| Communities | `communities` | `CM` | +| Technology | `technology` | `TE` | + +Fill every `[bracket]`. Two nested recipes are shown so the essay-wraps-workflow pattern is obvious. Add more at the points in the argument they belong. Delete the unused slot rather than leaving a hollow block. + +--- + +# [Chapter title] + +[Vertical] · 2026 edition · [Author names] + +## What this chapter is for + +[One short promise. The job this vertical's reader is trying to get done this week, and what they will be able to run by the end of the chapter.] + +**Skip to a Try-it:** [XX-01](#xx-01) · [XX-02](#xx-02) + +## What you need + +The chapter page shows this before the essay. Union of the nested workflows. Named tools, sample files, Try-it time, sample-run cost. No live client data. + +- Tools: [named] +- Files: [named samples we ship] +- Model: [named, or "the model you already use"] +- Time: [each Try-it] +- Cost: [sample-run total, or "unknown"] + +## [Essay: the stakes] + +[Why this work is hard here. Specific to the vertical, not a generic AI preamble. Name the actual failure: a listing that stalls, a client file that leaks, a committee that will not move.] + +## [Essay: constraints] + +[What you cannot ignore in this vertical. Tools people already use. Compliance, clients, time. What "done" looks like for them.] + +## [Essay: how we work here] + +[The practice this chapter argues for. Then the first workflow, at the moment the argument needs proof.] + +--- + + + +### [Job title. This is the workflow title, written as the job.] + +**XX-01** · v0.1 · ~[N] min · ~$[cost or "free with tools you already have"] + +#### Kit + +Shown at the top of the nested recipe. Inventory, not instructions. Setup below still explains how to use these. + +- You run: [role] +- Tools: [named tools, versions if it matters] +- Files: [sample files we ship] +- Model: [named, or "the model you already use"] +- Time: ~[N] min +- Cost: [amount or "free with tools you already have"] +- You produce: [artifact] + +#### Problem + +[The real task. One job, not a category.] + +#### Actors + +- Who runs it: [role] +- Who is affected: [client, student, team] +- What the model is allowed to do: [draft / classify / retrieve]. What a human must still do: [send / approve / file] + +#### Setup + +- Tools: [named tools, versions if it matters] +- Sample files: [what we ship with this recipe, or "use the anonymized packet below"] +- Cost: [model/tool cost if known. If unknown, say so.] + +#### Safeguards + +Read this before the steps. + +- Data handling: [what never goes into the prompt. What is ok if stripped.] +- Human oversight: [the checkpoint before anything leaves the building] +- Failure modes: [how this goes wrong in this vertical] +- Escalation: [who you call, and when you stop] + +#### Method + +Ordered steps. Paste the actual tool output inside the step that produced it. A screenshot or a quoted block beats a paraphrase. + +1. [Step] + ``` + [real output] + ``` +2. [Step] +3. [Step] + +#### Evidence + +[What "it worked" looks like. An artifact, a number, a before/after. Not "the user felt more confident."] + +#### Try it (~15 min) + +- Sample data: [what they use so they do not need a live client] +- What to produce: [the artifact] +- Done when: [a check they can mark. Completing this is activation.] + +#### Share the result + +[What they post: the outcome, not the workflow text. Point at the community template when it exists. Events, not content.] + +**Author:** [name] · **Sources:** [links or citations] · **Last updated:** [date] + +--- + +## [Essay continues] + +[The argument picks back up. What the first recipe proved, what it did not. Then the next workflow, when the next claim needs proof.] + +--- + + + +### [Second job title] + +**XX-02** · v0.1 · ~[N] min · ~$[cost] + +#### Kit + +Shown at the top of the nested recipe. Inventory, not instructions. Setup below still explains how to use these. + +- You run: [role] +- Tools: [named tools, versions if it matters] +- Files: [sample files we ship] +- Model: [named, or "the model you already use"] +- Time: ~[N] min +- Cost: [amount or "free with tools you already have"] +- You produce: [artifact] + +#### Problem + +[ ] + +#### Actors + +[ ] + +#### Setup + +[ ] + +#### Safeguards + +[ ] + +#### Method + +1. [ ] +2. [ ] + +#### Evidence + +[ ] + +#### Try it (~15 min) + +[ ] + +#### Share the result + +[ ] + +**Author:** [name] · **Sources:** [ ] · **Last updated:** [date] + +--- + +## Further workflows in this vertical + +- [XX-01](#xx-01) — [job title] +- [XX-02](#xx-02) — [job title] +- [Later IDs, once assigned] + +## Sources + +[Chapter-level sources. Recipe-level citations stay on the recipe.] + +**Last updated:** 2026-08-31