254 lines
8.1 KiB
TypeScript
254 lines
8.1 KiB
TypeScript
/** @file
|
|
* @author Edouard DUPIN
|
|
* @copyright 2018, Edouard DUPIN, all right reserved
|
|
* @license PROPRIETARY (see license file)
|
|
*/
|
|
|
|
import { Inject, Injectable } from '@angular/core';
|
|
import { Router } from '@angular/router';
|
|
|
|
import { StorageService } from '../service/local-storage';
|
|
import { SessionService } from './session';
|
|
import { SSOService } from './sso';
|
|
import { getApplicationLocation, isNullOrUndefined, sha512 } from '../utils';
|
|
import { HttpWrapperService, HTTPRequestModel, HTTPMimeType, ModelResponseHttp } from './http-wrapper_kjdhqslkjf';
|
|
import { Environment } from '../model/environment';
|
|
import { APP_BASE_HREF } from '@angular/common';
|
|
|
|
|
|
@Injectable()
|
|
export class UserService {
|
|
// 0: Not hide password; 1 hide password;
|
|
private identificationVersion: number = 1;
|
|
private cookiesRememberMe = 'remember-me';
|
|
private cookiesToken = 'token';
|
|
constructor(
|
|
@Inject('ENVIRONMENT') private environment: Environment,
|
|
private router: Router,
|
|
private storageService: StorageService,
|
|
private http: HttpWrapperService,
|
|
private sessionService: SessionService,
|
|
private ssoService: SSOService
|
|
) {
|
|
console.log('Start UserService');
|
|
}
|
|
|
|
/**
|
|
* Disconnect the user from the current session ==> this remove the current Token
|
|
*/
|
|
logOut(): void {
|
|
this.removeSession();
|
|
this.ssoService.requestSignOut('home');
|
|
}
|
|
removeSession(): void {
|
|
this.storageService.remove(this.cookiesRememberMe);
|
|
this.storageService.removeSession(this.cookiesToken);
|
|
this.storageService.remove(this.cookiesToken);
|
|
this.sessionService.destroy();
|
|
}
|
|
|
|
private isTokenUpToDate(token?: string): boolean {
|
|
if (isNullOrUndefined(token) || token.length < 25) {
|
|
return false;
|
|
}
|
|
// Separate the Data:
|
|
const elems = token.split('.');
|
|
if (elems.length !== 3) {
|
|
return false;
|
|
}
|
|
// const tokenHeader = decodeURIComponent(window.atob( elems[0] ));
|
|
const tokenData = decodeURIComponent(window.atob(elems[1]));
|
|
// console.error(`Retrieve local token: \nheader=${tokenHeader} \ndata=${tokenData}`);
|
|
const parsedData = JSON.parse(tokenData);
|
|
console.debug(
|
|
`Retrieve token exp data=${new Date(parsedData.exp * 1000).toISOString()} < ${new Date().toISOString()}`
|
|
);
|
|
const expireIn = new Date(parsedData.exp * 1000);
|
|
const nowTime = new Date();
|
|
// TODO: set a margin of 2 hours...
|
|
return expireIn > nowTime;
|
|
}
|
|
|
|
getRememberMe(): boolean {
|
|
return this.storageService.get(this.cookiesRememberMe) === 'true';
|
|
}
|
|
|
|
/**
|
|
* Check if the system can be connected
|
|
*/
|
|
checkAutoConnect(): Promise<void> {
|
|
let locationOrigin = getApplicationLocation(this.environment);
|
|
const self = this;
|
|
return new Promise<void>((resolve, reject) => {
|
|
// Need to use the windows global route to prevent the log in cycle ...
|
|
// And in the main application position, the route does not have currently root the page
|
|
let pathName = window.location.pathname;
|
|
// console.log("start Path-name: '" + pathName + "'");
|
|
// console.log("check with: '" + environment.applName + "/sso/" + "'");
|
|
if (pathName.startsWith('/sso/') || pathName.startsWith(this.environment.applName + '/sso/')) {
|
|
console.log(' ==> SSo section');
|
|
reject();
|
|
return;
|
|
}
|
|
console.log(' ==> Check if need reconnect?');
|
|
let rememberMe = self.getRememberMe();
|
|
// TODO: in case of jest reload ==> no need to manage the SSO ==> just keep the token ... it in enough...
|
|
let token: undefined | string = undefined;
|
|
if (
|
|
isNullOrUndefined(this.environment.tokenStoredInPermanentStorage) ||
|
|
this.environment.tokenStoredInPermanentStorage !== true
|
|
) {
|
|
token = self.storageService.getSession(self.cookiesToken);
|
|
} else {
|
|
token = self.storageService.get(self.cookiesToken);
|
|
}
|
|
// TODO: check validity of the Token:
|
|
if (self.isTokenUpToDate(token)) {
|
|
// remove in case of fail !!!
|
|
this.storageService.removeSession(this.cookiesToken);
|
|
this.storageService.remove(this.cookiesToken);
|
|
self.startSession(token ?? '', rememberMe)
|
|
.then(() => {
|
|
self.router.navigateByUrl(locationOrigin);
|
|
console.log(`update global URL = ${locationOrigin} APP_BASE_HREF=${APP_BASE_HREF}`);
|
|
resolve();
|
|
})
|
|
.catch(() => {
|
|
// jump in the sign-in page (automatically of request remember-me)
|
|
if (rememberMe) {
|
|
// jump to the sso !!! (remove local data to prevent login loop)
|
|
this.storageService.remove(this.cookiesRememberMe);
|
|
this.storageService.remove(this.cookiesToken);
|
|
this.storageService.removeSession(this.cookiesToken);
|
|
self.ssoService.requestSignIn(locationOrigin);
|
|
reject();
|
|
}
|
|
resolve();
|
|
});
|
|
} else {
|
|
console.log(`Get previous connection ... `);
|
|
if (rememberMe) {
|
|
// jump to the sso !!! (remove local data to prevent login loop)
|
|
this.storageService.remove(this.cookiesRememberMe);
|
|
this.storageService.remove(this.cookiesToken);
|
|
this.storageService.removeSession(this.cookiesToken);
|
|
self.ssoService.requestSignIn(locationOrigin);
|
|
reject();
|
|
}
|
|
resolve();
|
|
}
|
|
});
|
|
}
|
|
|
|
startSession(token: string, rememberMe: boolean): Promise<string> {
|
|
const self = this;
|
|
return new Promise((resolve, reject) => {
|
|
self.retrieveMe(token)
|
|
.then((value2: boolean) => {
|
|
if (rememberMe === true) {
|
|
self.storageService.set(self.cookiesRememberMe, rememberMe ? 'true' : 'false');
|
|
}
|
|
if (
|
|
isNullOrUndefined(this.environment.tokenStoredInPermanentStorage) ||
|
|
this.environment.tokenStoredInPermanentStorage !== true
|
|
) {
|
|
self.storageService.setSession(self.cookiesToken, token);
|
|
} else {
|
|
self.storageService.set(self.cookiesToken, token);
|
|
}
|
|
resolve(self.sessionService.getLogin() ?? '');
|
|
})
|
|
.catch(() => {
|
|
reject('sdfsdfsdf');
|
|
});
|
|
});
|
|
}
|
|
retrieveMe(token: string): Promise<boolean> {
|
|
console.log(`AuthService.loginWithToken ... '${token}'`);
|
|
const self = this;
|
|
return new Promise((resolve, reject) => {
|
|
this.http
|
|
.requestJson({
|
|
// server: 'karso',
|
|
endPoint: 'users/me',
|
|
requestType: HTTPRequestModel.GET,
|
|
accept: HTTPMimeType.JSON,
|
|
contentType: HTTPMimeType.JSON,
|
|
authorization: `Bearer ${token}`, // special case, the token is set after this request...
|
|
})
|
|
.then((response: ModelResponseHttp) => {
|
|
// TODO: check type ...
|
|
console.log(`loginWithToken : get some data to check: ${JSON.stringify(response.data)}`);
|
|
self.sessionService.create({
|
|
//sessionId: response.data.sessionId,
|
|
userId: response.data.id,
|
|
userLogin: response.data.login,
|
|
//userEMail: response.data.email,
|
|
//userAdmin: response.data.admin,
|
|
//userBlocked: response.data.blocked,
|
|
//userRemoved: response.data.removed,
|
|
//userAvatar: response.data.avatar,
|
|
tokenJwt: token,
|
|
});
|
|
resolve(true);
|
|
})
|
|
.catch((error: any) => {
|
|
reject(`return ERROR ${JSON.stringify(error, null, 2)}`);
|
|
});
|
|
});
|
|
}
|
|
|
|
create(login: string, email: string, password: string) {
|
|
return this.createSha(login, email, sha512(password));
|
|
}
|
|
createSha(login: string, email: string, password: string) {
|
|
let data = {
|
|
method: 'v?',
|
|
login: login,
|
|
email: email,
|
|
password: password,
|
|
};
|
|
console.log(`call users data=${JSON.stringify(data, null, 2)}`);
|
|
|
|
if (this.identificationVersion === 1) {
|
|
data.method = 'v1';
|
|
}
|
|
|
|
return new Promise((resolve, reject) => {
|
|
this.http
|
|
.requestJson({
|
|
server: 'karso',
|
|
endPoint: 'users',
|
|
requestType: HTTPRequestModel.POST,
|
|
accept: HTTPMimeType.JSON,
|
|
contentType: HTTPMimeType.JSON,
|
|
body: data,
|
|
})
|
|
.then((response: ModelResponseHttp) => {
|
|
// TODO: check type ...
|
|
console.log(`createSha : get some data to check: ${JSON.stringify(response.data)}`);
|
|
resolve(response.data);
|
|
})
|
|
.catch((error: any) => {
|
|
reject(`return ERROR ${JSON.stringify(error, null, 2)}`);
|
|
});
|
|
});
|
|
}
|
|
|
|
isAuthenticated(): boolean {
|
|
// return !!Session.userId;
|
|
return false;
|
|
}
|
|
isAuthorized(authorizedRoles: string): boolean {
|
|
/*
|
|
if (!angular.isArray(_authorizedRoles)) {
|
|
authorizedRoles = [_authorizedRoles];
|
|
}
|
|
return ( authService.isAuthenticated()
|
|
&& _authorizedRoles.indexOf(Session.userRole) !== -1
|
|
);
|
|
*/
|
|
return false;
|
|
}
|
|
}
|