【问题标题】:Opening FBSession in consecutive launches (FB SDK for SDK 3.0)在连续启动中打开 FBSession (FB SDK for SDK 3.0)
【发布时间】:2012-08-07 04:12:41
【问题描述】:

我正在尝试集成新的 iOS 版 Facebook SDK,但在理解某些概念时遇到了问题。

  1. 我使用[FBSession sessionOpenWithPermissions:...] 进行身份验证对话框出现并返回应用程序。认证成功。

  2. 然后关闭应用程序,重新启动。 [[FBSession activeSession] accessToken] 成功返回之前保存的令牌。

  3. 但是,与此同时,[[FBSession activeSession] isOpen] 返回 NO。 (这意味着会话尚未准备好使用。)

  4. 另外,此时[[FBSession activeSession] state]FBSessionStateCreatedTokenLoaded。教程here 使用isOpen 调用来验证活动会话是否已加载并使用令牌打开。

那么,在不将用户重定向到身份验证对话框的情况下,我们应该调用什么来打开令牌加载会话?

提示:

FBSessionState 枚举中,对于FBSessionStateOpen 它说:

表示用户已登录或缓存令牌可用的打开会话状态。

然而FBSessionStateCreatedTokenLoaded被描述为:

两种初始会话状态之一,指示已加载缓存的令牌;当会话处于此状态时,对 open* 的调用将导致会话打开,无需 UX 或应用切换

您能帮我弄清楚这些会话转换的含义吗?

【问题讨论】:

  • 您必须在每次应用启动时重新打开会话。
  • 怎么做?我错过了那部分。 [FBSession sessionOpenWithPermissions:...] 会在不每次都显示身份验证对话框的情况下做到这一点吗?
  • this: + (BOOL)openActiveSessionWithAllowLoginUI:(BOOL)allowLoginUI 以及 google FBSession - 字面上的第一击。
  • @ahmetalpbalkan 是的,就是这样。查看我的答案,了解更多详情

标签: ios facebook facebook-ios-sdk


【解决方案1】:

只需调用您的初始化视图控制器

self.FBloginView = [[FBLoginView alloc] init];

【讨论】:

    【解决方案2】:

    这可能是一个旧线程,但现在你所要做的就是在你的应用委托中的 (void)applicationDidBecomeActive:(UIApplication *)application 中调用你的 FBSession 对象中的 handleDidBecomeActive。

    例如:

    - (void)applicationDidBecomeActive:(UIApplication *)application
    {
        [[[MLSocialNetworksManager sharedManager] MLFacebook] handleDidBecomeActive];
    }
    

    MLFacebook 是我的 FBSession 对象。

    【讨论】:

    • 您为什么要创建另一个名为 MLFacebook 的类? handleDidBecomeActiveFBSession的方法吗?
    • 它封装了我的 facebook 逻辑。绝不是必需的。
    【解决方案3】:

    我包含了一个我编写的有助于理解登录状态的 Facebook 实用程序类,因为除了使用实际的'FBLoginView' 组件允许用户切换授权状态。

    下面的代码也可以通过gist获得。

    我可能没有正确解释我的 switch 语句中的所有 FBSessionState 类型,但到目前为止,在我测试过的情况下它对我很有帮助(我只是把它放在一起)。

    其他人提到的要注意的关键是,有时您有一个无法立即使用的缓存授权令牌,但如果您在其上调用 Facebook open,您可以将其用于可重复使用(刷新)。此公开调用在幕后工作,不会触发任何 UI/不和谐的 OAuth 窗口/应用切换(如果您有缓存的令牌)。

    在方法isLoggedInAfterOpenAttempt 中查看我的cmets。请注意我如何检查状态是否为 FBSessionStateCreatedTokenLoaded,然后才调用

    -openWithCompletionHandler:^(FBSession *session, FBSessionState status, NSError *error).

    关于这个课程的其他花絮:

    • 我这里有一个属性来缓存登录的用户,类型符合协议FBGraphUser。不过,这里演示的任何登录方法都没有使用它。
    • 适用于 iOS 的 Facebook SDK 3.0 示例代码建议构建您自己的类来保存和管理这些类型的操作,如果您有任何不只是一个微不足道的应用程序的话。下面的这门课是我的应用程序这个想法的开始。
    • 您可以将我的“log4Info”和“log4Debug”宏替换为 NSLog 以使其正常工作。
    #import "UWFacebookService.h" @implementation UWFacebookService // 静止的 静态常量 int ddLogLevel = LOG_LEVEL_DEBUG; // 强的 @synthesize facebookGraphUser = _facebookGraphUser; #pragma mark - 查询 - (BOOL)isSessionStateEffectivelyLoggedIn:(FBSessionState)state { BOOL 有效登录; 开关(状态){ 案例 FBSessionStateOpen: log4Info(@"Facebook 会话状态:FBSessionStateOpen"); 有效LoggedIn = YES; 休息; 案例 FBSessionStateCreatedTokenLoaded: log4Info(@"Facebook 会话状态:FBSessionStateCreatedTokenLoaded"); 有效LoggedIn = YES; 休息; 案例 FBSessionStateOpenTokenExtended: log4Info(@"Facebook 会话状态:FBSessionStateOpenTokenExtended"); 有效LoggedIn = YES; 休息; 默认: log4Info(@"Facebook 会话状态:不是打开或可打开类型之一。"); 有效登录 = 否; 休息; } 返回有效登录; } /** * 确定 Facebook 会话是否具有授权状态。如果它是缓存的,它可能仍需要打开 * 令牌,但此调用的目的是确定用户是否至少被授权 * 明确询问任何事情。 */ - (BOOL)isLoggedIn { FBSession *activeSession = [FBSession activeSession]; FBSessionState state = activeSession.state; BOOL isLoggedIn = activeSession && [self isSessionStateEffectivelyLoggedIn:state]; log4Info(@"Facebook 活动会话状态:%d;登录结论:%@", state, (isLoggedIn ?@"YES" : @"NO")); 返回是登录; } /** * 如果我们加载了有效令牌(可能需要后台刷新),则尝试静默打开 Facebook 会话。 * 在那次尝试之后,我们遵循会话处于有效授权状态之一的基本概念。 */ - (BOOL)isLoggedInAfterOpenAttempt { log4Debug(@"FBSession.activeSession: %@", FBSession.activeSession); // 如果我们没有缓存的令牌,在此处调用 open 将导致 UX 登录 // 发生;我们不希望这种情况发生,除非用户点击设置中的登录按钮,所以 // 我们在这里检查以确保在调用 open 之前我们有一个令牌 如果(FBSession.activeSession.state == FBSessionStateCreatedTokenLoaded){ log4Info(@"我们有一个缓存的令牌,所以我们要为用户重新建立登录。"); // 即使我们有一个缓存的令牌,我们也需要登录才能使会话可用: [FBSession.activeSession openWithCompletionHandler:^(FBSession *session, FBSessionState 状态, NSError *error) { log4Info(@"已完成打开登录会话,状态:%d", status); }]; } 别的 { log4Info(@"活动会话不在状态'FBSessionStateCreatedTokenLoaded'。它有状态:%d", FBSession.activeSession.state); } 返回 [self isLoggedIn]; } @结尾

    【讨论】:

      【解决方案4】:

      试试下面的代码示例:

      /////////////////////////////////
      
      -(void)CallBackOpenURLFromDelegate:(NSURL *)url
      {
          [FBSession.activeSession handleOpenURL:url];
      }
      
      -(id)init
      {
          self = [super init];
          FBSessionTokenCachingStrategy* pToken = [[[FBSessionTokenCachingStrategy alloc]initWithUserDefaultTokenInformationKeyName:@"STokenInfoX"]autorelease];
          FBSession.activeSession = [[FBSession alloc] initWithAppID:FACEBOOK_AppId
                                                         permissions:[NSArray arrayWithObject:@"status_update"]
                                                     urlSchemeSuffix:@""
                                                  tokenCacheStrategy: pToken];
          return self;
      }
      
      
      -(void)dealloc
      {
          [FBSession.activeSession close];
          [super dealloc];
      }
      
      -(void) UploadImpl:(NSString*)strImagePath
      {
          FBRequest *photoUploadRequest = [FBRequest requestForUploadPhoto: [UIImage imageWithContentsOfFile:strImagePath ]];
          [photoUploadRequest startWithCompletionHandler:^(FBRequestConnection *connection, id result, NSError *error)
          {
              NSLog(@"%@",[error description]);
              //self.delegate
          }];
      }
      

      【讨论】:

        【解决方案5】:

        这意味着,当您保存(缓存)或以其他方式已经可用的令牌时,Facebook iOS 库仍要求您使用 open 方法重新初始化会话。

        如果它可以重用现有令牌(这是您的情况),这样做会这样做,并且在这种情况下不会触发 UX(用户体验 - 即应用切换或 Facebook 登录弹出窗口)。

        用户的印象是他从未退出,但在应用程序中发生的事情是您正在联系 Facebook 以重新打开会话。

        之所以这样设计,是因为如果令牌可用但已过期,Facebook 库会告诉您 - “嘿,令牌已过期,请考虑您已注销,除非您现在获得新令牌。”

        希望对您有所帮助。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2012-08-06
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2015-03-06
          • 2012-10-25
          相关资源
          最近更新 更多