Невозможно вызвать setState внутри socket.io обратного вызова React.js - PullRequest
4 голосов
/ 03 мая 2019

Я сталкиваюсь со следующей проблемой:

Внутри реагирующего компонента, который обрабатывает состояние, существует соединение websocket с socket.io.Всякий раз, когда я получаю некоторые события, я должен выполнить некоторую операцию и обновить состояние компонента.Пример:

socket.on('some event', () => {
 this.aMethod() // this method calls setState()
})

Проблема в том, что появляется следующее сообщение:

Can't perform a React state update on an unmounted component. This is a no-op, but it indicates a memory leak in your application. To fix, cancel all subscriptions and asynchronous tasks in the componentWillUnmount method.

Но я не , использующий метод componentWillUnmount в любом месте.И этот компонент не отключен.

Если я заменим aMethod на this.props.aMethod() и обновлю состояние родительского компонента, который будет работать (aMethod существует в обоих компонентах).Проблема в том, что этот компонент огромен, потому что это контейнер, и перемещение всех состояний в родительские и использование реквизита вызовет много переписывания ..

Это дало мне представление о том, что могут быть проблемы с маршрутами реагированияприложение.

Родительский компонент имеет следующие маршруты (концептуально):

 <Switch>

          <Route exact path={'/user/:id'} render={(props) => <User />} />
          <Route exact path={'/users'} render={(props) => <User />} />

  </Switch>

Я использовал render вместо component, потому что мне нужно передать некоторые методы в качестве реквизита.React и response-router-dom имеет самую последнюю версию 16.x и 5.0.0.

Возможно ли как-то реагировать, что-то вроде "зависания" первого экземпляра компонента, а затем изменения URL и яне могу обновить состояние больше?Если я утешаю сообщение внутри componentWillUnmount(), я не вижу его размонтированным.

Любая идея будет принята с благодарностью!

Не стесняйтесь задавать вопросы.

1 Ответ

5 голосов
/ 03 мая 2019

React говорит вам, что вы ДОЛЖНЫ удалить слушателя в componentWillUnmount:

componentWillUnmount() {
 socket.off('some event');
}

Это связано с тем, что:

  • если вы добавите слушателя в componentDidMount, вы получите несколько слушателей
  • когда компонент размонтирован (при изменении маршрута) «this» и его привязка к контексту больше не имеет смысла, но обратный вызов все равно пытается установить состояние каждый раз, когда происходит событие

Форма реагирования документов:

componentWillUnmount () вызывается непосредственно перед тем, как компонент демонтирован и уничтожен. Выполните любую необходимую очистку в этом методе, такие как аннулирование таймеров, отмена сетевых запросов или очистка все подписки, созданные в componentDidMount ().

Ссылка: https://reactjs.org/docs/react-component.html?utm_source=caibaojian.com#componentwillunmount

Еще один ресурс, чтобы лучше понять проблему:

https://advancedweb.hu/2016/01/05/global-listener-patterns-in-react/

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...