islandflow/plans/synthetic-tape-redesign-impeccable.html

816 lines
33 KiB
HTML

<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<title>Hosted Synthetic Tape Redesign · Impeccable Version</title>
<style>
:root {
color-scheme: dark;
--bg: #0b0f13;
--bg-soft: #11161d;
--surface: rgba(14, 20, 27, 0.86);
--surface-strong: rgba(17, 24, 32, 0.96);
--line: rgba(151, 168, 186, 0.18);
--line-strong: rgba(151, 168, 186, 0.32);
--text: #ebf0f6;
--muted: #a0adbb;
--sage: #7cccb2;
--teal: #59b7c9;
--gold: #d5b26e;
--rose: #c78497;
--ink: #0a0d11;
--shadow: 0 24px 80px rgba(0, 0, 0, 0.34);
--radius-xl: 28px;
--radius-lg: 18px;
--radius-md: 14px;
}
* {
box-sizing: border-box;
}
html {
scroll-behavior: smooth;
}
body {
margin: 0;
font-family: "SF Pro Text", "Inter", "Segoe UI", sans-serif;
background:
radial-gradient(circle at 14% 12%, rgba(124, 204, 178, 0.12), transparent 24rem),
radial-gradient(circle at 86% 8%, rgba(89, 183, 201, 0.13), transparent 28rem),
linear-gradient(180deg, #091017, var(--bg) 32%, #0d1117 100%);
color: var(--text);
}
.shell {
width: min(1220px, calc(100vw - 1.5rem));
margin: 0 auto;
padding: 1.25rem 0 4rem;
}
.hero {
position: relative;
overflow: hidden;
border: 1px solid var(--line);
border-radius: 36px;
background:
linear-gradient(135deg, rgba(124, 204, 178, 0.1), transparent 26%),
linear-gradient(180deg, rgba(15, 21, 29, 0.95), rgba(10, 14, 19, 0.92));
box-shadow: var(--shadow);
padding: 2rem;
}
.hero::after {
content: "";
position: absolute;
inset: auto -6rem -7rem auto;
width: 18rem;
height: 18rem;
border-radius: 50%;
background: radial-gradient(circle, rgba(89, 183, 201, 0.18), transparent 70%);
pointer-events: none;
}
.hero-top {
display: flex;
flex-wrap: wrap;
gap: 0.75rem;
align-items: center;
margin-bottom: 1rem;
}
.pill {
display: inline-flex;
align-items: center;
gap: 0.5rem;
padding: 0.42rem 0.82rem;
border-radius: 999px;
border: 1px solid rgba(124, 204, 178, 0.22);
background: rgba(124, 204, 178, 0.08);
color: var(--sage);
font-size: 0.8rem;
font-weight: 700;
letter-spacing: 0.08em;
text-transform: uppercase;
}
.hero-grid {
display: grid;
grid-template-columns: minmax(0, 1.35fr) minmax(280px, 0.9fr);
gap: 1.25rem;
}
h1,
h2,
h3 {
margin: 0 0 0.7rem;
line-height: 1.05;
}
h1 {
max-width: 11ch;
font-size: clamp(2.4rem, 7vw, 4.6rem);
letter-spacing: -0.06em;
text-wrap: balance;
}
h2 {
font-size: 1.35rem;
letter-spacing: -0.03em;
}
h3 {
font-size: 0.98rem;
text-transform: uppercase;
letter-spacing: 0.09em;
color: var(--sage);
}
p,
li {
max-width: 74ch;
color: var(--text);
line-height: 1.6;
}
.lede {
font-size: 1.12rem;
color: #d8e1ea;
}
.hero-notes {
display: grid;
gap: 0.8rem;
align-content: start;
}
.note {
background: rgba(16, 23, 31, 0.72);
border: 1px solid var(--line);
border-radius: var(--radius-lg);
padding: 1rem;
}
.note strong {
display: block;
margin-bottom: 0.32rem;
color: #f7fbff;
}
.deck {
display: grid;
grid-template-columns: 260px minmax(0, 1fr);
gap: 1rem;
align-items: start;
margin-top: 1rem;
}
nav {
position: sticky;
top: 1rem;
border: 1px solid var(--line);
border-radius: 24px;
background: rgba(13, 19, 25, 0.86);
box-shadow: var(--shadow);
padding: 1rem;
}
nav h2 {
font-size: 0.95rem;
text-transform: uppercase;
letter-spacing: 0.09em;
color: var(--muted);
}
nav ol {
list-style: none;
padding: 0;
margin: 0;
}
nav li + li {
margin-top: 0.5rem;
}
nav a {
color: #d5e3ee;
text-decoration: none;
}
nav a:hover {
color: var(--sage);
}
article {
display: grid;
gap: 1rem;
}
section {
border: 1px solid var(--line);
border-radius: var(--radius-xl);
background: var(--surface);
box-shadow: var(--shadow);
padding: 1.4rem;
}
.overview {
display: grid;
grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
gap: 0.85rem;
}
.metric {
padding: 1rem;
border-radius: var(--radius-lg);
border: 1px solid var(--line);
background:
linear-gradient(180deg, rgba(124, 204, 178, 0.06), transparent 60%),
rgba(18, 24, 32, 0.76);
}
.metric-label {
display: block;
margin-bottom: 0.4rem;
color: var(--muted);
text-transform: uppercase;
font-size: 0.76rem;
letter-spacing: 0.09em;
}
.metric strong {
display: block;
margin-bottom: 0.35rem;
font-size: 1rem;
}
.split {
display: grid;
grid-template-columns: repeat(2, minmax(0, 1fr));
gap: 0.9rem;
}
.panel {
border: 1px solid var(--line);
border-radius: var(--radius-lg);
background: var(--surface-strong);
padding: 1rem;
}
ul,
ol {
padding-left: 1.15rem;
}
table {
width: 100%;
border-collapse: collapse;
margin-top: 0.75rem;
}
th,
td {
padding: 0.85rem 0.65rem;
border-bottom: 1px solid var(--line);
text-align: left;
vertical-align: top;
}
th {
color: var(--teal);
font-size: 0.78rem;
text-transform: uppercase;
letter-spacing: 0.09em;
}
pre {
overflow-x: auto;
margin: 0.85rem 0 0;
padding: 1rem;
border-radius: var(--radius-lg);
border: 1px solid var(--line);
background: var(--ink);
color: #dce7f0;
}
code,
pre {
font-family: "SF Mono", "JetBrains Mono", "Cascadia Code", monospace;
}
.chips {
display: flex;
flex-wrap: wrap;
gap: 0.55rem;
}
.chip {
display: inline-flex;
padding: 0.45rem 0.72rem;
border-radius: 999px;
border: 1px solid var(--line);
background: rgba(17, 24, 32, 0.9);
color: #dae4ec;
font-size: 0.86rem;
}
.accent-sage {
color: var(--sage);
}
.accent-gold {
color: var(--gold);
}
.accent-rose {
color: var(--rose);
}
.subdued {
color: var(--muted);
}
@media (max-width: 900px) {
.hero-grid,
.deck,
.split {
grid-template-columns: 1fr;
}
nav {
position: static;
}
h1 {
max-width: none;
}
}
</style>
</head>
<body>
<div class="shell">
<header class="hero">
<div class="hero-top">
<span class="pill">Plan · Impeccable HTML Version</span>
<span class="pill">Internal Control Surface</span>
<span class="pill">Hosted Synthetic Backend</span>
</div>
<div class="hero-grid">
<div>
<h1>Make the tape feel alive, not scheduled.</h1>
<p class="lede">
The hosted synthetic market already reaches the smart-money categories, but it often reaches them too cleanly. This redesign makes the demo feel more like a market session: one shared regime drives options, equities, quotes, event context, and coverage pressure, while operators keep a compact internal handle on the simulator through a bottom-right gear.
</p>
<div class="chips">
<span class="chip">Public smart-money taxonomy stays stable</span>
<span class="chip">Cross-asset coupling is the first priority</span>
<span class="chip">Internal-only controls, not a public settings page</span>
</div>
</div>
<div class="hero-notes">
<div class="note">
<strong>What changes for a viewer</strong>
The tape looks less templated, more coherent, and more educational because the surrounding market conditions finally support the category hits.
</div>
<div class="note">
<strong>What changes for an operator</strong>
A small bottom-right gear opens a non-modal synthetic-control drawer for the hosted backend.
</div>
<div class="note">
<strong>What does not change</strong>
Existing public smart-money event types, endpoints, and surface labels remain intact.
</div>
</div>
</div>
</header>
<div class="deck">
<nav>
<h2>Contents</h2>
<ol>
<li><a href="#overview">Simplified overview</a></li>
<li><a href="#scope">Scope</a></li>
<li><a href="#affected">Services affected</a></li>
<li><a href="#locked">Locked decisions</a></li>
<li><a href="#architecture">Full architecture</a></li>
<li><a href="#interfaces">Interfaces and env</a></li>
<li><a href="#sequence">Implementation phases</a></li>
<li><a href="#tests">Tests</a></li>
<li><a href="#assumptions">Assumptions</a></li>
</ol>
</nav>
<article>
<section id="overview">
<h2>Simplified Overview</h2>
<p>
The current synthetic system is strong at coverage and weaker at realism. It can produce the categories, but the tape often reveals the machinery: option bursts appear on a rhythm, quotes are too consistently clean, equities and options are only loosely related, and the market context around a labeled event is not convincing enough.
</p>
<p>
The redesign introduces a shared market regime engine. Instead of “emit a category-shaped burst now,” the system will model a believable session state first, then let both options and equities express that state. That keeps the smart-money demo behavior while making the experience feel more grounded.
</p>
<div class="overview">
<div class="metric">
<span class="metric-label">Audience</span>
<strong>Internal operators and demo owners</strong>
<span class="subdued">This is about making hosted synthetic sessions more convincing during demos and product evaluation.</span>
</div>
<div class="metric">
<span class="metric-label">Primary outcome</span>
<strong>Higher realism with preserved category coverage</strong>
<span class="subdued">The demo should still surface every smart-money category, but not in a visibly scripted way.</span>
</div>
<div class="metric">
<span class="metric-label">UI entry point</span>
<strong>Bottom-right gear, not a settings page</strong>
<span class="subdued">The operator control surface should stay compact and contextual.</span>
</div>
<div class="metric">
<span class="metric-label">Compatibility</span>
<strong>Public contracts remain stable</strong>
<span class="subdued">No public API break for smart-money consumers.</span>
</div>
</div>
</section>
<section id="scope">
<h2>Scope</h2>
<div class="split">
<div class="panel">
<h3>In scope</h3>
<ul>
<li>Hosted synthetic regime engine</li>
<li>Options and equities generator redesign</li>
<li>Hidden subtype scenario families</li>
<li>Soft coverage logic</li>
<li>Internal control API</li>
<li>Internal control drawer in the terminal shell</li>
<li>Regression and realism tests</li>
</ul>
</div>
<div class="panel">
<h3>Out of scope</h3>
<ul>
<li>Changing public smart-money categories</li>
<li>General settings-page work</li>
<li>User profile or token-spend UI</li>
<li>Public simulator controls</li>
<li>Live-feed product changes</li>
</ul>
</div>
</div>
</section>
<section id="affected">
<h2>Services Affected</h2>
<table>
<thead>
<tr>
<th>Area</th>
<th>Files</th>
<th>Why they change</th>
</tr>
</thead>
<tbody>
<tr>
<td>Shared types and regime model</td>
<td><code>packages/types/src/synthetic-market.ts</code>, <code>packages/types/src/events.ts</code></td>
<td>Introduce the control-state model and the deterministic shared market regime.</td>
</tr>
<tr>
<td>Hosted API</td>
<td><code>services/api/src/index.ts</code></td>
<td>Add internal synthetic-control status and mutation endpoints.</td>
</tr>
<tr>
<td>Options ingest</td>
<td><code>services/ingest-options/src/index.ts</code>, <code>services/ingest-options/src/adapters/synthetic.ts</code></td>
<td>Swap burst scheduling for regime-driven scenario selection and coverage debt.</td>
</tr>
<tr>
<td>Equities ingest</td>
<td><code>services/ingest-equities/src/index.ts</code>, <code>services/ingest-equities/src/adapters/synthetic.ts</code></td>
<td>Make equity prints and quotes react to the same latent regime as the options side.</td>
</tr>
<tr>
<td>Web and Electron shell</td>
<td><code>apps/web/app/terminal.tsx</code>, <code>apps/web/app/api/admin/synthetic/*</code></td>
<td>Add the internal-only gear trigger, drawer, and secure proxy layer.</td>
</tr>
<tr>
<td>Tests</td>
<td>Options tests, API tests, web tests</td>
<td>Protect determinism, realism, UI visibility rules, and classification alignment.</td>
</tr>
</tbody>
</table>
</section>
<section id="locked">
<h2>Locked Decisions</h2>
<div class="chips">
<span class="chip">Keep the six public smart-money categories</span>
<span class="chip">Add hidden subtype families</span>
<span class="chip">Use soft coverage guarantees</span>
<span class="chip">Prioritize cross-asset coupling first</span>
<span class="chip">Target the hosted synthetic backend</span>
<span class="chip">Internal-only control surface</span>
<span class="chip">No general settings page in this effort</span>
<span class="chip">Bottom-right gear opens a drawer</span>
</div>
</section>
<section id="architecture">
<h2>Full Architecture</h2>
<h3 class="accent-sage">1. Replace the burst pulse with a shared regime engine</h3>
<p>Expand <code>packages/types/src/synthetic-market.ts</code> into the shared deterministic engine used by both ingest services.</p>
<p>Shared functions:</p>
<ul>
<li><code>getSyntheticSessionState(ts, control)</code></li>
<li><code>getSyntheticUnderlyingState(symbol, ts, control, sessionState)</code></li>
<li><code>getSyntheticScenarioWeights(symbol, ts, control, sessionState)</code></li>
<li><code>getSyntheticCoverageBoost(profileId, coverageState, control)</code></li>
</ul>
<p><code>sessionState</code> includes:</p>
<ul>
<li><code>session_phase</code>: <code>open | midday | power_hour | after_event</code></li>
<li><code>regime</code>: <code>trend_up | trend_down | mean_revert | retail_chase | event_ramp | dealer_gamma | arb_calm</code></li>
<li><code>volatility_level</code></li>
<li><code>liquidity_level</code></li>
<li><code>quote_cleanliness</code></li>
<li><code>focus_symbols</code></li>
<li><code>event_symbols</code></li>
<li><code>seed_bucket</code></li>
</ul>
<h3 class="accent-teal">2. Add hosted synthetic control state</h3>
<p>Add internal control schemas in <code>packages/types</code>:</p>
<ul>
<li><code>SyntheticControlPresetId</code></li>
<li><code>SyntheticControlState</code></li>
<li><code>SyntheticProfileWeightMap</code></li>
<li><code>SyntheticCoverageConfig</code></li>
<li><code>SyntheticDerivedStatus</code></li>
</ul>
<pre><code>type SyntheticControlState = {
preset_id: "balanced_demo" | "event_day" | "dealer_day" | "retail_chase" | "quiet_range";
coverage_assist: boolean;
coverage_window_minutes: 10 | 20 | 30;
shared_seed: number;
profile_weights: {
institutional_directional: 0.6 | 1.0 | 1.6;
retail_whale: 0.6 | 1.0 | 1.6;
event_driven: 0.6 | 1.0 | 1.6;
vol_seller: 0.6 | 1.0 | 1.6;
arbitrage: 0.6 | 1.0 | 1.6;
hedge_reactive: 0.6 | 1.0 | 1.6;
};
updated_at: number;
updated_by: string;
};</code></pre>
<p>Defaults: <code>preset_id: balanced_demo</code>, <code>coverage_assist: true</code>, <code>coverage_window_minutes: 20</code>, all profile weights <code>1.0</code>.</p>
<h3 class="accent-gold">3. Persist and distribute control state through NATS</h3>
<ul>
<li>Use JetStream KV bucket <code>synthetic_control</code></li>
<li>Use key <code>global</code></li>
<li><code>services/api</code> reads and writes the KV entry</li>
<li><code>services/ingest-options</code> loads on boot and watches for updates</li>
<li><code>services/ingest-equities</code> does the same</li>
</ul>
<h3 class="accent-rose">4. Rebuild options scenarios as hidden subtype families</h3>
<ul>
<li><strong><code>institutional_directional</code></strong>: <code>call_sweep</code>, <code>put_sweep</code>, <code>ask_lift_accumulation</code>, <code>far_dated_conviction</code></li>
<li><strong><code>retail_whale</code></strong>: <code>0dte_call_chase</code>, <code>short_dated_put_panic</code>, <code>attention_contract_spike</code></li>
<li><strong><code>event_driven</code></strong>: <code>earnings_vol_probe</code>, <code>pre_event_directional_ramp</code>, <code>post_gap_followthrough</code></li>
<li><strong><code>vol_seller</code></strong>: <code>covered_call_overwrite</code>, <code>cash_secured_put_write</code>, <code>short_straddle_harvest</code></li>
<li><strong><code>arbitrage</code></strong>: <code>parity_vertical</code>, <code>conversion_reversal</code>, <code>box_spread</code></li>
<li><strong><code>hedge_reactive</code></strong>: <code>gamma_pinch_call_hedge</code>, <code>reactive_put_wall</code>, <code>dealer_unwind</code></li>
<li><strong><code>neutral_noise</code></strong>: <code>single_print_mid</code>, <code>two_sided_scalp</code>, <code>stale_quote_noise</code></li>
</ul>
<p>Hidden subtype labels remain internal and test-only. They should never appear on emitted option prints or public smart-money events.</p>
<h3>5. Make equities and options react to the same latent state</h3>
<div class="split">
<div class="panel">
<h3>Equities changes</h3>
<ul>
<li>Remove the fixed dark-sequence loop</li>
<li>Make lit versus dark balance regime-dependent</li>
<li>Make spread, quote cleanliness, off-exchange frequency, and clustering regime-dependent</li>
<li>Use shared focus symbols</li>
<li>Make <code>event_ramp</code> and <code>retail_chase</code> show modest trend and wider quotes</li>
<li>Make <code>dealer_gamma</code> show choppier reversals and denser quote changes</li>
<li>Make <code>arb_calm</code> quieter and more neutral</li>
</ul>
</div>
<div class="panel">
<h3>Options changes</h3>
<ul>
<li>Replace hardcoded coverage forcing with weighted family selection plus coverage debt</li>
<li>Make venue count, placement, stale or missing quote probability, and structure prevalence regime-sensitive</li>
<li>Derive <code>execution_iv_shock</code>, <code>underlying_move_bps</code>, and <code>nbbo_spread_z</code> from shared state</li>
<li>Generate event-driven timestamps and symbols from shared regime state</li>
</ul>
</div>
</div>
<h3>6. Add soft coverage accounting</h3>
<ul>
<li>Track rolling coverage debt per public profile inside each ingest service</li>
<li>Maintain a rolling counter across the selected <code>coverage_window_minutes</code></li>
<li>Only public profiles count toward coverage</li>
<li>Missing profiles get a bounded weight boost</li>
<li>Noise and low-key scenarios continue to appear between labeled bursts</li>
</ul>
<h3>7. Add internal hosted control endpoints</h3>
<p>Add routes in <code>services/api/src/index.ts</code>:</p>
<ul>
<li><code>GET /admin/synthetic/status</code></li>
<li><code>GET /admin/synthetic/control</code></li>
<li><code>PUT /admin/synthetic/control</code></li>
</ul>
<pre><code>{
enabled: boolean;
backend_mode: "synthetic" | "mixed" | "live";
adapters: {
options: string;
equities: string;
};
control: SyntheticControlState | null;
derived: {
session_phase: string;
regime: string;
focus_symbols: string[];
profile_hit_counts: Record&lt;SmartMoneyProfileId, number&gt;;
coverage_window_minutes: number;
} | null;
disabled_reason?: string;
}</code></pre>
<p>Behavior: return <code>404</code> when admin mode is disabled, return <code>409</code> when hosted adapters are not synthetic, validate full payloads on <code>PUT</code>, and keep public smart-money interfaces unchanged.</p>
<h3>8. Keep secrets out of the browser with Next.js proxy routes</h3>
<ul>
<li><code>apps/web/app/api/admin/synthetic/status/route.ts</code></li>
<li><code>apps/web/app/api/admin/synthetic/control/route.ts</code></li>
</ul>
<p>The proxy reads server-only <code>SYNTHETIC_ADMIN_TOKEN</code>, forwards to <code>NEXT_PUBLIC_API_URL</code>, returns <code>404</code> when the internal UI flag is off, and never exposes the token client-side.</p>
<h3>9. Add an internal control surface</h3>
<p>UI rules for the first pass:</p>
<ul>
<li>Small floating gear in the bottom-right corner</li>
<li>Opens a right-edge non-modal drawer</li>
<li>Internal-only visibility</li>
<li>Preset dropdown: <code>Balanced Demo</code>, <code>Event Day</code>, <code>Dealer Day</code>, <code>Retail Chase</code>, <code>Quiet Range</code></li>
<li>Coverage assist toggle</li>
<li>Coverage window selector: <code>10m</code>, <code>20m</code>, <code>30m</code></li>
<li>Six profile-weight controls: <code>Low</code>, <code>Normal</code>, <code>High</code></li>
<li>Read-only live status: regime, session phase, focus symbols, rolling hit counts, backend state</li>
<li>Optimistic updates with rollback on error</li>
<li>Debounced writes at <code>250ms</code></li>
<li>Status polling every <code>5s</code>, no admin websocket in v1</li>
</ul>
</section>
<section id="interfaces">
<h2>Interfaces and Environment</h2>
<div class="split">
<div class="panel">
<h3>Public contracts unchanged</h3>
<ul>
<li><code>SmartMoneyProfileId</code></li>
<li><code>SmartMoneyEvent</code></li>
<li><code>/flow/smart-money</code></li>
<li><code>/history/smart-money</code></li>
<li><code>/replay/smart-money</code></li>
<li><code>/ws/smart-money</code></li>
</ul>
</div>
<div class="panel">
<h3>New internal contracts</h3>
<ul>
<li><code>SyntheticControlState</code></li>
<li><code>SyntheticControlPresetId</code></li>
<li><code>SyntheticDerivedStatus</code></li>
</ul>
</div>
</div>
<div class="split">
<div class="panel">
<h3>New internal endpoints</h3>
<ul>
<li><code>GET /admin/synthetic/status</code></li>
<li><code>GET /admin/synthetic/control</code></li>
<li><code>PUT /admin/synthetic/control</code></li>
</ul>
</div>
<div class="panel">
<h3>New env vars</h3>
<p class="subdued">Backend</p>
<ul>
<li><code>SYNTHETIC_CONTROL_ENABLED=0|1</code></li>
<li><code>SYNTHETIC_ADMIN_TOKEN=...</code></li>
</ul>
<p class="subdued">Web</p>
<ul>
<li><code>NEXT_PUBLIC_SYNTHETIC_ADMIN=0|1</code></li>
<li><code>SYNTHETIC_ADMIN_TOKEN=...</code> for the Next server proxy only</li>
</ul>
</div>
</div>
</section>
<section id="sequence">
<h2>Implementation Phases</h2>
<ol>
<li>
<strong>Phase 1. Shared types and regime engine</strong>
<p class="subdued">Touch <code>packages/types/src/synthetic-market.ts</code> and related exports and tests. Deliver control schemas, preset definitions, deterministic session and regime functions, and coverage boost helpers.</p>
</li>
<li>
<strong>Phase 2. Hosted control plane</strong>
<p class="subdued">Touch <code>services/api/src/index.ts</code> and NATS or KV helpers as needed. Deliver admin endpoints, KV persistence, status payloads, and disabled or error behavior.</p>
</li>
<li>
<strong>Phase 3. Ingest service coupling</strong>
<p class="subdued">Touch both ingest services and their synthetic adapters. Deliver boot-time control loading, KV watch updates, shared regime-driven generation, and removal of visibly scripted fixed sequences.</p>
</li>
<li>
<strong>Phase 4. Internal control UI</strong>
<p class="subdued">Touch <code>apps/web/app/terminal.tsx</code> and the internal admin proxy routes. Deliver the floating gear, non-modal drawer, polling, optimistic updates, and disabled state.</p>
</li>
<li>
<strong>Phase 5. Regression and realism tests</strong>
<p class="subdued">Deliver determinism tests, control API tests, scenario coverage tests, UI visibility tests, and classifier-alignment tests for hidden subtype families.</p>
</li>
</ol>
</section>
<section id="tests">
<h2>Tests and Acceptance</h2>
<div class="split">
<div class="panel">
<h3>Shared engine</h3>
<ul>
<li>Same <code>timestamp + control snapshot + seed</code> yields the same regime and focus symbols in both ingest services.</li>
<li>Presets materially change regime weights without breaking determinism.</li>
<li><code>balanced_demo</code> yields mixed regimes over a session.</li>
<li><code>quiet_range</code> yields lower volatility, tighter spreads, and fewer labeled events than <code>retail_chase</code>.</li>
</ul>
</div>
<div class="panel">
<h3>Cross-asset coupling</h3>
<ul>
<li><code>event_ramp</code> produces event-aligned option scenarios and synchronized underlying drift and spread behavior.</li>
<li><code>dealer_gamma</code> produces short-dated ATM-heavy options plus choppier underlying reversals.</li>
<li><code>arb_calm</code> increases neutral multi-leg structures without strong directional underlying moves.</li>
<li><code>retail_chase</code> increases short-dated OTM call behavior, IV shock, and louder underlying momentum.</li>
</ul>
</div>
</div>
<div class="split">
<div class="panel">
<h3>Coverage and classification</h3>
<ul>
<li>With default controls, every public smart-money profile appears at least once in a 20-minute synthetic session sample.</li>
<li>With <code>coverage_assist=false</code>, there is no forced coverage logic.</li>
<li>Raising one profile to <code>High</code> increases its frequency without starving other categories.</li>
<li>Neutral noise remains below the smart-money emission threshold.</li>
<li>Each hidden subtype family still classifies into the intended public profile.</li>
</ul>
</div>
<div class="panel">
<h3>Admin API and UI</h3>
<ul>
<li>Disabled admin mode returns <code>404</code>.</li>
<li>Non-synthetic hosted mode returns <code>409</code> with a useful reason.</li>
<li>Valid <code>PUT</code> persists to KV and becomes visible to both ingest services.</li>
<li>The floating gear is hidden when <code>NEXT_PUBLIC_SYNTHETIC_ADMIN</code> is off.</li>
<li>The browser client never receives the backend admin token.</li>
</ul>
</div>
</div>
</section>
<section id="assumptions">
<h2>Assumptions and Defaults</h2>
<ul>
<li>Hosted synthetic control applies only when both options and equities ingest adapters are synthetic.</li>
<li>No general settings page, user-info work, or token-spend work is in scope here.</li>
<li>Hidden subtype labels remain internal and test-only and never attach to emitted prints.</li>
<li>The first pass uses polling for admin status rather than a new admin websocket.</li>
<li>The default operator experience is <code>Balanced Demo</code> with soft coverage on and a 20-minute window.</li>
<li>The repo currently lacks local <code>PRODUCT.md</code>, <code>DESIGN.md</code>, and the local impeccable loader path. This version therefore follows the spirit of the terminal shell and impeccable product-UI principles rather than project-specific design-context files.</li>
</ul>
</section>
</article>
</div>
</div>
</body>
</html>