Share credentials between app tabs
This commit is contained in:
@@ -13,16 +13,29 @@ export class AuthGuard {
|
|||||||
private router$: Router,
|
private router$: Router,
|
||||||
) {}
|
) {}
|
||||||
canActivate(): Observable<boolean | UrlTree> | Promise<boolean | UrlTree> | boolean | UrlTree {
|
canActivate(): Observable<boolean | UrlTree> | Promise<boolean | UrlTree> | boolean | UrlTree {
|
||||||
if (this.auth$.user && this.auth$.webCredentials) {
|
if (this.auth$.isAuthenticated()) {
|
||||||
if (this.loginUrl) {
|
if (this.loginUrl) {
|
||||||
this.router$.navigate([this.loginUrl]);
|
this.router$.navigate([this.loginUrl]);
|
||||||
this.loginUrl = null;
|
this.loginUrl = null;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
this.loginUrl = window.location.pathname;
|
console.log('Not auth try to wait');
|
||||||
this.router$.navigate(['']);
|
return this.tryWaitForAuthData();
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
async tryWaitForAuthData(): Promise<boolean> {
|
||||||
|
return new Promise((resolve) => {
|
||||||
|
setTimeout(() => {
|
||||||
|
if (this.auth$.isAuthenticated()) {
|
||||||
|
resolve(true);
|
||||||
|
} else {
|
||||||
|
console.log('GoToLogin');
|
||||||
|
this.loginUrl = window.location.pathname;
|
||||||
|
this.router$.navigate(['']);
|
||||||
|
resolve(false);
|
||||||
|
}
|
||||||
|
}, 100);
|
||||||
|
})
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -16,9 +16,14 @@ export class AuthService {
|
|||||||
user!: User;
|
user!: User;
|
||||||
apiTokenExpirationTime!: Moment;
|
apiTokenExpirationTime!: Moment;
|
||||||
|
|
||||||
|
bc!: BroadcastChannel;
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
private http$: HttpClient,
|
private http$: HttpClient,
|
||||||
) { }
|
) {
|
||||||
|
this.createBroadcastChannel();
|
||||||
|
this.askForAuthData();
|
||||||
|
}
|
||||||
|
|
||||||
ping() {
|
ping() {
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
@@ -64,4 +69,73 @@ export class AuthService {
|
|||||||
getAPITokenObservable(): Observable<void> {
|
getAPITokenObservable(): Observable<void> {
|
||||||
return from(this.getAPIToken());
|
return from(this.getAPIToken());
|
||||||
}
|
}
|
||||||
|
isAuthenticated(): boolean {
|
||||||
|
return !!this.apiToken &&
|
||||||
|
!!this.webCredentials &&
|
||||||
|
!!this.user &&
|
||||||
|
this.apiTokenExpirationTime.isAfter(moment());
|
||||||
|
}
|
||||||
|
// broadcastChannel
|
||||||
|
createBroadcastChannel() {
|
||||||
|
try {
|
||||||
|
this.bc = new BroadcastChannel('auth');
|
||||||
|
this.bc.onmessage = (event: MessageEvent<AuthMessage>) => {
|
||||||
|
this.broadcastListener(event);
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
console.log('eee', e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
broadcastListener(event: MessageEvent<AuthMessage>) {
|
||||||
|
switch (event.data.type) {
|
||||||
|
case BroadcastType.REQUEST_AUTH_DATA:
|
||||||
|
this.sendAuthData();
|
||||||
|
break;
|
||||||
|
case BroadcastType.SEND_AUTH_DATA:
|
||||||
|
this.recieveAuthData(event.data.data!);
|
||||||
|
break;
|
||||||
|
case BroadcastType.LOGOUT:
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
askForAuthData() {
|
||||||
|
this.bc.postMessage({
|
||||||
|
type: BroadcastType.REQUEST_AUTH_DATA
|
||||||
|
});
|
||||||
|
}
|
||||||
|
sendAuthData() {
|
||||||
|
this.bc.postMessage({
|
||||||
|
type: BroadcastType.SEND_AUTH_DATA,
|
||||||
|
data: {
|
||||||
|
webCredentials: this.webCredentials,
|
||||||
|
apiToken: this.apiToken,
|
||||||
|
apiTokenExpirationTime: this.apiTokenExpirationTime.toISOString()
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
recieveAuthData(data: AuthData) {
|
||||||
|
this.webCredentials = data.webCredentials;
|
||||||
|
this.apiToken = data.apiToken;
|
||||||
|
this.apiTokenExpirationTime = moment(data.apiTokenExpirationTime);
|
||||||
|
this.retrieveUserFromCredentials(this.webCredentials);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
enum BroadcastType {
|
||||||
|
REQUEST_AUTH_DATA = 'request',
|
||||||
|
SEND_AUTH_DATA = 'send',
|
||||||
|
LOGOUT = 'logout'
|
||||||
|
}
|
||||||
|
interface AuthData {
|
||||||
|
webCredentials: string,
|
||||||
|
apiToken: string,
|
||||||
|
apiTokenExpirationTime: string
|
||||||
|
}
|
||||||
|
interface AuthMessage {
|
||||||
|
sender: string,
|
||||||
|
type: BroadcastType,
|
||||||
|
data?: AuthData
|
||||||
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user