phase-7: code restructure

This commit is contained in:
Sai Kiran Vella
2026-06-05 22:05:55 -04:00
parent c1b3b26caa
commit 5185f03c12
108 changed files with 8931 additions and 3434 deletions
+124
View File
@@ -0,0 +1,124 @@
import { test } from 'node:test';
import assert from 'node:assert/strict';
import { StockScorer } from '../server/scorers/StockScorer';
import type { StockMetrics } from '../server/types';
const baseRules = {
gates: { maxDebtToEquity: 3.0, minQuickRatio: 0.5, maxPERatio: 20, maxPegGate: 1.5 },
weights: { margin: 2, opMargin: 2, roe: 3, peg: 2, revenue: 2, fcf: 2 },
thresholds: {
marginHigh: 20,
marginMed: 10,
opMarginHigh: 20,
opMarginMed: 10,
roeHigh: 20,
roeMed: 10,
pegHigh: 1.0,
pegMed: 1.5,
revHigh: 15,
revMed: 5,
fcfHigh: 5,
fcfMed: 2,
},
};
// Minimal fixture — tests exercise specific fields; unused metrics are null.
const nullMetrics: Omit<
StockMetrics,
| 'sector'
| 'capCategory'
| 'growthCategory'
| 'currentPrice'
| 'peRatio'
| 'pegRatio'
| 'debtToEquity'
| 'quickRatio'
| 'returnOnEquity'
| 'operatingMargin'
| 'netProfitMargin'
| 'revenueGrowth'
| 'fcfYield'
> = {
priceToBook: null,
grossMargin: null,
earningsGrowth: null,
pFFO: null,
dividendYield: null,
beta: null,
week52High: null,
week52Low: null,
week52Change: null,
week52FromHigh: null,
week52FromLow: null,
marketCap: null,
analystRating: null,
analystTargetPrice: null,
analystUpside: null,
numberOfAnalysts: null,
dcfIntrinsicValue: null,
dcfMarginOfSafety: null,
};
const pass: StockMetrics = {
...nullMetrics,
sector: 'GENERAL',
capCategory: 'Large Cap',
growthCategory: 'Growth',
currentPrice: 150,
peRatio: 15,
pegRatio: 1.2,
debtToEquity: 1.0,
quickRatio: 1.0,
returnOnEquity: 22,
operatingMargin: 25,
netProfitMargin: 18,
revenueGrowth: 16,
fcfYield: 6,
};
test('rejects on high D/E', () => {
const result = StockScorer.score({ ...pass, debtToEquity: 4.0 }, baseRules);
assert.equal(result.label, '🔴 REJECT');
assert(result.scoreSummary.includes('D/E'));
});
test('rejects on high P/E', () => {
const result = StockScorer.score({ ...pass, peRatio: 25 }, baseRules);
assert.equal(result.label, '🔴 REJECT');
assert(result.scoreSummary.includes('P/E'));
});
test('rejects on high PEG', () => {
const result = StockScorer.score({ ...pass, pegRatio: 2.0 }, baseRules);
assert.equal(result.label, '🔴 REJECT');
});
test('skips gate when metric is null (missing data)', () => {
const result = StockScorer.score({ ...pass, pegRatio: null, peRatio: null }, baseRules);
assert.notEqual(result.label, '🔴 REJECT');
});
test('high-conviction BUY on strong metrics', () => {
const result = StockScorer.score(pass, baseRules);
assert.equal(result.label, '🟢 BUY (High Conviction)');
});
test('audit breakdown contains scored factors', () => {
const result = StockScorer.score(pass, baseRules);
assert(result.audit.passedGates);
assert(result.audit.breakdown!.roe != null);
assert(result.audit.breakdown!.margin != null);
});
test('beta > 1.5 surfaces as risk flag', () => {
const result = StockScorer.score({ ...pass, beta: 2.0 }, baseRules);
assert(result.audit.riskFlags?.some((f) => f.includes('High volatility')));
});
test('near 52-week high surfaces as risk flag', () => {
const result = StockScorer.score(
{ ...pass, week52High: 200, week52Low: 100, currentPrice: 195 },
baseRules,
);
assert(result.audit.riskFlags?.some((f) => f.includes('52-week high')));
});