繁体   English   中英

反应子组件不会在父强制更新时重新渲染

[英]React child component not re-rendering on parent force update

我面临一个问题,即在父组件上调用 forceUpdate 不会重新渲染子组件。 我附上了下面的代码片段。

父组件

    const forceUpdate = React.useReducer(() => ({}))[1];

    const getAccountDetails = () => {
    const opts = {
        mailboxKey: details.getMailboxKey()
    };
    details.getAccountDetails(opts).then((response) => {
        if (response.resp.data.lastSyncTime && response.resp.data.lastSyncTime !== -1) {
            setLastSyncTime(response.resp.data.lastSyncTime);
            if (response?.resp?.data?.ssi) {
                details.set("ssi", response.resp.data.ssi);
            }
            if (response?.resp?.data?.fsi) {
                details.set("fsi", response.resp.data.fsi);
            }
        }
        details.set("isSyncCompleted", response.resp.data?.isSyncCompleted);
    }).catch((ex) => {
        succErrMsg(getI18N("ERROR"), {
            severity: "error",
            ...succErrMsgOption
        });
    });
    forceUpdate();
};

useEffect(() => {
    getAccountDetails();
}, []);

const renderStatustable = () => {
    const isSyncCompleted = details.getIsSyncCompleted();
    if (isSyncCompleted) {
        return <ImapSyncStatus {...{details}} />;
    }
    return <ImapFolderSyncStatus {...{details, getAccountDetails}} />;
};
return (showSyncStatusTable && renderStatustable())

子组件 ImapFolderSyncStatus.js

const [fsiData, setFsiData] = useState();

useEffect(() => {
    setFsiData(details.getFolderSyncStatusInfo());
}, []);

function renderFolderSyncStatusRows () {
    const rows = [];
    for (const key in fsiData) {
        if (Object.hasOwnProperty.call(fsiData, key)) {
            const element = fsiData[key];
            rows.push(
                <Tr>
                    <Td>
                        {element.folderName}
                    </Td>
                    <Td>
                        {element.ci.ZCount}
                    </Td>
                    <Td>
                        {element.ci.mailCount}
                    </Td>
                </Tr>
            );
        }
    }
    return rows;
}

    return (<>
<ButtonColumn align="right">
                            <Button variant="flat" variantColor="primary" size="custom" onClick={getAccountDetails}>
                                <Icon className="rotate-right" />
                                {getI18N("Refresh folder")}
                            </Button>
                        </ButtonColumn>{renderFolderSyncStatusRows()}
</>);

如您所见,我正在从孩子那里调用父getAccountDetails function。 function 被正确调用并且 forceUpdate 也被触发。 但是,如果我在const [fsiData, setFsiData] = useState();行上添加断点而在子组件的useEffect里面,只会触发前一个断点。 我通过向子组件添加一个键来解决这个问题,但我不明白到底发生了什么。

您的子组件更新得很好。 只是您看到的数据不会因为您滥用useEffect

使用类似的组件

function Component(...) {
  const [fsiData, setFsiData] = useState();

  useEffect(() => {
    setFsiData(details.getFolderSyncStatusInfo());
  }, []);
  // ... use fsiData for rendering...
}

该效果仅在组件安装时运行,并且不再运行。

道具更改不会导致组件(重新)安装,因此效果永远不会运行,并且您会遇到相同的数据。 (组件的key更改将导致重新安装。)

做就是了

function Component(...) {
  const fsiData = details.getFolderSyncStatusInfo();
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM