簡體   English   中英

this.props.history.push 不重新渲染反應組件

[英]this.props.history.push not re-rendering react component

在我的組件中,我使用 this.props.history.push(pathname:.. search:..) 重新渲染組件並從第三方服務獲取新數據。 當我第一次調用它呈現的頁面時。 但是當我在組件內部調用歷史推送時,URL 會正確更新,但組件不會重新呈現。 我讀了很多,但無法讓它工作。 有任何想法嗎?

我正在使用反應路由器 v4

 //index.js <Provider store={store}> <BrowserRouter> <Switch> <Route path="/login" component={Login}/> <Route path="/" component={Main}/> </Switch> </BrowserRouter> </Provider> //Main.js //PropsRoute is used to push props to logs component so I can use them when fetching new data const PropsRoute = ({ component: Component, ...rest }) => { return ( <Route {...rest} render={props => <Component {...props} />}/> ); }; class Main extends Component { render() { return ( <div className="app"> <NavigationBar/> <div className="app-body"> <SideBar/> <Switch> <PropsRoute path="/logs" component={Log}/> //this component is not rerendering <Route path="/reports" component={Reports}/> <Route path="/gen" component={Dashboard}/> <Redirect from="/" to="/gen"/> </Switch> </div> </div> ) } } export default Main; //inside 'Log' component I call import React, {Component} from 'react'; import {getSystemLogs} from "../api"; import {Link} from 'react-router-dom'; import _ from "lodash"; import queryString from 'query-string'; let _isMounted; class Log extends Component { constructor(props) { super(props); //check if query params are defined. If not re render component with query params let queryParams = queryString.parse(props.location.search); if (!(queryParams.page && queryParams.type && queryParams.pageSize && queryParams.application)) { this.props.history.push({ pathname: '/logs', search: `?page=1&pageSize=25&type=3&application=fdce4427fc9b49e0bbde1f9dc090cfb9` }); } this.state = { logs: {}, pageCount: 0, application: [ { name: 'internal', id: '...' } ], types: [ { name: 'Info', id: 3 } ], paginationPage: queryParams.page - 1, request: { page: queryParams.page === undefined ? 1 : queryParams.page, type: queryParams.type === undefined ? 3 : queryParams.type, pageSize: queryParams.pageSize === undefined ? 25 : queryParams.pageSize, application: queryParams.application === undefined ? 'fdce4427fc9b49e0bbde1f9dc090cfb9' : queryParams.application } }; this.onInputChange = this.onInputChange.bind(this); } componentDidMount() { _isMounted = true; this.getLogs(this.state.request); } componentWillUnmount() { _isMounted = false; } getLogs(request) { getSystemLogs(request) .then((response) => { if (_isMounted) { this.setState({ logs: response.data.Data, pageCount: (response.data.TotalCount / this.state.request.pageSize) }); } }); } applyFilter = () => { //reset page to 1 when filter changes console.log('apply filter'); this.setState({ request: { ...this.state.request, page: 1 } }, () => { this.props.history.push({ pathname: '/logs', search: `?page=${this.state.request.page}&pageSize=${this.state.request.pageSize}&type=${this.state.request.type}&application=${this.state.request.application}` }); }); }; onInputChange = () => (event) => { const {request} = this.state; //create copy of current object request[event.target.name] = event.target.value; //update object this.setState({request}); //set object to new object }; render() { let logs = _.map(this.state.logs, log => { return ( <div className="bg-white rounded shadow mb-2" key={log.id}> ... </div> ); }); return ( <main className="main"> ... </main> ); } } export default Log;

Reactjs 不會在propsstate改變時重新運行constructor方法,他會在你第一次調用組件時調用constructor

如果您的nextProps.location.pathname與您的this.props.location.pathname ( react-router location ) 不同,您應該使用componentDidUpdate並進行獲取

我在功能組件上遇到了同樣的問題,我使用鈎子 useEffect 和props.location作為依賴項解決了這個問題。

  import React, { useEffect } from 'react';
  const myComponent = () => {
    useEffect(() => {
      // fetch your data when the props.location changes
    }, [props.location]);
  } 


這將useEffect每次props.location更改時調用useEffect以便您可以獲取數據。 它的作用類似於componentDidMountcomponentDidUpdate

getderivedstatefromprops生命周期方法創建一個容器組件/提供者getderivedstatefromprops ,它更像反應:

class ContainerComp extends Component {
  state = { needRerender: false };

  static getderivedstatefromprops(nextProps, nextState) {
    let queryParams = queryString.parse(nextProps.location.search);

    if (!(queryParams.page && queryParams.type && queryParams.pageSize && queryParams.application)) {
      return { needRefresh: true };
    } else {
      return { needRefresh: false };
    }

  }

  render() {
    return (
      <div>
        {this.state.needRefresh ? <Redirect params={} /> : <Log />}
      </div>
    );
  }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM