Skip to content

Commit 302f2b3

Browse files
committed
Merge pull request #80 from rackt/remove-replacereducer-magic
Remove support for changing store on the fly
2 parents 10a7245 + ecdc094 commit 302f2b3

File tree

3 files changed

+51
-28
lines changed

3 files changed

+51
-28
lines changed

package.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -52,14 +52,14 @@
5252
"mocha-jsdom": "~0.4.0",
5353
"react": "^0.14.0-beta3",
5454
"react-addons-test-utils": "^0.14.0-beta3",
55-
"redux": "^1.0.1",
55+
"redux": "^2.0.0",
5656
"rimraf": "^2.3.4",
5757
"webpack": "^1.11.0"
5858
},
5959
"dependencies": {
6060
"invariant": "^2.0.0"
6161
},
6262
"peerDependencies": {
63-
"redux": "^1.0.0 || 1.0.0-rc"
63+
"redux": "^2.0.0"
6464
}
6565
}

src/components/createProvider.js

Lines changed: 29 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -18,31 +18,47 @@ export default function createProvider(React) {
1818
const storeShape = createStoreShape(PropTypes);
1919
const requireFunctionChild = isUsingOwnerContext(React);
2020

21-
let didWarn = false;
22-
function warnAboutFunction() {
23-
if (didWarn || requireFunctionChild) {
21+
let didWarnAboutChild = false;
22+
function warnAboutFunctionChild() {
23+
if (didWarnAboutChild || requireFunctionChild) {
2424
return;
2525
}
2626

27-
didWarn = true;
27+
didWarnAboutChild = true;
2828
console.error( // eslint-disable-line no-console
2929
'With React 0.14 and later versions, you no longer need to ' +
3030
'wrap <Provider> child into a function.'
3131
);
3232
}
33-
function warnAboutElement() {
34-
if (didWarn || !requireFunctionChild) {
33+
function warnAboutElementChild() {
34+
if (didWarnAboutChild || !requireFunctionChild) {
3535
return;
3636
}
3737

38-
didWarn = true;
38+
didWarnAboutChild = true;
3939
console.error( // eslint-disable-line no-console
4040
'With React 0.13, you need to ' +
4141
'wrap <Provider> child into a function. ' +
4242
'This restriction will be removed with React 0.14.'
4343
);
4444
}
4545

46+
let didWarnAboutReceivingStore = false;
47+
function warnAboutReceivingStore() {
48+
if (didWarnAboutReceivingStore) {
49+
return;
50+
}
51+
52+
didWarnAboutReceivingStore = true;
53+
console.error( // eslint-disable-line no-console
54+
'<Provider> does not support changing `store` on the fly. ' +
55+
'It is most likely that you see this error because you updated to ' +
56+
'Redux 2.x and React Redux 2.x which no longer hot reload reducers ' +
57+
'automatically. See https://github.com/rackt/react-redux/releases/' +
58+
'tag/v2.0.0 for the migration instructions.'
59+
);
60+
}
61+
4662
return class Provider extends Component {
4763
static childContextTypes = {
4864
store: storeShape.isRequired
@@ -57,32 +73,31 @@ export default function createProvider(React) {
5773
};
5874

5975
getChildContext() {
60-
return { store: this.state.store };
76+
return { store: this.store };
6177
}
6278

6379
constructor(props, context) {
6480
super(props, context);
65-
this.state = { store: props.store };
81+
this.store = props.store;
6682
}
6783

6884
componentWillReceiveProps(nextProps) {
69-
const { store } = this.state;
85+
const { store } = this;
7086
const { store: nextStore } = nextProps;
7187

7288
if (store !== nextStore) {
73-
const nextReducer = nextStore.getReducer();
74-
store.replaceReducer(nextReducer);
89+
warnAboutReceivingStore();
7590
}
7691
}
7792

7893
render() {
7994
let { children } = this.props;
8095

8196
if (typeof children === 'function') {
82-
warnAboutFunction();
97+
warnAboutFunctionChild();
8398
children = children();
8499
} else {
85-
warnAboutElement();
100+
warnAboutElementChild();
86101
}
87102

88103
return Children.only(children);

test/components/Provider.spec.js

Lines changed: 20 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -171,10 +171,10 @@ describe('React', () => {
171171
expect(child.context.store).toBe(store);
172172
});
173173

174-
it('should replace just the reducer when receiving a new store in props', () => {
174+
it('should warn once when receiving a new store in props', () => {
175175
const store1 = createStore((state = 10) => state + 1);
176176
const store2 = createStore((state = 10) => state * 2);
177-
const spy = expect.createSpy(() => ({}));
177+
const store3 = createStore((state = 10) => state * state);
178178

179179
class ProviderContainer extends Component {
180180
state = { store: store1 };
@@ -192,18 +192,26 @@ describe('React', () => {
192192
const child = TestUtils.findRenderedComponentWithType(container, Child);
193193
expect(child.context.store.getState()).toEqual(11);
194194

195-
child.context.store.subscribe(spy);
196-
child.context.store.dispatch({});
197-
expect(spy.calls.length).toEqual(1);
198-
expect(child.context.store.getState()).toEqual(12);
199-
195+
let spy = expect.spyOn(console, 'error');
200196
container.setState({ store: store2 });
201-
expect(spy.calls.length).toEqual(2);
202-
expect(child.context.store.getState()).toEqual(24);
197+
spy.destroy();
198+
199+
expect(child.context.store.getState()).toEqual(11);
200+
expect(spy.calls.length).toBe(1);
201+
expect(spy.calls[0].arguments[0]).toBe(
202+
'<Provider> does not support changing `store` on the fly. ' +
203+
'It is most likely that you see this error because you updated to ' +
204+
'Redux 2.x and React Redux 2.x which no longer hot reload reducers ' +
205+
'automatically. See https://github.com/rackt/react-redux/releases/' +
206+
'tag/v2.0.0 for the migration instructions.'
207+
);
203208

204-
child.context.store.dispatch({});
205-
expect(spy.calls.length).toEqual(3);
206-
expect(child.context.store.getState()).toEqual(48);
209+
spy = expect.spyOn(console, 'error');
210+
container.setState({ store: store3 });
211+
spy.destroy();
212+
213+
expect(child.context.store.getState()).toEqual(11);
214+
expect(spy.calls.length).toBe(0);
207215
});
208216
});
209217
});

0 commit comments

Comments
 (0)