Как ждать App.js код для запуска перед установкой компонентов?

#javascript #reactjs

#javascript #reactjs

Вопрос:

Итак, у меня проблема, когда я использую фрагмент кода в App.js чтобы войти в систему пользователя, если у него есть сохраненный токен JWT (чтобы сохранить их вход в систему, если они покинут страницу, а затем вернутся). Я использую сокет.ввод-вывод для связи с сервером.

Проблема в том, что в моем компоненте я создаю сокет.io вызывает внутри componentDidMount(), но этот код выполняется перед App.js код, поэтому сокет еще не сохранен в моем бэкэнде. В том виде, в котором сейчас работает приложение, я сохраняю идентификаторы сокетов и идентификаторы пользователей пользователей, чтобы отслеживать открытые сокеты для каждого пользователя.

Если код componentDidMount() запускается перед сохранением вновь созданного соединения с сокетами (при открытии новой вкладки создается новый сокет) Я не могу использовать новый сокет в этом вызове.

Я зарегистрировал функции, чтобы увидеть порядок, и это то, что я получил, поэтому я подозреваю, что код componentDidMount() запускается первым.

 userID empty null
usersOfCall null
socketAssign
[
  {
    userID: '5fb483cf93b92d651a281450',
    socketIDs: [ 'hdLMOfFhFXHGyOpDAAAB' ],
    socketPreserved: null
  },
  {
    userID: '5fb47647c93e23622c4e1c10',
    socketIDs: [ 'JAcC2XwLuoZTsgIiAAAC', '7vgKN-sqkqUNS7L_AAAD' ],
    socketPreserved: null
  }
]
 

Из socketAssign приведенной ниже строки следует, что именно там я храню сокет для пользователя.
Выше это результат вызова, который я делаю изнутри componentDidMount()
userID empty null Строка является результатом функции, которая получит идентификатор пользователя пользователя, связанного с сокетом, который отправил сигнал. Он становится нулевым, поскольку сокет еще не сохранен, поэтому он не может найти совпадений.

App.js фрагмент кода:

 if(localStorage.jwtToken){
    const token = localStorage.jwtToken;
    const tokenDecoded = jwt_decode(token);
    const user = tokenDecoded.response;
    store.dispatch(userSocketAssign(user));
    const currentTime = Date.now() / 1000;
    if(tokenDecoded.exp < currentTime){
        console.log('expired');
        store.dispatch(userSocketDeassign());
        window.location.href = './login';
    }
}

function App() {
    return (
        <Provider store = {store}>
            <AppComponent />
        </Provider>
    );
}
 

AppComponent просто отображает маршруты для приложения со свойствами компонента, которые указывают, какой компонент должен отображаться при выборе определенного маршрута.

 class App extends Component
{
    componentDidMount(){
        
    }

    render(){
        return (
            <Router>
                <Navbar />
                <Switch className = "container-fluid">
                    <Route exact path = "/" component = {Dashboard} />
                    <Route exact path = "/login" component = {Login} />
                    ...
                </Switch>
                <CallReceived />
            </Router>
        );
    }
}
 

Как я мог бы заставить процесс монтирования ждать, пока сокет не будет сохранен на серверной части?

Комментарии:

1. Просто используйте условный рендеринг для всей <Router> детали. {this.state.hasLoaded amp;amp; <Router>...</Router>}

Ответ №1:

Я предлагаю вам прочитать о цикле состояний. В зависимости от вашей ситуации вы можете установить таймер для запуска компонента. Внутри компонента попробуйте добавить setInterval для задержки, при которой приложение будет отображаться первым. Вот документация о цикле состояния https://reactjs.org/docs/state-and-lifecycle.html .

Комментарии:

1. Использование таймера для ожидания ответа API является плохой практикой и в любом случае не является необходимым (если только речь не идет о реализации пользовательского тайм-аута для запроса API)