데스크톱 앱 리프레시 기능 추가

This commit is contained in:
Macbook
2026-06-22 16:47:20 +09:00
parent 1180cd53f0
commit 5871eb2465
17 changed files with 165 additions and 5 deletions
@@ -12,6 +12,8 @@ interface Options {
/** 직접 지정할 페치 봉 수 — UPBIT_DIRECT 전용 (deepObvHistory·WARMUP_COUNT 무시) */
fetchCount?: number;
source?: ChartRealtimeSource;
/** 증가 시 초기 캔들 REST 재로드 (화면 새로고침) */
refreshToken?: number;
}
export function useChartRealtimeData(
@@ -25,6 +27,7 @@ export function useChartRealtimeData(
onNewCandle: opts.onNewCandle,
enabled: opts.enabled !== false && useStomp,
deepObvHistory: opts.deepObvHistory,
refreshToken: opts.refreshToken,
});
const upbit = useUpbitData(market, timeframe, {
onTickUpdate: opts.onTickUpdate,
@@ -32,6 +35,7 @@ export function useChartRealtimeData(
enabled: opts.enabled !== false && !useStomp,
deepObvHistory: opts.deepObvHistory,
fetchCount: opts.fetchCount,
refreshToken: opts.refreshToken,
});
return useStomp ? stomp : upbit;
}
+3 -1
View File
@@ -46,6 +46,8 @@ interface Options {
enabled?: boolean;
/** OBV 누적 정확도 — 더 많은 초기 봉 로드 */
deepObvHistory?: boolean;
/** 화면 새로고침 — REST 초기 로드 재실행 */
refreshToken?: number;
}
interface Return {
@@ -141,7 +143,7 @@ export function useStompChartData(
setIsLoading(false);
});
return () => { cancelled = true; };
}, [market, candleType, timeframe, opts.enabled, opts.deepObvHistory]);
}, [market, candleType, timeframe, opts.enabled, opts.deepObvHistory, opts.refreshToken]);
const syncBarsToReactIfNeeded = useCallback((marketId: string) => {
if (!bootstrapFromStompRef.current) return;
+10 -3
View File
@@ -28,6 +28,8 @@ interface UpbitDataOptions {
deepObvHistory?: boolean;
/** 직접 지정할 페치 봉 수 (deepObvHistory·WARMUP_COUNT 무시) */
fetchCount?: number;
/** 화면 새로고침 — REST 초기 로드 재실행 */
refreshToken?: number;
}
interface UseUpbitDataReturn {
@@ -73,6 +75,7 @@ export function useUpbitData(
// ── 1. REST API: 초기 캔들 로딩 (표시용 + 워밍업 합산) ─────────────────
// 이전 market 값을 기억해 종목 변경 시에만 캐시를 무효화한다.
const prevMarketRef = useRef<string>('');
const prevRefreshTokenRef = useRef(opts.refreshToken ?? 0);
useEffect(() => {
if (opts.enabled === false) return;
@@ -85,15 +88,19 @@ export function useUpbitData(
setLatestBar(null);
barsRef.current = [];
const refreshToken = opts.refreshToken ?? 0;
const bustCache = refreshToken > 0 && refreshToken !== prevRefreshTokenRef.current;
prevRefreshTokenRef.current = refreshToken;
// 종목(market)이 변경된 경우에는 캐시를 무효화해 신규 요청을 강제한다.
// 타임프레임만 바뀐 경우도 캐시 키가 다르므로 자동으로 새 요청이 발생한다.
const marketChanged = prevMarketRef.current !== '' && prevMarketRef.current !== market;
prevMarketRef.current = market;
if (bustCache) invalidateMarketCache(market);
const fetchCount = opts.fetchCount
?? (opts.deepObvHistory ? OBV_DEEP_HISTORY : DISPLAY_COUNT + WARMUP_COUNT);
fetchUpbitCandlesCached(market, timeframe, fetchCount, marketChanged)
fetchUpbitCandlesCached(market, timeframe, fetchCount, marketChanged || bustCache)
.then(newBars => {
if (cancelled) return;
barsRef.current = newBars;
@@ -109,7 +116,7 @@ export function useUpbitData(
});
return () => { cancelled = true; };
}, [market, timeframe, opts.enabled, opts.deepObvHistory, opts.fetchCount]);
}, [market, timeframe, opts.enabled, opts.deepObvHistory, opts.fetchCount, opts.refreshToken]);
// ── 2. WebSocket: 실시간 체결 구독 ────────────────────────────────────
const handleMessage = useCallback((msg: UpbitMessage) => {