Je développe une application Android qui s'intègre à Facebook. J'aimerais:
Techniquement, ce serait:
email
)publish_stream
permission } _J'ai appelé Session.openActiveSession()
avec un Session.StatusCallback
(j'ai déjà vérifié qu'il n'y avait aucune session ouverte active auparavant):
final Session.StatusCallback sessionStatusCallback = new Session.StatusCallback() {
public void call(final Session session, SessionState state, Exception exception) {
// If there is an exception...
if(exception != null)
{
// Handle fail case here.
return;
}
// If session is just opened...
if(state == SessionState.OPENED)
{
// Handle success case here.
return;
}
};
};
// Start Facebook Login.
Session.openActiveSession(activity, true, sessionStatusCallback);
Mon rappel est appelé après une connexion réussie. Jusqu'ici tout va bien.
email
} _Ceci est mon rappel de statut:
new Session.StatusCallback() {
public void call(final Session session, SessionState state, Exception exception) {
// If there is an exception...
if(exception != null)
{
// Handle fail case here.
return;
}
// If token is just updated...
if(state == SessionState.OPENED_TOKEN_UPDATED)
{
// Handle success case here.
return;
}
};
};
Je demande l'autorisation avec Session.requestNewReadPermissions()
:
final Session session = Session.getActiveSession();
final static String[] PERMISSION_ARRAY_READ = {"email"};
final List<String> permissionList = Arrays.asList(PERMISSION_ARRAY_READ);
// If all required permissions are available...
if(session.getPermissions().containsAll(permissionList))
{
// Handle success case here.
return;
}
// Request permissions.
session.requestNewReadPermissions(new Session.NewPermissionsRequest(activity, permissionList));
Mon rappel est appelé après autorisation. Jusqu'ici tout va bien.
publish_stream
)Ceci est mon rappel de statut:
new Session.StatusCallback() {
public void call(final Session session, SessionState state, Exception exception) {
// If there is an exception...
if(exception != null)
{
// Handle fail case here.
return;
}
// If token is just updated...
if(state == SessionState.OPENED_TOKEN_UPDATED)
{
// Handle success case here.
return;
}
};
};
Je demande l'autorisation avec Session.requestNewPublishPermissions()
:
final Session session = Session.getActiveSession();
final static String[] PERMISSION_ARRAY_PUBLISH = {"publish_stream"};
final List<String> permissionList = Arrays.asList(PERMISSION_ARRAY_PUBLISH);
// If all required permissions are available...
if(session.getPermissions().containsAll(permissionList))
{
// Handle success case here.
return;
}
// Request permissions.
session.requestNewPublishPermissions(new Session.NewPermissionsRequest(activity, permissionList));
Cette fois-ci, mon rappel est not appelé après autorisation.
Après une enquête plus poussée, j'ai trouvé que mon rappel était déclenché par com.facebook.Session#postStateChange(SessionState, SessionState, Exception)
:
void postStateChange(final SessionState oldState, final SessionState newState, final Exception exception) {
if (oldState == newState && exception == null) {
return;
}
/* ... */
}
Puisque oldState
et newState
sont égaux (tous deux étant SessionState.OPENED_TOKEN_UPDATED
_, mon rappel n'est pas appelé.
Comment puis-je recevoir une notification après la permission est accordée pour la deuxième fois? Suis-je censé (close()
} _ la session et rouvrir le cache ?
Mon Facebook SDK 3.0 Android est téléchargé à partir de ici , comme indiqué dans le Premiers pas avec le SDK de Facebook pour Android de Facebook.
C'est un bug.
[edit: Comme Guy le fait remarquer dans les commentaires, cela a été corrigé dans la version 3.0.1, cette solution de contournement n'est plus nécessaire]
La solution de contournement que vous avez mentionnée est fondamentalement correcte, bien que vous n’ayez pas besoin d’appeler de près. Si vous utilisez la seule session active, avant d'appeler requestNewPublishPermissions (), appelez simplement:
Session.openActiveSessionFromCache(myContext);
Si vous utilisez plusieurs sessions, vous devez initialiser une nouvelle session avec TokenCachingStrategy, vérifier qu'elle est dans l'état CREATED_TOKEN_LOADED et appeler openForRead (null);
Après avoir effectué l'une de ces tâches, requestNewPublishPermissions () devrait appeler votre notification une fois qu'elle est terminée.
Avant de demander la permission pour la deuxième fois (c'est-à-dire avant Session.requestNewPublishPermissions()
), procédez comme suit:
// Re-initialize Facebook session.
session.removeCallback(sessionStatusCallback); // Remove callback from old session.
session = Session.openActiveSessionFromCache(context); // Create new session by re-opening from cache.
session.addCallback(sessionStatusCallback); // Add callback to new session.
Le code est toujours basé sur Facebook Android SDK 3.0, comme dans la question.
Un autre problème que j'ai rencontré est que mon requestCode pour la NewPermissionRequest
n'était pas défini sur le même requestCode que j'avais l'habitude d'ouvrir ma Session
pour la lecture avec, ainsi mon Session.StatusCallback
n'a jamais été appelé lorsque les nouvelles autorisations ont été accordées.
Par exemple, dans ma onActivityResult
, j'ai un chèque pour le requestCode et je délègue l'appel en conséquence, car d'autres éléments entrent dans cette méthode.
public void onActivityResult(Activity activity, int requestCode, int resultCode, Intent data) {
if (requestCode == FACEBOOK_AUTH_RESULT_CODE) {
Session session = Session.getActiveSession();
if(session != null) {
session.onActivityResult(activity, requestCode, resultCode, data);
}
}
}
J'ai ensuite ouvert ma Session
avec le code suivant:
Session.getActiveSession().openForRead(
new Session.OpenRequest(activity).
setLoginBehavior(SessionLoginBehavior.SSO_WITH_FALLBACK).
setRequestCode(FACEBOOK_AUTH_RESULT_CODE).
setPermissions(MY_READ_PERMISSIONS));
J'ai ensuite oublié d'utiliser le même requestCode lors de la construction de ma NewPermissionRequest
.
Voici à quoi la NewPermissionRequest
correcte doit ressembler:
Session.getActiveSession().requestNewPublishPermissions(
new NewPermissionsRequest(activity, MY_PUBLISH_PERMISSIONS)
.setRequestCode(FACEBOOK_AUTH_RESULT_CODE));