refactor: optimize swr data refresh paths

This commit is contained in:
Tunglies
2026-06-28 19:42:21 +08:00
parent e71e701fd0
commit b9da0875cd
16 changed files with 153 additions and 162 deletions
+10 -7
View File
@@ -7,8 +7,12 @@ import {
getRuntimeConfig,
patchClashConfig,
} from '@/services/cmds'
import { useQuery } from '@/services/query-client'
import { queryClient } from '@/services/query-client'
import {
getCacheData,
revalidateQuery,
setCacheData,
useQuery,
} from '@/services/query-client'
type MutateClashUpdater =
| ((old: IConfigData | undefined) => IConfigData | undefined)
@@ -90,9 +94,9 @@ export const useClash = () => {
}
const next =
typeof updater === 'function'
? updater(queryClient.getQueryData<IConfigData>(['getRuntimeConfig']))
? updater(getCacheData<IConfigData>(['getRuntimeConfig']))
: updater
queryClient.setQueryData(['getRuntimeConfig'], next)
setCacheData(['getRuntimeConfig'], next)
if (revalidate !== false) {
return refetch()
}
@@ -130,11 +134,10 @@ export const useClashInfo = () => {
await patchClashConfig(patch)
mutateInfo()
queryClient.invalidateQueries({ queryKey: ['getClashConfig'] })
revalidateQuery(['getClashConfig'])
})
const invalidateClashConfig = () =>
queryClient.invalidateQueries({ queryKey: ['getClashConfig'] })
const invalidateClashConfig = () => revalidateQuery(['getClashConfig'])
return {
clashInfo,
-1
View File
@@ -42,7 +42,6 @@ export const useIconCache = ({
refetchOnWindowFocus: false,
refetchOnReconnect: false,
staleTime: Infinity,
gcTime: 30 * 60 * 1000,
retry: 2,
})
+2 -2
View File
@@ -3,7 +3,7 @@ import { useEffect, useRef } from 'react'
import { MihomoWebSocket, type LogLevel } from 'tauri-plugin-mihomo-api'
import { getClashLogs } from '@/services/cmds'
import { queryClient } from '@/services/query-client'
import { setCacheData } from '@/services/query-client'
import { useClashLog } from './use-clash-log'
import { useMihomoWsSubscription } from './use-mihomo-ws-subscription'
@@ -155,7 +155,7 @@ export const useLogData = () => {
const refreshGetClashLog = (clear = false) => {
if (clear) {
if (subscriptionCacheKey) {
queryClient.setQueryData<ILogItem[]>([subscriptionCacheKey], [])
setCacheData<ILogItem[]>([subscriptionCacheKey], [])
}
} else {
hasLoadedInitialLogsRef.current = false
+12 -9
View File
@@ -2,7 +2,12 @@ import { useLocalStorage } from 'foxact/use-local-storage'
import { type MutableRefObject, useCallback, useEffect, useRef } from 'react'
import { type Message, type MihomoWebSocket } from 'tauri-plugin-mihomo-api'
import { queryClient, useQuery } from '@/services/query-client'
import {
getCacheData,
removeCacheData,
setCacheData,
useQuery,
} from '@/services/query-client'
export const RECONNECT_DELAY_MS = 1000
@@ -137,7 +142,7 @@ const createSharedSubscriptionEntry = (
/**
* Mirrors SWR's MutatorCallback: consumers can pass either a plain value or a
* functional updater `(current?: T) => T`. The functional form is resolved
* against the current cache entry before calling `queryClient.setQueryData`.
* against the current cache entry before calling `setCacheData`.
*/
type NextFn<T> = (
error?: any,
@@ -205,7 +210,7 @@ export const useMihomoWsSubscription = <T>(
): T => {
if (typeof data === 'function') {
const updater = data as (current?: T) => T | undefined
const current = queryClient.getQueryData<T>([cacheKey])
const current = getCacheData<T>([cacheKey])
return updater(current) ?? fallbackData
}
return data ?? fallbackData
@@ -215,13 +220,11 @@ export const useMihomoWsSubscription = <T>(
const response = useQuery<T>({
queryKey: responseCacheKey ? [responseCacheKey] : ['$sub$__disabled__'],
queryFn: () =>
queryClient.getQueryData<T>([responseCacheKey!]) ?? fallbackData,
queryFn: () => getCacheData<T>([responseCacheKey!]) ?? fallbackData,
initialData: () =>
queryClient.getQueryData<T>([responseCacheKey ?? '$sub$__disabled__']) ??
getCacheData<T>([responseCacheKey ?? '$sub$__disabled__']) ??
fallbackData,
staleTime: Infinity,
gcTime: 30_000,
enabled: subscriptionCacheKey !== null,
})
@@ -248,7 +251,7 @@ export const useMihomoWsSubscription = <T>(
}
if (data === undefined) return
const resolved = resolveNextData(data, subscriptionCacheKey)
queryClient.setQueryData<T>([subscriptionCacheKey], resolved)
setCacheData<T>([subscriptionCacheKey], resolved)
}
if (throttleMs && throttleMs > 0) {
@@ -351,7 +354,7 @@ export const useMihomoWsSubscription = <T>(
const refresh = useCallback(() => {
if (subscriptionCacheKey) {
queryClient.removeQueries({ queryKey: [subscriptionCacheKey] })
removeCacheData([subscriptionCacheKey])
}
setDate(Date.now())
}, [subscriptionCacheKey, setDate])
+2 -3
View File
@@ -6,8 +6,7 @@ import {
patchProfile,
patchProfilesConfig,
} from '@/services/cmds'
import { useQuery } from '@/services/query-client'
import { queryClient } from '@/services/query-client'
import { setCacheData, useQuery } from '@/services/query-client'
import { debugLog } from '@/utils/debug'
export const useProfiles = () => {
@@ -201,7 +200,7 @@ export const useProfiles = () => {
await patchProfile(current.uid, { selected: newSelected })
debugLog('[ActivateSelected] 代理选择配置保存成功')
queryClient.setQueryData(['getProxies'], await calcuProxies())
setCacheData(['getProxies'], await calcuProxies())
} catch (error: unknown) {
console.error(
'[ActivateSelected] 保存代理选择配置失败:',
+3 -10
View File
@@ -4,8 +4,7 @@ import { closeAllConnections } from 'tauri-plugin-mihomo-api'
import { useVerge } from '@/hooks/use-verge'
import { useClashConfigData, useSystemData } from '@/providers/app-data-context'
import { getAutotemProxy } from '@/services/cmds'
import { useQuery } from '@/services/query-client'
import { queryClient } from '@/services/query-client'
import { revalidateQueries, useQuery } from '@/services/query-client'
// 系统代理状态检测统一逻辑
export const useSystemProxyState = () => {
@@ -65,18 +64,12 @@ export const useSystemProxyState = () => {
}
} finally {
busyRef.current = false
await Promise.all([
queryClient.invalidateQueries({ queryKey: ['getSystemProxy'] }),
queryClient.invalidateQueries({ queryKey: ['getAutotemProxy'] }),
])
await revalidateQueries([['getSystemProxy'], ['getAutotemProxy']])
}
}
const invalidateProxyState = () =>
Promise.all([
queryClient.invalidateQueries({ queryKey: ['getSystemProxy'] }),
queryClient.invalidateQueries({ queryKey: ['getAutotemProxy'] }),
])
revalidateQueries([['getSystemProxy'], ['getAutotemProxy']])
return {
indicator,
+5 -1
View File
@@ -5,6 +5,7 @@ import { showNotice } from '@/services/notice-service'
import { useQuery } from '@/services/query-client'
import { useVerge } from './use-verge'
import { useVisibility } from './use-visibility'
export interface SystemState {
runningMode: 'Sidecar' | 'Service'
@@ -27,6 +28,7 @@ const STARTUP_GRACE_MS = 10_000
*/
export function useSystemState() {
const { verge, patchVerge } = useVerge()
const pageVisible = useVisibility()
const disablingTunRef = useRef(false)
const [isStartingUp, setIsStartingUp] = useState(true)
@@ -49,7 +51,9 @@ export function useSystemState() {
])
return { runningMode, isAdminMode, isServiceOk } as SystemState
},
refetchInterval: isStartingUp ? 2000 : 30000,
refetchInterval: pageVisible ? (isStartingUp ? 2000 : 30000) : false,
refetchOnWindowFocus: true,
refetchOnReconnect: true,
})
const isSidecarMode = systemState.runningMode === 'Sidecar'
+3 -3
View File
@@ -1,5 +1,4 @@
import { useQuery } from '@/services/query-client'
import { queryClient } from '@/services/query-client'
import { setCacheData, useQuery } from '@/services/query-client'
import { checkUpdateSafe } from '@/services/update'
import { useVerge } from './use-verge'
@@ -24,7 +23,7 @@ export const readLastCheckTime = (): number | null => {
export const updateLastCheckTime = (timestamp?: number): number => {
const now = timestamp ?? Date.now()
localStorage.setItem(LAST_CHECK_KEY, now.toString())
queryClient.setQueryData([LAST_CHECK_KEY], now)
setCacheData([LAST_CHECK_KEY], now)
return now
}
@@ -54,6 +53,7 @@ export const useUpdate = (enabled: boolean = true) => {
retry: 2,
staleTime: 60 * 60 * 1000,
refetchInterval: 24 * 60 * 60 * 1000,
refetchIntervalInBackground: false,
refetchOnWindowFocus: false,
})
+4 -4
View File
@@ -2,7 +2,7 @@ import { useCallback } from 'react'
import { getVergeConfig, patchVergeConfig } from '@/services/cmds'
import { getPreloadConfig, setPreloadConfig } from '@/services/preload'
import { queryClient, useQuery } from '@/services/query-client'
import { getCacheData, setCacheData, useQuery } from '@/services/query-client'
export const useVerge = () => {
const initialVergeConfig = getPreloadConfig()
@@ -30,11 +30,11 @@ export const useVerge = () => {
return
}
if (typeof updaterOrData === 'function') {
const prev = queryClient.getQueryData<IVergeConfig>(['getVergeConfig'])
const prev = getCacheData<IVergeConfig>(['getVergeConfig'])
const next = updaterOrData(prev)
queryClient.setQueryData(['getVergeConfig'], next)
setCacheData(['getVergeConfig'], next)
} else {
queryClient.setQueryData(['getVergeConfig'], updaterOrData)
setCacheData(['getVergeConfig'], updaterOrData)
}
}