Reputation: 1992
I would like the value of one of the properties in my class to be an asynchronous value. It almost works; when you call setTimeout
, profile.songs
is in fact resolved with Promise {<resolved>: Array(100)}
.
Except, I want the value (in this case, Array(100)
) of the Promise
to be the value of property.songs
.
Edit: I should add some clarity to the question. The object must be instantiated synchronously i.e. profile.toxicGarbageIsland
and profile.spiceUpYourLife
are mandatory, and are required for the object to instantiate. The promise value, profile.songs
however, is optional, and can come after the object is instantiated.
class Gojira {
constructor (profile) {
Object.assign(this, profile)
}
static init () {
let profile = {};
profile.toxicGarbageIsland = true;
profile.spiceUpYourLife = false;
profile.songs = axios.get('https://jsonplaceholder.typicode.com/posts')
.then(function(response){
return response.data;
}).catch(function (error) {
console.log(error)
})
return new Gojira(profile);
}
}
let gojiraInstance = Gojira.init();
setTimeout(function(){
console.log(gojiraInstance)
}, 2000)
N.B. I've removed the promise from the constructor
to ensure it's only concern is with returning an object instance, which I've read is best practice.
Upvotes: 2
Views: 86
Reputation: 370989
Don't assign the promise to profile.songs
- instead, simply run the promise, and on resolution, assign the result to profile.songs
and call the constructor.
static init() {
let profile = {};
profile.toxicGarbageIsland = true;
profile.spiceUpYourLife = false;
return axios.get('https://jsonplaceholder.typicode.com/posts')
.then(function(response) {
profile.songs = response.data;
return new Gojira(profile);
}).catch(function(error) {
console.log(error)
});
}
You'll also have to consume it asynchronously:
Gojira.init()
.then(gojiraInstance => {
// ...
});
I'm assuming the constructor requires the profile
to be fully set before running. If not, then allow the constructor to accept a Promise
as a parameter as well, which then assigns the songs
property on resolution, like this:
class Gojira {
constructor (profile, songsPromise) {
Object.assign(this, profile);
if (songsPromise) songsPromise.then(({ data }) => this.songs = data);
}
static init () {
const profile = {};
profile.toxicGarbageIsland = true;
profile.spiceUpYourLife = false;
const songsPromise = axios.get('https://jsonplaceholder.typicode.com/posts')
.catch(error => console.log(error));
return new Gojira(profile, songsPromise);
}
}
const gojiraInstance = Gojira.init();
setTimeout(function(){
console.log(gojiraInstance)
}, 2000)
Upvotes: 1