Quiero persistir algunas partes de mi árbol de estado en localStorage. ¿Cuál es el lugar apropiado para hacerlo? ¿Reductor o acción?
fuente
Quiero persistir algunas partes de mi árbol de estado en localStorage. ¿Cuál es el lugar apropiado para hacerlo? ¿Reductor o acción?
Reductor nunca es un lugar apropiado para hacer esto porque los reductores deben ser puros y no tener efectos secundarios.
Recomendaría solo hacerlo en un suscriptor:
store.subscribe(() => {
// persist your state
})
Antes de crear la tienda, lea esas partes persistentes:
const persistedState = // ...
const store = createStore(reducer, persistedState)
Si usa combineReducers()
, notará que los reductores que no han recibido el estado se "arrancarán" normalmente usando su valor de state
argumento predeterminado . Esto puede ser bastante útil.
Es recomendable que renuncies a tu suscriptor para que no escribas en localStorage demasiado rápido, o tendrás problemas de rendimiento.
Finalmente, puede crear un middleware que encapsule eso como una alternativa, pero comenzaría con un suscriptor porque es una solución más simple y funciona bien.
Para completar los espacios en blanco de la respuesta de Dan Abramov, podría usar
store.subscribe()
así:Antes de crear la tienda, verifique
localStorage
y analice cualquier JSON bajo su clave de esta manera:Luego pasa esta
persistedState
constante a sucreateStore
método de esta manera:fuente
persistedState
regresar eninitialState
lugar de un objeto vacío? De lo contrario, creo quecreateStore
se inicializará con ese objeto vacío.En una palabra: middleware.
Echa un vistazo a redux-persist . O escribe el tuyo.
[ACTUALIZACIÓN 18 de diciembre de 2016] Editado para eliminar la mención de dos proyectos similares ahora inactivos o en desuso.
fuente
Si alguien tiene algún problema con las soluciones anteriores, puede escribir el suyo. Déjame mostrarte lo que hice. Ignorar las
saga middleware
cosas solo se centran en dos cosaslocalStorageMiddleware
yreHydrateStore
métodos. ellocalStorageMiddleware
extrae todoredux state
y lo colocalocal storage
yrehydrateStore
extrae todo elapplicationState
almacenamiento local si está presente y lo coloca enredux store
fuente
localStorage
incluso cuando nada en la tienda ha cambiado? Cómo compensa las escrituras innecesariasNo puedo responder a @Gardezi, pero una opción basada en su código podría ser:
la diferencia es que solo estamos guardando algunas acciones, podría utilizar una función antirrebote para guardar solo la última interacción de su estado
fuente
Llegué un poco tarde, pero implementé un estado persistente de acuerdo con los ejemplos aquí expuestos. Si desea actualizar el estado solo cada X segundos, este enfoque puede ayudarlo a:
Definir una función de contenedor
Llame a una función de contenedor en su suscriptor
En este ejemplo, el estado se actualiza como máximo cada 5 segundos, independientemente de la frecuencia con que se active una actualización.
fuente
(state) => { updateLocalStorage(store.getState()) }
enlodash.throttle
este aspecto:store.subscribe(throttle(() => {(state) => { updateLocalStorage(store.getState())} }
y quitar tiempo comprobando el interior de la lógica.Sobre la base de las excelentes sugerencias y extractos de código breve proporcionados en otras respuestas (y el artículo de Jam Creencia's Medium ), ¡aquí hay una solución completa!
Necesitamos un archivo que contenga 2 funciones que guarden / carguen el estado a / desde el almacenamiento local:
Esas funciones son importadas por store.js donde configuramos nuestra tienda:
NOTA: Deberá agregar una dependencia:
npm install lodash.throttle
La tienda se importa a index.js para que se pueda pasar al proveedor que envuelve App.js :
Tenga en cuenta que las importaciones absolutas requieren este cambio en YourProjectFolder / jsconfig.json : esto le indica dónde buscar archivos si no puede encontrarlos al principio. De lo contrario, verá quejas sobre el intento de importar algo desde fuera de src .
fuente