Files
clash-verge-rev/src/components/proxy/use-head-state.ts
T
wonfen 5e6a696087 revert(tray): revert per-group latency testing (#8173)
This reverts commit cb751052a4.

Remove the tray latency test and its dashboard URL persistence and cache
changes because the two entry points have diverging behavior.

Preserve the subsequent IPC binding migration and remove generated fields,
input projections, and locale entries that depended on the reverted feature.
2026-10-21 05:37:18 +08:00

108 lines
2.6 KiB
TypeScript

import { useCallback, useEffect, useReducer } from 'react'
import { useProfiles } from '@/hooks/use-profiles'
import { ProxySortType } from './use-filter-sort'
export interface HeadState {
open?: boolean
showType: boolean
sortType: ProxySortType
filterText: string
filterMatchCase?: boolean
filterMatchWholeWord?: boolean
filterUseRegularExpression?: boolean
textState: 'url' | 'filter' | null
testUrl: string
}
type HeadStateStorage = Record<string, Record<string, HeadState>>
const HEAD_STATE_KEY = 'proxy-head-state'
export const DEFAULT_STATE: HeadState = {
open: false,
showType: true,
sortType: 0,
filterText: '',
filterMatchCase: false,
filterMatchWholeWord: false,
filterUseRegularExpression: false,
textState: null,
testUrl: '',
}
type HeadStateAction =
| { type: 'reset' }
| { type: 'replace'; payload: Record<string, HeadState> }
| { type: 'update'; groupName: string; patch: Partial<HeadState> }
function headStateReducer(
state: Record<string, HeadState>,
action: HeadStateAction,
): Record<string, HeadState> {
switch (action.type) {
case 'reset':
return {}
case 'replace':
return action.payload
case 'update': {
const prev = state[action.groupName] || DEFAULT_STATE
return { ...state, [action.groupName]: { ...prev, ...action.patch } }
}
default:
return state
}
}
export function useHeadStateNew() {
const { profiles } = useProfiles()
const current = profiles?.current || ''
const [state, dispatch] = useReducer(headStateReducer, {})
useEffect(() => {
try {
const data = JSON.parse(
localStorage.getItem(HEAD_STATE_KEY)!,
) as HeadStateStorage
const value = data[current] || {}
if (value && typeof value === 'object') {
dispatch({ type: 'replace', payload: value })
} else {
dispatch({ type: 'reset' })
}
} catch {
dispatch({ type: 'reset' })
}
}, [current])
useEffect(() => {
const timer = setTimeout(() => {
try {
const item = localStorage.getItem(HEAD_STATE_KEY)
let data = (item ? JSON.parse(item) : {}) as HeadStateStorage
if (!data || typeof data !== 'object') data = {}
data[current] = state
localStorage.setItem(HEAD_STATE_KEY, JSON.stringify(data))
} catch {}
})
return () => clearTimeout(timer)
}, [state, current])
const setHeadState = useCallback(
(groupName: string, obj: Partial<HeadState>) => {
dispatch({ type: 'update', groupName, patch: obj })
},
[],
)
return [state, setHeadState] as const
}