Search code examples
javascriptasync-awaites6-promise

Call JavaScript class method synchronously


I'm building a package with JavaScript which has two functions: init and sendData.

class Client {
   init() {
     return axios.post(this.baseUrl).then((response) => {
       this.token = response.data.token
     })
   }

   sendData() {
     return axios.post(this.baseUrl, {token: this.token})
   }
}

The init method needs to be called before the sendData method as this returns a token. Is there a way to wait for the init method to be called before calling the sendData method?


Solution

  • Do you need the consumer of your API to do this?

    // within an async function
    const client = new Client();
    await client.init();
    await client.sendDate();
    
    // or anywhere just using promises
    const client = new Client();
    client.init().then(() => client.sendDate());
    

    or the API itself?

    // definition
    class Client {
       async init() {
         const response = await axios.post(this.baseUrl);
         this.token = response.data.token;
       }
    
       async sendData() {
         await this.init(); // call init before sending data
         return axios.post(this.baseUrl, {token: this.token})
       }
    }
    
    // usage somewhere in an async function
    const client = new Client();
    client.sendDate() // calls init, then sends the data
    

    Maybe remove the redundant calls if the token doesn't change?

    class Client {
       async init() {
         const response = await axios.post(this.baseUrl);
         this.token = response.data.token;
       }
    
       async sendData() {
         if (!this.token) { // now you'll only call init for missing token
           await this.init();
         }
         return axios.post(this.baseUrl, {token: this.token})
       }
    }
    
    // usage somewhere in an async function
    const client = new Client();
    await client.sendDate(); // calls init (only the first time), then sends the data
    

    Do note that promise returning functions are inherently asynchronous so there isn't a way of obtaining their result in a synchronous manner. However, we can write the asynchronous code using async/await to make it syntactically look (almost) identical to a synchronous version.