How do I ensure that my program halts until my axios requests have been resolved?

Viewed 458

I'm working on a project using React as my front-end. When I create an item, my intention is to first send a request to my server to create the item (using only the textual form data) and then to send an individual request per image upload.

// handles item creation
handleCreate = async (data) => {
    let id = await axios({
                            method: 'post',
                            url: <item_creation_URL>,
                            data: data
                        })
                        .then(res => {
                            return res.data();
                        })
                        .catch(err => {
                            this.handleErrors(err);
                        })
    return id;
}

// handles image uploads for a specific item
handleUpload = async (fd, itemId) => {
    let response = await axios({
                                 method: 'post',
                                 url: <img_upload_URL>,
                                 headers: {
                                     'content-type': 'multipart/form-data'
                                 },
                                 data: fd
                               })
                               .then(res => {
                                   return res;
                               })
                               .catch(err => {
                                   this.handleErrors(err.response.data);
                               });
    return response;
}

// prepares and sends the data to the server to create a new item
handleSubmit = event => {

    event.preventDefault();

    this.setState({ loading: true });

    // data needed to make an item on firebase
    const itemData = {
        name       : this.state.name,
        desc       : this.state.desc,
        cover      : this.state.coverImgIndex,
        visibleTo  : this.state.visibleTo,
        assignedTo : this.state.assignedTo,
        photos     : this.state.photos
    }

    // create a new item using the data
    let itemId = this.handleCreate(itemData);

    // upload the photos
    if (!this.state.errors){
        for (let i=0; i < this.state.uploadedFiles.length; i++) {
            let file = this.state.uploadedFiles[i];
            let fd = new FormData();
            fd.append('file', file, file.name);

            // send each file as its own upload request
            this.handleUpload(fd, itemId);

            if (this.state.errors) break;
        }
    }

    // submission was successful
    if (!this.state.errors){
        this.setState({ loading : false });
    }
}

I did some research online and thought I could achieve the desired effect by wrapping each axios request in an async block with an await. However, execution seems to progress without waiting for each request to finish.

I'm fairly new to using Promises in Javascript. Is there something I'm doing wrong here?

1 Answers

you made handleCreate() and handleUpload() functions asynchronous. therefore, when you call these functions use await if you should go ahead after axios end.

Like this

// handles item creation
handleCreate = async data => {
  try {
    const res = await axios({
      method: "post",
      url: `<item_creation_URL>`,
      data: data
    });
    return res.data();
  } catch (err) {
    throw err;
  }
};

// handles image uploads for a specific item
handleUpload = async (fd, itemId) => {
  try {
    const res = await axios({
      method: "post",
      url: `<img_upload_URL>`,
      headers: {
        "content-type": "multipart/form-data"
      },
      data: fd
    });
    return res;
  } catch (err) {
    throw err.response.data;
  }
};

// prepares and sends the data to the server to create a new item
handleSubmit = event => {
  event.preventDefault();

  // data needed to make an item on firebase
  const { name, desc, cover, visibleTo, assignedTo, photos } = this.state;
  this.setState({ loading: true });
  this._asyncSubmit({ name, desc, cover, visibleTo, assignedTo, photos });
};

_asyncSubmit = async itemData => {
  try {
    // create a new item using the data
    const itemId = await this.handleCreate(itemData);
    for (let i = 0; i < this.state.uploadedFiles.length; i++) {
      const file = this.state.uploadedFiles[i];
      let fd = new FormData();
      fd.append("file", file, file.name);
      // send each file as its own upload request
      await this.handleUpload(fd, itemId);
    }
  } catch(err) {
    // you can handle errors here
    this.handleErrors(err);
  }
  this.setState({ loading: false });
};
Related