diff --git a/src/addons/presenter.js b/src/addons/presenter.js index 1aa76d29..ffaae405 100644 --- a/src/addons/presenter.js +++ b/src/addons/presenter.js @@ -210,12 +210,8 @@ export default class Presenter extends Component { console.warn(`No presenter implements intent “${ intent }”.`) } - /** - * Presenters require a render method. This will throw an error unless - * implemented by a subclass. - */ render () { - throw new Error('Presenter must implement a render method.') + return this.props.children ? React.Children.only(this.props.children) : null } } diff --git a/src/addons/provider.js b/src/addons/provider.js index 8da40a91..b527ad5b 100644 --- a/src/addons/provider.js +++ b/src/addons/provider.js @@ -1,5 +1,4 @@ -import Microcosm from '../microcosm' -import React, { Component, Children } from 'react' +import Presenter from './presenter' /** * Sets up the required context for a React component tree @@ -15,21 +14,6 @@ import React, { Component, Children } from 'react' * * ), document.getElementById('repo')) */ -export default class Provider extends Component { - getChildContext() { - return { repo: this.props.repo } - } +export default class Provider extends Presenter { - render() { - return Children.only(this.props.children) - } -} - -Provider.propTypes = { - repo : React.PropTypes.instanceOf(Microcosm).isRequired, - children : React.PropTypes.element.isRequired -} - -Provider.childContextTypes = { - repo : React.PropTypes.instanceOf(Microcosm).isRequired } diff --git a/test/addons/presenter.test.js b/test/addons/presenter.test.js index ea92901f..135eb075 100644 --- a/test/addons/presenter.test.js +++ b/test/addons/presenter.test.js @@ -14,8 +14,10 @@ const View = React.createClass({ } }) -test('requires an implementation of a render method', t => { - t.throws(() => mount(), /implement a render method/) +test('the default render implementation passes children', t => { + let wrapper = mount(

Test

) + + t.is(wrapper.text(), 'Test') }) test('receives intent events', t => { @@ -208,10 +210,6 @@ test('does not update the view model when umounted', t => { t.pass() return {} } - - render() { - return - } } let repo = new Microcosm({ pure: false }) @@ -227,9 +225,6 @@ test('calling setState in setup does not raise a warning', t => { setup() { this.setState({ foo: 'bar' }) } - render() { - return - } } console.record() @@ -246,9 +241,6 @@ test('warns when setState in setup does not raise a warning', t => { viewModel() { return this.repo.state } - render() { - return

Test

- } } console.record() @@ -265,9 +257,6 @@ test('allows functions to return from viewModel', t => { viewModel() { return state => state } - render() { - return

Test

- } } const el = mount() diff --git a/test/addons/provider.test.js b/test/addons/provider.test.js new file mode 100644 index 00000000..58d99fe6 --- /dev/null +++ b/test/addons/provider.test.js @@ -0,0 +1,15 @@ +import test from 'ava' +import Provider from '../../src/addons/provider' +import Connect from '../../src/addons/connect' +import Microcosm from '../../src/microcosm' +import React from 'react' +import {mount} from 'enzyme' + +test('injects an repo from context into the wrapped component', t => { + const repo = new Microcosm() + const Child = () => (

Test

) + const Parent = Connect()(Child) + + const component = mount() + t.is(component.find(Child).prop('repo'), repo) +})