Skip to content

Commit beb51e2

Browse files
Hooks instead of class-based component (#419)
1 parent 44e0957 commit beb51e2

File tree

16 files changed

+2463
-1714
lines changed

16 files changed

+2463
-1714
lines changed

README.md

Lines changed: 52 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -131,17 +131,36 @@ export const wrapper = createWrapper(makeStore, {debug: true});
131131

132132
</details>
133133

134+
## `wrapper.useWrappedStore`
135+
134136
It is highly recommended to use `pages/_app` to wrap all pages at once, otherwise due to potential race conditions you may get `Cannot update component while rendering another component`:
135137

136-
```typescript
138+
````typescript
137139
import React, {FC} from 'react';
140+
import {Provider} from 'react-redux';
138141
import {AppProps} from 'next/app';
139142
import {wrapper} from '../components/store';
140143

141144
const WrappedApp: FC<AppProps> = ({Component, pageProps}) => <Component {...pageProps} />;
142145

143-
export default wrapper.withRedux(WrappedApp);
144-
```
146+
Instead of `wrapper.useWrappedStore` you can also use legacy HOC, that can work with class-based components.
147+
148+
:warning: Next.js provides [generic `getInitialProps`](https://github.com/vercel/next.js/blob/canary/packages/next/pages/_app.tsx#L21) when using `class MyApp extends App` which will be picked up by wrapper, so you **must not extend `App`** as you'll be opted out of Automatic Static Optimization: https://err.sh/next.js/opt-out-auto-static-optimization. Just export a regular Functional Component as in the example above.
149+
150+
```typescript
151+
import React from 'react';
152+
import {wrapper} from '../components/store';
153+
import {AppProps} from 'next/app';
154+
155+
class MyApp extends React.Component<AppProps> {
156+
render() {
157+
const {Component, pageProps} = this.props;
158+
return <Component {...pageProps} />;
159+
}
160+
}
161+
162+
export default wrapper.withRedux(MyApp);
163+
````
145164
146165
<details>
147166
<summary>Same code in JavaScript (without types)</summary>
@@ -681,60 +700,61 @@ import {Action} from 'redux';
681700
import {createWrapper, HYDRATE} from 'next-redux-wrapper';
682701

683702
export const subjectSlice = createSlice({
684-
name: 'subject',
703+
name: 'subject',
685704

686-
initialState: {} as any,
705+
initialState: {} as any,
687706

688-
reducers: {
689-
setEnt(state, action) {
690-
return action.payload;
691-
},
707+
reducers: {
708+
setEnt(state, action) {
709+
return action.payload;
692710
},
711+
},
693712

694-
extraReducers: {
695-
[HYDRATE]: (state, action) => {
696-
console.log('HYDRATE', state, action.payload);
697-
return {
698-
...state,
699-
...action.payload.subject,
700-
};
701-
},
713+
extraReducers: {
714+
[HYDRATE]: (state, action) => {
715+
console.log('HYDRATE', state, action.payload);
716+
return {
717+
...state,
718+
...action.payload.subject,
719+
};
702720
},
721+
},
703722
});
704723

705724
const makeStore = () =>
706-
configureStore({
707-
reducer: {
708-
[subjectSlice.name]: subjectSlice.reducer,
709-
},
710-
devTools: true,
711-
});
725+
configureStore({
726+
reducer: {
727+
[subjectSlice.name]: subjectSlice.reducer,
728+
},
729+
devTools: true,
730+
});
712731

713732
export type AppStore = ReturnType<typeof makeStore>;
714733
export type AppState = ReturnType<AppStore['getState']>;
715734
export type AppThunk<ReturnType = void> = ThunkAction<ReturnType, AppState, unknown, Action>;
716735

717-
export const fetchSubject = (id: any): AppThunk => async dispatch => {
736+
export const fetchSubject =
737+
(id: any): AppThunk =>
738+
async dispatch => {
718739
const timeoutPromise = (timeout: number) => new Promise(resolve => setTimeout(resolve, timeout));
719740

720741
await timeoutPromise(200);
721742

722743
dispatch(
723-
subjectSlice.actions.setEnt({
724-
[id]: {
725-
id,
726-
name: `Subject ${id}`,
727-
},
728-
}),
744+
subjectSlice.actions.setEnt({
745+
[id]: {
746+
id,
747+
name: `Subject ${id}`,
748+
},
749+
}),
729750
);
730-
};
751+
};
731752

732753
export const wrapper = createWrapper<AppStore>(makeStore);
733754

734755
export const selectSubject = (id: any) => (state: AppState) => state?.[subjectSlice.name]?.[id];
735756
```
736757
737-
738758
It is recommended to export typed `State` and `ThunkAction`:
739759
740760
```ts

package.json

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -21,12 +21,12 @@
2121
"devDependencies": {
2222
"eslint": "7.32.0",
2323
"eslint-config-ringcentral-typescript": "0.0.0-master.212.1",
24-
"husky": "7.0.2",
24+
"husky": "7.0.4",
2525
"lerna": "4.0.0",
2626
"lint-staged": "11.1.2",
27-
"prettier": "2.4.0",
27+
"prettier": "2.5.0",
2828
"rimraf": "3.0.2",
29-
"typescript": "4.4.3"
29+
"typescript": "4.5.2"
3030
},
3131
"workspaces": [
3232
"packages/*"
@@ -41,5 +41,8 @@
4141
},
4242
"homepage": "https://github.com/kirill-konshin/next-redux-wrapper",
4343
"license": "MIT",
44-
"packageManager": "[email protected]"
44+
"packageManager": "[email protected]",
45+
"resolutions": {
46+
"@types/react": "17.0.37"
47+
}
4548
}

packages/demo-page/package.json

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -13,20 +13,21 @@
1313
"next-redux-wrapper": "*",
1414
"react": "17.0.2",
1515
"react-dom": "17.0.2",
16-
"react-redux": "7.2.5",
17-
"redux": "4.1.1",
16+
"react-redux": "7.2.6",
17+
"redux": "4.1.2",
1818
"redux-logger": "3.0.6"
1919
},
2020
"devDependencies": {
21-
"@playwright/test": "1.14.1",
22-
"@types/react-dom": "17.0.9",
23-
"@types/react-redux": "7.1.18",
21+
"@playwright/test": "1.17.1",
22+
"@types/react": "17.0.37",
23+
"@types/react-dom": "17.0.11",
24+
"@types/react-redux": "7.1.20",
2425
"@types/redux-logger": "3.0.9",
2526
"next": "12.0.4",
2627
"next-redux-wrapper-configs": "*",
27-
"playwright": "1.14.1",
28+
"playwright": "1.17.1",
2829
"rimraf": "3.0.2",
29-
"typescript": "4.4.3"
30+
"typescript": "4.5.2"
3031
},
3132
"author": "Kirill Konshin",
3233
"repository": {

packages/demo-page/tsconfig.json

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,14 @@
11
{
22
"extends": "../configs/tsconfig.demo.json",
3-
"include": ["next-env.d.ts", "**/*.ts", "**/*.tsx"],
4-
"exclude": ["node_modules"]
3+
"include": [
4+
"next-env.d.ts",
5+
"**/*.ts",
6+
"**/*.tsx"
7+
],
8+
"exclude": [
9+
"node_modules"
10+
],
11+
"compilerOptions": {
12+
"incremental": true
13+
}
514
}

packages/demo-redux-toolkit/package.json

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -8,17 +8,17 @@
88
"start": "next --port=6060"
99
},
1010
"dependencies": {
11-
"@reduxjs/toolkit": "1.6.1",
11+
"@reduxjs/toolkit": "1.6.2",
1212
"next-redux-wrapper": "*",
13-
"react": "^17.0.2",
14-
"react-dom": "^17.0.2",
15-
"react-redux": "7.2.5",
16-
"redux": "4.1.1"
13+
"react": "17.0.2",
14+
"react-dom": "17.0.2",
15+
"react-redux": "7.2.6",
16+
"redux": "4.1.2"
1717
},
1818
"devDependencies": {
19-
"@playwright/test": "1.14.1",
19+
"@playwright/test": "1.17.1",
2020
"next": "12.0.4",
21-
"playwright": "1.14.1"
21+
"playwright": "1.17.1"
2222
},
2323
"license": "MIT"
2424
}
Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,15 @@
11
import React, {FC} from 'react';
2+
import {Provider} from 'react-redux';
23
import {AppProps} from 'next/app';
34
import {wrapper} from '../store';
45

5-
const MyApp: FC<AppProps> = ({Component, pageProps}) => <Component {...pageProps} />;
6+
const MyApp: FC<AppProps> = ({Component, ...rest}) => {
7+
const {store, props} = wrapper.useWrappedStore(rest);
8+
return (
9+
<Provider store={store}>
10+
<Component {...props.pageProps} />
11+
</Provider>
12+
);
13+
};
614

7-
export default wrapper.withRedux(MyApp);
15+
export default MyApp;
Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,14 @@
11
{
22
"extends": "../configs/tsconfig.demo.json",
3-
"include": ["next-env.d.ts", "**/*.ts", "**/*.tsx"],
4-
"exclude": ["node_modules"]
3+
"include": [
4+
"next-env.d.ts",
5+
"**/*.ts",
6+
"**/*.tsx"
7+
],
8+
"exclude": [
9+
"node_modules"
10+
],
11+
"compilerOptions": {
12+
"incremental": true
13+
}
514
}

packages/demo-saga-page/package.json

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -13,21 +13,22 @@
1313
"next-redux-wrapper": "*",
1414
"react": "17.0.2",
1515
"react-dom": "17.0.2",
16-
"react-redux": "7.2.5",
17-
"redux": "4.1.1",
16+
"react-redux": "7.2.6",
17+
"redux": "4.1.2",
1818
"redux-logger": "3.0.6",
1919
"redux-saga": "1.1.3"
2020
},
2121
"devDependencies": {
22-
"@playwright/test": "1.14.1",
23-
"@types/react-dom": "17.0.9",
24-
"@types/react-redux": "7.1.18",
22+
"@playwright/test": "1.17.1",
23+
"@types/react": "17.0.37",
24+
"@types/react-dom": "17.0.11",
25+
"@types/react-redux": "7.1.20",
2526
"@types/redux-logger": "3.0.9",
2627
"next": "12.0.4",
2728
"next-redux-wrapper-configs": "*",
28-
"playwright": "1.14.1",
29+
"playwright": "1.17.1",
2930
"rimraf": "3.0.2",
30-
"typescript": "4.4.3"
31+
"typescript": "4.5.2"
3132
},
3233
"author": "Kirill Konshin",
3334
"repository": {
Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,14 @@
11
{
22
"extends": "../configs/tsconfig.demo.json",
3-
"include": ["next-env.d.ts", "**/*.ts", "**/*.tsx"],
4-
"exclude": ["node_modules"]
3+
"include": [
4+
"next-env.d.ts",
5+
"**/*.ts",
6+
"**/*.tsx"
7+
],
8+
"exclude": [
9+
"node_modules"
10+
],
11+
"compilerOptions": {
12+
"incremental": true
13+
}
514
}

packages/demo-saga/package.json

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -13,21 +13,22 @@
1313
"next-redux-wrapper": "*",
1414
"react": "17.0.2",
1515
"react-dom": "17.0.2",
16-
"react-redux": "7.2.5",
17-
"redux": "4.1.1",
16+
"react-redux": "7.2.6",
17+
"redux": "4.1.2",
1818
"redux-logger": "3.0.6",
1919
"redux-saga": "1.1.3"
2020
},
2121
"devDependencies": {
22-
"@playwright/test": "1.14.1",
23-
"@types/react-dom": "17.0.9",
24-
"@types/react-redux": "7.1.18",
22+
"@playwright/test": "1.17.1",
23+
"@types/react": "17.0.37",
24+
"@types/react-dom": "17.0.11",
25+
"@types/react-redux": "7.1.20",
2526
"@types/redux-logger": "3.0.9",
2627
"next": "12.0.4",
2728
"next-redux-wrapper-configs": "*",
28-
"playwright": "1.14.1",
29+
"playwright": "1.17.1",
2930
"rimraf": "3.0.2",
30-
"typescript": "4.4.3"
31+
"typescript": "4.5.2"
3132
},
3233
"author": "Kirill Konshin",
3334
"repository": {

0 commit comments

Comments
 (0)