So I have been placing the following code within my React JS component and I am basically trying to put both API calls into one state called vehicles
however I am getting an error with the following code:
componentWillMount() {
// Make a request for vehicle data
axios.all([
axios.get('/api/seat/models'),
axios.get('/api/volkswagen/models')
])
.then(axios.spread(function (seat, volkswagen) {
this.setState({ vehicles: seat.data + volkswagen.data })
}))
//.then(response => this.setState({ vehicles: response.data }))
.catch(error => console.log(error));
}
Now I am guessing I can't add two sources of data like I have this.setState({ vehicles: seat.data + volkswagen.data })
however how else can this be done? I just want all of the data from that API request to be put into the one state.
This is the current error I am receiving:
TypeError: Cannot read property 'setState' of null(…)
Thanks
You cannot "add" arrays together. Use the array.concat function (https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/concat) to concatenate both arrays into one and then set that as the state.
componentWillMount() {
// Make a request for vehicle data
axios.all([
axios.get('/api/seat/models'),
axios.get('/api/volkswagen/models')
])
.then(axios.spread(function (seat, volkswagen) {
let vehicles = seat.data.concat(volkswagen.data);
this.setState({ vehicles: vehicles })
}))
//.then(response => this.setState({ vehicles: response.data }))
.catch(error => console.log(error));
}
There are two issues with this:
1) In your .then "this" is undefined, so you'll need to store a reference to this at the top layer.
2) As the other answer stated, you can't add arrays together in JS like that and need to use concat, although since they're server responses I'd add a default as well to stop it erroring if either of those don't actually return you something.
All together I think it should look like:
componentWillMount() {
// Make a request for vehicle data
var that = this;
axios.all([
axios.get('/api/seat/models'),
axios.get('/api/volkswagen/models')
])
.then(axios.spread(function (seat, volkswagen) {
var seatData = seat.data || [];
var volkswagenData = volkswagen.data || [];
var vehicles = seatData.concat(volkswagenData);
that.setState({ vehicles: vehicles })
}))
.catch(error => console.log(error));
}
I want to mention something different. According to the react life cycle, you should prefer call api in componentDidMount()
method.
"componentDidMount() is invoked immediately after a component is mounted. Initialization that requires DOM nodes should go here. If you need to load data from a remote endpoint, this is a good place to instantiate the network request."
https://reactjs.org/docs/react-component.html#componentdidmount
constructor(){
super();
this.state = {};
}
componentDidMount(){
axios.all([
axios.post('http://localhost:1234/api/widget/getfuel'),
axios.post('http://localhost:1234/api/widget/getdatarate')
])
.then(axios.spread((fuel,datarate) => {
this.setState({
fuel:fuel.data.data[0].fuel,
datarate:datarate.data.data[0].data
})
console.log(this.state.fuel)
console.log(this.state.datarate)
}))
}