import { connect } from 'dva';
import React, { useEffect } from 'react';
const Page = props => {
const { dispatch, text } = props;
useEffect(() => {
dispatch({ type: 'xxx/fetchText' });
}, []);
return <div>{text}</div>
}
export default connect(({ xxx }) => ({ text: xxx.text }))(Page);
์ด๋ฐ ์์ผ๋ก ์์ฑํ๋ฉด ํ์ธ ์ react-hooks/exhaustive-deps
React Hook useEffect has a missing dependency: dispatch.
๊ท์น์ ๋ฐ๋ผ ํ๋กฌํํธ๋ฉ๋๋ค.
ํ์ง๋ง useEffect์ DependencyList์ ๋์คํจ์น๋ฅผ โโ์ถ๊ฐํ๋ฉด ๊ทธ ์์ ์์ฒญ์ด ๊ณ์ํด์ ์คํ๋๋๋ฐ, React Hooks๋ฅผ dva์ ํจ๊ป ์ฌ์ฉํ ๋ ์ด๋ป๊ฒ ์์ฑํด์ผ ํ ๊น์?
useDispatch, ํํฌ๋ฅผ ์ฌ์ฉํ ํ์๋ ์ฐ๊ฒฐํ ํ์๊ฐ ์์ง๋ง ๊ฒ์ผ๋ฅด๊ธฐ ์ํด ์ ์ฅ์์์ ๋ชจ๋ ํจ๊ณผ์ ๋ฆฌ๋์๋ฅผ ๊บผ๋ด๊ณ ๋ค์์คํ์ด์ค๋ฅผ ๊ฒ์ํ๊ณ ๋ชจ๋ ์์ ์ ๋ฐํํ์ต๋๋ค. ๋ค์์ ์ฐธ์กฐํ์ธ์.
function useActions(namespace) {
const dispatch = useDispatch();
const actions = useMemo(() => {
const { _models } = getStore();
const targetModel = _models.find(model => model.namespace === namespace);
return targetModel ? Object.keys({ ...targetModel.effects, ...targetModel.reducers }).reduce((prev, curre) => {
const actionName = curre.replace(new RegExp(`^${namespace}/`), '');
prev[actionName] = payload => dispatch({ type: curre, payload });
return prev;
}, {}) : {};
}, [namespace, dispatch]);
return actions;
}
useDispatch, ํํฌ๋ฅผ ์ฌ์ฉํ ํ์๋ ์ฐ๊ฒฐํ ํ์๊ฐ ์์ง๋ง ๊ฒ์ผ๋ฅด๊ธฐ ์ํด ์ ์ฅ์์์ ๋ชจ๋ ํจ๊ณผ์ ๋ฆฌ๋์๋ฅผ ๊บผ๋ด๊ณ ๋ค์์คํ์ด์ค๋ฅผ ๊ฒ์ํ๊ณ ๋ชจ๋ ์์ ์ ๋ฐํํ์ต๋๋ค. ๋ค์์ ์ฐธ์กฐํ์ธ์.
function useActions(namespace) { const dispatch = useDispatch(); const actions = useMemo(() => { const { _models } = getStore(); const targetModel = _models.find(model => model.namespace === namespace); return targetModel ? Object.keys({ ...targetModel.effects, ...targetModel.reducers }).reduce((prev, curre) => { const actionName = curre.replace(new RegExp(`^${namespace}/`), ''); prev[actionName] = payload => dispatch({ type: curre, payload }); return prev; }, {}) : {}; }, [namespace, dispatch]); return actions; }
๊ณต๋ฌด์์ useDispatch() ์ฌ์ฉ์ ์ ๊ฑฐํ ๊ฒ์ผ๋ก ๋ณด์
๋๋ค.
์ง๊ธ
์ด ๋ฐฉ๋ฒ์ ์ฌ์ฉ
@UlyC ๋ ์ด๋์์ ์ ๊ฑฐ๋์์ต๋๊น? ๋งํฌ๋ฅผ ์ค ์ ์์ต๋๊น?
@UlyC ๋ ์ด๋์์ ์ ๊ฑฐ๋์์ต๋๊น? ๋งํฌ๋ฅผ ์ค ์ ์์ต๋๊น?
๋ด๊ฐ ํ๋ ธ์ด.
https://reactjs.org/docs/hooks-reference.html ์ ๊ณต์ React Hooks API์๋ useDispatch() ์ฌ์ฉ๋ฒ์ด ์์ต๋๋ค.
์ด๊ฒ์ react-redux์์ ๊ฐ์ ธ์ค๊ธฐ ์ํ react-redux https://react-redux.js.org/next/api/hooks#useddispatch ์ ์ฌ์ฉ๋ฒ์
๋๋ค.
import { useDispatch } from 'react-redux'
@UlyC ๋ ์ด๋์์ ์ ๊ฑฐ๋์์ต๋๊น? ๋งํฌ๋ฅผ ์ค ์ ์์ต๋๊น?
๋ด๊ฐ ํ๋ ธ์ด.
https://reactjs.org/docs/hooks-reference.html ์ ๊ณต์ React Hooks API์๋ useDispatch() ์ฌ์ฉ๋ฒ์ด ์์ต๋๋ค.
์ด๊ฒ์ react-redux์์ ๊ฐ์ ธ์ค๊ธฐ ์ํ react-redux https://react-redux.js.org/next/api/hooks#useddispatch ์ ์ฌ์ฉ๋ฒ์ ๋๋ค.
import { useDispatch } from 'react-redux'
= - ๊ธ์
~ const dispatch = useDispatch();
hooks dva๊ฐ ์ฝ์ํ์ง ์์ต๋๊น? ~
ํจ๊ณผ๋ dva์ ์ฝ์์ ์ถ๊ฐ๋ฉ๋๋ค.
dva/umi๊ฐ ํํฌ ํตํฉ์ ๊ณ ๋ คํ์ต๋๊น? ์ฌ์ฉํ๋ ค๋ฉด ์ด๋ ๊ฒ import { useDispatch } from 'react-redux'
๋ฅผ ์ฌ์ฉํด์ผ ํฉ๋๋ค. ๊ตฌ๋ฉ์ด ์์๊น์?
์ฌ์ฉํ๋๋ฐ ๋ฌธ์ ์์ด์
@yoyo837
````
'dva'์์ { useDispatch } ๊ฐ์ ธ์ค๊ธฐ;
console.log('6:23:08 PM', useDispatch)
````
์ด๋ ๊ฒ undefined๋ฅผ ์ถ๋ ฅํ๋๋ฐ react-redux๋ฅผ ์
๊ทธ๋ ์ด๋ ํด์ผ ํ๋์?์ด๋ค ๋ฒ์ ์ผ๋ก?
dva ์ต์ ๋ฒ ํ ์ ๊ทธ๋ ์ด๋
๋น์ ์ ๋ ๋์ ๋ฆด๋ฆฌ์ค๋ฅผ๋ณด๊ณ
์ ๊ทธ๋ ์ด๋ ํ ๋ฌธ์๋ฅผ ์ ๋ฐ์ดํธํ๊ณ ์ถ์๋ฐ useDispatch ํจ์๊ฐ ๋ฌด์์ ํ๋์ง ๋ชจ๋ฅด๊ฒ ์ต๋๋ค.
dva
์ react-redux
useDispatch
์์ ์ง์ ํ์๋ฉ๋๋ค. react-redux
๋ฌธ์๋ฅผ ๋ณด๋ฉด ๋ฉ๋๋ค.
1. dva๋ฅผ ์ต์ ๋ฒ์ ์ผ๋ก ์
๊ทธ๋ ์ด๋ํฉ๋๋ค(๋ด ๋ฒ์ ์ 2.6.0-beta.12).
2.
์ฐธ์กฐ ์ฃผ์: https://react-redux.js.org/api/hooks
๋์์ด ๋๊ธฐ๋ฅผ ๋ฐ๋๋๋ค
Antd Pro V4๋ 2.6beta 12๋ก ์ ๊ทธ๋ ์ด๋ ๋์ด ์ ์์ ์ผ๋ก ์ฌ์ฉ์ด ๊ฐ๋ฅํ๋ ์ฐ๊ฒฐ ๋ณด๊ณ ํ์์ด ํ๋ฆฝ๋๋ค. ๋ค์์ TableList์ ์๋ฌ ๋ฉ์์ง, ์ด๋ป๊ฒ ํด๊ฒฐํ๋์?
ไฝไธบ่กจ่พพๅผ่ฐ็จๆถ๏ผๆ ๆณ่งฃๆ็ฑปไฟฎ้ฅฐๅจ็็ญพๅใ
ไธ่ฝๅฐ็ฑปๅโConnectedComponentClass<typeof TableList, Pick<TableListProps, "form" | "wrappedComponentRef">>โๅ้
็ป็ฑปๅโtypeof TableListโใ
Type 'Component<Pick<TableListProps, "form" | "wrappedComponentRef">, any, any>' is missing the following properties from type 'TableList': columns, handleStandardTableChange, handleFormReset, toggleForm, and 10 more.
@wangzhipeng404 ํํฌ๋ฅผ ์ฌ์ฉํ๊ณ ๊ตฌ์ฑ ์์๋ฅผ ์ฐ๊ฒฐํ ํ์๊ฐ ์์ต๋๋ค.
ํ์ง๋ง pro ํ๋ ์์ํฌ์ ๋ ์ด์์๊ณผ ๋ธ๋ก์ conect๋ฅผ ์ฌ์ฉํฉ๋๋ค. ์ง์ ๋ณ๊ฒฝํด์ผ ํฉ๋๊น? ์ด๋ฌํ ์ ํ์ ์ค๋ฅ๋ฅผ ๋น ๋ฅด๊ฒ ์์ ํ ์ ์๋ ๋ฐฉ๋ฒ์ด ์์ต๋๊น?
๊ฐ๋จํ ํ ์คํธ ์ผ์ด์ค๋ฅผ ์์ฑํ๋๋ฐ ๋ค์ ์ฝ๋๋ ์ ์์ ์ผ๋ก ์์ฑ๋์ด ์ ์์ ์ผ๋ก ์ฌ์ฉํ ์ ์์ต๋๋ค
import React, { Component } from 'react';
import { connect } from 'dva';
import ProductList from '../components/ProductList';
@connect(({ products }) => ({
products,
}))
export default class Products extends Component {
componentDidMount() {
const { dispatch } = this.props;
dispatch({
type: 'products/fetch',
});
}
handleDelete = id => {
const { dispatch } = this.props;
dispatch({
type: 'products/delete',
payload: id,
});
};
render() {
const { products } = this.props;
return (
<div>
<h2>List of Products</h2>
<ProductList onDelete={this.handleDelete} products={products} />
</div>
);
}
}
๋์ค์ https://react-redux.js.org/next/api/hooks ๋ฅผ ์ฐธ์กฐํ์ฌ ํํฌ๋ก ๋ค์ ์์ฑํ๊ณ ์ถ์์ต๋๋ค.
import React, { useEffect } from 'react';
// import { connect } from 'dva';
import ProductList from '../components/ProductList';
import { useSelector, useDispatch } from 'react-redux';
// https://react-redux.js.org/next/api/hooks
export default function Products() {
console.info(`useDispatch: `,useDispatch)
const dispatch = useDispatch();
const products = useSelector(state => state.products);
useEffect(() => {
dispatch({
type: 'products/fetch',
});
});
const handleDelete = id => {
dispatch({
type: 'products/delete',
payload: id,
});
};
return (
<div>
<h2>List of Products</h2>
<ProductList onDelete={handleDelete} products={products} />
</div>
);
}
ํ์ง๋ง ์ด๋ฒ์๋ ์ค๋ฅ๊ฐ ๋ฐ์ํฉ๋๋ค.
ํํฌ ์ง์์ ๊ฐ๋ ฅํ ํฌ๋งํฉ๋๋ค.
@liudonghua123 ์ด ์ด๋ฒ์๋ dva ์์ค์ฝ๋๋ฅผ ์ดํด๋ณด๋ฏ ์ฌ๋นจ๋ฆฌ ๋ฌป๋๋ค.์๋ ์ฝ๋๋ dva๋ฅผ ์ฌ์ฉํ์ง ์์ผ๋ฉฐ react-redux์์ ์๊ตฌํ๋ ๋๋ก ์๋ํ์ง ์์ต๋๋ค.
@liudonghua123 ์์ ์์ ์ฌ์ฉ ๊ฐ๋ฅํ ์์ ๋ dva ์ด๊ธฐํ๋ฅผ ๋ก๋ํ์ง ์๊ณ ๋ ์ฌ์ฉํ ์ ์์ผ๋ฉฐ dva๋ connect, useSelector ๋ฐ ๊ธฐํ react-redux ๋ฉ์๋๋ฅผ ์ง์ ๋ด๋ณด๋ ๋๋ค.
@yoyo837 ์์์ ์ ์์ ์ผ๋ก ์ฌ์ฉํ ์ ์๋ ์ฝ๋๋ ์ฝ๋์ ์ผ๋ถ์ด๊ณ dva ์ด๊ธฐํ ๋ถ๋ถ์ ๋ค๋ฅธ ๊ณณ์ ์์ผ๋ฉฐ ์ฌ๊ธฐ์ ๋ค ์ฐ์ง๋ ์์์ต๋๋ค. ์ฝ๋๋ https://dvajs.com/guide/getting- ์ ์ฐธ์กฐํ์ฌ ์์ฑ๋์์ต๋๋ค. https://github.com/liudonghua123/dva-quickstart/blob/hooks/src/routes/Products.js ํํฌ ๋ถ๊ธฐ์ ๋ฌธ์ ๊ฐ ์๊ณ ๋ง์คํฐ ๋ถ๊ธฐ๋ฅผ ์ ์์ ์ผ๋ก ์ฌ์ฉํ ์ ์์ต๋๋ค.
์์์ ์ธ๊ธํ ๋๋ก dva
์์ 2.6.0-beta.14
๋ก ์
๋ฐ์ดํธ๋ฅผ ์๋ํ๋๋ฐ ์ฝ๋๋ฅผ ์์ ํ์ง ์๊ณ ์ ์์ ์ผ๋ก ์ฌ์ฉํ ์ ์์ง๋ง ํตํฉ์ ์ํด useSelector
, useDispatch
์์ ๋ณ๊ฒฝ๋์์ต๋๋ค. dva
๋ด๋ณด๋ด๊ธฐ๋ ๋ชจ๋ ์์ ์ฌํญ์ด ์กฐ๊ธ ๋ ์ข์ต๋๋ค.
https://github.com/liudonghua123/dva-quickstart/commit/f9bd1dd1332e62739d15050c4d50bc069a7fb58f
ํ์ง๋ง pro ํ๋ ์์ํฌ์ ๋ ์ด์์๊ณผ ๋ธ๋ก์ conect๋ฅผ ์ฌ์ฉํฉ๋๋ค. ์ง์ ๋ณ๊ฒฝํด์ผ ํฉ๋๊น? ์ด๋ฌํ ์ ํ์ ์ค๋ฅ๋ฅผ ๋น ๋ฅด๊ฒ ์์ ํ ์ ์๋ ๋ฐฉ๋ฒ์ด ์์ต๋๊น?
์๋ ํ์ธ์, ์ด ๋ฌธ์ ๋ฅผ ํด๊ฒฐํ์ จ๋์?antd-pro-ts์ ์ฌ์ฉ๋ dva_beta ๋ฒ์ ์ด ์ค๋ฅ๋ฅผ ๋ณด๊ณ ํ๋ ๊ฒ ๊ฐ์ต๋๋ค.
could not find react-redux context value; please ensure the component is wrapped in a <Provider>
์์ ๋ด์ฉ๋ฌผ์ด ๋ง์ด ๋ค์ด์๋ ๋๋
@liudonghua123 ์์ ์์ ์ฌ์ฉ ๊ฐ๋ฅํ ์์ ๋ dva ์ด๊ธฐํ๋ฅผ ๋ก๋ํ์ง ์๊ณ ๋ ์ฌ์ฉํ ์ ์์ผ๋ฉฐ dva๋ connect, useSelector ๋ฐ ๊ธฐํ react-redux ๋ฉ์๋๋ฅผ ์ง์ ๋ด๋ณด๋ ๋๋ค.
๋ง์ด ๋ผ ์ง์ง ์์ผ ์ ์์ ๊ฒ ๊ฐ์ ๊ฐ์ ์๋ฆฌ๊ฐ ์๋์ผ
Antd Pro V4๋ 2.6beta 12๋ก ์ ๊ทธ๋ ์ด๋ ๋์ด ์ ์์ ์ผ๋ก ์ฌ์ฉ์ด ๊ฐ๋ฅํ๋ ์ฐ๊ฒฐ ๋ณด๊ณ ํ์์ด ํ๋ฆฝ๋๋ค. ๋ค์์ TableList์ ์๋ฌ ๋ฉ์์ง, ์ด๋ป๊ฒ ํด๊ฒฐํ๋์?
ไฝไธบ่กจ่พพๅผ่ฐ็จๆถ๏ผๆ ๆณ่งฃๆ็ฑปไฟฎ้ฅฐๅจ็็ญพๅใ ไธ่ฝๅฐ็ฑปๅโConnectedComponentClass<typeof TableList, Pick<TableListProps, "form" | "wrappedComponentRef">>โๅ้ ็ป็ฑปๅโtypeof TableListโใ Type 'Component<Pick<TableListProps, "form" | "wrappedComponentRef">, any, any>' is missing the following properties from type 'TableList': columns, handleStandardTableChange, handleFormReset, toggleForm, and 10 more.
์ ๋ ์ด๋ฌธ์ ์ธ๋ฐ ํด๊ฒฐํ์ จ๋์?
ํํฌ๋ฅผ ์ฌ์ฉํ๋ฉด ์ฐ๊ฒฐ์ ๋ค์ ์ฌ์ฉํ ํ์๊ฐ ์์ต๋๋ค.
ํํฌ๋ฅผ ์ฌ์ฉํ๋ฉด ์ฐ๊ฒฐ์ ๋ค์ ์ฌ์ฉํ ํ์๊ฐ ์์ต๋๋ค.
๊ธ์, ํ์ง๋ง ํ๋ก์ ํธ๋ ์ด์ ์ ํด๋์ค ๊ตฌ์ฑ ์์๋ก ์์ฑ๋์์ผ๋ฉฐ ํํฌ๋ก ๋ฆฌํฉํ ๋งํ๋ ์์ ๋์ ์ฝ๊ฐ ๋ฌด๊ฒ๊ณ ์ด๋ฌํ ์ ํ์ ๊ฒฝ๊ณ ๋ ๋๋ฌด ์ฑ๊ฐ ์๊ฒ ๋ณด์ ๋๋ค.
์ด ๋ฌธ์ ๋ ์ต๊ทผ ํ๋์ด ์์๊ธฐ ๋๋ฌธ์ ์๋์ผ๋ก ์ค๋๋ ๊ฒ์ผ๋ก ํ์๋์์ต๋๋ค. ๋ ์ด์ ํ๋์ด ์์ผ๋ฉด ํ์๋ฉ๋๋ค. ๊ทํ์ ๊ธฐ์ฌ์ ๊ฐ์ฌ๋๋ฆฝ๋๋ค.
https://github.com/dvajs/dva/issues/2140#issuecomment -507620628 ๋ฐ๊ฐ์ต๋๋ค
๊ฐ์ฅ ์ ์ฉํ ๋๊ธ
https://www.npmjs.com/package/dva-react-hook