Friday, May 20, 2011

Facebook Authorization from C# -- OAuth2

This past week facebook announced plans to turn off the OAuth 1.0 authorized users starting in September. This means we need to bring the RightNow CX product up to their new OAuth 2.0 authorization flow. Based on the information provided to me I assumed this would be a pretty straight forward move and there shouldn't be many problems.  I was only partially right.

Things that needed to be done:

  1. Find a way to upgrade the users who have already authorized RightNow using OAuth 1.0
  2. Move our application authorization to the new OAuth 2 flow.
  3. Move our back end implementation to using the single access_token (and possibly some new apis)
Upgrading the tokens turned out to be super easy.  Facebook provides a great little upgrade path using curl

Upgrading the authorization flow seems easy enough.  According to their documentation, I simply direct the application at a website and detect the redirects.  Once it's all done, I have the token and they're "logged in".  Of course I don't want to leave them logged in, so I want to log them out and save the token for future use.  Facebook has always been notoriously bad at giving developers a good way to do this, so in our previous implementation I devised a reasonably clever method that takes advantage of HTTP's stateless nature. I simply grabbed the document object of the browser and cleared all the cookies for facebook.com. This meant that the browser literally could not remember who was logged in, so no matter how Facebook changed their pages it should still work.  Come to find out, in the new authorization flow, this method does not work.  At first I couldn't figure out what the problem was.  It appeared to be logging the user out, but I could not log back in. It turns out there is a different type of cookie I had never heard of, called the http-only cookie.

"The HttpOnly cookie is supported by most modern browsers.  On a supported browser, a HttpOnly cookie will only be used when transmitting HTTP (or HTTPS) requests. In addition, the cookie value is not available to client side script (such as Javascript), thereby mitigating the threat of cookie theft via Cross-Site-Scripting." via Wikipedia.

So, though I was clearing the session of all cookies I could see, I could not clear the HttpOnly cookies.  So when the user went to log back in, it didn't look like there was anyone logged in, but the login was broken for the next user.  I began to search around for some answers and decided it would be good to see how the C# SDK did it.  I dug in just a bit only to find out that they are just directing the user to the logout page for mobile facebook, which logs the user out.  There are some other suggestions here, but none of them will work for C# since the login was not done with Javascript.  I'm personally appalled and scared of using this solution, but alas, it seems to be the only one available.

Moving our back end implementation was easy enough.  I simply upgraded our php-sdk to the newest version and began using the api function to make the same calls we were using before.  Since we have the access token I can skip the use of the session validation and start making api calls right from the get go.

All in all the conversion is going well, but I don't know how Facebook has managed to go this long without creating a proper way to programmatically "log out". It makes me sad to be using such an obscure (and seemingly fragile) way to log a user out of facebook.  If you know of a better way, I'd be open to suggestions.

--Colt




1 comment:

karthireva said...

Excellent article,it was helpful to us to learn more and useful to teach others.This like valuable information is very interesting to read,thanks for sharing this impressive informative.



DotNet Training in Chennai