Reputation: 2212
I'm building a small itunes application to fetch data from the Itunes api. I'm trying to implement the searchbar to make a relevant fetch to the server but I can't seem to figure out the correct props passed down from the Redux state. Since it is a small app I have used just the main App.js and index.js instead of separate folders for actions and reducers. My main App.js is as below:
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);
So my issue is with my axios url. For example if I hard code the url such as
axios.get(`${PATH_BASE}?${PATH_TERM}&${'someband'}${COUNTRY}&${ALBUMS}&${LIMIT}`)
the I'm able to fetch the results from the server but not when I insert
axios.get(`${PATH_BASE}?${PATH_TERM}${searchTerm}&${COUNTRY}&${ALBUMS}&${LIMIT}`)
and below is my 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'));
Any help is highly appreciated...
Upvotes: 0
Views: 1119
Reputation: 425
Can you try this on the search bar
onChange={(e) => props.fetchItunesAlbums(e.target.value)}
And update your fetchItunesAlbums to:
axios.get(`${PATH_BASE}?${PATH_TERM}${e}&${COUNTRY}&${ALBUMS}&${LIMIT}`)
Instead of saving the search term on app state redux. see if it works.
Upvotes: 0
Reputation: 5669
I think your issue lies with the search term, try to pass the value as a param,
<Navbar
searchTerm={this.props.searchItunes.searchTerm}
onSearchChange={(e) => this.props.onSearchChange(e.target.value)}
fetchITunesAlbums={(e) => this.props.fetchITunesAlbums(e,this.props.searchItunes.searchTerm)}
/>
and then the fetchItunes function as,
fetchITunesAlbums: (e,searchTerm) => {
e.preventDefault();
axios.get(`${PATH_BASE}?${PATH_TERM}${searchTerm}&${COUNTRY}&${ALBUMS}&${LIMIT}`)
.then(response =>{
dispatch({
type: 'FETCHITUNESALBUMS',
payload: response.data
});
});
}
};
};
Upvotes: 1