feat(service): add localStorage custom React hooks

Created a new service, localStorage.ts to handle localStorage operations in React, introducing two new custom hooks, useLocalStorage and useEncodedLocalStorage. These hooks provide functionalities to store, retrieve, and update data in the browser's localStorage.
This commit is contained in:
Mathis H (Avnyr) 2024-06-06 14:04:44 +02:00
parent bde56f4bb2
commit 7910c5ef25

View File

@ -0,0 +1,74 @@
'use client'
import React, {useEffect, useState} from "react";
/**
* A custom React hook that allows you to store and retrieve data in the browser's localStorage.
*
* @param {string} key - The key under which the data should be stored in localStorage.
* @param {T} initial - The initial value for the stored data.
* @returns {[T, React.Dispatch<React.SetStateAction<T>>]} - An array containing the stored value and a function to update the stored value.
*/
export function useLocalStorage<T>(key: string, initial: T): [T, React.Dispatch<React.SetStateAction<T>>] {
const readValue = () => {
const item = typeof window !== 'undefined' ? window.localStorage.getItem(key) : null
if (item) {
try {
return JSON.parse(item)
} catch(error) {
console.warn(`Error reading localStorage key “${key}”:`, error)
}
}
return initial
}
const [storedValue, setStoredValue] = useState<T>(readValue)
useEffect(() => {
try {
typeof window !== 'undefined' && window.localStorage.setItem(key, JSON.stringify(storedValue))
} catch (error) {
console.warn(`Error setting localStorage key “${key}”:`, error)
}
}, [key, storedValue])
return [storedValue, setStoredValue]
}
/**
* Custom hook that provides a way to store and retrieve encoded values in local storage.
*
* @template T - The type of the value to be stored.
*
* @param {string} key - The key to be used for storing the encoded value in local storage.
* @param {T} fallbackValue - The fallback value to be used if no value is found in local storage.
*
* @return {readonly [T, React.Dispatch<React.SetStateAction<T>>]} - An array containing the encoded value and a function to update the encoded value.
*/
export function useEncodedLocalStorage<T>(key: string, fallbackValue: T): readonly [T, React.Dispatch<React.SetStateAction<T>>] {
const [encodedValue, setEncodedValue] = useState<T>(() => {
const stored = localStorage.getItem(key);
return stored ? safelyParse(stored, fallbackValue) : fallbackValue;
});
useEffect(() => {
localStorage.setItem(key, safelyStringify(encodedValue));
}, [key, encodedValue]);
return [encodedValue, setEncodedValue] as const;
function safelyParse(stored: string, fallback: T): T {
try {
return JSON.parse(atob(stored));
} catch {
return fallback;
}
}
function safelyStringify(value: T): string {
try {
return btoa(JSON.stringify(value));
} catch {
return btoa(JSON.stringify(fallbackValue));
}
}
}