0

I am using all the latest and greatest : XCode 13.2.1, Salesforce Mobile SDK 10.

I am writing a native iOS Swift app and I wish to DEFER the Salesforce login to a point in the application that makes sense. (Perhaps the user doesn't even want to connect to Salesforce :) )

It's all very easy. I simply defer the call to AuthHelper.loginIfRequired() to wherever it makes sense for me.

OK, very good.

Now I want the same ability if the user logs off yes? I do NOT want the Login Page in my face just because they log off. I want to decide what happens.

Hmmmm?? I call UserAccountManager.shared.logout() to logout (please correct me if that is the wrong thing to do). It appears (from the logs) to do what I think it should do, and the handleLogout() method of AuthHelper is invoked (not by me of course, by the SDK). The code (in handleLogout()) tries to help?? and decides that if there are no current active users left, then it will call AuthHelper.loginIfRequired() on my behalf :( OK, that's pretty solid logic, if that's what I want, but I don't!! :) I want to control if/when the login flow should be initiated.

I can't figure out how to do it :(

I can of course register call backs for 'forLogoutNotifications' and all that jazz works, but I cannot stop the call to the existing AuthHelper.handleLogout() method from executing. I want my own version :)

Yes, I'm an iOS newbie, and perhaps there is a simple answer, but I don't get it :( You can see the 'problem child' line of code (in the SDK AuthHelper) at the bottom there :(

Thanks in advance for any iOS dudes helping me!!

+ (void)handleLogout:(UIScene *)scene completion:(void (^)(void))completionBlock {
    // Multi-user pattern:
    // - If there are two or more existing accounts after logout, let the user choose the account
    //   to switch to.
    // - If there is one existing account, automatically switch to that account.
    // - If there are no further authenticated accounts, present the login screen.
    //
    // Alternatively, you could just go straight to re-initializing your app state, if you know
    // your app does not support multiple accounts.  The logic below will work either way.
    NSArray *allAccounts = [SFUserAccountManager sharedInstance].allUserAccounts;
    if ([allAccounts count] > 1) {
        SFDefaultUserManagementViewController *userSwitchVc = [[SFDefaultUserManagementViewController alloc] initWithCompletionBlock:^(SFUserManagementAction action) {
            [[[SFSDKWindowManager sharedManager] mainWindow:scene].window.rootViewController dismissViewControllerAnimated:YES completion:NULL];
        }];
        [[[SFSDKWindowManager sharedManager] mainWindow:scene].window.rootViewController presentViewController:userSwitchVc animated:YES completion:NULL];
    } else {
        if ([allAccounts count] == 1) {
            [[SFUserAccountManager sharedInstance] switchToUser:([SFUserAccountManager sharedInstance].allUserAccounts)[0]];
            if (completionBlock) {
                completionBlock();
            }
        } else {
            [self loginIfRequired:scene completion:completionBlock];
        }
    }
}

1 Answer 1

0

The forceioscreate wizard thingee will generate code in the SceneDelegate that looks like this :

AuthHelper.registerBlock(forCurrentUserChangeNotifications: scene) {
            self.resetViewState {
                self.setupRootViewController()
            }
        }

So they're using AuthHelper to register a block of code to be run whenever a User Change Notification is received. OK, fair enough ...

Let's look at that code (in AuthHelper) for a bit (hope the image is clear enough)

#124 is where we end up as a result of the call from the SceneDelegate. In this function (on #125) it registerForLogoutNotifications.

Well, OK I guess. A logout is a change I suppose, so I'll give them that.

But what does registering for LogoutNotifications do exactly (#135)?

Well, it adds an observer for the logout (event), and when it receives one, it actually executes it's OWN 'handleLogout() function' (#137) That is the function that has the logic that will eventually call the loginIfRequired() function.

No mate. I don't want that at all!!!

For logout scenarios I want a pattern similar to what you see at the bottom there (handling switchUser scenarios). There it is doing what I asked and that is to run the completion block that 'I' supply when this notification is received.

enter image description here

Either I'm missing something very basic (quite possible as I am a newb), or this AuthHelper thing cannot help me at all. The only way I can NOT run the handleLogout() is to not use AuthHandler at all. So, yes, I'm questioning my stupidity or the design of this helper (or both) !!!!

My solution : I don't (can't) use AuthHelper, so I do it myself like so :

enter image description here

There is a lot of cool stuff in the SDK and obviously a lot of work has been put into it, but for me at least, documentation is sorely lacking (just my opinion) (or perhaps I really am an idiot :( )

anyway, perhaps someone can find some of this useful.... or not .....

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .