2017-10-16 62 views
1

由於某些原因,我的路由只渲染一半時間 - 看起來像某種競爭條件。它會打印出「OK」,但沒有任何路線,甚至沒有404。很清晰的剪輯。如果路由在render中更改()

如果我刪除加載位,它將始終呈現預期的開關塊。

有沒有更好/不同的方式來做到這一點?

V4.2.0

render() { 
    const { hasInitialized } = this.props; 
    if (!hasInitialized) { 
     return (
     <div>Loading...</div> 
    ); 
    } 

    return (
     <div style={{ height: '100%', width: '100%' }}> 
     <Helmet titleTemplate="%s - Resilient" defaultTitle="Resilient" /> 
     <div>OK</div> 
     <Switch> 
      <Redirect from="/" to="/auth/check" exact={true} /> 
      <Route path="/auth" component={AuthLayout} /> 

      <AuthenticatedRoute path="/x" component={AdminLayout} /> 
      <Route component={Miss404} /> 
     </Switch> 
     </div> 
    ); 
    } 

https://github.com/ReactTraining/react-router/issues/5621

+1

不知道爲什麼你的代碼不能正常工作,對我來說看起來很不錯......但是你真的需要這個加載條件渲染嗎?我在路由中看不到需要外部數據的任何內容,但是您可能故意留下了這些內容?我的觀點是,你能否將有條件地委託給其中一個路由到的組件? – Jaxx

+0

謝謝Jaxx。爲了簡單起見,我沒有留下一堆代碼。我只是試圖在發生任何事情之前通過獲取調用加載用戶。向下遊移動這種邏輯是沒有意義的,因爲它必須在任何地方。我想我會嘗試將它們反射到處理auth的路由,然後將它們發回,但我試圖避免這種情況,因爲它是一種糟糕的UX。我已經嘗試了一大堆類似於上面的代碼的東西,看起來像react-router不支持在渲染中更改路由。 – Justin

+0

找到了解決兩種情況的解決方法。 1)我創建了一個包含我所有路由邏輯的HOC。 2)我將最初的歷史更改邏輯從'componentDidMount'移到'componentWillMount'。不知道爲什麼這使它工作,但很高興有一個解決方法。 – Justin

回答

0

我讀了反應,路由器文檔很多次,約Blocked Updates部分似乎有關。但是,當我在<Layout />中放置調試器行時,位置和歷史記錄始終具有正確的信息,並且仍然不會渲染任何路由。

我還是不明白問題是什麼,但這裏是我提出的解決方法。下面的代碼將包含我的<Layout />組件,其中包含所有路由。

import React, { Component } from 'react'; 
import { connect } from 'react-redux'; 
import { withRouter } from 'react-router-dom'; 
import LocalStorageManager from 'utils/LocalStorageManager'; 
import { selectCurrentUser, selectHasInitialized } from 'client/selectors/authSelectors'; 
import { setAccessToken, getProfile } from 'shared/api'; 
import { setHasInitialized, signIn } from 'modules/auth/actions.js'; 
import SinglePageCard from 'components/layout/SinglePageCard'; 

const mapStateToProps = (state) => { 
    return { 
    currentUser: selectCurrentUser(state), 
    hasInitialized: selectHasInitialized(state), 
    }; 
}; 

export default (WrappedComponent) => { 
    class Layout extends Component { 
    componentWillMount() { 
     const accessToken = LocalStorageManager.getAccessToken(); 
     if (!accessToken) { 
     this.props.setHasInitialized(); 
     return; 
     } 

     setAccessToken(accessToken); 
     getProfile().then((response) => { 
     console.log(response); 
     const { user } = response.data.data; 
     this.props.signIn(user); 
     }).catch((error) => { 
     console.log(error); 
     this.props.setHasInitialized(); 
     }); 
    } 

    render() { 
     const { currentUser, hasInitialized, ...rest } = this.props; 
     if (!hasInitialized) { 
     return (
      <SinglePageCard> 
      <div>Initializing...</div> 
      </SinglePageCard> 
     ); 
     } 

     return (
     <WrappedComponent {...rest} /> 
    ); 
    } 
    } 
    return withRouter(connect(mapStateToProps, { setHasInitialized, signIn })(Layout)); 
};