Files
LlamaCasty/TASKS/task-10-monetization.md
T
gramps 7827d239e2 docs(commercial): one source of truth for the money — prices, entitlement, channels
The commercial plan was spread over five documents written in five different weeks,
and they contradicted each other: product.md sold the Store, decisions.md called the
Store dead then re-opened, Distribution.md (736 lines) still described Polar as a
download host, MARCOM.md quoted "no subscription" next to a paid tier, and README.md
promised "free forever". An outsider could not tell what ships.

docs/ai/commercial.md is now the only place money is decided: free = whole app at a
921,600 px / 30 fps output profile covering the recording as well as the stream; Pro =
$10/mo or $400 lifetime through Polar, key bound to the buyer's YouTube channel ID via
a claim page, 2 activations, 7–14 day lease with offline grace, fail closed, never
downgrade a running stream; one portable zip + winget primary, Steam and the Store
parked; Azure Trusted Signing (~$9.99/mo), no EV; Founding 200 promo; ~$135/yr costs;
anti-piracy posture and what is permanently rejected.

Everything else now points at it instead of restating it:
- product.md — money sections replaced with pointers; packaging rewritten to
  winget-first, Store parked; signing updated to Trusted Signing.
- decisions.md — graveyard with cause of death for free-forever, the Store ordering,
  the updater, and the 2026-10-30 reversal of the quality-ceiling rejection.
- Distribution.md — rewritten to release mechanics only (artifact, GitHub Releases,
  winget manifest, signing, checklist, takedown): 736 → 120 lines.
- TASKS.md — TASK 54 rewritten, TASK 48's route settled, TASK 10 superseded, five new
  rows (entitlement seam, output-profile gate, licence UI, system messages, packaging).
- README.md — "free forever" replaced with the real split.
- capture.md — obs-backgroundremoval is GPL-3.0 and so licence-INCOMPATIBLE since the
  proprietary EULA; the old "compatible" line was falsified by that change.
- TASKS/task-10, task-48, task-51, task-54 — superseded-banner at the top of each, so
  none of them reads as current policy.
- HANDOFF.md — rewritten: plan settled, next code unit is the entitlement seam.

MARCOM.md and MONETIZATION.md (gitignored) were corrected in place: policy pointer at
the top of each, the flash removed from every live claim, the Polar fee break-even
corrected to ~$900/mo, and the projections flagged as written against a dead model.
2026-10-31 08:32:25 -07:00

80 lines
5.7 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# TASK 10 — Monetization: watermark-only paid delta (branding flash)
> ⛔ **RETIRED — 2026-10-30.** Both halves of this file are dead: the watermark/branding-flash
> delta (retired 2026-10-30) and Store IAP as the billing provider (Store is parked, third channel,
> 2026-10-31). The paid delta is **output quality** now, sold through **Polar**. Live policy:
> [`docs/ai/commercial.md`](../docs/ai/commercial.md); cause of death:
> [`docs/ai/decisions.md`](../docs/ai/decisions.md). Nothing here is a build instruction.
> Catalog: [`TASKS.md`](../TASKS.md) — status and requirements live here.
**Goal:** a **paid tier that removes the branding flash and nothing else.** Every feature is free
— Alerts, social bar slots, voice filters, TRAX, recording, analytics. The free tier is the *full*
app. ⛔ **There is no feature gating, ever** — revenue argument, not taste: the free tier's reach
is the funnel, and the flash is an ad running inside other people's content, so a free user with a
flash every 30–60s is already paying in exposure.
**⚠️ STATUS: THIS IS A TEARDOWN, NOT A BUILD (2026-09-27).** The billing provider is
**Microsoft Store IAP**, not Polar. Everything below describing Polar is **dead** and is retained
only as history. **Do not resurrect any of it.** The teardown's file-by-file list lives in
[`TASKS/task-48-distribution-msix.md`](task-48-distribution-msix.md) item 0 — **work from there,
not from this file.**
**Pricing — ✅ DECIDED 2026-09-27: `$10/mo` subscription, or `$400` lifetime. No annual.**
| Tier | Price | Net after 15% | Role |
|---|---|---|---|
| Free | $0 | — | Everything, plus the branding flash. The funnel. |
| **Pro monthly** | **$10/mo** | ~$8.50/mo | The default. Low-risk entry. |
| **Pro lifetime** | **$400** | ~$340 | The hedge. Committed / subscription-hostile buyers. |
- **15% Store revenue share, subscriptions included** — verified from the ADA v8.10 PDF, §6(b)(i).
Net receipts are after VAT/GST, so commission is not paid on pass-through tax.
- **Break-even is month 40**, so the two tiers barely compete — which is why lifetime is safe to
offer at launch rather than saving it for later.
- ⛔ **No annual tier** — Microsoft does not pro-rate and the developer cannot refund the
forfeited remainder. ⛔ **No `.99` prices.** ⛔ **No discounted upgrade SKU.**
- **ADA §6(h): raising the price disables auto-renew ⇒ `$10` is effectively locked for life.**
- ⛔ **Superseded pricing, do not cite:** the 2026-09-21 one-time model (`$29` founder → `$49`
list lifetime) and the earlier `$49.99/yr → $99/yr` subscription.
**Related work — monetization awareness (2026-09-01, ungated, free):** this task's billing is the
*payer* side; the *product* also carries built-in, ungated monetization awareness for every creator —
reward-event capture (all 7 `liveChatMessage` reward event types → canonical `RewardEvent` → SQLite
persistence), per-session/broadcast reports (members, Super Chat $, stickers, gifts, milestones — the
in-app replacement for the emailed "stream activity report"), and a journey tracker (position % +
ETA vs. versioned, date-aware YPP thresholds; the Tier-2 bar doubles for new applicants 2027-02-01).
Details and design notes: `ai.md` → Monetization. This is tracked as related work under this task's
narrative, not a separate task number — it ships in its own code slices with one integration test each.
**Scope: v1** (2026-09-01 complete-v1 ruling — there is no v1.x): slice order = reward-event capture →
session report → journey tracker → Alerts (TASK 3 item 20).
**Business details (pricing, Partner Center product declaration) in `MONETIZATION.md` (gitignored).**
### Status: 🔶 TEARDOWN — steps 1–7 shipped under Polar, all now to be removed
Steps 1–7 below are a **record of what was built**, not a description of what ships. The Polar
licensing path is being deleted because Store IAP supplies the same bit from the OS entitlement.
1. ⛔ **Billing provider** — was Polar (polar.sh). **DELETED.** The product, checkout link, and the
discount codes `LLAMAFOUNDER` / `LLAMA50` no longer exist. Store IAP products are declared in
**Partner Center**, not Polar.
2. ⛔ **License key entry + verification UI** — was the About-overlay swap panel
("Enter License Key"). **DELETING.**
3. ⛔ **Offline entitlement** — was `LayoutStore` Settings (`LicenseKey`, `LicenseValidatedAt`,
`IsPremium`) + a 14-day offline grace period + startup re-validation. **DELETING.** The OS
supplies license state, so the entire offline-grace machine goes with it — along with the whole
"network flaky → app thinks I'm expired" bug class.
4. ✅ **BrandFlash → watermark toggle** — `IsPremium` setter flips `BrandFlashEnabled = !value`, so
the flash stops the moment the entitlement flips. **This survives the teardown.** Under Store IAP
`IsPremium` is derived from the Store entitlement rather than a remote HTTP call. One bit,
locally cached, refreshed by the OS. ⚠️ **This is the whole product surface of the paid tier.**
5. ✅ **Remove social slot locks** — all 6 social bar slots open to everyone. **Survives.**
6. ⛔ **"Unlock Premium" button** — `PremiumUrl` pointed at Polar checkout. **DELETING**; the Store
handles purchase. Paid users see zero license UI.
7. ⛔ **Licensing model / renewal-lapse path** — already dead before the Store ruling (a perpetual
key never expires). Now superseded again: **Store IAP has no keys at all.**
8. ✅ **Velopack auto-updates** — NuGet package + bootstrap in `App.xaml.cs`. **DELETED
2026-10-22 (TASK 48 slice 3)** — a compliance action, not cleanup: the updater downloaded
*and executed*, and Store policy 10.2.2 does not permit it. The Store updates the app
instead. Guard: `ytLive.Tests/StorePackagingTests.cs`.