DEV Community πŸ‘©β€πŸ’»πŸ‘¨β€πŸ’»

Cover image for Project 69 of 100 - Basic Redux Subscriber
James Hubert
James Hubert

Posted on • Updated on

Project 69 of 100 - Basic Redux Subscriber

Hey! I'm on a mission to make 100 React.js projects ending May 31st. Please follow my dev.to profile or my twitter for updates and feel free to reach out if you have questions. Thanks for your support!

Link to today's deployed app: Link
Link to the repo: github

This project is exciting not in material but in the milestone it represents. I'm finally learning Redux, one of the many buzzwords that populate the majority of React job ads online. As the Scrimba React grand master Bob Ziroll points out, the Context API is now pretty fully fleshed out, so Redux may not be as necessary as it used to be for state management in React apps. That said, it's still widely used and is perceived as being an enterprise state management tool, so it's cool to finally get it on the tool belt.

1 - Setting up Redux

// 1 - import redux
const redux = require('redux')

// 2 - create actions
function increment() {
  return {type: "INCREMENT"}
}

function decrement() {
  return {type: "DECREMENT"}
}

function double() {
  return {type: "DOUBLE"}
}

function halve() {
  return {type: "HALVE"}
}

// 3 - create reducer
function reducer(state = {count: 0}, action) {
  switch (action.type) {
    case "INCREMENT":
      return {count: state.count + 1}
    case "DECREMENT":
      return {count: state.count - 1}
    case "DOUBLE":
      return {count: state.count * 2}
    case "HALVE":
      return {count: Math.floor(state.count / 2)}
    default:
      return state
  }
}

// 4 - create store from reducer
const store = redux.createStore(reducer)

// 5 - subscribe to store changes and console.log() them
store.subscribe(() => {
  console.log(store.getState())
})

// 6 - call actions
export {increment,decrement,double,halve,store};
Enter fullscreen mode Exit fullscreen mode

As you can see above, first we include the Redux package in our application. I did all of the above in a file called redux.js in the src folder. After including the packing with Require, I built four simple functions called actions to manipulate the count variable we are going to be returning in state. Notice that we return objects where only the value of the type changes and not of the type itself. This is for extensibility later.

Next, we create a reducer. This is the function that can be used later to actually read state directly and then return results of state being manipulated, without changing state itself. Pretty neat!

The next step is to create a store using the redux.createStore() method and using our reducer as the argument. This sort of creates a distinct state which can keep track of changes to a sort of subsidiary, subscribed state without changing the app-wide state; a key part of the Redux philosophy.

Next, we subscribe to changes in the store, which occur when any of the action functions are run. When a change occurs I'm just going to console.log() it into dev tools.

I then export all four actions for use elsewhere in the application and I export the store we created so it can be read- again, this is distinct from app-wide state.

2 - Interacting with Redux in a React File

In my file I created four simple buttons- a control panel that will call the four Redux actions we defined earlier. I am simply doing this is the App file in src.

To interact with the Redux file I have simple imported the file and destructured the four actions from it as well as the store for use here in this component. I've placed calls to call the store.dispatch() function we defined earlier with the actions called as arguments in handler functions because I know we are going to have 4 buttons with that each has one of these abilities.

import {increment,decrement,double,halve,store} from './redux'
import './App.css';

function App() {

  function handleIncrement() {
    store.dispatch(increment())
  }

  function handleDecrement() {
    store.dispatch(decrement())
  }

  function handleDouble() {
    store.dispatch(double())
  }

  function handleHalve() {
    store.dispatch(halve())
  }

  return (...)
...
Enter fullscreen mode Exit fullscreen mode

Now in JSX we simply write the buttons out and place the handlers in onClick props to call them when clicked.

// App.js
...
  return (
    <div className="App">
      <div className='App__buttonsContainer'>
        <h1>Simple Redux Control Panel</h1>
        <p>Open your broswer dev tools and watch for console.log() changes upon clicking the buttons. They are minupulating app-wide state directly through Redux.</p>
        <button onClick={handleIncrement}>Increment</button>
        <button onClick={handleDecrement}>Decrement</button>
        <button onClick={handleDouble}>Double</button>
        <button onClick={handleHalve}>Halve</button>
      </div>
    </div>
  );
Enter fullscreen mode Exit fullscreen mode

Now if you open your developer console you'll see those changes logged as you click the different buttons.

If you like projects like this and want to stay up to date with more, check out my Twitter @jwhubert91, I follow back! See you tomorrow for another project.

Top comments (0)

Here is a post you might want to check out:

Regex for lazy developers

regex for lazy devs

Sorry for the callout πŸ˜†