feat: dealer flow, mirror portfolio (M21), options convexity, FINRA short interest, alert producers, vendor gate
CI / Test & Type-Check (push) Canceled after 0s
CI / Test & Type-Check (push) Canceled after 0s
Snapshot of in-progress module work across multiple slices: - Dealer Flow: dealerExposureEngine, dealerMapService, dealerMapExplain, dealerMapIntegrity, dealerMapReplay, dealerStudyEngine, hanStyleLevels - Mirror Portfolio (M21): fundRepository, captureIngest, mirrorAlertProducers, fund holdings strip, live book, position capture ingest - Options: BSM, NormalizedOptionSurface types, OptionsChainRouter, ConvexityGate, option legs panel - Alert producers: vixLevel, rotation, thesis, unlock, portfolioRisk, mirror (fund_capture, fund_13f, mirror_diff) - FINRA short interest adapter + queue integration - SEC company tickers adapter + ingest (symbol search index seed) - Vendor gate (rate-limit-first data plane, ADR-0009) - CUSIP registry, reverse 13F refresh, stock float service - LRU cache, portfolio backtest engine - Frontend: dealer-flow, funds, journal, lab, monitor, plan, portfolio, reports, screener, strategies, theses, guided-start, exits, more pages - Volume profile, workspace profile, visibility-aware poll - ADRs 0010 (mirror math not advice), 0011 (symbol search index) - VENDOR_INTEGRATIONS.md, END_USER_TEST.md - .gitignore: exclude DBs, .DS_Store, local config, agent scratch
This commit is contained in:
@@ -0,0 +1,84 @@
|
||||
#!/usr/bin/env npx tsx
|
||||
/**
|
||||
* CLI: backtest GEX/VEX integrity by replaying chains as-of a timestamp.
|
||||
*
|
||||
* npx tsx scripts/dealer-map-replay.ts --symbol IREN --as-of 2026-08-07T13:14:00.000Z
|
||||
* npx tsx scripts/dealer-map-replay.ts --symbol IREN --from-snapshots --days 7
|
||||
*
|
||||
* Exit 1 if integrity incomplete or snapshot drift too large.
|
||||
*/
|
||||
|
||||
import { DatabaseSync } from 'node:sqlite';
|
||||
import { resolve } from 'node:path';
|
||||
import { replayDealerMapAt, replayFromSnapshots } from '../src/analysis/dealerMapReplay.ts';
|
||||
|
||||
function arg(name: string): string | undefined {
|
||||
const i = process.argv.indexOf(name);
|
||||
if (i < 0 || i + 1 >= process.argv.length) return undefined;
|
||||
return process.argv[i + 1];
|
||||
}
|
||||
|
||||
function has(name: string): boolean {
|
||||
return process.argv.includes(name);
|
||||
}
|
||||
|
||||
const symbol = (arg('--symbol') ?? 'IREN').toUpperCase();
|
||||
const asOf = arg('--as-of');
|
||||
const days = Number(arg('--days') ?? '7');
|
||||
const fromSnapshots = has('--from-snapshots');
|
||||
|
||||
const dbPath =
|
||||
arg('--db') ??
|
||||
resolve(process.cwd(), 'data/investor-flow.db');
|
||||
|
||||
const db = new DatabaseSync(dbPath, { readOnly: true });
|
||||
|
||||
function printResult(r: ReturnType<typeof replayDealerMapAt>) {
|
||||
console.log('---');
|
||||
console.log(r.symbol, r.asOf);
|
||||
console.log(' ok:', r.ok, '|', r.integrity.status);
|
||||
console.log(' ', r.summary);
|
||||
if (r.map?.levels.king) {
|
||||
console.log(
|
||||
' king:',
|
||||
r.map.levels.king.strike,
|
||||
r.map.levels.king.expiry,
|
||||
`gex=${(r.map.levels.king.gex / 1000).toFixed(1)}K`,
|
||||
);
|
||||
}
|
||||
console.log(
|
||||
' metrics:',
|
||||
JSON.stringify(r.integrity.metrics),
|
||||
);
|
||||
const fails = r.integrity.checks.filter((c) => !c.ok);
|
||||
if (fails.length) {
|
||||
console.log(' failed checks:');
|
||||
for (const c of fails) {
|
||||
console.log(` [${c.level}] ${c.id}: ${c.detail}`);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
let anyFail = false;
|
||||
|
||||
if (fromSnapshots) {
|
||||
const results = replayFromSnapshots(db, symbol, days);
|
||||
if (results.length === 0) {
|
||||
console.error('No snapshots for', symbol);
|
||||
process.exit(2);
|
||||
}
|
||||
for (const r of results) {
|
||||
printResult(r);
|
||||
if (!r.ok) anyFail = true;
|
||||
}
|
||||
} else if (asOf) {
|
||||
const r = replayDealerMapAt(db, symbol, asOf);
|
||||
printResult(r);
|
||||
if (!r.ok) anyFail = true;
|
||||
} else {
|
||||
console.error('Usage: --symbol SYM --as-of ISO | --from-snapshots [--days N] [--db path]');
|
||||
process.exit(2);
|
||||
}
|
||||
|
||||
db.close();
|
||||
process.exit(anyFail ? 1 : 0);
|
||||
Reference in New Issue
Block a user