Support error boundaries on ReactTestRenderer (#7558)
Miller Medeiros committed
Aug 25, 2016 at 15:35 UTC
38f74bcaf4a4a787dc5634c56c660beacd7df074
2 files changed
+51
src/renderers/testing/ReactTestReconcileTransaction.js
+13
@@ -89,6 +89,19 @@ var Mixin = {
89
return ReactUpdateQueue;
90
},
91
92
+ /**
93
+ * Save current transaction state -- if the return value from this method is
94
+ * passed to `rollback`, the transaction will be reset to that state.
95
+ */
96
+ checkpoint: function() {
97
+ // reactMountReady is the our only stateful wrapper
98
+ return this.reactMountReady.checkpoint();
99
+ },
100
+
101
+ rollback: function(checkpoint) {
102
+ this.reactMountReady.rollback(checkpoint);
103
+ },
104
+
105
/**
106
* `PooledClass` looks for this, and will invoke this before allowing this
107
* instance to be reused.
src/renderers/testing/__tests__/ReactTestRenderer-test.js
+38
@@ -206,4 +206,42 @@ describe('ReactTestRenderer', function() {
206
expect(log).toEqual([null]);
207
});
208
209
+ it('supports error boundaries', function() {
210
+ class Angry extends React.Component {
211
+ render() {
212
+ throw new Error('Please, do not render me.');
213
+ }
214
+ }
215
+
216
+ class Boundary extends React.Component {
217
+ constructor(props) {
218
+ super(props);
219
+ this.state = {error: false};
220
+ }
221
+ render() {
222
+ if (!this.state.error) {
223
+ return (<div><button onClick={this.onClick}>ClickMe</button><Angry /></div>);
224
+ } else {
225
+ return (<div>Happy Birthday!</div>);
226
+ }
227
+ }
228
+ onClick() {
229
+ /* do nothing */
230
+ }
231
+ unstable_handleError() {
232
+ this.setState({error: true});
233
+ }
234
+ }
235
+
236
+ var EventPluginHub = require('EventPluginHub');
237
+ EventPluginHub.putListener = jest.fn();
238
+ var renderer = ReactTestRenderer.create(<Boundary />);
239
+ expect(renderer.toJSON()).toEqual({
240
+ type: 'div',
241
+ props: {},
242
+ children: ['Happy Birthday!'],
243
+ });
244
+ expect(EventPluginHub.putListener).not.toBeCalled();
245
+ });
246
+
247
});