WWW Response handling

Hello, I am trying to use the WWW object for OAuth implementation, and as per OAuth specification the server returns a HTTP Status code 400 along with some data to inform you what is wrong.

However, the WWW object gives me this exception when I try to read the response:
You are trying to load data from a www stream which had the following error when downloading.
400 Bad Request

This is my code:

        string oauthURL = "https://localhost:44301/oauth/token";
        string postDataString = "grant_type=password&client_id=" + oauthClientId + "&client_secret=" + oauthClientSecret;
        postDataString += "&username=" + username + "&password=" + password;
        byte[] postData = Encoding.UTF8.GetBytes(postDataString);
        WWW www = new WWW(oauthURL, postData);

        yield return www;
        while (www.isDone == false)
            yield return null;

        string response = www.text;
        Debug.Log("Response: " + response);

The expected OAuth response for incorrect credentials would be:

Http status code: 400 Bad Request
{"error":"invalid_grant","error_description":"Invalid resource owner password credential."}

Is there a way around this limitation? And why is this limitation there by default?

Finally, if there is no way around it, what are my alternatives? Will System.Net.HttpWebRequest work on iOS and Android platforms?

Thanks!

400 errors are not for failed authentication. They’re to signal that the information sent to the server was malformed and not to HTTP specifications.

403 error is more appropriate for failed auth. See answer at http - Signalling authentication failure in a RESTful API - Stack Overflow

Most probably you’'ll need to change the server response (it shouldn’t return an HTTP error, but a normal response - inside this response you should signalize the authentication error).

It will be generally easy if the server-side code is written by yourself, but don’t be afraid even if it isn’t (I had the similar problem - even had to change some of the Drupal (CMS) classes in order to make it work) :slight_smile:

However, do not use anything else than WWW (or some wrapper classes), because only the WWW class is guaranteed to work across platforms (except Flash, with which you should write Actionscript in order to make the server call).

You might want to try this wrapper class in order to have the asynchronous syntax (no yields) - WebPlayer demo and usage here.

1 Like

I understand, except the OAuth 2.0 specification states it should return a 400 error:
See: http://tools.ietf.org/html/draft-ietf-oauth-v2-31#section-5.2

Altering the default OAuth 2.0 implementation in some kind way breaks with the standards and is something I would like to avoid if at all possible. Not to mention all the additional documentation I will have to type up, plus I’d have to recompile the DotNetOpenAuth package.

I guess there’s not a lot of choice open to me though. It’s either that or manually implement the connection layer in iOS instead using NSURLConnection, and work it through an interface. (Not very portable)

Thanks for the heads up, I’ll take a look at the code you linked, though the yields aren’t much of a problem. :slight_smile:

Tim, what did you do in the end?