glem1337
@glem1337

Как запомнить значение переменной что бы не вызывать эффект при монтировании и перемонтировании?

Добрый день. Если в url присутствует имя покемона, то приложение рендерит компонент детального просмотра.

App.js
import React from 'react';
import { Route } from 'react-router-dom';
import Header from './components/Header/Header';
import Pokedex from './components/Pokedex/Pokedex';
import PokePage from './components/PokePage/PokePage';

const App = () => (
    <React.Fragment>
        <Header />
        <Route exact path="/pokedex/">
            <Pokedex />
        </Route>
        <Route path="/pokedex/:pokeName">
            <PokePage /> // страница детального просмотра покемона
        </Route>
    </React.Fragment>
);

export default App;


В компоненте детального просмотра я получаю имя покемона через `useParams()` react-router-dom

PokePage.js
import React, {useEffect} from 'react';
import { useDispatch, useSelector } from 'react-redux';
import {useParams} from 'react-router-dom';
import {Container} from '@material-ui/core';
import {fetchPokemonByName} from "../../redux/PokeDetail/operations";
import pokeDetailSelectors from "../../redux/PokeDetail/selectors";

const mapState = (state) => ({
    pokemon: pokeDetailSelectors.getPokemon(state),
    error: pokeDetailSelectors.getError(state),
});

const PokePage = () => {
    const { pokeName } = useParams();
    const dispatch = useDispatch();
    const {pokemon, error} = useSelector(mapState);

    useEffect(() => {
        dispatch(fetchPokemonByName(pokeName));
    }, [pokeName]);

    return (
        <React.Fragment>
            <Container maxWidth="lg">
                <h1>Detail page in dev process</h1>
                Pokemon name: {pokeName}
            </Container>
        </React.Fragment>
    );
};
export default PokePage;


Переменная pokeName является зависимостью для эффекта.

Вопрос: Возможно ли сделать так, что бы при повторном монтировании компонента уже было доступно прошлое значение переменной pokeName, и только если она изменилась диспатчить? Я новичок в react, и мне почему-то хочется смотреть в сторону useMemo или useCallback, но хоть убей не могу придумать как это использовать именно в этом компоненте, который каждый раз умирает, если мы уходим из него. Есть идея что бы в App.js проверять изменилось значение, и на основе этого передавать соответствующий флаг в пропсы, но есть ощущение что это костыль, и есть более просто и изящное решение, которое позволит сохранить ответственность в этом компоненте.
  • Вопрос задан
  • 186 просмотров
Решения вопроса 1
mbelskiy
@mbelskiy
Software Developer
Нельзя умирающему компоненту сказать: Передай это будущему поколению.

Раз уже есть редакс, можно организовать на нем кэширование данных. При диспатче проверять наличие данных в кэше, их свежесть. Нет - пошли за данными, положили в кэш. Есть - ничего не делаем, компонент селектом и так их вытянет.
Ответ написан
Комментировать
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы