알림목록 전략지표 없음 문제 수정

This commit is contained in:
Macbook
2026-06-08 01:31:02 +09:00
parent 0229799383
commit 2f1a4d3bca
9 changed files with 230 additions and 36 deletions
+63
View File
@@ -0,0 +1,63 @@
/**
* 전략 DTO 정규화 — API·DB에서 문자열 JSON·flowLayout 보정
*/
import type { LogicNode } from './strategyTypes';
import type { StrategyDto } from './backendApi';
import { extractVirtualConditions } from './virtualStrategyConditions';
import { decodeConditionForEditor, encodeConditionForSave } from './strategyConditionSerde';
import type { StrategyFlowLayoutStore } from './strategyEditorLayoutStorage';
export function asLogicNode(raw: unknown): LogicNode | null {
if (!raw) return null;
if (typeof raw === 'string') {
const t = raw.trim();
if (!t) return null;
try {
return JSON.parse(t) as LogicNode;
} catch {
return null;
}
}
if (typeof raw === 'object') return raw as LogicNode;
return null;
}
export function normalizeMarketCode(market: string): string {
const s = market.trim().toUpperCase();
if (!s) return 'KRW-BTC';
return s.startsWith('KRW-') ? s : `KRW-${s}`;
}
/** buy/sell DSL 파싱·flowLayout 재인코딩으로 조건 추출 가능 상태로 보정 */
export function hydrateStrategyDto(strategy: StrategyDto): StrategyDto {
const buy = asLogicNode(strategy.buyCondition);
const sell = asLogicNode(strategy.sellCondition);
let next: StrategyDto = {
...strategy,
buyCondition: buy ?? undefined,
sellCondition: sell ?? undefined,
};
if (extractVirtualConditions(next).length > 0) return next;
const layout = strategy.flowLayout as StrategyFlowLayoutStore | null | undefined;
if (!layout) return next;
try {
const buyState = decodeConditionForEditor(buy);
const sellState = decodeConditionForEditor(sell);
const encodedBuy = encodeConditionForSave(buyState);
const encodedSell = encodeConditionForSave(sellState);
if (encodedBuy || encodedSell) {
next = {
...next,
buyCondition: encodedBuy ?? buy ?? undefined,
sellCondition: encodedSell ?? sell ?? undefined,
};
}
} catch {
/* flowLayout 보정 실패 — 원본 유지 */
}
return next;
}