使用facebook登录IOS延迟查找用户的电子邮件

时间:2013-12-28 17:18:54

标签: ios objective-c facebook cocoa-touch facebook-login

请求和登录发生得很好但延迟会破坏我想要做的事情。

当用户点击startButton时,我调用了facebook登录方法并且发生了正常,会话打开然后调用'populateUserDetails'来获取用户的电子邮件,该信息带有延迟,使我的变量名称和电子邮件变为空service,因为在用户的电子邮件和populateUserDetails的名称到达之前调用signIn方法。

登录按钮操作和facebook方法:

- (IBAction)actionButtonStart:(id)sender
{
    if (FBSession.activeSession.state == FBSessionStateOpen
        || FBSession.activeSession.state == FBSessionStateOpenTokenExtended) {

        [FBSession.activeSession closeAndClearTokenInformation];

    } else {

        [FBSession openActiveSessionWithReadPermissions:@[@"basic_info"]
                                           allowLoginUI:YES
                                      completionHandler:
         ^(FBSession *session, FBSessionState state, NSError *error) {

             [self sessionStateChanged:session state:state error:error];
         }];
    }
}

- (void)populateUserDetails
{
    if (FBSession.activeSession.isOpen) {
        [[FBRequest requestForMe] startWithCompletionHandler:
         ^(FBRequestConnection *connection,
           NSDictionary<FBGraphUser> *user,
           NSError *error) {
             if (!error) {
                 NSLog(@"%@", user.name);
                 NSLog(@"%@", [user objectForKey:@"email"]);
                 self.nome = user.name;
                 self.email = [user objectForKey:@"email"];
             }
         }];
    }
}

- (void)sessionStateChanged:(FBSession *)session state:(FBSessionState) state error:(NSError *)error
{
    if (!error && state == FBSessionStateOpen){
        NSLog(@"Session opened");

        [self populateUserDetails];
        [self signIn];

        return;
    }
    if (state == FBSessionStateClosed || state == FBSessionStateClosedLoginFailed){
        NSLog(@"Session closed");
    }
    if (error){
        NSLog(@"Error");
        NSString *alertText;
        NSString *alertTitle;

        if ([FBErrorUtility shouldNotifyUserForError:error] == YES){

            alertTitle = @"Something went wrong";
            alertText = [FBErrorUtility userMessageForError:error];
            //[self showMessage:alertText withTitle:alertTitle];
        } else {

            if ([FBErrorUtility errorCategoryForError:error] == FBErrorCategoryUserCancelled) {
                NSLog(@"User cancelled login");

            } else if ([FBErrorUtility errorCategoryForError:error] == FBErrorCategoryAuthenticationReopenSession){
                alertTitle = @"Session Error";
                alertText = @"Your current session is no longer valid. Please log in again.";
                //[self showMessage:alertText withTitle:alertTitle];

              https://developers.facebook.com/docs/ios/errors
            } else {
                //Get more error information from the error
                NSDictionary *errorInformation = [[[error.userInfo objectForKey:@"com.facebook.sdk:ParsedJSONResponseKey"] objectForKey:@"body"] objectForKey:@"error"];

                alertTitle = @"Something went wrong";
                alertText = [NSString stringWithFormat:@"Please retry. \n\n If the problem persists contact us and mention this error code: %@", [errorInformation objectForKey:@"message"]];
                //[self showMessage:alertText withTitle:alertTitle];
            }
        }

        [FBSession.activeSession closeAndClearTokenInformation];
        //[self userLoggedOut];
    }
}

- (void)loginView:(FBLoginView *)loginView handleError:(NSError *)error {
    NSString *alertMessage, *alertTitle;

    if ([FBErrorUtility shouldNotifyUserForError:error]) {
        alertTitle = @"Facebook error";
        alertMessage = [FBErrorUtility userMessageForError:error];

    } else if ([FBErrorUtility errorCategoryForError:error] == FBErrorCategoryAuthenticationReopenSession) {
        alertTitle = @"Session Error";
        alertMessage = @"Your current session is no longer valid. Please log in again.";

    } else if ([FBErrorUtility errorCategoryForError:error] == FBErrorCategoryUserCancelled) {
        NSLog(@"user cancelled login");

    } else {
        alertTitle  = @"Something went wrong";
        alertMessage = @"Please try again later.";
        NSLog(@"Unexpected error:%@", error);
    }

    if (alertMessage) {
        [[[UIAlertView alloc] initWithTitle:alertTitle
                                    message:alertMessage
                                   delegate:nil
                          cancelButtonTitle:@"OK"
                          otherButtonTitles:nil] show];
    }
}

登录方法

- (void)signIn
{

    if([GenericService checkConnection]){

        GenericService *service = [[GenericService alloc] initWithDelegate:self andCallback:@selector(answerSignIn:)];
        service.metodo = 1;
        service.messageLoading = @"Wait...";
        service.url = @"http://myservice.com/signIn.json";
        [service addParameter:self.name withKey:@"name"];
        [service addParameter:self.email withKey:@"email"];
        [service request];

    }
}

- (NSString *) answerSignIn:(NSDictionary *)answer {

    NSLog(@"%@", [answer description]);

    NSString *sucess = [answer objectForKey:@"sucesso"];

    if (sucess)
        [self.navigationController pushViewController:self.tabBarController animated:YES];

    return sucess;
}

1 个答案:

答案 0 :(得分:20)

这种情况正在发生,因为FBRequest块是异步的,即它在后台执行FBRequest,以允许您的应用在忙于获取信息时继续其他进程。所以是的,会有延迟,但为了在您需要时仍然拥有您需要的信息,请在signIn块中的FBRequest方法中调用populateUserDetails方法 1}}而不是在sessionStateChanged:state:error:中调用它,就像这样:

- (void)populateUserDetails
{
    if (FBSession.activeSession.isOpen) {
        [[FBRequest requestForMe] startWithCompletionHandler:
         ^(FBRequestConnection *connection,
           NSDictionary<FBGraphUser> *user,
           NSError *error) {
             if (!error) {
                 NSLog(@"%@", user.name);
                 NSLog(@"%@", [user objectForKey:@"email"]);
                 self.nome = user.name;
                 self.email = [user objectForKey:@"email"];

                 [self signIn];
             }
         }];
    }
}