{"id":498,"date":"2020-04-01T18:15:58","date_gmt":"2020-04-01T18:15:58","guid":{"rendered":"https:\/\/www.loadsys.com\/blog\/redux-toolkit-with-react-and-react-native\/"},"modified":"2025-01-15T03:09:19","modified_gmt":"2025-01-15T03:09:19","slug":"redux-toolkit-with-react-and-react-native","status":"publish","type":"post","link":"https:\/\/www.loadsys.com\/blog\/redux-toolkit-with-react-and-react-native\/","title":{"rendered":"Redux Toolkit with React and React Native"},"content":{"rendered":"<p class=\"p1\">React is a super fast, reliable Javascript framework for single page applications with responsive UI. React and Redux work perfectly together. Redux is a very flexible immutable state management tool built for performance and customization. Redux helps to keep track of the state and data for React screens and components.<\/p>\n<p class=\"p1\">Setting up <a href=\"https:\/\/redux.js.org\/\" target=\"_blank\" rel=\"noopener noreferrer\">Redux<\/a> with <a href=\"https:\/\/reactjs.org\/\" target=\"_blank\" rel=\"noopener noreferrer\">React<\/a> could feel like a very confusing and complicated process. There are many packages to install and writing quite a bit of boiler plate code is needed to get redux to do anything. That&#8217;s where Redux Toolkit steps in.<\/p>\n<p class=\"p1\">Redux Toolkit very is simple to setup, it provides immutable update logic and warnings if your state mutates outside the state. The toolkit allows to merge the state object many levels deep through a proxy by just assigning a value to an object. You no longer need to use spread operator to merge the objects:<\/p>\n<p class=\"p1\">Before:<\/p>\n<pre class=\"lang:default decode:true\">state = {\n  user: {\n    firstName: 'User',\n    lastName: 'Last',\n    ...newUser,\n  groups: {\n    sales: true,\n    hr: false,\n    admin: false,\n    ...newUser.groups\n  }\n}<\/pre>\n<p class=\"p1\">After:<\/p>\n<pre class=\"lang:js decode:true\">state = _.deepMerge(state, newUser);<\/pre>\n<p class=\"p1\">Redux Toolkit provides a very useful feature that allows to create the whole state management in one call and keep all of the logic and actions in the same place. There is no need to separate actions and reducers into separate files.<\/p>\n<p class=\"p1\">Instead of:<\/p>\n<pre class=\"lang:default decode:true \">const increment = createAction('INCREMENT')\nconst decrement = createAction('DECREMENT')\n\nconst reducer = createReducer(0, {\n\u00a0 [increment]: state =&gt; state + 1,\n\u00a0 [decrement]: state =&gt; state - 1\n})<\/pre>\n<p class=\"p1\">Now we can do:<\/p>\n<pre class=\"lang:default decode:true\">const counterSlice = createSlice({\n\u00a0 name: 'counter',\n\u00a0 initialState: 0,\n\u00a0 reducers: {\n\u00a0 \u00a0 increment: state =&gt; state + 1,\n\u00a0 \u00a0 decrement: state =&gt; state - 1\n\u00a0 }\n})\n\nconst {\n  increment,\n  decrement\n} = counterSlice.actions;\n\nconst reducer = counterSice.reducer;<\/pre>\n<p class=\"p1\">createSlice allows us to configure all the actions as functions and define actions as functions and control types of passed functions, which is a must when working with Typescript. With Redux Toolkit, we can create<span class=\"Apple-converted-space\">\u00a0 <\/span>a completely type safe state and actions.<\/p>\n<p class=\"p1\">Here is an example:<\/p>\n<pre class=\"lang:default decode:true \">import { createSlice, PayloadAction } from 'redux-starter-kit';\nimport { CompanyParams } from '..\/..\/schema\/company';\nimport * as StateHelpers from '..\/..\/redux\/stateHelpers';\nimport _ from 'lodash';\n\ninterface CompaniesState {\n\u00a0 companiesStatus: StateHelpers.StateStatusProps,\n\u00a0 activeCompanyId: string,\n\u00a0 companies: CompanyParams[],\n}\n\nconst initialState: CompaniesState = {\n\u00a0 companiesStatus: null,\n\u00a0 activeCompanyId: null,\n\u00a0 companies: [],\n};\n\nconst findIndex = (companies: CompanyParams[], searchId: string) =&gt; {\n\u00a0 return _.findIndex(companies, company =&gt; {\n\u00a0 \u00a0 return company.id === searchId;\n\u00a0 });\n};\n\nconst companies = createSlice({\n\u00a0 name: 'companies',\n\u00a0 initialState: initialState,\n\u00a0 reducers: {\n\u00a0 \u00a0 updateStatus(state, action: PayloadAction&lt;Partial&lt;StateHelpers.StateStatusProps&gt;&gt;) {\n\u00a0 \u00a0 \u00a0 state.companiesStatus = StateHelpers.updateStatus(state.companiesStatus, action.payload);\n\u00a0 \u00a0 },\n\n\u00a0 \u00a0 saveCompanies(state, action: PayloadAction&lt;CompanyParams[]&gt;) {\n\u00a0 \u00a0 \u00a0 \u00a0 state.companies = action.payload;\n\u00a0 \u00a0 \u00a0 \u00a0 state.companiesStatus = StateHelpers.updateStatus(state.companiesStatus, {status: StateHelpers.StateStatuses.FETCHED});\n\u00a0 \u00a0 },\n\n\u00a0 \u00a0 saveCompany(state, action: PayloadAction&lt;CompanyParams&gt;) {\n\u00a0 \u00a0 \u00a0 const company = action.payload;\n\u00a0 \u00a0 \u00a0 const index = findIndex(state.companies, company.id);\n\u00a0 \u00a0 \u00a0 const companies = _.cloneDeep(state.companies);\n\u00a0 \u00a0 \u00a0 if (index &gt;= 0) {\n\u00a0 \u00a0 \u00a0 \u00a0 \u00a0 if (!_.isEmpty(company.deleted)) {\n\u00a0 \u00a0 \u00a0 \u00a0 \u00a0 \u00a0 \u00a0 companies.splice(index, 1);\n\u00a0 \u00a0 \u00a0 \u00a0 \u00a0 } else {\n\u00a0 \u00a0 \u00a0 \u00a0 \u00a0 \u00a0 \u00a0 companies[index] = company;\n\u00a0 \u00a0 \u00a0 \u00a0 \u00a0 }\n\u00a0 \u00a0 \u00a0 \u00a0 \u00a0 state.companies = companies;\n\u00a0 \u00a0 \u00a0 }\n\u00a0 \u00a0 \u00a0 else if (company.id &amp;&amp; _.isEmpty(company.deleted)) {\n\u00a0 \u00a0 \u00a0 \u00a0 \u00a0 companies.unshift(company);\n\u00a0 \u00a0 \u00a0 \u00a0 \u00a0 state.companies = companies;\n\u00a0 \u00a0 \u00a0 }\n\u00a0 \u00a0 },\n\u00a0 \u00a0 updateCompany(state, action: PayloadAction&lt;Partial&lt;CompanyParams&gt;&gt;) {\n\u00a0 \u00a0 \u00a0 const company = action.payload;\n\u00a0 \u00a0 \u00a0 const index = findIndex(state.companies, company.id);\n\u00a0 \u00a0 \u00a0 const companies = _.cloneDeep(state.companies);\n\u00a0 \u00a0 \u00a0 if (index &gt;= 0) {\n\u00a0 \u00a0 \u00a0 \u00a0 \u00a0 companies[index] = {...companies[index], ...company};\n\u00a0 \u00a0 \u00a0 \u00a0 \u00a0 state.companies = companies;\n\u00a0 \u00a0 \u00a0 }\n\u00a0 \u00a0 },\n\u00a0 \u00a0 selectCompany(state, action: any) {\n\u00a0 \u00a0 \u00a0 state.activeCompanyId = action.payload;\n\u00a0 \u00a0 }\n\u00a0 }\n});\n\nexport const {\n\u00a0 updateStatus,\n\u00a0 saveCompanies,\n\u00a0 saveCompany,\n\u00a0 updateCompany,\n\u00a0 selectCompany,\n} = companies.actions\n\nexport default companies.reducer;<\/pre>\n<p class=\"p1\">Redux Toolkit is very opinionated framework forcing developers to follow the guidelines and write the code in a similar manner thus simplifying maintenance and training. The Typescript support helps to minimize errors and testing by enforcing concrete types.<\/p>\n<p><a href=\"https:\/\/www.loadsys.com\/contact-us\/\">Contact us today<\/a> for any React, React Native, or Redux support.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>React is a super fast, reliable Javascript framework for single page applications with responsive UI. React and Redux work perfectly together. Redux is a very flexible immutable state management tool built for performance and customization. Redux helps to keep track of the state and data for React screens and components. Setting up Redux with React [&hellip;]<\/p>\n","protected":false},"author":2,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"inline_featured_image":false,"_daextam_enable_autolinks":"","_analytify_skip_tracking":false,"footnotes":""},"categories":[90,94,95,74],"tags":[],"ttd_topic":[542,484,545,487,549,209,528,496,553,240],"class_list":["post-498","post","type-post","status-publish","format-standard","hentry","category-mobile-development","category-react","category-react-native","category-web-development","ttd_topic-clonedeep","ttd_topic-company","ttd_topic-deepmerge","ttd_topic-javascript","ttd_topic-lodash","ttd_topic-react","ttd_topic-react-native","ttd_topic-redux","ttd_topic-state-management","ttd_topic-typescript"],"acf":[],"_links":{"self":[{"href":"https:\/\/www.loadsys.com\/wp-json\/wp\/v2\/posts\/498","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.loadsys.com\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.loadsys.com\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.loadsys.com\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/www.loadsys.com\/wp-json\/wp\/v2\/comments?post=498"}],"version-history":[{"count":0,"href":"https:\/\/www.loadsys.com\/wp-json\/wp\/v2\/posts\/498\/revisions"}],"wp:attachment":[{"href":"https:\/\/www.loadsys.com\/wp-json\/wp\/v2\/media?parent=498"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.loadsys.com\/wp-json\/wp\/v2\/categories?post=498"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.loadsys.com\/wp-json\/wp\/v2\/tags?post=498"},{"taxonomy":"ttd_topic","embeddable":true,"href":"https:\/\/www.loadsys.com\/wp-json\/wp\/v2\/ttd_topic?post=498"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}