30 lines
812 B
TypeScript
30 lines
812 B
TypeScript
|
|
import { useState, useEffect, useCallback } from 'react'
|
||
|
|
|
||
|
|
export function useLocalStorage<T>(key: string, initialValue: T): [T, (value: T | ((prev: T) => T)) => void] {
|
||
|
|
const [storedValue, setStoredValue] = useState<T>(() => {
|
||
|
|
try {
|
||
|
|
const item = localStorage.getItem(key)
|
||
|
|
return item !== null ? (JSON.parse(item) as T) : initialValue
|
||
|
|
} catch {
|
||
|
|
return initialValue
|
||
|
|
}
|
||
|
|
})
|
||
|
|
|
||
|
|
useEffect(() => {
|
||
|
|
try {
|
||
|
|
localStorage.setItem(key, JSON.stringify(storedValue))
|
||
|
|
} catch {
|
||
|
|
// storage full or unavailable
|
||
|
|
}
|
||
|
|
}, [key, storedValue])
|
||
|
|
|
||
|
|
const setValue = useCallback((value: T | ((prev: T) => T)) => {
|
||
|
|
setStoredValue((prev) => {
|
||
|
|
const next = value instanceof Function ? value(prev) : value
|
||
|
|
return next
|
||
|
|
})
|
||
|
|
}, [])
|
||
|
|
|
||
|
|
return [storedValue, setValue]
|
||
|
|
}
|