diff --git a/plugins/auth-backend/src/providers/PassportStrategyHelper.ts b/plugins/auth-backend/src/providers/PassportStrategyHelper.ts index 5c02930c2c..bea349ce97 100644 --- a/plugins/auth-backend/src/providers/PassportStrategyHelper.ts +++ b/plugins/auth-backend/src/providers/PassportStrategyHelper.ts @@ -16,7 +16,43 @@ import express from 'express'; import passport from 'passport'; -import { RedirectInfo, RefreshTokenResponse } from './types'; +import jwtDecoder from 'jwt-decode'; +import { RedirectInfo, RefreshTokenResponse, ProfileInfo } from './types'; + +export const makeProfileInfo = ( + profile: passport.Profile, + params: any, +): ProfileInfo => { + const { provider, displayName: name } = profile; + + let email = ''; + if (profile.emails) { + const [firstEmail] = profile.emails; + email = firstEmail.value; + } + + if (!email && params.id_token) { + try { + const decoded: { email: string } = jwtDecoder(params.id_token); + email = decoded.email; + } catch (e) { + console.error('Failed to parse id token and get profile info'); + } + } + + let picture = ''; + if (profile.photos) { + const [firstPhoto] = profile.photos; + picture = firstPhoto.value; + } + + return { + provider, + name, + email, + picture, + }; +}; export const executeRedirectStrategy = async ( req: express.Request, @@ -98,10 +134,22 @@ export const executeRefreshTokenStrategy = async ( ), ); } - resolve({ + + anyStrategy.userProfile( accessToken, - params, - }); + (err: Error, passportProfile: passport.Profile) => { + if (err) { + reject(err); + } + + const profile = makeProfileInfo(passportProfile, params); + resolve({ + accessToken, + params, + profile, + }); + }, + ); }, ); }); diff --git a/plugins/auth-backend/src/providers/google/provider.ts b/plugins/auth-backend/src/providers/google/provider.ts index fa6e0085bf..b6690b0b82 100644 --- a/plugins/auth-backend/src/providers/google/provider.ts +++ b/plugins/auth-backend/src/providers/google/provider.ts @@ -15,7 +15,6 @@ */ import express from 'express'; -import jwtDecoder from 'jwt-decode'; import { Strategy as GoogleStrategy } from 'passport-google-oauth20'; import { executeFrameHandlerStrategy, @@ -77,30 +76,15 @@ export class GoogleAuthProvider implements OAuthProviderHandlers { } async refresh( - provider: string, refreshToken: string, scope: string, ): Promise { - const { accessToken, params } = await executeRefreshTokenStrategy( + const { accessToken, params, profile } = await executeRefreshTokenStrategy( this._strategy, refreshToken, scope, ); - // TODO(soapraj): check what happens when you return undefined - let profile; - try { - const { email, name, picture } = jwtDecoder(params.id_token); - profile = { - provider, - email, - name, - picture, - }; - } catch (e) { - console.error('Failed to parse id token and get profile info'); - } - return { accessToken, idToken: params.id_token, diff --git a/plugins/auth-backend/src/providers/types.ts b/plugins/auth-backend/src/providers/types.ts index b78fa73070..a8239b397a 100644 --- a/plugins/auth-backend/src/providers/types.ts +++ b/plugins/auth-backend/src/providers/types.ts @@ -15,7 +15,6 @@ */ import express from 'express'; -import passport from 'passport'; export type AuthProviderConfig = { provider: string; @@ -26,7 +25,7 @@ export type AuthProviderConfig = { export interface OAuthProviderHandlers { start(req: express.Request, options: any): Promise; handler(req: express.Request): Promise; - refresh?(provider: string, refreshToken: string, scope: string): Promise; + refresh?(refreshToken: string, scope: string): Promise; logout?(): Promise; } @@ -78,7 +77,15 @@ export type RedirectInfo = { status?: number; }; +export type ProfileInfo = { + provider: string; + email: string; + name: string; + picture: string; +}; + export type RefreshTokenResponse = { accessToken: string; params: any; + profile: ProfileInfo; };