Skip to content

Commit

Permalink
support cond in tests (#54)
Browse files Browse the repository at this point in the history
  • Loading branch information
MicheleBertoli committed Jun 5, 2018
1 parent dbe69ee commit 719348b
Show file tree
Hide file tree
Showing 4 changed files with 135 additions and 85 deletions.
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -248,10 +248,10 @@ The component to define which parts of the tree should be rendered for a given s
/>
```

## testStatechart({ statechart[, fixtures] }, Component)
## testStatechart({ statechart[, fixtures][, extendedState] }, Component)

The method to automagically generate tests given a statechart definition, and a component.
It accepts an optional `fixtures` configuration to describe which data should be injected into the component for a given transition.
It accepts an additional `fixtures` option to describe the data to be injected into the component for a given transition, and an `extendedState` option to control the statechart's conditions - both are optional.

> Please note that the component should be a base component not wrapped into `withStateChart` (see [#46](https://github.com/MicheleBertoli/react-automata/issues/46)).
Expand Down
10 changes: 5 additions & 5 deletions src/testStatechart.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,27 +7,27 @@ import invariant from 'invariant'
import { getContextValue } from './utils'
import withStatechart from './withStatechart'

const testStatechart = (config, Component) => {
const testStatechart = (options, Component) => {
invariant(
!Component.isStateMachine,
`It seems you are testing a component wrapped into \`withStatechart\`, please use a base component instead.
See https://github.com/MicheleBertoli/react-automata/issues/46`
)

const { channel, statechart } = config
const { statechart, extendedState, channel } = options
const machine = Machine(statechart)
const paths = getShortestPaths(machine)
const paths = getShortestPaths(machine, extendedState)

Object.keys(paths).forEach(key => {
const initialData = idx(config, _ => _.fixtures.initialData)
const initialData = idx(options, _ => _.fixtures.initialData)
const StateMachine = withStatechart(statechart, { channel })(Component)
const renderer = TestRenderer.create(
<StateMachine initialData={initialData} />
)
const instance = renderer.getInstance()

paths[key].forEach(({ event, state }) => {
const fixtures = idx(config, _ => _.fixtures[state][event])
const fixtures = idx(options, _ => _.fixtures[state][event])

instance.handleTransition(event, fixtures)
})
Expand Down
60 changes: 33 additions & 27 deletions test/__snapshots__/testStatechart.spec.js.snap
Original file line number Diff line number Diff line change
@@ -1,30 +1,54 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`action: a 1`] = `
exports[`channels: outer 1`] = `
<div>
outer
<div>
inner
outer
</div>
</div>
`;

exports[`cond fail: a 1`] = `"A"`;

exports[`cond pass: a 1`] = `"A"`;

exports[`cond pass: b 1`] = `"B"`;

exports[`conditional action: a 1`] = `
<div>
a
</div>
`;

exports[`action: b.a 1`] = `
exports[`conditional action: b.a 1`] = `
<div>
b.a
</div>
`;

exports[`action: b.b 1`] = `
exports[`conditional action: b.b 1`] = `
<div>
b.b
</div>
`;

exports[`channels: outer 1`] = `
exports[`conditional state: a 1`] = `
<div>
outer
<div>
inner
outer
</div>
a
</div>
`;

exports[`conditional state: b.a 1`] = `
<div>
b.a
</div>
`;

exports[`conditional state: b.b 1`] = `
<div>
b.b
</div>
`;

Expand Down Expand Up @@ -243,21 +267,3 @@ exports[`parallel: bold.on,underline.on,italics.on,list.numbers 1`] = `
list.numbers
</div>
`;

exports[`state: a 1`] = `
<div>
a
</div>
`;

exports[`state: b.a 1`] = `
<div>
b.a
</div>
`;

exports[`state: b.b 1`] = `
<div>
b.b
</div>
`;
146 changes: 95 additions & 51 deletions test/testStatechart.spec.js
Original file line number Diff line number Diff line change
@@ -1,67 +1,69 @@
import React from 'react'
import { Action, State, testStatechart, withStatechart } from '../src'

const secondMachine = {
initial: 'a',
states: {
a: {
on: {
SECOND_NEXT: 'b',
describe('conditional', () => {
const secondMachine = {
initial: 'a',
states: {
a: {
on: {
SECOND_NEXT: 'b',
},
onEntry: 'enterBA',
},
onEntry: 'enterBA',
},
b: {
on: {
SECOND_NEXT: 'a',
b: {
on: {
SECOND_NEXT: 'a',
},
onEntry: 'enterBB',
},
onEntry: 'enterBB',
},
},
}

const firstMachine = {
initial: 'a',
states: {
a: {
on: {
FIRST_NEXT: 'b',
}

const firstMachine = {
initial: 'a',
states: {
a: {
on: {
FIRST_NEXT: 'b',
},
onEntry: 'enterA',
},
onEntry: 'enterA',
},
b: {
on: {
FIRST_NEXT: 'a',
b: {
on: {
FIRST_NEXT: 'a',
},
onEntry: 'enterB',
...secondMachine,
},
onEntry: 'enterB',
...secondMachine,
},
},
}
}

test('action', () => {
const App = () => (
<div>
<Action show="enterA" hide="enterB">
a
</Action>
<Action show="enterBA">b.a</Action>
<Action show="enterBB">b.b</Action>
</div>
)
test('action', () => {
const App = () => (
<div>
<Action show="enterA" hide="enterB">
a
</Action>
<Action show="enterBA">b.a</Action>
<Action show="enterBB">b.b</Action>
</div>
)

testStatechart({ statechart: firstMachine }, App)
})
testStatechart({ statechart: firstMachine }, App)
})

test('state', () => {
const App = () => (
<div>
<State value="a">a</State>
<State value="b.a">b.a</State>
<State value="b.b">b.b</State>
</div>
)
test('state', () => {
const App = () => (
<div>
<State value="a">a</State>
<State value="b.a">b.a</State>
<State value="b.b">b.b</State>
</div>
)

testStatechart({ statechart: firstMachine }, App)
testStatechart({ statechart: firstMachine }, App)
})
})

test('parallel', () => {
Expand Down Expand Up @@ -171,3 +173,45 @@ test('channels', () => {

testStatechart({ statechart: outer, channel: 'outer' }, Outer)
})

describe('cond', () => {
const statechart = {
initial: 'a',
states: {
a: {
on: {
EVENT: {
b: {
cond: extState => extState.shouldPass,
},
},
},
},
b: {},
},
}

const Cond = () => (
<React.Fragment>
<State value="a">A</State>
<State value="b">B</State>
</React.Fragment>
)

test('pass', () => {
const extendedState = {
shouldPass: true,
}
const fixtures = {
a: {
EVENT: extendedState,
},
}

testStatechart({ statechart, fixtures, extendedState }, Cond)
})

test('fail', () => {
testStatechart({ statechart }, Cond)
})
})

0 comments on commit 719348b

Please sign in to comment.