Как динамически обновить поисковый запрос с помощью React / Redux / Axios? - PullRequest
0 голосов
/ 28 мая 2018

Я создаю небольшое приложение itunes для извлечения данных из API Itunes.Я пытаюсь реализовать панель поиска, чтобы сделать соответствующую выборку на сервер, но я не могу понять, какие правильные реквизиты были переданы из состояния Redux.Поскольку это небольшое приложение, я использовал только основные App.js и index.js вместо отдельных папок для действий и редукторов.Мой основной файл App.js выглядит следующим образом:

import React, { Component } from 'react';
import './App.css';
import Navbar from './components/Navbar';
import Results from './components/Results';
import ToggleLayout from './components/ToggleLayout';
import AdditionalPages from './components/AdditionalPages';
import axios from 'axios';
import { connect } from 'react-redux';

const PATH_BASE = 'https://itunes.apple.com/search';
const PATH_TERM = 'term=';
const COUNTRY = 'country=es';
const ALBUMS = 'entity=album';
const LIMIT = 'limit=60';  

class App extends Component {
  constructor(props){
    super(props);
    }
  }

  render() {
    return (
       <div>
          <Navbar
            searchTerm={this.props.searchItunes.searchTerm}
            onSearchChange={(e) => this.props.onSearchChange(e.target.value)}
            fetchITunesAlbums={(e) => this.props.fetchITunesAlbums(e)}
          /> 
          { this.props.searchItunes.itunes &&
              <Results itunes={this.props.searchItunes.itunes} grid={this.props.toggle.grid} additionalPages={this.props.toggle.additionalPages} fetchMorePages={this.fetchMorePages}/>
          }

          { this.props.toggle.additionalPages &&
              <AdditionalPages itunes={this.props.searchItunes.itunes} grid={this.props.toggle.grid}/>
          }

          <ToggleLayout
            switchLayout={()=> this.props.switchLayout()}
            grid={this.props.toggle.grid}
          />
      </div>
    );
  }
}

const mapStateToProps = (state) => {
  return {
    toggle: state.booleanReducer,
    searchItunes: state.searchItunesReducer
  };
};

const mapDispatchToProps = (dispatch) => {
  return {

    switchLayout: () => {
      dispatch({
        type:"GRID"
      });
    },

    fetchMorePages: () => {
      dispatch({
        type:"ADDITIONALPAGES"
      });
    },

    onSearchChange: (term) => {
      dispatch({
        type:"SEARCHTERM",
        payload:term
      });
    },

    fetchITunesAlbums: (e) => {
      e.preventDefault();
        axios.get(`${PATH_BASE}?${PATH_TERM}${searchTerm}&${COUNTRY}&${ALBUMS}&${LIMIT}`)
          .then(response =>{
            dispatch({
              type: 'FETCHITUNESALBUMS',
              payload: response.data
            });
          });
        }
      };
    };

export default connect(mapStateToProps,mapDispatchToProps)(App);

Так что моя проблема связана с моим axios url.Например, если я жестко запрограммировал URL-адрес, такой как

axios.get(`${PATH_BASE}?${PATH_TERM}&${'someband'}${COUNTRY}&${ALBUMS}&${LIMIT}`)

, я могу получить результаты с сервера, но не тогда, когда я вставляю

axios.get(`${PATH_BASE}?${PATH_TERM}${searchTerm}&${COUNTRY}&${ALBUMS}&${LIMIT}`)

и ниже это мой index.js

import React from 'react';
import ReactDOM from 'react-dom';
import './index.css';
import App from './App';
import registerServiceWorker from './registerServiceWorker';
import { render } from 'react-dom';
import  { Provider }  from 'react-redux';
import { createStore, combineReducers, applyMiddleware } from 'redux';
import thunk from 'redux-thunk';
import logger from 'redux-logger';

const booleanReducer = (state = { grid:true, additionalPages:false }, action) => {
  if (action.type === 'GRID'){
    return state = {
      ...state,
      grid:!state.grid
    }
  }
  if (action.type === 'ADDITIONALPAGES'){
    return state = {
      ...state,
      additionalPages:!state.additionalPages
    }
  }
  return state;
};

const searchItunesReducer = (state = { searchTerm:'', itunes:null }, action) => {
  if (action.type === 'SEARCHTERM'){
    return state = {
      ...state,
      searchTerm:action.payload
      }
    }
  if (action.type === 'FETCHITUNESALBUMS'){
    return state = {
      ...state,
      itunes: action.payload

      }
    }
      return state;
  }


const middleware = applyMiddleware(thunk, logger)
const store = createStore(combineReducers({booleanReducer,searchItunesReducer}),middleware);
console.log(store.getState());

store.subscribe(() =>{
  console.log("store updated!", store.getState());
});

registerServiceWorker();
ReactDOM.render(
<Provider store={store}>
  <App />
</Provider>
, document.getElementById('root'));

Любая помощь высоко ценится ...

Ответы [ 2 ]

0 голосов
/ 28 мая 2018

Можете ли вы попробовать это в строке поиска

onChange={(e) => props.fetchItunesAlbums(e.target.value)}

И обновить свои fetchItunesAlbums на:

  axios.get(`${PATH_BASE}?${PATH_TERM}${e}&${COUNTRY}&${ALBUMS}&${LIMIT}`)

Вместо сохранения поискового термина в редукции состояния приложения.посмотрите, работает ли он.

0 голосов
/ 28 мая 2018

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

     <Navbar
        searchTerm={this.props.searchItunes.searchTerm}
        onSearchChange={(e) => this.props.onSearchChange(e.target.value)}
        fetchITunesAlbums={(e) => this.props.fetchITunesAlbums(e,this.props.searchItunes.searchTerm)}
      /> 

, а затем функцию fetchItunes, как,

fetchITunesAlbums: (e,searchTerm) => {
      e.preventDefault();
        axios.get(`${PATH_BASE}?${PATH_TERM}${searchTerm}&${COUNTRY}&${ALBUMS}&${LIMIT}`)
          .then(response =>{
            dispatch({
              type: 'FETCHITUNESALBUMS',
              payload: response.data
            });
          });
        }
      };
    };
...