2012-09-27 14 views
9

Używam 3.1 Facebook SDK z iOS 6 Facebook skonfigurowany w Ustawieniach i moja aplikacja autoryzowana.Nieaktualny token dostępu po openActiveSession dla Facebook iOS SDK

ten wykonuje bezbłędnie:

[FBSession openActiveSessionWithReadPermissions:nil allowLoginUI:YES completionHandler:^(FBSession *fbSession, FBSessionState fbState, NSError *error) { ... } 

Jednak teraz, gdy próbuję dostać się 'ja' informacje dostaję błąd:

com.facebook.sdk:ParsedJSONResponseKey = { 
    body =  { 
     error =   { 
      code = 190; 
      "error_subcode" = 463; 
      message = "Error validating access token: Session has expired at unix time 1348704000. The current unix time is 1348706984."; 
      type = OAuthException; 
     }; 
    }; 
    code = 400; 
} 

Jeśli patrzę na [error code] to równe 5. Czy po zalogowaniu nie powinienem mieć ważnego tokena dostępu? Czy muszę wywoływać ponowne autoryzowanie?

UPDATE: Ponowne autoryzowanie nie pomaga. Dziwne, że token dostępu dla mojej aktywnej sesji zawsze powraca tak samo. Pomimo wywołania closeAndClearToken.

+2

Aby rozpocząć diagnozowanie, czy możesz zalogować się do otrzymanego klucza dostępu i wkleić go do https://developers.facebook.com/tools/debug - czy znajduje się tam znacznik czasu? –

+0

Dobra wskazówka. Teraz problem zniknął i muszę go odtworzyć. Wypróbuję twoją sugestię następnym razem, gdy ją zobaczę. –

+0

Mam ten sam problem z iPhone5/iOS6. Wydaje się jednak bardzo sporadyczne. Daj mi znać, jeśli znajdziesz coś więcej na temat tego problemu i zrobię to samo. – Chad

Odpowiedz

4

UPDATE: Ten problem został rozwiązany w Facebook iOS SDK 3.1.1.


I zsynchronizowane kod off github i okazało się, że nie były one nazywając accountStore renewCredentialsForAccount:completion: wszędzie. Zmieniłem następujący kod w authorizeUsingSystemAccountStore i wygląda na to, że problem został rozwiązany.

// we will attempt an iOS integrated facebook login 
[accountStore requestAccessToAccountsWithType:accountType 
             options:options 
            completion:^(BOOL granted, NSError *error) { 

             // this means the user has not signed-on to Facebook via the OS 
             BOOL isUntosedDevice = (!granted && error.code == ACErrorAccountNotFound); 

             dispatch_block_t postReauthorizeBlock = ^{ 
              NSString *oauthToken = nil; 
              if (granted) {                          
               NSArray *fbAccounts = [accountStore accountsWithAccountType:accountType]; 
               id account = [fbAccounts objectAtIndex:0]; 
               id credential = [account credential];             
               oauthToken = [credential oauthToken]; 
              } 

              // initial auth case 
              if (!isReauthorize) { 
               if (oauthToken) { 
                _isFacebookLoginToken = YES; 
                _isOSIntegratedFacebookLoginToken = YES; 

                // we received a token just now 
                self.refreshDate = [NSDate date]; 

                // set token and date, state transition, and call the handler if there is one 
                [self transitionAndCallHandlerWithState:FBSessionStateOpen 
                        error:nil 
                        token:oauthToken 
                // BUG: we need a means for fetching the expiration date of the token 
                      expirationDate:[NSDate distantFuture] 
                       shouldCache:YES 
                       loginType:FBSessionLoginTypeSystemAccount]; 
               } else if (isUntosedDevice) { 
                // even when OS integrated auth is possible we use native-app/safari 
                // login if the user has not signed on to Facebook via the OS 
                [self authorizeWithPermissions:permissions 
                    defaultAudience:defaultAudience 
                    integratedAuth:NO 
                     FBAppAuth:YES 
                     safariAuth:YES 
                     fallback:YES 
                    isReauthorize:NO]; 
               } else { 
                // create an error object with additional info regarding failed login 
                NSError *err = [FBSession errorLoginFailedWithReason:nil 
                           errorCode:nil 
                          innerError:error]; 

                // state transition, and call the handler if there is one 
                [self transitionAndCallHandlerWithState:FBSessionStateClosedLoginFailed 
                        error:err 
                        token:nil 
                      expirationDate:nil 
                       shouldCache:NO 
                       loginType:FBSessionLoginTypeNone]; 
               } 
              } else { // reauth case 
               if (oauthToken) { 
                // union the requested permissions with the already granted permissions 
                NSMutableSet *set = [NSMutableSet setWithArray:self.permissions]; 
                [set addObjectsFromArray:permissions]; 

                // complete the operation: success 
                [self completeReauthorizeWithAccessToken:oauthToken 
                      expirationDate:[NSDate distantFuture] 
                       permissions:[set allObjects]]; 
               } else { 
                // no token in this case implies that the user cancelled the permissions upgrade 
                NSError *error = [FBSession errorLoginFailedWithReason:FBErrorReauthorizeFailedReasonUserCancelled 
                           errorCode:nil 
                           innerError:nil]; 
                // complete the operation: failed 
                [self callReauthorizeHandlerAndClearState:error]; 

                // if we made it this far into the reauth case with an untosed device, then 
                // it is time to invalidate the session 
                if (isUntosedDevice) { 
                 [self closeAndClearTokenInformation]; 
                } 
               } 
              } 
             }; 



             if (granted) { 
              [accountStore renewCredentialsForAccount:[[accountStore accountsWithAccountType:accountType] lastObject] completion:^(ACAccountCredentialRenewResult renewResult, NSError *error) { 
               dispatch_async(dispatch_get_main_queue(), postReauthorizeBlock); 
              }]; 
             } else { 
              // requestAccessToAccountsWithType:options:completion: completes on an 
              // arbitrary thread; let's process this back on our main thread 
              dispatch_async(dispatch_get_main_queue(), postReauthorizeBlock); 
             } 

            }]; 

} 
+0

Najprawdopodobniej powinniśmy sprawdzić datę ważności przed odnowieniem (ponieważ odnowienie wymaga czasu), ale pomimo tego, co jest napisane w dokumentach firmy Apple (http://developer.apple.com/library/ios/#documentation/Accounts/Reference/ACAccountCredentialClassRef /Reference/Reference.html#//apple_ref/doc/c_ref/ACAccountCredential), parametr expiryData wydaje się nie istnieć. –

+2

Witaj Ben, masz rację, jeśli musisz zadzwonić, aby odnowić *. Dzwonienie z tego miejsca działa dobrze. Wybór miejsca wykonywania połączeń zależy zasadniczo od kompromisu między konsekwencją zachowania i dodatkowych wizyt w sieci. W kolejnej aktualizacji SDK rozważamy wykonanie wywołania w logice FBRequestConnection, która obsługuje nieprawidłowe tokeny. –

+0

@JasonClark To wydaje się rozsądnym wyborem. Sugerowałbym również posiadanie zwykłego starego odnowienia połączenia w SDK FB. Byłoby to użyteczne, gdybyś używał pakietu SDK do zarządzania tokenami, a nie kanału do wykonywania wywołań grafów. Dziękuję za odpowiedź! –

0

Więc to zająć, ale byłem nazywając/mi z naszego zaplecza do weryfikacji, ponieważ nie można ufać urządzenia.

Tak więc nawiązuję połączenie z FBSession+ (void)renewSystemAuthorization, gdy backend wraca z błędem autoryzacji.

+1

Nie widzę metody klasy renewSystemAuthorization w FBSession w wersji 3.1.1. – gerry3

+0

Wygląda na to, że zajęli się tą kwestią w ramach tego zatwierdzenia, z którego jestem związany. https://github.com/facebook/facebook-ios-sdk/commit/0b3d28b7bea8b63dd9efca67e1438d72fc78daf5 – hawflakes

Powiązane problemy