angular-oauth2-oidc, how to detect if I logged in somewhere else?

MaXon picture MaXon · Aug 9, 2018 · Viewed 9.9k times · Source

I'm using the angular-oauth2-oidc library in combination with the Implicit Flow with keycloak.

There is no problem to login with this.oauthService.initImplicitFlow(); or logout with this.oauthService.logOut();

However, I'm wondering, is it possible to check if I already logged in at somewhere else? (different domain but use the same keycloak server)

I've searched through the docs of angular-oauth2-oidc but didn't find any.

I've tried this.oauthService.initImplicitFlowInternal(); but it seems works the same as the this.oauthService.initImplicitFlow();

UPDATE:

I've got the token using silentRefresh, however, it seems created another nav component (or maybe an entirely new page). The problem is, this 'new' page is hidden and I can only see the 'old' page. enter image description here

I created an id for the nav component using timestamp, as you can see, there are actually two ids.

The 'new' component got the token, so it's logged in (but the component is hidden!).

The 'old' component doesn't know the token, so it's still shows 'LOGIN' on navbar, unless I manually make a button and fetch the token from session storage on click.

UPDATE: That second component is iframe. I will explore more.

Answer

Jeroen picture Jeroen · Aug 9, 2018

I suggest setting up silent refreshes if you haven't already, then use this.oauthService.silentRefresh().

Technically, that doesn't answer your question straight up, because it doesn't "check" if you're logged in, but instead just straight up logs you into the application. And if it would fail (you're not yet logged in) it would reject the promise returned from silentRefresh().

For reference, you can check my sample repo that has this login flow which supports silently logging a user in even if the login happened elsewhere. This is the nitty gritty:

// 0. LOAD CONFIG:
// First we have to check to see how the IdServer is
// currently configured:
this.authService.loadDiscoveryDocument()

  // 1. HASH LOGIN:
  // Try to log in via hash fragment after redirect back
  // from IdServer from initImplicitFlow:
  .then(() => this.authService.tryLogin())

  .then(() => {
    if (!this.authService.hasValidAccessToken()) {

      // 2. SILENT LOGIN:
      // Try to log in via silent refresh because the IdServer
      // might have a cookie to remember the user, so we can
      // prevent doing a redirect:
      this.authService.silentRefresh()
        .catch(result => {
          // Subset of situations from https://openid.net/specs/openid-connect-core-1_0.html#AuthError
          // Only the ones where it's reasonably sure that sending the
          // user to the IdServer will help.
          const errorResponsesRequiringUserInteraction = [
            'interaction_required',
            'login_required',
            'account_selection_required',
            'consent_required',
          ];

          if (result && result.reason && errorResponsesRequiringUserInteraction.indexOf(result.reason.error) >= 0) {

            // 3. ASK FOR LOGIN:
            // At this point we know for sure that we have to ask the
            // user to log in, so we redirect them to the IdServer to
            // enter credentials:
            this.authService.initImplicitFlow();
          }
        });
    }
});

The straight up answer to you question though is likely that you cannot get a push notification ("check") when you are logged in elsewhere, because to do that you need to know who you are (log in) to establish session checks. (The sessionChecksEnabled config however does help you "check" when you get logged out elsewhere, see this recent question)