Отправка не сохраняет данные в слое данных в Api контекста реакции

#javascript #reactjs #react-context

Вопрос:

Я следую учебнику, в котором они делают клон Spotify. Для этого я получил маркер доступа пользователя для доступа ко всем пользовательским данным. И чтобы избежать детализации, я использую React Context-api для сохранения и извлечения пользовательских данных (токен, информация о пользователе, информация о списке воспроизведения и т. Д.). В моем Sidebar.js случае я хочу извлечь информацию о списке воспроизведения из контекста слоя данных и показать ее пользователю. Но информация о плейлисте там не отображается, и после входа в консоль я получил undefined . Чтобы быть уверенным, я также зарегистрировал информацию о плейлисте в консоли App.js , там я получаю всю необходимую информацию, но не в Sidebar.js . Я прикрепил скриншот того, что я получаю по этой ссылке —> >https://ibb.co/PGj4XcT , Любая помощь будет признательна.

Sidebar.js

 function SideBar() {
  const [{ playlists }, dispatch] = UseDataLayerValue();
  console.log("user playlist from sidebar.js", playlists);

  return (
    <div className="sidebar">
      <img
        className="sidebar__logo"
        src="https://getheavy.com/wp-content/uploads/2019/12/spotify2019-830x350.jpg"
        alt="spotify-logo"
      />
      <SidebarOption Icon={HomeIcon} title="Home" />
      <SidebarOption Icon={SearchIcon} title="Search" />
      <SidebarOption Icon={LibraryMusicIcon} title="Your Library" />
      <br />
      <strong className="sidebar__title">PLAYLISTS</strong>
      <hr />

      {playlists?.items?.map((list) => {
        return <SidebarOption title={list.name} />;
      })}
    </div>
  );
}
 

App.js

 function App() {
  const [{ token }, dispatch] = UseDataLayerValue();

  useEffect(() => {
    const hash = getTokenFromUrl;
    window.location.hash = "";
    const _token = hash.access_token;

    if (_token) {
      dispatch({
        type: "SET_TOKEN",
        token: _token,
      });
      // setToken(_token);

      spotify.setAccessToken(_token);

      spotify.getMe().then((user) => {
        dispatch({
          type: "SET_USER",
          user: user,
        });
      });

      spotify.getUserPlaylists().then((playlist) => {
        console.log("user playlist from app.js", playlist);
        dispatch({
          type: "SET_PLAYLIST",
          playlists: playlist,
        });
      });
    }
  }, [dispatch]);

  //console.log(user);
  //console.log(token);
  return (
    <div className="app">
      {token ? <Player spotify={spotify} /> : <Login />}
    </div>
  );
}
 

Reducer.js

 export const initialState = {
  user: null,
  playlists: [],
  playing: false,
  item: null,
  token: null,
};

export const reducer = (state, action) => {
  switch (action.type) {
    case "SET_USER":
      return {
        ...state,
        user: action.user,
      };
    case "SET_TOKEN":
      return {
        ...state,
        token: action.token,
      };
    case "SET_PLAYLIST":
      return {
        ...state,
        playlists: action.playlist,
      };
    default:
      return state;
  }
};
 

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

1. В вашем редукторе есть опечатка, должно быть playlists: action.playlists

2. @BankBuilder но по-моему App.js , я получаю playlist от обещания, не так ли? почему плейлисты? Также в Sidebar.js я получаю информацию о плейлисте, но отображение не работает

3. Все остальное кажется мне правильным, но ваше сообщение выглядит так: dispatch({type: "SET_PLAYLIST", playlists: playlist}); . Обратите внимание, что ключ в вашем действии назван playlists (как в action.playlists ), но в вашем редукторе вы ссылаетесь на него как action.playlist .

4. @BankBuilder да, я понял, но отображение все равно не работает. Я зарегистрировал каждый элемент в консоли, но они не вызываются в SidebarOption компоненте

5. @BankBuilder нет, сейчас это решено… Все , что мне нужно было сделать, это добавить return перед <SidebarOption title={list.name} />; … Так как я использую фигурные скобки, вот почему я забыл добавить return , Сначала я подумал, что функция стрелки автоматически возвращает что-то, но я ошибся. Поскольку я использовал {} это, мне пришлось добавить return перед заявлением. Я обновил Sidebar.js

Ответ №1:

Все , что мне нужно было сделать, это добавить возврат до <SidebarOption title={list.name} />; … Так как я использую фигурные скобки, вот почему я забыл добавить return , Сначала я подумал, что функция стрелки автоматически возвращает что-то, но я ошибся. Поскольку я использовал {} это, мне пришлось добавить return перед заявлением. Я обновил Sidebar.js