Lock Android: Customize Your UI

This document covers an outdated version of Lock for Android. We recommend you to upgrade to v2

We are going to use the library EventBus in order to post authentication related events like authentication done and uthentication failed

Add the following dependencies to your project:

compile 'com.auth0.android:core:1.+'
compile 'de.greenrobot:eventbus:2.4.+'

Create a new resource file named auth0.xml under values and add the following content, replacing the values with your Auth0 ClientId and Domain

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <string name="auth0_client_id">YOUR_CLIENT_ID</string>
    <string name="auth0_domain_name">YOUR_AUTH0_DOMAIN</string>
</resources>

Create two classes AuthenticationEvent and ErrorEvent that will represent a successful authentication or a failed one

public class AuthenticationEvent {
    private final UserProfile profile;
    private final Token token;

    public AuthenticationEvent(UserProfile profile, Token token) {
        this.profile = profile;
        this.token = token;
    }

    public Token getToken() { return token; }

    public UserProfile getProfile() { return profile; }
}

public class ErrorEvent {
    private Dialog dialog;
    private int title;
    private int message;
    private Throwable throwable;

    public ErrorEvent(Dialog dialog) {
        this.dialog = dialog;
    }

    public ErrorEvent(int title, int message, Throwable throwable) {
        this.title = title;
        this.message = message;
        this.throwable = throwable;
    }
}

Then in your Login Activity add the following fields

private AuthenticationAPIClient client;
private EventBus eventBus;

In the same Activity onCreate method add the following lines to initialize Auth0 and the fields we added earlier

Auth0 auth0 = new Auth0(getString(R.string.auth0_client_id), getString(R.string.auth0_domain_name));
this.client = auth0.newAuthenticationAPIClient();
this.eventBus = new EventBus();

When you need to login your user with email/password credentials, just paste the following code

String email = ... // Get email
String password = ... // Get password
//add your DB connection name, since you are using email / pwd login
//will throw a 400 error if not set
ParameterBuilder parameterBuilder = ParameterBuilder.newBuilder();
Map<String, Object> authenticationParameters = parameterBuilder
          .setConnection("YOUR_DB_CONNECTION_NAME")
          .asDictionary();
client.login(email, password)
    .addParameters(authenticationParameters)
    .start(new AuthenticationCallback() {
        @Override
        public void onSuccess(UserProfile userProfile, Token token) {
            eventBus.post(new AuthenticationEvent(userProfile, token));
        }

        @Override
        public void onFailure(Throwable throwable) {
            eventBus.post(new ErrorEvent(R.string.login_failed_title, R.string.login_failed_message, throwable));
        }
    });

For more details about the parameters you can check this wiki page.

Finally handle both AuthenticationEvent and ErrorEvent

@Override
protected void onStart() {
    super.onStart();
    eventBus.register(this);
}

@Override
protected void onStop() {
    super.onStop();
    eventBus.unregister(this);
}

public void onEvent(ErrorEvent event) {
  //Handle Error
}

public void onEvent(AuthenticationEvent event) {
  //Handle authentication
}

Social Authentication

This feature relies on a deprecated grant type. Clients created after June 8th 2017 won't be able to use this feature. We recommend using browser-based flows, as explained in Authentication with Auth0 Hosted Login Page.

Include the following libraries in your build.gradle:

compile 'com.auth0.android:identity-core:1.+'
compile 'com.auth0.android:lock-facebook:2.4.+'
compile 'com.auth0.android:lock-googleplus:2.4.+'

In your auth0.xml file add the following entry

<string name="auth0_scheme">a0__auth0_client_id__</string>

Configure your Login Activity adding the following intent filters in your AndroidManifest.xml file

<intent-filter>
    <action android:name="android.intent.action.VIEW"/>
    <category android:name="android.intent.category.DEFAULT"/>
    <category android:name="android.intent.category.BROWSABLE"/>
    <data android:scheme="@string/auth0_scheme" android:host="@string/auth0_domain_name"/>
</intent-filter>

Create a new class that implements IdentityProviderCallback, that will handle social authentication (via native integration or using web browser) and post a new event either on success or failure

public class MyIdentityProviderCallback implements IdentityProviderCallback {
    private final EventBus bus;
    private final AuthenticationAPIClient client;

    public MyIdentityProviderCallback(EventBus bus, AuthenticationAPIClient client) {
        this.bus = bus;
        this.client = client;
    }

    @Override
    public void onFailure(Dialog dialog) {
        //Authentication failed and a Error dialog is provided
        bus.post(new ErrorEvent(dialog));
    }

    @Override
    public void onFailure(int title, int message, Throwable throwable) {
        //Authentication failed and a title & message resource are provided.
        //The throwable parameter will include the reason (if any)
        bus.post(new ErrorEvent(title, message, throwable));
    }

    @Override
    public void onSuccess(String serviceName, String accessToken) {
        //Authenticate with Auth0 using the IdP token obtained from a native integration like Facebook
        client.loginWithOAuthAccessToken(accessToken, serviceName)
          .start(new AuthenticationCallback() {
              @Override
              public void onSuccess(UserProfile userProfile, Token token) {
                  bus.post(new AuthenticationEvent(userProfile, token));
              }

              @Override
              public void onFailure(Throwable throwable) {
                  bus.post(new ErrorEvent(R.string.login_failed_title, R.string.login_failed_message, throwable));
              }
          });
    }

    @Override
    public void onSuccess(final Token token) {
        //Already authenticated with Auth0 using Web Browser (when no native integration is available), then we just fetch the user's profile
        client.tokenInfo(token.getIdToken())
          .start(new BaseCallback<UserProfile>() {
              @Override
              public void onSuccess(UserProfile profile) {
                  bus.post(new AuthenticationEvent(profile, token));
              }

              @Override
              public void onFailure(Throwable throwable) {
                  bus.post(new ErrorEvent(R.string.login_failed_title, R.string.login_failed_message, throwable));
              }
          });
    }
}

In your Login Activity add the following fields

private WebIdentityProvider webProvider;
private IdentityProvider identity;
private GooglePlusIdentityProvider googleplus;
private FacebookIdentityProvider facebook;

And implement the following methods

@Override
protected void onStop() {
    webProvider.stop();
}

@Override
protected void onNewIntent(Intent intent) {
    super.onNewIntent(intent);
    Log.v(TAG, "Received new Intent with URI " + intent.getData());
    if (identity != null) {
        identity.authorize(this, IdentityProvider.WEBVIEW_AUTH_REQUEST_CODE, RESULT_OK, intent);
    }
}

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
    super.onActivityResult(requestCode, resultCode, data);
    if (identity != null) {
        identity.authorize(this, requestCode, resultCode, data);
    }
}

In the method onCreate initialize Auth0 web provider and store it in a field

final MyIdentityProviderCallback callback = new MyIdentityProviderCallback(eventBus, client);
this.webProvider = new WebIdentityProvider(new CallbackParser(), auth0.getClientId(), auth0.getAuthorizeUrl());
this.webProvider.setCallback(callback);

Configure Facebook Native integration

this.facebook = new FacebookIdentityProvider(this);
this.facebook.setCallback(callback);

You need to configure your Android app for Facebook

Configure Google+ Native integrationApplication class)

this.googleplus = new GooglePlusIdentityProvider(this);
this.googleplus.setCallback(callback);

Before using Google+, you need to register your Application with Google as explained in this guide

To trigger Facebook authentication just add the following code:

identity = facebook;
identity.start(this, Strategies.Facebook.getName());

To trigger Google+ authentication just add the following code:

identity = googleplus;
identity.start(this, Strategies.GooglePlus.getName());

To trigger authentication with any IdP without native integration just add the following code:

identity = webProvider;
identity.start(this, Strategies.Twitter.getName());