Skip to content

Instantly share code, notes, and snippets.

@wislon
Created February 7, 2015 01:09
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save wislon/ccc0d85723f3c7ea1c9e to your computer and use it in GitHub Desktop.
Save wislon/ccc0d85723f3c7ea1c9e to your computer and use it in GitHub Desktop.
OAuth2 Facebook Authentication with Xamarin.Auth component example
using System;
using System.Threading.Tasks;
using Android.Content;
using Xamarin.Auth; // install this component from the component store or nuget
namespace Mobile.Droid.Classes
{
public static class FacebookOAuth2Helper
{
/// <summary>
/// OAuth2 async login helper specifically for Facebook, based on
/// https://components.xamarin.com/gettingstarted/xamarin.auth.Can easily be tweaked for other oauth providers.
/// The access token it gets is only valid for two hours, after which you'll either have to log in again,
/// or get it refreshed/replaced somehow. It works really well, but the Facebook SDK component gets you a
/// token valid for 60 days, and handles refresh/replacement automatically for you.
/// Invoke this with await FacebookOAuth2Helper.LoginAsync(etc), parameter descriptions are below.
/// </summary>
/// <param name="appId">The AppId (sometimes called the app secret or project id) generated for you by facebook</param>
/// <param name="requestedScope">Comma-delimited list of permissions required (other oauth providers usually use spaces, not commas)</param>
/// <param name="context">The Android Application context which invoked this method (usually 'this')</param>
/// <param name="authoriseUrl">The url to authorise against. For FB it's 'https://m.facebook.com/dialog/oauth/'</param>
/// <param name="redirectUrl">The url to be redirected to when auth succeeded For FB it's 'https://m.facebook.com/connect/login_success.html' </param>
/// <param name="allowCancel">Allow cancellation of the request</param>
/// <returns>If it succeeds, a <see cref="Xamarin.Auth.Account"/>.</returns>
public static Task<Account> LoginAsync(string appId, string requestedScope, Uri authoriseUrl, Uri redirectUrl, Context context, bool allowCancel)
{
var tcs = new TaskCompletionSource<Account>();
var auth = new OAuth2Authenticator(appId, requestedScope, authoriseUrl, redirectUrl)
{
AllowCancel = allowCancel,
Title = "Connect to Alphatise using Facebook",
};
auth.Completed += (sender, e) => tcs.SetResult(e.IsAuthenticated ? e.Account : null);
auth.Error += (sender, e) => tcs.SetException(e.Exception);
//// iOS
//var ui = auth.GetUI();
//someViewController.PresentViewController(ui, true, null);
context.StartActivity(auth.GetUI(context));
return tcs.Task;
}
}
}
// this is just a couple of demo method calls to show how to invoke the login above, retrieve the
// account info and then use it to load the facebook user the account is associated with.
private async Task LoginToFacebook()
{
string appId = Resources.GetString(Resource.String.facebook_app_id);
string permissions = Resources.GetString(Resource.String.facebook_read_permissions);
var authUri = new Uri("https://m.facebook.com/dialog/oauth/");
// note that this is the default redirect uri. your organisation may have a different one,
// and if facebook is set to use your organisation's one, and you use this one (or vice versa),
// you'll get a rude error message telling you that one or more of your oauth urls is incorrect.
var redirectUri = new Uri("http://www.facebook.com/connect/login_success.html");
const bool allowCancel = true;
var account =
await FacebookOAuth2Helper.LoginAsync(appId, permissions, authUri, redirectUri, this, allowCancel: allowCancel);
if (account != null)
{
this.Log().Info(string.Format("Account info: {0}", account.ToString()));
string name = await GetFacebookUserInfoAsync(account);
Toast.MakeText(this, string.Format("{0} connected via Facebook", name), ToastLength.Long).Show();
}
}
public async Task<string> GetFacebookUserInfoAsync(Account account)
{
try
{
var request = new OAuth2Request("GET", new Uri("https://graph.facebook.com/me"), null, account);
var userInfoResult = await request.GetResponseAsync();
var obj = JObject.Parse(userInfoResult.GetResponseText());
this.Log().Info(obj.ToString());
if (obj != null)
{
return obj.GetValue("name").ToString();
}
}
catch (Exception ex)
{
// say what went wrong here.
}
return null;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment