Loupe

[Unity] Gérer les requêtes HTTP

Une problématique qui revient souvent lors d’un développement nécessitant de faire des requêtes HTTP, lorsque vous utilisez une API REST par exemple, est la gestion des appels et des retours des requêtes que vous lancez. Dans nos différents exemples, on va simplement récupérer le contenu de la page Bing. Voici ce qu’il est possible de faire :

La version simple

Cet exemple est basé sur la documentation officielle de Unity. L’inconvénient de cette façon de faire est que la requête est bloquante.

public class GetBingOnStart : MonoBehaviour
{
    public string url = "http://www.bing.com/";

    private IEnumerator Start()
    {
        WWW www = new WWW(url);
        yield return www;

        if (string.IsNullOrEmpty(www.error))
        {
            Debug.Log("[OK] " + www.text);
        }
        else
        {
            Debug.Log("[Error] " + www.error);
        }
    }
}

La version avec Coroutine

L’utilisation d’une coroutine nous permet de lancer la requête de façon autonome. On crée aussi un objet dans notre scène auquel on affecte notre classe en tant que composant, ce qui nous permet de voir directement quand une requête se lance et se termine.

Voici le script que l’on ajoutera à notre objet :

public class GetBingWithCoroutine : MonoBehaviour
    {
        public string Result { get; set; }
        public bool HasError { get; set; }
        public string Error { get; set; }

        public Action OnCompleted;

        public void Startup()
        {
            StartCoroutine(Process("http://www.bing.com/"));
        }

        private IEnumerator Process(string url)
        {
            var request = new WWW(url);
            yield return request;

            DestroyObject(gameObject);
            if (!string.IsNullOrEmpty(request.error))
            {
                HasError = true;
                Error = request.error;

                if (OnCompleted != null)
                {
                    OnCompleted();
                }
                yield break;
            }

            Result = request.text;

            if (OnCompleted != null)
            {
                OnCompleted();
            }
        }
    }

Pour lancer la requête rien de plus simple :

public class LaunchGetBingWithCoroutine : MonoBehaviour
{
    public void Start()
    {
        var request = new GameObject("[Request] GetBingWithCoroutine");

        request.AddComponent<GetBingWithCoroutine>();
        var query = request.GetComponent<GetBingWithCoroutine>();
        query.OnCompleted = () =>
        {
            if (!query.HasError)
            {
                Debug.Log("[OK] " + query.Result);
            }
            else
            {
                Debug.Log("[Error] " + query.Error);
            }
        };
        query.Startup();
    }
}

Cette solution est plus souple à utiliser mais demande pas mal de code à écrire, on peut surement faire mieux.

La version avec UniRx

Si vous ne connaissez pas UniRX, je vous invite à visiter le site de ce package. Il permet d’utiliser les Reactive Extensions dans Unity. Voici ce que peut donner notre script en utilisant cette méthode :

public class GetBingWithUniRx
    {
        public void Start()
        {
            ObservableWWW.Get("http://www.bing.com/")
                .Subscribe(result => Debug.Log("[OK] " + result),
                            ex => Debug.Log("[Error] " + ex));
        }
    }
Vous noterez ici que j’ai enlevé le fait d’encapsuler la requête dans un objet de notre scène comme dans l’exemple précédent. Pour ma part, je trouve que la synthaxe de Rx est vraiment très simple et pratique.

Conclusion

Comme vous avez pu le voir, il existe plusieurs façons de gérer vos requêtes HTTP qui peuvent varier selon vos besoins (bloquante ou non, gestion des erreurs, etc). Je vous en ai présenté 3 ici mais il en existe certainement beaucoup d’autres. Ma préférée ? UniRx  Sourire

Ces billets pourraient aussi vous intéresser

Vous nous direz ?!

Commentaires

comments powered by Disqus