Created
January 15, 2021 00:20
-
-
Save coreyward/50e4a8c387ce476b362c2c6f128ad61f to your computer and use it in GitHub Desktop.
Persisted useState hook backed by the Local Storage API
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { useState, useCallback, useEffect } from "react" | |
/** | |
* Similar to `useState` but with some lightweight behind-the-scenes | |
* writing to localStorage; also subscribes to changes in localStorage | |
* | |
* @param {string} key The string key name to be written to localStorage | |
* @param {object} options | |
* @param {*} options.initialValue Initial value for setState | |
* @param {boolean} options.bool Treat values as boolean types | |
* @returns | |
*/ | |
const useStorage = (key, { initialValue, bool }) => { | |
const [value, setValue] = useState(initialValue) | |
useEffect(() => { | |
const rawValue = window.localStorage.getItem(key) | |
if (rawValue != null) setValue(bool ? parseRawValue(rawValue) : rawValue) | |
const handleChanges = (e) => { | |
if (e.key === key) { | |
setValue(bool ? parseRawValue(e.newValue) : e.newValue) | |
} | |
} | |
window.addEventListener("storage", handleChanges) | |
return () => { | |
window.removeEventListener("storage", handleChanges) | |
} | |
}, [key, bool]) | |
const updater = useCallback( | |
(newValue) => { | |
setValue(newValue) | |
window.localStorage.setItem(key, newValue) | |
}, | |
[key] | |
) | |
return [value, updater] | |
} | |
export default useStorage | |
const parseRawValue = (rawValue) => | |
rawValue === "true" || rawValue === "1" | |
? true | |
: rawValue === "false" || rawValue === "0" | |
? false | |
: rawValue |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment