• This repository has been archived on 28/Mar/2023
  • Stars
    star
    368
  • Rank 115,958 (Top 3 %)
  • Language
    JavaScript
  • License
    MIT License
  • Created about 6 years ago
  • Updated over 1 year ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

Declarative mocks for React state and global APIs

React mock

Build Coverage

Declarative mocks for React state and global APIs.

Jump to

Why?

The motivation for this project comes from wanting to load any type of React component in isolation—inside automated tests as well as in component explorers such as Cosmos or Storybook. Some components as stateful, while others fetch data or interact with some other external input.

The aim here is to isolate all components, not just presentational and stateless components.

Declarative

Tools like fetch-mock and xhr-mock are already used by many of us in component tests. But they require imperative setups and teardowns, which has two drawbacks:

  1. They require before/after orchestration in component tests, which is tedious and can create convoluted test cases.

  2. They're difficult to integrate in component explorers where a usage file is a declarative component element.

To overcome these drawbacks, react-mock offers mocking techniques as declarative React elements. Lifecycle methods take care of setting up and reverting mocks behind the hood.

Composition

Two or more mocks can be composed into a single React element.

render(
  <LocalStorageMock items={{ userId: 123 }}>
    <FetchMock matcher="/user/123" response={{ name: 'Jessica' }}>
      <StateMock state={{ show: true }}>
        <ToggleShow>
          <UserGreeting />
        </ToggleShow>
      </StateMock>
    </FetchMock>
  </LocalStorageMock>
);

Limitations

  • Some react-mock components mock a global API entirely, like fetch or localStorage. For this reason only one instance of each should be rendered at once. There might be ways to compose these mocks in the future.

  • To keep this codebase light, the declarative APIs mirror the params of their underlying APIs. Eg. Although they both mock server requests, the FetchMock API is different from the XhrMock API because they rely on different libs. More concise interfaces are possible, but they increase the scope of this project.

Component state

Inject React component state declaratively.

StateMock must be the direct parent of the stateful component for the state injection to work.

import { StateMock } from '@react-mock/state';

render(
  <StateMock state={{ count: 5 }}>
    <Counter />
  </StateMock>
);

Warning: StateMock delays ref calls. This means refs can get called after componentDidMount, instead of before as you might expect.

Fetch requests

A declarative wrapper for the wonderful fetch-mock.

Note: FetchMock mocks the global Fetch API, so only one FetchMock instance should be rendered at once.

import { FetchMock } from '@react-mock/fetch';

// Passing fetch-mock options
render(
  <FetchMock options={{ matcher: '/login', response: 401, method: 'POST' }}>
    <MyComponent />
  </FetchMock>
);

// Passing fetch-mock config
render(
  <FetchMock
    matcher="/posts"
    response={200}
    config={{ fallbackToNetwork: true }}
  >
    <MyComponent />
  </FetchMock>
);

Multiple mocks

render(
  <FetchMock
    mocks={[
      { matcher: '/users', response: [{ id: 123 }] },
      { matcher: '/user/123', response: { name: 'Jessica' } }
    ]}
  >
    <MyComponent />
  </FetchMock>
);

Inspection

See fetch-mock's inspection methods to check how fetch was called.

Note: Import fetchMock from @react-mock/fetch to ensure you're inspecting on the right fetch-mock instance.

import { fetchMock } from '@react-mock/fetch';

const [, { body }] = fetchMock.lastCall('/login', 'POST');
expect(JSON.parse(body)).toEqual({ user: 'harry' });

LocalStorage

Mock LocalStorage data declaratively.

Note: LocalStorageMock mocks the global localStorage API, so only one LocalStorageMock instance should be rendered at once.

import { LocalStorageMock } from '@react-mock/localstorage';

render(
  <LocalStorageMock items={{ sessionId: 're4lt0k3n' }}>
    <MyComponent />
  </LocalStorageMock>
);

XHR requests

A declarative wrapper for the great xhr-mock.

Note: XhrMock mocks the global XMLHttpRequest API, so only one XhrMock instance should be rendered at once.

import { XhrMock } from '@react-mock/xhr';

// GET
render(
  <XhrMock
    url="/users"
    response={(req, res) => res.body(JSON.stringify(users))}
  >
    <MyComponent />
  </XhrMock>
);

// POST
render(
  <XhrMock url="/login" method="POST" response={(req, res) => res.status(401)}>
    <MyComponent />
  </XhrMock>
);

Multiple mocks

const res = body => (req, res) => res.body(JSON.stringify(body));

render(
  <XhrMock
    mocks={[
      { url: '/users', response: res([{ id: 123 }]) },
      { url: '/user/123', response: res({ name: 'Jessica' }) }
    ]}
  >
    <MyComponent />
  </XhrMock>
);

How to contribute

Intention

Please take a minute to understand this project's purpose and ensure your contribution is thoughtful and relevant. Preserving the integrity of an open source project is hard. Thanks!

Check your code

You have the following weapons at your disposal: yarn lint, yarn flow and yarn test. Use them.

New package

Run yarn new-package and you'll follow this friendly flow that will generate initial boilerplate.

New package

Docs

Each package has its own README. This is useful for keeping docs close to code, as well as for showing docs on each package's npm page.

The root README is generated using a script. Do not edit it by hand. It's assembled from a template, individual package docs and the CONTRIBUTING.md.

Run npm generate-readme to update the root README.

License

MIT © Ovidiu Cherecheș

More Repositories

1

illustrated-algorithms

Interactive algorithm visualizations
JavaScript
2,770
star
2

flatris

Fast-paced two-player web game
JavaScript
1,446
star
3

dragdealer

Drag-based vanilla JS component
JavaScript
1,051
star
4

jobs-done

Ritual app for ending the work day inspired by Deep Work
JavaScript
943
star
5

react-testing-examples

Searchable library of React testing examples
JavaScript
387
star
6

react-component-tree

Serialize and reproduce the state of an entire tree of React components.
JavaScript
87
star
7

aufond

A résumé for the modern age
JavaScript
77
star
8

react-component-playground

Minimal frame for loading and testing React components in isolation.
JavaScript
76
star
9

obvious-buttons

Almost flat CSS buttons
CSS
62
star
10

babel-plugin-trace-execution

Trace execution context of JS functions
JavaScript
61
star
11

async-hacker-handbook

The Asynchronous Hacker Handbook
35
star
12

github-issue-template

BDD Issue Template for Github (with Chrome Extension)
JavaScript
18
star
13

chrome-imdb-ratings

Chrome extension for displaying IMDB ratings in listings
JavaScript
16
star
14

async-until

Wait until a given callback returns true
TypeScript
10
star
15

cosmos-example

Example of loading components and fixtures using Cosmos.
JavaScript
10
star
16

react-data-fetch

A good-enough data fetching mixin for React components.
JavaScript
8
star
17

react-querystring-router

Bare router for React components, using query string as props.
JavaScript
8
star
18

play

Agnostic frame-skipping animation library
JavaScript
6
star
19

react-redux-layout

Unleash your creativity with dynamic layouts!
JavaScript
4
star
20

react-cosmos-redux

Redux mock for React Cosmos fixtures
TypeScript
4
star
21

chrome-hide-facebook-sponsored-posts

A Chrome extension for automatically hiding sponsored posts from your Facebook News Feed.
JavaScript
4
star
22

ui-development-made-simple

My JSHeroes talk on how to build a scalable UI architecture
JavaScript
4
star
23

gutenHashTag

Dynamic Twitter background
PHP
3
star
24

mode

A node.js web framework for real-world applications
JavaScript
3
star
25

stoic-guide-to-good-life

Notes from William B. Irvine's book, A Guide to the Good Life: The Ancient Art of Stoic Joy.
3
star
26

berlinjs-2017

Code used for my BerlinJS talk
JavaScript
2
star
27

hacker-comments

A browser hack for hackers
JavaScript
2
star
28

react-animation-loop

React mixin for running a callback at 60fps with frame skipping
JavaScript
2
star
29

react-test-useeffect

JavaScript
2
star
30

react-testing-talk

Slides and resources for my React testing talk
JavaScript
2
star
31

linked-list

Turn an array into a stateless linked list
TypeScript
2
star
32

react-plugin

API for composable 3rd party React plugins
TypeScript
1
star
33

YOH2011

1
star
34

flux-dispatcher-game

Fun with Flux
CSS
1
star
35

chrome-mozaic-profiler

JavaScript
1
star
36

after-pending-promises

Wait for pending promises to resolve
JavaScript
1
star
37

jLaid

JavaScript
1
star
38

async-retry

Wait until cb doesn't throw or time out
TypeScript
1
star