渲染组件时不触发 useEffect

Posted

技术标签:

【中文标题】渲染组件时不触发 useEffect【英文标题】:useEffect not triggers when rendering a component 【发布时间】:2021-10-31 05:30:33 【问题描述】:

我正在单击主页上的单个帖子,该帖子会将我发送到被点击帖子的页面。在此组件的渲染中,我正在从 useEffect 调度一个操作,该操作将从后端获取发布数据。但是 useEffect 甚至不会被触发一次,而是页面渲染两次。 请帮忙

import 
  Container,
  Typography,
  LinearProgress,
  CircularProgress,
  Paper
 from '@material-ui/core';
import React, 
  useEffect
 from 'react';
import 
  getPost
 from "../../actions/posts";
import Navbar from '../Navbar/Navbar';
import 
  useDispatch,
  useSelector
 from 'react-redux';
import 
  useParams
 from 'react-router-dom';
import useStyles from "./styles";

const PostDetails = () => 
    const dispatch = useDispatch();
    const 
      id
     = useParams();
    const classes = useStyles();
    const 
      post,
      isLoading
     = useSelector((state) => (state.posts));

    console.log(post);
    useEffect(() => 
      console.log(post);
      dispatch(getPost(id));
    , [id, dispatch]);

    return ( < div >
        <
        Navbar color = "#808080" / > 
          isLoading ? ( < div > < LinearProgress / > < /div>) : 
            ( < Container className = 
                classes.root
               >
              <
              Typography variant = "h1" > 
                post.title
               < /Typography> <
              /Container>)</div > )
          
          export default PostDetails

我的行动:

export const getPost = (id) => async(dispatch) => 
  try 
    dispatch(
      type: "START_LOADING"
    );
    const 
      data
     = await api.fetchPost(id);
    dispatch(
      type: "FETCH_POST",
      payload: 
        post: data
      
    );
    dispatch(
      type: "END_LOADING"
    );
   catch (error) 
    console.log(error);
  
;

减速器:

export default (state = 
  isLoading: true,
  posts: []
, action) => 
  switch (action.type) 
    case "START_LOADING":
      return  ...state,
        isLoading: true
      ;

    case "FETCH_POST":
      return  ...state,
        post: action.payload.post
      ;

    case "FETCH_ALL":
      return  ...state,
        posts: action.payload.data,
        currentPage: action.payload.currentPage,
        numberOfPages: action.payload.numberOfPages
      ;

    case "CREATE":
      return  ...state,
        posts: [...state.posts, action.payload]
      ;

    case "END_LOADING":
      return  ...state,
        isLoading: false
      ;

    default:
      return "";
  

我的后端很好,因为当我在 localhost 上运行 api 请求到后端时,它会向我发送一个带有帖子数据的 JSON 对象。

【问题讨论】:

“useEffect 一次都不会被触发”是什么意思? 它不会在初始渲染时触发,但我在 useEffect 中得到 2 个未定义和 console.log 的 console.log 值,但未触发。这意味着组件渲染了两次但 useEffect 没有被触发。 【参考方案1】:

UseEffect 仅在方括号内给出的值更改时才会触发。因此,如果您希望它仅在第一次加载页面时触发,请将其留空。

useEffect(() => 
      console.log(post);
      await dispatch(findPost(id));
    , []);

【讨论】:

它没有用。我收到错误“TypeError: Cannot read property 'title' of undefined” useeffect 有效吗?在useeffect中尝试console.log @NamanKedia 你读过错误吗?您从状态加载“post”,但您的选择器加载“posts”复数。 由于 dispatch() 是异步函数,你添加了 await 吗? 请人帮忙!我之前做了一个类似的网络应用程序,但没有这样的问题,我什至比较了代码。请帮忙【参考方案2】:
dispatch(findPost(id)); //No findPost in ../../actions/posts

没有 findPost 操作。你认为你应该把它改成 getPost

dispatch(getPost(id)); 

【讨论】:

以上是关于渲染组件时不触发 useEffect的主要内容,如果未能解决你的问题,请参考以下文章

在条件渲染组件中,状态更新不会触发重新渲染。

组件渲染已触发,但 DOM 未更新

Vue 组件 prop 更改不会触发重新渲染

尽管状态发生了变化,但自定义钩子不会触发组件重新渲染

为啥在组件加载时不调用 useEffect(()=...,[]) ?

Vuex 全局状态更改不会触发 Nuxt 中 v-for 循环中的重新渲染组件