Reputation: 11
class ItemsPage extends React.Component {
constructor(props)
{
super(props)
this.state = {items: null }
this.fetchImages = this.fetchImages.bind(this)
}
fetchImages()
{
var self = this
axios.get('https://api.instagram.com/v1/users/self/media/recent/?access_token=')
.then(function (result) {
const items = result
self.setState({ items: 'test' })
});
}
componentDidMount()
{
this.fetchImages()
console.log(this.state.items)
}
render () {
return (
<div>Test</div>
);
}
}
I set items
to null
and console.log
with null
still appearing
I've tried logging the result and I get my data Im looking for help please!
Also have tried using arrow function in es6 still doesn't setState
Upvotes: 1
Views: 4268
Reputation: 17638
Let's gather all the comments and suggestions then provide an answer :)
Your main problem, as said in the comments, logging your state in the wrong place. Since setState
is asynchronous, right after putting a console.log
did not work. Here, you have two options.
First one is using a callback in your setState
method.
self.setState({ items: "test" }, () => console.log(this.state.items))
Your second option is using console.log
in your render
method.
render () {
console.log( this.state.items );
return (
...
So, in the first render, you see the initial value, after the update you see the data.
Remember, never use setState
in the render
method but logging your state is OK here.
The second problem, not actually a problem but not necessary maybe, you don't need to use var self = this
in your function. If you use an arrow function instead of the regular one, you can directly use this
there since arrow functions do not create own scopes.
axios.get('https://api.instagram.com/v1/users/self/media/recent/?access_token=')
.then( result => this.setState({ items: 'test' })
);
So, your whole component would be something like that:
class ItemsPage extends React.Component {
constructor(props) {
super(props)
this.state = { items: null }
this.fetchImages = this.fetchImages.bind(this)
}
fetchImages() {
axios.get( "https://api.instagram.com/v1/users/self/media/recent/?access_token=" )
.then(result => this.setState({ items: "test"} )
);
}
componentDidMount() {
this.fetchImages();
}
render() {
console.log( this.state.items );
return <div>Test</div>;
}
}
If you have proper Babel plugins and configuration, you can even use class-fields proposal to simplify your code.
class ItemsPage extends React.Component {
state = { items: null };
fetchImages() {
axios.get( "https://api.instagram.com/v1/users/self/media/recent/?access_token=" )
.then((result) => this.setState({ items: "test"} )
);
}
componentDidMount() {
this.fetchImages();
}
render() {
console.log( this.state );
return <div>Test</div>;
}
}
As in the current situation, you don't need to bind your function. But remember, if you use this fetchImages
in a callback (like in a button) you will need to bind it. If you use an arrow function it is bond automatically.
class ItemsPage extends React.Component {
state = { items: null };
fetchImages = () =>
axios.get( "https://api.instagram.com/v1/users/self/media/recent/?access_token=" )
.then((result) => this.setState({ items: "test"} )
);
componentDidMount() {
this.fetchImages();
}
render() {
console.log( this.state );
return <div>Test</div>;
}
}
Upvotes: 5