feat(NetworkMapDashboard): implement cache handling for ping and speed requests to optimize data fetching
Publish Fast Tabler Docker image / build-and-push-fast (push) Successful in 2m0s

This commit is contained in:
2026-02-18 13:06:00 +07:00
parent 6f13f39685
commit b1834e988b
+14 -2
View File
@@ -78,11 +78,14 @@ export default function NetworkMapDashboard() {
const [error, setError] = useState(null); const [error, setError] = useState(null);
const pingAbortRef = useRef(false); const pingAbortRef = useRef(false);
const speedAbortRef = useRef(false); const speedAbortRef = useRef(false);
/** Время применения кеша от планировщика (чтобы не запускать пинг/скорость повторно при открытии) */
const cacheAppliedAtRef = useRef(null);
/** Связи строятся из интерфейсов раздела «Сетевые настройки» (/network-config), tunnelInterfaces */ /** Связи строятся из интерфейсов раздела «Сетевые настройки» (/network-config), tunnelInterfaces */
const fetchData = useCallback(async () => { const fetchData = useCallback(async () => {
setLoading(true); setLoading(true);
setError(null); setError(null);
cacheAppliedAtRef.current = null;
try { try {
const [serversRes, configRes, uiSettingsRes, cacheRes] = await Promise.all([ const [serversRes, configRes, uiSettingsRes, cacheRes] = await Promise.all([
api.get('/servers'), api.get('/servers'),
@@ -142,6 +145,7 @@ export default function NetworkMapDashboard() {
Object.keys(cache.pingMap || {}).forEach((k) => { Object.keys(cache.pingMap || {}).forEach((k) => {
pingTimestampsRef.current[k] = cache.updatedAt; pingTimestampsRef.current[k] = cache.updatedAt;
}); });
cacheAppliedAtRef.current = cache.updatedAt;
} else { } else {
setSpeedMap({}); setSpeedMap({});
} }
@@ -276,21 +280,29 @@ export default function NetworkMapDashboard() {
useEffect(() => { useEffect(() => {
if (!loading && servers.length > 0 && connections.length > 0) { if (!loading && servers.length > 0 && connections.length > 0) {
const cacheMaxAgeMs = Math.max((pingCacheSeconds || 60) * 1000, 60 * 1000);
if (cacheAppliedAtRef.current && Date.now() - cacheAppliedAtRef.current < cacheMaxAgeMs) {
return;
}
requestPings(); requestPings();
} }
return () => { return () => {
pingAbortRef.current = true; pingAbortRef.current = true;
}; };
}, [loading, connections.length]); }, [loading, connections.length, pingCacheSeconds, requestPings]);
useEffect(() => { useEffect(() => {
if (!loading && connections.length > 0) { if (!loading && connections.length > 0) {
const cacheMaxAgeMs = Math.max((pingCacheSeconds || 60) * 1000, 60 * 1000);
if (cacheAppliedAtRef.current && Date.now() - cacheAppliedAtRef.current < cacheMaxAgeMs) {
return;
}
requestSpeeds(); requestSpeeds();
} }
return () => { return () => {
speedAbortRef.current = true; speedAbortRef.current = true;
}; };
}, [loading, connections.length, requestSpeeds]); }, [loading, connections.length, pingCacheSeconds, requestSpeeds]);
const handleRefreshPings = () => { const handleRefreshPings = () => {
requestPings(); requestPings();