In questa lezione, vedremo come integrare il social login tramite Twitter utilizzando Firebase nella nostra applicazione. I passi da compiere sono molto simili a quelli illustrati nella lezione 8, a differenza dell'implementazione dei metodi di login e logout.
Modifica del build.gradle del modulo app
Apriamo il build.gradle del Module:app e nelle dipendenze dell'applicazione aggiungiamo la dipendenza mancante per Twitter.
dependencies {
. . .
// Twitter Kit
compile 'com.twitter.sdk.android:twitter:3.1.1'
}
Sincronizziamo il gradle cliccando sul Sync Now che comparirà in alto a destra dopo aver aggiunto la dipendenza.
Modifica del layout
Passiamo adesso alla modifica del layout per aggiungere il bottone che permetterà all'utente di effettuare il login. Per farlo, apriamo il file activity_login.xml che si trova in src/main/res/layout, e inseriamo all'interno del ConstaintLayout
il codice seguente:
<com.twitter.sdk.android.core.identity.TwitterLoginButton
android:id="@+id/bt_log_in"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintBottom_toBottomOf="parent"
android:visibility="visible"
tools:visibility="gone"/>
In questo modo abbiamo aggiunto il TwitterLoginButton
fornito da Twitter, posizionandolo al centro del parent.
Modifica della LoginActivity
Configuriamo ora la logica per eseguire il processo di autorizzazione e autenticazione.
All'interno dell'Activity
dovremo compiere diverse operazioni che si riassumono nei seguenti passi:
- implementare l'interfaccia
OnClickListener
; - inizializzazione della SDK di Twitter e della callback per il processo di login;
- implementazione dell'autenticazione tramite Firebase definendo il metodo
onActivityResult
; - aggiornare l'interfaccia in base all'esito dell'autenticazione;
- definire il metodo di logout;
Iniziamo con l'instanziare il bottone di login che utilizzeremo nella nostra Activity
e impostiamo la callback
per il processo di autenticazione.
public class LoginActivity extends AppCompatActivity implements View.OnClickListener {
private TwitterLoginButton mLoginButton;
private FirebaseAuth mFirebaseAuth;
. . .
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
initializeTwitter();
. . .
mLoginButton = findViewById(R.id.bt_log_in);
mLoginButton.setCallback(new Callback<TwitterSession>() {
@Override
public void success(Result<TwitterSession> result) {
handleTwitterSession(result.data);
}
@Override
public void failure(TwitterException exception) {
updateUI(null);
}
});
mFirebaseAuth = FirebaseAuth.getInstance();
}
}
Dove il metodo initializeTwitter()
è definito come segue:
private void initializeTwitter(){
TwitterConfig config = new TwitterConfig.Builder(this)
.logger(new DefaultLogger(Log.DEBUG))
.twitterAuthConfig(new TwitterAuthConfig(
getString(R.string.com_twitter_sdk_android_CONSUMER_KEY),
getString(R.string.com_twitter_sdk_android_CONSUMER_SECRET)))
.debug(true)
.build();
Twitter.initialize(config);
}
Tramite questo metodo è possibile inizializzare la libreria di Twitter, il TwitterCore, e deve essere collocato immediatamente prima del metodo setContentView()
, altrimenti l’applicazione restituirà un errore relativo all’impossibilità di inizializzare un'istanza della liberia per il bottone di login. In particolare, Il metodo imposta:
- un oggetto
TwitterAuthConfig
che definisce la consumer key e il consumer secret necessari per compiere il processo di autorizzazione e autenticazione; - un
logger
per catturare gli eventi durante l’utilizzo della API.
Nel codice proposto è stata definita la callback
che, in caso di successo, richiamerà il metodo handleTwitterSession()
; altrimenti, essa ripristinerà l'interfaccia di login per permettere all'utente di riprovare l'autenticazione. Infine, abbiamo inizializzato l'istanza di FirebaseAuth
.
Implementiamo ora i metodi handleTwitterSession
e updateUI
richiamati all'interno della callback
.
Il handleTwitterSession
va implementato come segue.
private void handleTwitterSession(TwitterSession session) {
showProgressDialog();
AuthCredential credential = TwitterAuthProvider.getCredential(
session.getAuthToken().token,
session.getAuthToken().secret);
mFirebaseAuth.signInWithCredential(credential)
.addOnCompleteListener(this, new OnCompleteListener<AuthResult>() {
@Override
public void onComplete(@NonNull Task<AuthResult> task) {
if (task.isSuccessful()) {
FirebaseUser user = mFirebaseAuth.getCurrentUser();
updateUI(user);
} else {
Toast.makeText(LoginActivity.this, "Authentication failed.",
Toast.LENGTH_SHORT).show();
updateUI(null);
}
hideProgressDialog();
}
});
}
All'interno del metodo, si è:
- richiamato il metodo per mostrare la
ProgressDialog
; - ottenuto l'oggetto
AuthCredential
che contiente le credenziali attraverso il metodo staticogetCredential
dell'oggettoTwitterAuthProvider
che prende in input token (sottoforma di stringa ottenuto durante l'autenticazione) e il Twitter secret; - tentato l'accesso a Twitter tramite il metodo
signInWithCredential
passando in input le credenziali ottenute e restituendo un oggettoTask<AuthResult>
; - aggiunto un
listener
alTask
che viene richiamato quando quest'ultimo sarà terminato; - richiamato il metodo per nascondere la
ProgressDialog
.
In particolare, quando il Task
sarà terminato, in caso di successo verrà creato un oggetto FirebaseUser
contenente le informazioni dell'utente e sarà aggiornata di conseguenza l'interfaccia tramite il metodo updateUI
. Contrariamente, verrà visualizzato un messaggio di errore e l'utente visualizzerà nuovamente la schermata iniziale.
Definiamo, ora, il metodo onActivityResult
che inoltrerà al mLoginButton
il risultato ottenuto durante il processo di login.
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
mLoginButton.onActivityResult(requestCode, resultCode, data);
}
Implementiamo, infine, il metodo updateUI
che verificherà se l'oggetto FirebaseUser
è stato inizializzato aggiornando l'interfaccia. In caso di successo, verrà nascosto il bottone di login rendendo visibile e popolando il LinearLayout
definito in precedenza. Contrariamente, verrà mostrato solo il bottone di login. Si riporta per completezza l'implementazione del metodo:
private void updateUI(FirebaseUser user) {
if (user != null) {
mLoginButton.setVisibility(View.GONE);
mUserInfoLayout.setVisibility(View.VISIBLE);
mUserNameTV.setText(user.getDisplayName());
String imageUrl = user.getPhotoUrl().toString(); // image size small
imageUrl = imageUrl.replace("_normal", "");
Picasso.with(this)
.load(imageUrl)
.into(mUserImageIV);
} else {
mLoginButton.setVisibility(View.VISIBLE);
mUserInfoLayout.setVisibility(View.GONE);
}
}
In particolare, per popolare il layout con le informazioni dell'utente è possibile utilizzare l'oggetto FirebaseUser
da cui estrarre i dati dell'utente.
L'URL dell'immagine del profilo può essere ottenuta tramite il metodo getPhotoUrl().toString()
dell'oggetto, ma questa soluzione limita la dimensione dell'immagine a quella più piccola offerta dalle API di Twitter. Questa limitazione è facilmente superabile effettuando una sostituzione all'interno dell'URL in formato stringa. In particolare, basta eliminare la dimensione _normal
ottenendo un'immagine di profilo quadrata dalle dimensioni di 512x512 pixel e di buona risoluzione che potrà essere ridimensionata tramite layout.
Infine, la responsabilità di caricare l'immagine verrà assegnata alla libreria Picasso che prende in input l'URL da caricare e il contenitore in cui inserirla.
Per completare l'integrazione del login, aggiungiamo la definizione del metodo signOut
che avvierà il processo di logout da Firebase e da Twitter, come mostrato di seguito.
private void signOut() {
mFirebaseAuth.signOut();
TwitterCore.getInstance().getSessionManager().clearActiveSession();
updateUI(null);
}
In particolare, per Twitter cancelleremo la sessione attiva che sta gestendo il SessionMenager
.
Risultato finale
Eseguiamo l'applicazione sul dispositivo mobile o sull'emulatore.
All'avvio dell'applicazione, viene mostrata la schermata iniziale contenente il bottone di default precedentemente aggiunto all'interfaccia e qui di seguito riportato.
Cliccando sul bottone verrà richiesto all'utente di autenticarsi con il proprio account Twitter, chiedendo allo stesso l'autorizzazione per l'accesso ai dati personali da parte dell'applicazione.
Una volta loggati, verremo nuovamente reindirizzati alla schermata della LoginActivity
ma, al posto del bottone di login, verranno mostrate le informazioni dell'utente e il bottone di logout.
Cliccando sul bottone di logout verrà effettuato il logout da Twitter e l'applicazione mostrerà nuovamente il bottone di login.