JAVASCRIPT
Custom Hook for Local Storage Persistence
Learn to build a reusable custom React hook, `useLocalStorage`, to effortlessly synchronize component state with the browser's local storage for persistent data management.
import React, { useState, useEffect } from 'react';
function useLocalStorage(key, initialValue) {
// State to store our value
// Pass initial state function to useState so logic is only executed once
const [storedValue, setStoredValue] = useState(() => {
try {
const item = window.localStorage.getItem(key);
return item ? JSON.parse(item) : initialValue;
} catch (error) {
console.error(`Error reading local storage key "${key}":`, error);
return initialValue;
}
});
// useEffect to update local storage when the state changes
useEffect(() => {
try {
window.localStorage.setItem(key, JSON.stringify(storedValue));
} catch (error) {
console.error(`Error writing to local storage key "${key}":`, error);
}
}, [key, storedValue]); // Re-run if key or storedValue changes
return [storedValue, setStoredValue];
}
// Example Usage Component
function SettingsPanel() {
const [userName, setUserName] = useLocalStorage('userName', 'Guest');
const [notificationsEnabled, setNotificationsEnabled] = useLocalStorage('notifications', true);
return (
<div>
<h2>User Settings</h2>
<label>
User Name:
<input
type="text"
value={userName}
onChange={(e) => setUserName(e.target.value)}
/>
</label>
<p>Hello, {userName}!</p>
<label>
<input
type="checkbox"
checked={notificationsEnabled}
onChange={(e) => setNotificationsEnabled(e.target.checked)}
/>
Enable Notifications
</label>
<p>Notifications are {notificationsEnabled ? 'enabled' : 'disabled'}.</p>
<button onClick={() => {
setUserName('Reset User');
setNotificationsEnabled(false);
}}>Reset Settings</button>
</div>
);
}
export default SettingsPanel;
How it works: This snippet provides a custom React hook `useLocalStorage` that seamlessly synchronizes a piece of component state with the browser's local storage. It initializes the state by attempting to retrieve a previously stored value, or defaults to an `initialValue`. An `useEffect` hook ensures that whenever the `storedValue` changes, the new value is automatically persisted to local storage, making the data persistent across browser sessions and reloads. This pattern creates highly reusable state management for persistent user preferences or data.