Manejo del estado con Redux y Angular
En este curso aprenderás a controlar el estado global de nuestra aplicación Angular de eCommerce mediante Redux a...
Redux Toolkit permite gestionar el estado de forma más clara y eficiente, minimizando el código repetitivo. Aprende cómo esta herramienta está cambiando el desarrollo de aplicaciones.
Si estás buscando una forma más clara de organizar tu código y mejorar tu flujo de trabajo, Redux Toolkit es la solución.
Con esta herramienta, los desarrolladores pueden manejar el estado de manera más eficiente y con menos código.
¿Quieres saber cómo Redux Toolkit te ayuda a hacer un desarrollo más ágil y sencillo?… te lo contamos en este artículo.
Redux Toolkit es una biblioteca oficial de Redux que simplifica significativamente la configuración y el uso de Redux en aplicaciones JavaScript, especialmente en aquellas desarrolladas con React.
Fue creada por el equipo oficial de Redux con el objetivo de resolver muchas de las complejidades y patrones repetitivos que surgían en la implementación tradicional de Redux, como la necesidad de escribir grandes cantidades de código boilerplate, código repetido, para configurar el estado global, las acciones y los reducers.
Con Redux Toolkit, los desarrolladores pueden acceder a un conjunto de herramientas avanzadas que no solo hacen que Redux sea más accesible, sino que también optimizan el proceso de desarrollo, mejorando tanto la productividad como la calidad del código.
El estado es lo que permite a las aplicaciones reaccionar dinámicamente a las interacciones del usuario y a los cambios en los datos. A medida que las aplicaciones crecen en tamaño y complejidad, la gestión del estado puede volverse cada vez más compleja. Suelen producirse problemas con la sincronización de estados entre diferentes componentes, el manejo de la lógica asincrónica, y la prevención de inconsistencias en el estado global.
Redux Toolkit se presenta como una solución estructurada y eficiente a estos problemas, ofreciendo herramientas que permiten a los desarrolladores manejar el estado de manera más intuitiva y con menos código. Al reducir la complejidad asociada con la gestión del estado, no solo facilita la escritura de aplicaciones más robustas y predecibles, sino que también mejora la capacidad de los equipos para mantener y escalar estas aplicaciones a medida que evolucionan.
ConfigureStore: ConfigureStore es una función que simplifica la creación del store de Redux. Automáticamente combina los reducers, funciones puras que especifican cómo cambia el estado de la aplicación en respuesta a una acción, añade el middleware de Redux Thunk y habilita la extensión Redux DevTools.
CreateSlice: CreateSlice es una función que genera automáticamente action creators y action types basados en los reducers que defines. Esto reduce significativamente el código boilerplate necesario para implementar funcionalidades de Redux.
CreateAsyncThunk: CreateAsyncThunk simplifica la gestión de acciones asíncronas en Redux. Genera automáticamente los action types para los estados pending, fulfilled y rejected de las promesas.
Uno de los beneficios más destacados de Redux Toolkit es la simplificación drástica del uso de Redux. Tradicionalmente, la configuración de Redux implicaba escribir una cantidad considerable de código boilerplate, como la definición de acciones, tipos de acciones, creadores de acciones, y el manejo de reducers.
Redux Toolkit reduce drásticamente esta complejidad al proporcionar una serie de abstracciones que automatizan muchas de estas tareas. Por ejemplo, con la función createSlice
, los desarrolladores pueden definir el estado, los reducers y las acciones de una sola vez, reduciendo significativamente el código necesario.
Además, las configuraciones predeterminadas que ofrece Redux Toolkit están diseñadas siguiendo las mejores prácticas, lo que permite a los desarrolladores enfocarse en la lógica de negocio de la aplicación en lugar de preocuparse por la configuración detallada de Redux.
Redux Toolkit no solo simplifica el proceso de configuración, sino que también mejora la eficiencia en el desarrollo. Al reducir la cantidad de código repetitivo y proporcionar herramientas integradas como createAsyncThunk
para manejar la lógica asincrónica, los desarrolladores pueden ser mucho más productivos.
Estas herramientas automatizan tareas comunes, como la creación de estados de carga y errores para peticiones asincrónicas, lo que anteriormente requería escribir código adicional y tedioso. Como resultado, el tiempo de desarrollo se acorta considerablemente, permitiendo a los equipos entregar características más rápidamente y con menos errores.
La reducción en el código escrito también disminuye las posibilidades de introducir bugs, lo que contribuye a un desarrollo más robusto y confiable.
Otra ventaja clave de Redux Toolkit es su capacidad para facilitar el mantenimiento y escalabilidad de aplicaciones grandes. A medida que una aplicación crece en complejidad, mantener un código limpio y organizado se vuelve crítico.
Redux Toolkit soporta esta necesidad al promover una estructura modular, donde el código se organiza en slices, que encapsulan de manera coherente la lógica de cada parte de la aplicación. Esto no solo mejora la legibilidad del código, sino que también facilita la incorporación de nuevas características y la refactorización del código existente.
Además, Redux Toolkit es compatible con TypeScript, lo que agrega tipado estático al estado y las acciones, ayudando a prevenir errores y mejorar la experiencia de desarrollo en aplicaciones de gran escala.
Para comenzar con Redux Toolkit, primero debes instalarlo en tu proyecto. Puedes hacerlo fácilmente usando npm o yarn:
npm install @reduxjs/toolkit react-redux
La configuración del store es el primer paso para integrar Redux Toolkit en tu aplicación. Aquí tienes un ejemplo básico:
import { configureStore } from "@reduxjs/toolkit";
import rootReducer from "./reducers";
const store = configureStore({
reducer: rootReducer,
});
export default store;
Los slices son una característica clave de Redux Toolkit. Permiten definir una porción del estado global junto con sus reducers y actions en un solo lugar:
import { createSlice } from "@reduxjs/toolkit";
const counterSlice = createSlice({
name: "counter",
initialState: 0,
reducers: {
increment: (state) => state + 1,
decrement: (state) => state - 1,
},
});
export const { increment, decrement } = counterSlice.actions;
export default counterSlice.reducer;
createAsyncThunk
createAsyncThunk
es una función proporcionada por Redux Toolkit que simplifica el manejo de operaciones asíncronas, como llamadas a API, en aplicaciones Redux. Esta función permite definir acciones asíncronas que siguen un ciclo de vida estándar (pendiente, completada, fallida) y maneja automáticamente los estados de cada paso.
Aquí tienes un ejemplo básico de cómo se utiliza createAsyncThunk
:
import { createAsyncThunk, createSlice } from "@reduxjs/toolkit";
import axios from "axios";
// Definición de la acción asíncrona
export const fetchUser = createAsyncThunk(
"user/fetchUser",
async (userId, thunkAPI) => {
const response = await axios.get(`/api/user/${userId}`);
return response.data;
}
);
// Creación del slice con los reducers generados automáticamente por createAsyncThunk
const userSlice = createSlice({
name: "user",
initialState: {
userData: null,
status: "idle",
error: null,
},
extraReducers: (builder) => {
builder
.addCase(fetchUser.pending, (state) => {
state.status = "loading";
})
.addCase(fetchUser.fulfilled, (state, action) => {
state.status = "succeeded";
state.userData = action.payload;
})
.addCase(fetchUser.rejected, (state, action) => {
state.status = "failed";
state.error = action.error.message;
});
},
});
export default userSlice.reducer;
La integración de Redux Toolkit con React simplifica considerablemente la gestión del estado en aplicaciones React al proporcionar una serie de herramientas y convenciones preconfiguradas. Redux Toolkit facilita la creación de slices, que combinan la lógica de acciones y reducers en un solo lugar, y ofrece funciones como createSlice
y configureStore
para reducir la cantidad de código repetitivo.
Además, su integración con React mediante react-redux
permite a los componentes conectarse fácilmente al estado global usando hooks como useSelector
y useDispatch
, mejorando la eficiencia y la mantenibilidad del código.
Mantener una estructura de carpetas bien organizada es primordial para asegurar que un proyecto basado en Redux Toolkit sea escalable y fácil de mantener. Una estructura clara no solo facilita la navegación por el código, sino que también permite que diferentes desarrolladores puedan trabajar de manera eficiente y sin conflictos.
Un ejemplo de una estructura de carpetas bien organizada podría verse así:
src/
components/
features/
counter/
counterSlice.js
users/
usersSlice.js
app/
store.js
App.js
En esta estructura, el directorio features
agrupa cada “slice” del estado en su propia carpeta, como counter
y users
, lo que permite que la lógica específica de cada característica esté encapsulada y sea fácilmente identificable.
Esto no solo mejora la organización, sino que también facilita la escalabilidad, ya que nuevas funcionalidades pueden añadirse creando nuevos directorios dentro de features
sin interferir con el código existente. Además, centralizar la configuración del store en app/store.js
ayuda a mantener la claridad en la gestión global del estado.
Optimizar el rendimiento es clave en aplicaciones que utilizan Redux, especialmente cuando estas comienzan a manejar grandes volúmenes de datos o a tener muchos componentes conectados al estado global. Redux Toolkit incluye varias optimizaciones de rendimiento por defecto que facilitan este proceso.
Uno de los componentes clave es el uso de Immer, que simplifica las actualizaciones inmutables del estado. Con Immer, los desarrolladores pueden escribir lógica de actualización de estado de manera más intuitiva, sin tener que preocuparse por crear copias profundas manualmente, lo que reduce el riesgo de errores y mejora el rendimiento al minimizar las operaciones innecesarias.
Además, el uso eficiente del hook useSelector
es esencial para prevenir renderizaciones innecesarias en los componentes React. useSelector
suscribe los componentes al store de Redux y desencadena una re-renderización cuando el estado al que hace referencia cambia.
Para optimizar su uso, es recomendable pasarle funciones de selección lo más específicas posible, minimizando el número de datos que el componente debe observar. También es útil memorizar los selectores con herramientas como reselect
, lo que evita cálculos redundantes y mejora el rendimiento general de la aplicación.
La mantenibilidad del código es un aspecto importante en proyectos a largo plazo, especialmente en aplicaciones grandes que siguen creciendo con el tiempo. Para asegurar que el código se mantenga limpio y fácil de trabajar, hay varias prácticas recomendadas a seguir:
Uso de slices para organizar la lógica relacionada: Cada slice debe contener la lógica relacionada con una única funcionalidad o característica de la aplicación. Esto encapsula la lógica de estado y la hace más fácil de gestionar y modificar, sin afectar otras partes de la aplicación.
Aprovechamiento de herramientas de depuración como Redux DevTools: Estas herramientas son esenciales para rastrear y entender cómo fluye el estado a través de la aplicación. Redux DevTools permite inspeccionar las acciones y el estado en cualquier momento, hacer time-travel debugging, y aplicar cambios de estado condicionalmente, lo que es invaluable para identificar y solucionar bugs.
Escritura de pruebas unitarias para reducers y thunks: Las pruebas unitarias son fundamentales para asegurar que cada parte de la lógica funcione como se espera. Al probar los reducers, puedes confirmar que las actualizaciones de estado se realicen correctamente, mientras que las pruebas de thunks aseguran que la lógica asincrónica se ejecute correctamente. Redux Toolkit, al integrar herramientas como createAsyncThunk
, facilita la escritura de estas pruebas al manejar automáticamente el ciclo de vida de las acciones asincrónicas.
Aquí tienes un ejemplo simple de cómo usar Redux Toolkit en una aplicación React para manejar un contador.
Primero, asegúrate de tener una aplicación React configurada. Si aún no la tienes, puedes crear una rápidamente usando Create React App:
npx create-react-app my-redux-app
cd my-redux-app
npm install @reduxjs/toolkit react-redux
En src/features/counter/counterSlice.js
, define el estado inicial del contador y las acciones que lo modifican usando createSlice
de Redux Toolkit:
import { createSlice } from "@reduxjs/toolkit";
export const counterSlice = createSlice({
name: "counter",
initialState: {
value: 0,
},
reducers: {
increment: (state) => {
state.value += 1;
},
decrement: (state) => {
state.value -= 1;
},
incrementByAmount: (state, action) => {
state.value += action.payload;
},
},
});
export const { increment, decrement, incrementByAmount } = counterSlice.actions;
export default counterSlice.reducer;
En src/app/store.js
, configura el store de Redux e incluye el reducer del contador:
import { configureStore } from "@reduxjs/toolkit";
import counterReducer from "../features/counter/counterSlice";
export const store = configureStore({
reducer: {
counter: counterReducer,
},
});
Envuelve tu aplicación con el Provider
de react-redux
en src/index.js
para que todos los componentes tengan acceso al store:
import React from "react";
import ReactDOM from "react-dom/client";
import "./index.css";
import App from "./App";
import { store } from "./app/store";
import { Provider } from "react-redux";
const root = ReactDOM.createRoot(document.getElementById("root"));
root.render(
<React.StrictMode>
<Provider store={store}>
<App />
</Provider>
</React.StrictMode>
);
En src/App.js
, usa el estado del contador y despacha las acciones para modificarlo:
import React from "react";
import { useSelector, useDispatch } from "react-redux";
import {
increment,
decrement,
incrementByAmount,
} from "./features/counter/counterSlice";
function App() {
const count = useSelector((state) => state.counter.value);
const dispatch = useDispatch();
return (
<div className="App">
<h1>Counter: {count}</h1>
<button onClick={() => dispatch(increment())}>Increment</button>
<button onClick={() => dispatch(decrement())}>Decrement</button>
<button onClick={() => dispatch(incrementByAmount(5))}>
Increment by 5
</button>
</div>
);
}
export default App;
Finalmente, ejecuta la aplicación con:
npm start
Ahora deberías ver un contador que se incrementa, decrementa y aumenta por 5 cuando se hacen clic en los botones. Este ejemplo muestra cómo Redux Toolkit simplifica la gestión del estado global en una aplicación React.
Redux Toolkit ha transformado la forma en que los desarrolladores implementan Redux en sus aplicaciones React. Al simplificar la configuración, reducir el código boilerplate y proporcionar herramientas poderosas para manejar operaciones asíncronas, Redux Toolkit se ha convertido en una elección popular para la gestión del estado en aplicaciones de gran escala.
Recuerda que en OpenWebinars dispones la ruta de desarrollador Frontend con React, en la que puedes profundizar en la gestión de estados con Redux Toolkit.
También te puede interesar
En este curso aprenderás a controlar el estado global de nuestra aplicación Angular de eCommerce mediante Redux a...
Uno de los perfiles más demandando por las empresas.
Astro.js no es solo una nueva herramienta más para el Desarrollo Web, es un cambio de juego que viene a redefinir la...