Trabaja con localStorage como useState. Persistencia automática y sincronización entre componentes.
Trabajar con localStorage es tan simple como usar useState, pero con persistencia automática entre sesiones. Los cambios se sincronizan automáticamente entre todos los componentes que usen la misma clave.
import { useLocalStorage } from "@blifedesarrollo/hooks";function ThemeToggle() {
const [theme, { setValue: setTheme, clear: clearTheme }] = useLocalStorage({
key: "user-theme",
defaultValue: "light",
});
return (
<div>
<p>Tema actual: {theme}</p>
<button onClick={() => setTheme("dark")}>Tema Oscuro</button>
<button onClick={() => setTheme("light")}>Tema Claro</button>
<button onClick={clearTheme}>Resetear</button>
</div>
);
}Cómo funciona:
[valor, { setValue, clear }] como useStatesetValue acepta valor directo o función updater// Objeto
const [user, { setValue }] = useLocalStorage({
key: "current-user",
defaultValue: { name: "", email: "" },
});
// Array
const [items, { setValue }] = useLocalStorage({
key: "shopping-cart",
defaultValue: [],
});
// Objeto complejo
const [settings, { setValue }] = useLocalStorage({
key: "app-settings",
defaultValue: {
theme: "light",
language: "es",
notifications: true,
},
});const [count, { setValue }] = useLocalStorage({
key: "counter",
defaultValue: 0,
});
// Valor directo
setValue(5);
// Función updater (como useState)
setValue((prev) => prev + 1);
// Actualizar objeto parcialmente
setValue((prev) => ({ ...prev, theme: "dark" }));Los componentes que usen la misma clave se sincronizan automáticamente:
// Componente A
function ComponentA() {
const [count, { setValue }] = useLocalStorage({
key: "shared-counter",
defaultValue: 0,
});
return <button onClick={() => setValue(count + 1)}>Contador A: {count}</button>;
}
// Componente B (se actualiza automáticamente)
function ComponentB() {
const [count] = useLocalStorage({
key: "shared-counter", // ← Misma clave
defaultValue: 0,
});
return <p>Contador B: {count}</p>; // Se actualiza automáticamente
}function UserSettings() {
const [settings, { setValue: setSettings }] = useLocalStorage({
key: "user-settings",
defaultValue: {
theme: "light",
language: "es",
notifications: true,
},
});
const updateSetting = (key, value) => {
setSettings((prev) => ({ ...prev, [key]: value }));
};
return (
<div>
<label>
<input
type="checkbox"
checked={settings.notifications}
onChange={(e) => updateSetting("notifications", e.target.checked)}
/>
Notificaciones
</label>
<select value={settings.language} onChange={(e) => updateSetting("language", e.target.value)}>
<option value="es">Español</option>
<option value="en">English</option>
</select>
</div>
);
}function AutoSaveForm() {
const [formData, { setValue: setFormData, clear: clearForm }] = useLocalStorage({
key: "draft-form",
defaultValue: {
title: "",
description: "",
category: "",
},
});
const updateField = (field, value) => {
setFormData((prev) => ({ ...prev, [field]: value }));
};
const handleSubmit = async (e) => {
e.preventDefault();
await submitForm(formData);
clearForm(); // Limpiar después de envío exitoso
};
return (
<form onSubmit={handleSubmit}>
<input
type="text"
value={formData.title}
onChange={(e) => updateField("title", e.target.value)}
placeholder="Título..."
/>
<textarea
value={formData.description}
onChange={(e) => updateField("description", e.target.value)}
placeholder="Descripción..."
/>
<button type="submit">Enviar</button>
<button type="button" onClick={clearForm}>
Limpiar
</button>
</form>
);
}| Parámetro | Tipo | Requerido | Descripción |
|---|---|---|---|
key | string | Sí | Clave única para identificar el valor |
defaultValue | any | Sí | Valor por defecto si no existe |
Retorna un array con dos elementos:
const [value, { setValue, clear }] = useLocalStorage({ key, defaultValue });| Elemento | Tipo | Descripción |
|---|---|---|
value | any | Valor actual (parseado de JSON) |
setValue | (value | updater) => void | Establece un nuevo valor (como useState) |
clear | () => void | Elimina el valor del localStorage |
Formas de usar setValue:
setValue(nuevoValor) → Establece valor directosetValue((prev) => nuevoValor) → Usa función updater