import { HttpClient, HttpHeaders } from '@angular/common/http'; import { Injectable, NgZone, Optional } from '@angular/core'; import { MatSnackBar } from '@angular/material'; import { ActivatedRoute, Router } from '@angular/router'; import { TranslateService } from '@ngx-translate/core'; import { environment } from '../../../environments/environment'; import { Credential } from '../../models/login/Credential'; import { LoginProviders } from '../../models/login/LoginInfo'; import { AuthService } from '../../services/auth/auth.service'; import { SnackBarNotificationComponent } from '../../shared/components/notificaiton/snack-bar-notification.component'; import { CultureService } from '../../utilities/culture/culture-service'; import { LoginOptions } from './LoginOptions'; import { LoginProviderConfiguration } from './LoginProviderConfiguration'; import { LoginServiceConfiguration } from './LoginServiceConfiguration'; declare const gapi: any; declare const FB: any; declare const IN: any; @Injectable() export class LoginService { private providers: LoginOptions[]; private auth2: any; constructor( private router: Router, public authService: AuthService, public route: ActivatedRoute, public snackBar: MatSnackBar, public language: TranslateService, private zone: NgZone, private httpClient: HttpClient, private cultureService: CultureService, @Optional() private config: LoginServiceConfiguration ) { if (config) { this.providers = config.loginProviders; } else { this.providers = [LoginOptions.nativeLogin]; } } public initProviders() { if (this.hasProvider(LoginOptions.googleOauth)) { this.initialiseGoogleOauth(); } if (this.hasProvider(LoginOptions.facebookOauth)) { this.initialiseFacebookOauth(); } } public hasProvider(provider: LoginOptions) { for (let i = 0; i < this.providers.length; i++) { if (provider === this.providers[i]) { return this.isProviderProperlyConfigured(provider); } } return false; } private isProviderProperlyConfigured(provider: LoginOptions) { switch (provider) { case LoginOptions.facebookOauth: return this.hasAllRequiredFieldsConfigured(this.config.facebookConfiguration); case LoginOptions.googleOauth: return this.hasAllRequiredFieldsConfigured(this.config.googleConfiguration); case LoginOptions.linkedInOauth: return this.hasAllRequiredFieldsConfigured(this.config.linkedInConfiguration); case LoginOptions.twitterOauth: return this.hasAllRequiredFieldsConfigured(this.config.twitterConfiguration); case LoginOptions.b2Access: return this.hasAllRequiredFieldsConfigured(this.config.b2accessConfiguration); case LoginOptions.nativeLogin: return true; default: throw new Error('Unsupported Provider Type'); } } private hasAllRequiredFieldsConfigured(configuration: LoginProviderConfiguration) { if (configuration != null && configuration.clientId != null) { return true; } return false; } /* * GOOGLE SIGN IN */ private initialiseGoogleOauth(): void { gapi.load('auth2', () => { this.auth2 = gapi.auth2.init({ client_id: this.config.googleConfiguration.clientId, cookiepolicy: 'single_host_origin', scope: 'profile email' }); this.attachGoogleSignin(document.getElementById('googleSignInButton')); }); } public attachGoogleSignin(element) { if (!element) { return; } this.auth2.attachClickHandler(element, {}, (googleUser) => { const id_token = googleUser.getAuthResponse().id_token; if (id_token) { this.authService.login({ ticket: id_token, provider: LoginProviders.Google }).subscribe( res => this.onLogInSuccess(res), error => this.onLogInError(error) ); } }, (error) => { }); } /* * FACEBOOK SIGN IN */ private initialiseFacebookOauth(): void { FB.init({ appId: this.config.facebookConfiguration.clientId, cookie: false, xfbml: true, version: 'v2.8' }); } public facebookLogin() { FB.login((response: any) => { if (response.status === 'connected' || 'not_authorized') { this.authService.login({ ticket: response.authResponse.accessToken, provider: LoginProviders.Facebook }).subscribe( res => this.onLogInSuccess(res), error => this.onLogInError(error) ); } }, { scope: 'user_friends,email' }); } /* * LINKEDIN SIGN IN */ public linkedinAuthorize() { window.location.href = this.config.linkedInConfiguration.oauthUrl + '?response_type=code&client_id=' + this.config.linkedInConfiguration.clientId + '&redirect_uri=' + this.config.linkedInConfiguration.redirectUri + '&state=987654321'; } public linkedInInitialiseLogin() { this.router.navigate(['/login/linkedin']); } public linkedInloginUser(code: string) { this.authService.login({ ticket: code, provider: LoginProviders.LinkedIn }).subscribe( res => this.onLogInSuccess(res), error => this.onLogInError(error) ); } /* * TWITTER SIGN IN */ public twitterInitialiseLogin() { this.router.navigate(['/login/twitter']); } public twitterAuthorize() { let headers = new HttpHeaders(); headers = headers.set('Content-Type', 'application/json'); headers = headers.set('Accept', 'application/json'); this.httpClient.get(environment.Server + 'auth/twitterRequestToken', { headers: headers }).subscribe((data: any) => { window.location.href = this.config.twitterConfiguration.oauthUrl + '?oauth_token=' + data.payload.value; }); } public twitterLogin(token: string, verifier: string) { this.authService.login({ ticket: token, provider: LoginProviders.Twitter, data: verifier }).subscribe( res => this.onLogInSuccess(res), error => this.onLogInError(error) ); } /* * B2ACCESS LOG IN */ public b2AccessInitialiseLogin() { this.router.navigate(['/api/oauth/authorized/b2access']); } public b2AccessGetAuthCode() { window.location.href = this.config.b2accessConfiguration.oauthUrl + '?response_type=code&client_id=' + this.config.b2accessConfiguration.clientId + '&redirect_uri=' + this.config.b2accessConfiguration.redirectUri + '&state=987654321&scope=USER_PROFILE'; } public b2AccessLogin(code: String) { let headers = new HttpHeaders(); headers = headers.set('Content-Type', 'application/json'); headers = headers.set('Accept', 'application/json'); this.httpClient.post(environment.Server + 'auth/b2AccessRequestToken', { code: code }, { headers: headers }) .subscribe((data: any) => { this.authService.login({ ticket: data.payload.accessToken, provider: LoginProviders.B2Accesss, data: null }).subscribe( res => this.onLogInSuccess(res), error => this.onLogInError(error) ); }); } /* * NATIVE LOGIN */ public nativeLogin(credentials: Credential) { this.authService.nativeLogin(credentials).subscribe( res => this.onLogInSuccess(res), error => this.onLogInError(error) ); } /* * LOGIN HANDLERS */ public onLogInSuccess(logoutMessage: any) { this.snackBar.openFromComponent(SnackBarNotificationComponent, { data: { message: 'GENERAL.SNACK-BAR.SUCCESSFUL-LOGIN', language: this.language }, duration: 3000, }); if (this.authService.current().culture) { this.cultureService.cultureSelected(this.authService.current().culture); } const params = this.router['rawUrlTree'].queryParams; const redirectUrl = params['returnUrl'] ? params['returnUrl'] : '/'; this.zone.run(() => this.router.navigate([redirectUrl])); } public onLogInError(errorMessage: string) { this.snackBar.openFromComponent(SnackBarNotificationComponent, { data: { message: 'GENERAL.SNACK-BAR.UNSUCCESSFUL-LOGIN', language: this.language }, duration: 3000, }); } }