React / Apollo fetchMore перезагружает всю страницу

#reactjs #apollo #react-apollo

#reactjs #apollo #react-apollo

Вопрос:

У меня проблема при попытке выполнить разбивку на страницы / кнопку fetchMore для списка данных в моем веб-приложении. Моя проблема в том, что когда я нажимаю на кнопку fetchMore, перезагружается вся страница в стиле старой школы, в то время как я хотел бы, чтобы был перезагружен только обновленный список «вычислений», но не остальная часть запроса (пользователи …).

Есть ли способ ограничить то, что обновляется после fetchMore? Не хочу, чтобы весь DOM был повторно отображен.

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

Вот необходимая часть кода:

 export const query = gql`
    query UserAndData($limit: Int!) {
        user {
            _id,
            nom,
            prenom,
            email,
            isAdmin
        }
        adminCalculations {
            _id,
            lastUpdated,
            comments
        }
        adminUsers {
            _id,
            lastConnect,
            nom,
            prenom,
            email,
            societe
        }
        calculs(limit: $limit) {
            _id,
            userId,
            date,
            duration,
            user {
                email
            }
        }
        count
    }
`

class Admin extends Component {

    state = {
        limit : 100,
    }

    render() {
        return(
            <Query query={query} variables={{ limit : this.state.limit}} fetchPolicy="cache-and-network">
                {({ loading, error, data, fetchMore }) => {
                    if (loading) return <p>Loading...</p>;
                    if (error) return <p>Error</p>;
                    console.log(data);
                    if (!data || (!data.user || !data.user.isAdmin)){
                        return (<Redirect to="/" />)
                    }
                    return(
                        <div className="admin">
  (lot of coding and rendering users list, calculs lists, etc...)

   <div className="bouton" onClick={() => {
       fetchMore({                               
          variables : { limit : this.state.limit   100 },
          updateQuery : (prev, { fetchMoreResult }) => {
          if (!fetchMoreResult) return prev;
          return Object.assign({}, prev, { calculs : 
          fetchMoreResult.calculs });
      }

                                                })
                                                this.setState({ limit : this.state.limit   100 })
                                            }
                                                }>Charger plus de calculs</div>

                                        </div>
                                    </div>
                                </div>
                            </div>
                        )
                    }}
                </Query>
            )
        }
    }

export default Admin;
  

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

1. Я не уверен, что это проблема, но это определенно проблематично. Не устанавливайте состояние внутри метода рендеринга. React называется React, потому что он «реагирует» на изменения реквизита и состояния с помощью нового рендеринга. Ваше состояние расположено ближе к корню вашего примера. На таком высоком уровне все в вашем методе render() будет повторно отображаться при изменении состояния.

2. состояние установлено для действия onClick не видите, где это проблематично, за исключением случаев, когда это мешает повторной выборке?

3. Из любопытства я попробовал @mrbinky3000 idea и удалил setState и попробовал снова, но ничего не изменил. Поскольку это является частью действия onclick, я не вижу, как это создает проблему.

4. Оператор if, который имеет if (!data || (!data.user || !data.user.isAdmin)){ перенаправление на «». введите туда консольный журнал, чтобы проверить, существуют ли data.user и data.user.isAdmin, когда Apollo начнет извлекать больше данных.

Ответ №1:

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

 if(loading)
  

утверждение, вся страница загружалась снова каждый раз, когда выполнялась повторная загрузка, и, следовательно, вся страница отображала

 <p>Loading...</p>
  

даже если время загрузки было очень маленьким -> это привело к «обновлению» всей моей страницы

Чтобы решить эту проблему, я создал дочерний компонент, который также включает компонент запроса Apollo, но только запрос, который я хочу повторно получить. Родительский компонент с запросом user, adminCalculations и adminUsers не обновляется бессмысленно, и только необходимые дочерние запросы повторно извлекаются и отправляются повторно.

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

1. Возникла точно такая же проблема, спасибо, что поделились своим решением

2. ДА. точная проблема, с которой я столкнулся, loading состояние технически изменяется при каждом событии выборки, кроме первого рендеринга. Не осознавал этого, пока не увидел ваш ответ. Мы должны действительно заботиться о состоянии apollo из запроса