Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. Voting for the Unity Awards are OPEN! We’re looking to celebrate creators across games, industry, film, and many more categories. Cast your vote now for all categories
    Dismiss Notice
  3. Dismiss Notice

Waiting for the first WWW request to finish before starting the next one.

Discussion in 'Scripting' started by zoe_nightshade, Feb 28, 2018.

  1. zoe_nightshade

    zoe_nightshade

    Joined:
    May 12, 2016
    Posts:
    27
    I'm trying to upload my files in my server using a foreach loop.

    Code (csharp):
    1.  
    2. foreach (string str_path in path_list)
    3. {
    4.       string file_path = str_path;
    5.       StartCoroutine(UploadToServer(file_path));
    6. }
    7.  
    I'm currently successful with uploading my files however, they are overlapping. I want to somehow wait for the first one to finish before moving on the next one on the list.

    My upload to server code is this :

    Code (csharp):
    1.  
    2.  
    3. using (UnityWebRequest www = UnityWebRequest.Post(post_link, form))
    4. {
    5.       AsyncOperation request = www.SendWebRequest();
    6.       while(!request.isDone)
    7.       {
    8.          Debug.Log(request.progress);
    9.          yield return null;
    10.       }
    11.      
    12.       Debug.Log("Success!");
    13. }
    14.  
    15.  
     
  2. Aurimas-Cernius

    Aurimas-Cernius

    Unity Technologies

    Joined:
    Jul 31, 2013
    Posts:
    3,635
    Put that foreach into a separate method that returns IEnumerator, call that new method as a coroutine (via StartCoroutine) and instead of doing each upload in a coroutine simply do:
    yield return UploadToServer(file_path);
     
    Kiwasi likes this.
  3. zoe_nightshade

    zoe_nightshade

    Joined:
    May 12, 2016
    Posts:
    27

    okay so I changed my code to this

    Code (csharp):
    1.  
    2. IEnumerator UploadMultipleFiles()
    3. {
    4. foreach (string str_path in path_list)
    5. {
    6.       string file_path = str_path;
    7.       yield return UploadToServer(file_path);
    8. }
    9. }
    10.  
    Then called it as

    Code (csharp):
    1.  
    2. StartCoroutine(UploadMultipleFiles());
    3.  
    but it's still overlapping?
     
  4. Aurimas-Cernius

    Aurimas-Cernius

    Unity Technologies

    Joined:
    Jul 31, 2013
    Posts:
    3,635
    Oh, if you yield return the async operation, then the next line will execute after request is finished.
     
  5. zoe_nightshade

    zoe_nightshade

    Joined:
    May 12, 2016
    Posts:
    27
    I've searched the forums as well regarding this.

    If I were to change my code to this,
    Code (csharp):
    1.  
    2. using (UnityWebRequest www = UnityWebRequest.Post(post_link, form))
    3. {
    4.       yield return www.Send();
    5.       while(!www.isDone)
    6.      {
    7.          Debug.Log(www.progress);
    8.          yield return null;
    9.       }    
    10.  
    11.      Debug.Log("Success!");
    12. }
    13.  
    it should work, but it's still overlapping.
     
  6. Aurimas-Cernius

    Aurimas-Cernius

    Unity Technologies

    Joined:
    Jul 31, 2013
    Posts:
    3,635
    Can you show the whole script, not just pieces?
     
  7. zoe_nightshade

    zoe_nightshade

    Joined:
    May 12, 2016
    Posts:
    27
    Sorry. Here it is:

    Code (csharp):
    1.  
    2. public class MyScript : MonoBehaviour
    3. {
    4.          public void CallUpload(string file_path) // Called on button tap. File path is forwarded by plugin.
    5.          {
    6.                   StartCoroutine(UploadMultipleFiles(file_path));
    7.          }
    8.  
    9.          IEnumerator UploadMultipleFiles(string file_path)
    10.          {
    11.                   foreach(string str in photoList)
    12.                     {
    13.                         // string img_path = "file://" + str;
    14.                         string img_path = str;
    15.                         yield return UserUploadFile(img_path);
    16.                     }
    17.         }
    18.      
    19.         IEnumerator UserUploadFile(string img_path)
    20.         {
    21.                 create_link = "https://www.somelink.com/upload"
    22.                 WWWForm form = new WWWForm ();
    23.                 form.AddBinaryData ("scene[image]", File.ReadAllBytes(img_path));
    24.  
    25.                 using (UnityWebRequest www = UnityWebRequest.Post(create_link, form))
    26.                 {
    27.                         yield return www.Send();
    28.                         if (!string.IsNullOrEmpty(www.error))
    29.                         {
    30.                                   Debug.Log(www.error.ToString());
    31.                         }
    32.                         else
    33.                         {
    34.                                  Debug.Log("Success!");
    35.                         }
    36.                 }
    37. }
    38.  
     
  8. Aurimas-Cernius

    Aurimas-Cernius

    Unity Technologies

    Joined:
    Jul 31, 2013
    Posts:
    3,635
    That's certainly not all script, I don't see the definition for photoList. Also, this code seem to upload one image, possibly multiple times.
     
  9. zoe_nightshade

    zoe_nightshade

    Joined:
    May 12, 2016
    Posts:
    27
    the photoList is a List<string> where i saved all the paths of the selected images. also, the images are being uploaded properly, no repeating images.
     
  10. zoe_nightshade

    zoe_nightshade

    Joined:
    May 12, 2016
    Posts:
    27
    UPDATE: It turns out www.Send(); isn't compatible with UnityWebRequest so I changed it to www.SendWebRequest().It's return value apparently isnt compatible with Coroutines. Thanks for all the help. :)
     
  11. Aurimas-Cernius

    Aurimas-Cernius

    Unity Technologies

    Joined:
    Jul 31, 2013
    Posts:
    3,635
    Doesn't sound right. SendWebReuest() returns a derivative of AsyncOperation which should suspend coroutine until completion.