Rangle.io: React Training
gitbook
gitbook
  • Introduction
  • Setup
  • Functional JavaScript
  • ES6 constructs
    • Default Params
    • Template Literals
    • Destructuring
    • Arrow Functions
    • Promises
    • let and const
    • Modules
  • Thinking in Components
    • Atomic Design
    • Atomic Component Principles
    • Benefits of This Approach
    • The Process
    • Task #1
  • React Components
    • Stateless Components
    • Stateful Components
    • Stateful vs Stateless Components
    • Composition
    • Task #2
    • Task #3
    • Task #4
    • Task #5
  • Immutable
    • What Is Immutability?
    • The Case for Immutability
    • JavaScript Solutions
      • Object.assign
      • Object.freeze
    • Immutable.js Basics
      • Immutable.Map
        • Map.merge
      • Nested Objects
        • Deleting Keys
        • Maps are Iterable
      • Immutable.List
      • Performance
      • Persistent and Transient Data Structures
      • Official Documentation
    • Exercises
      • Task #1
      • Task #2
      • Task #3
      • Task #4
      • Task #5
      • Task #6
      • Task #7
  • Redux
    • Review of Reducers and Pure Functions
    • Redux Reducers
    • Redux Actions
    • Configuring your Application to use Redux
    • Using Redux with Components
    • Redux and Component Architecture
  • Routing
    • React Router
    • Router Redux
  • Forms
    • Redux Form
  • Testing
    • Setup
    • Components
    • Reducers
    • Actions
Powered by GitBook
On this page

Was this helpful?

  1. Testing

Reducers

Since reducers are pure functions, they can be tested like a JavaScript function (i.e. given an action, confirm the expected result)

Example

// ./reducers/counter.js
import { INCREMENT_COUNTER, DECREMENT_COUNTER } from '../constants';
import { fromJS } from 'immutable';

const INITIAL_STATE = fromJS({
  count: 0,
});

function counterReducer(state = INITIAL_STATE, action = {}) {
  switch (action.type) {

  case INCREMENT_COUNTER:
    return state.update('count', (value) => value + 1);

  case DECREMENT_COUNTER:
    return state.update('count', (value) => value - 1);

  default:
    return state;
  }
}

export default counterReducer;
// ./reducers/counter.test.js
import { assert } from 'chai';
import counterReducer from './counter';
import { INCREMENT_COUNTER, DECREMENT_COUNTER } from '../constants';
import { Map } from 'immutable';

//Used for testing to fire actions against a reducer.
function fireAction(reducer, currentState, type, payload = {}) {
  return reducer(currentState, {
    type,
    payload,
  });
}

let state = counterReducer(undefined, {});

describe('counter reducer', () => {
  describe('inital state', () => {
    it('should be a Map', () => {
      assert.strictEqual(Map.isMap(state), true);
    });
  });

  describe('on INCREMENT_COUNTER', () => {
    it('should increment state.count', () => {
      const previousValue = state.get('count');
      state = fireAction(counterReducer, state, INCREMENT_COUNTER);
      assert.strictEqual(state.get('count'), previousValue + 1);
    });
  });

  describe('on DECREMENT_COUNTER', () => {
    it('should decrement state.count', () => {
      const previousValue = state.get('count');
      state = fireAction(counterReducer, state, DECREMENT_COUNTER);
      assert.strictEqual(state.get('count'), previousValue - 1);
    });
  });
});
PreviousComponentsNextActions

Last updated 6 years ago

Was this helpful?