chat interceptor added

This commit is contained in:
Eudes Inácio
2024-03-06 15:20:35 +01:00
parent d4c20457a2
commit af5d428134
4 changed files with 152 additions and 182 deletions
+3 -2
View File
@@ -87,7 +87,7 @@ import { LoggingInterceptorService } from './services/logging-interceptor.servic
import { PopupQuestionPipe } from './modals/popup-question.pipe'; import { PopupQuestionPipe } from './modals/popup-question.pipe';
import '@teamhive/capacitor-video-recorder'; import '@teamhive/capacitor-video-recorder';
import { tokenInterceptor } from './interceptors/token.interceptors'; import { tokenInterceptor } from './interceptors/token.interceptors';
import { ChatTokenInterceptor } from './interceptors/chatToken.interceptor'; import { chatTokenInterceptor } from './interceptors/chatToken.interceptor';
import { InputFilterDirective } from './services/directives/input-filter.directive'; import { InputFilterDirective } from './services/directives/input-filter.directive';
import { VisibilityDirective } from './services/directives/visibility.directive'; import { VisibilityDirective } from './services/directives/visibility.directive';
@@ -217,8 +217,9 @@ import { FirebaseX } from '@ionic-native/firebase-x/ngx'; */
DocumentViewer, DocumentViewer,
FFMpeg, FFMpeg,
{ provide: HTTP_INTERCEPTORS, useClass: LoggingInterceptorService, multi: true }, { provide: HTTP_INTERCEPTORS, useClass: LoggingInterceptorService, multi: true },
chatTokenInterceptor,
tokenInterceptor, tokenInterceptor,
/* ChatTokenInterceptor */
], ],
bootstrap: [AppComponent], bootstrap: [AppComponent],
+133 -113
View File
@@ -1,12 +1,12 @@
import { Injectable } from '@angular/core'; import { Injectable } from '@angular/core';
import { import {
HttpInterceptor, HttpInterceptor,
HttpRequest, HttpRequest,
HttpHandler, HttpHandler,
HttpEvent, HttpEvent,
HttpErrorResponse, HttpErrorResponse,
HTTP_INTERCEPTORS, HTTP_INTERCEPTORS,
HttpHeaders, HttpHeaders,
} from '@angular/common/http'; } from '@angular/common/http';
import { Observable, throwError, BehaviorSubject } from 'rxjs'; import { Observable, throwError, BehaviorSubject } from 'rxjs';
import { catchError, switchMap, filter, take } from 'rxjs/operators'; import { catchError, switchMap, filter, take } from 'rxjs/operators';
@@ -15,138 +15,158 @@ import { Router } from '@angular/router';
import { SessionStore } from '../store/session.service'; import { SessionStore } from '../store/session.service';
import { environment } from "src/environments/environment"; import { environment } from "src/environments/environment";
import { PermissionService } from '../services/permission.service'; import { PermissionService } from '../services/permission.service';
import { NetworkServiceService , ConnectionStatus} from 'src/app/services/network-service.service'; import { NetworkServiceService, ConnectionStatus } from 'src/app/services/network-service.service';
import { RochetChatConnectorService } from 'src/app/services/chat/rochet-chat-connector.service'; import { RochetChatConnectorService } from 'src/app/services/chat/rochet-chat-connector.service';
@Injectable() @Injectable()
export class ChatTokenInterceptor implements HttpInterceptor { export class ChatTokenInterceptor implements HttpInterceptor {
private isRefreshing = false; private isRefreshing = false;
headers: HttpHeaders; headers: HttpHeaders;
options: any; options: any;
private refreshTokenSubject: BehaviorSubject<any> = new BehaviorSubject<any>( private refreshChatTokenSubject: BehaviorSubject<any> = new BehaviorSubject<any>(
null null
);
private excludedDomain = 'https://gdchat-dev.dyndns.info';// Add other domains as needed
constructor(private http: HttpClient, private router: Router,private p: PermissionService,private NetworkServiceService: NetworkServiceService,
private RochetChatConnectorService: RochetChatConnectorService) {}
intercept(
request: HttpRequest<any>,
next: HttpHandler
): Observable<HttpEvent<any>> {
if (this.shouldExcludeDomain(request)) {
return next.handle(request);
}
return next.handle(request).pipe(
catchError((error) => {
if (error instanceof HttpErrorResponse && error.status === 401) {
return this.handle401Error(request, next);
} else {
return throwError(error);
}
})
); );
}
private shouldExcludeDomain(request: HttpRequest<any>): boolean { private excludedDomains = ['Login',environment.apiURL];// Add other domains as needed
const url = request.url.toLowerCase();
return !url.includes(this.excludedDomain.toLowerCase());
}
private handle401Error( constructor(private http: HttpClient, private router: Router, private p: PermissionService, private NetworkServiceService: NetworkServiceService,
request: HttpRequest<any>, private RochetChatConnectorService: RochetChatConnectorService) { }
next: HttpHandler
): Observable<HttpEvent<any>> {
if (!this.isRefreshing) {
this.isRefreshing = true;
this.refreshTokenSubject.next(null);
return this.refreshToken().pipe( intercept(
switchMap((token: any) => { request: HttpRequest<any>,
this.isRefreshing = false; next: HttpHandler
): Observable<HttpEvent<any>> {
if (this.shouldExcludeDomain(request)) {
return next.handle(request);
}
let data = { if (SessionStore.user.Authorization) {
status: token['status'], request = this.addToken(request, SessionStore.user.Authorization);
data: {
userId: token['data'].userId,
authToken: token['data'].authToken
}
} }
SessionStore.user.ChatData = data
SessionStore.save()
this.setheader()
return next.handle(request).pipe(
catchError((error) => {
this.refreshTokenSubject.next(token.Authorization); if (error instanceof HttpErrorResponse && error.status === 401) {
return next.handle(this.addToken(request, token.Authorization)); return this.handle401Error(request, next);
}) } else {
); return throwError(error);
} else { }
return this.refreshTokenSubject.pipe( })
filter((token) => token != null), );
take(1),
switchMap((jwt) => {
return next.handle(this.addToken(request, jwt));
})
);
} }
}
private addToken(request: HttpRequest<any>, token: string) { private shouldExcludeDomain(request: HttpRequest<any>): boolean {
return request.clone({ const url = request.url.toLowerCase();
/* setHeaders: { return this.excludedDomains.some((domain) => url.includes(domain.toLowerCase()));
Authorization: `Bearer ${token}`, }
}, */
});
}
private refreshToken(): Observable<any> { private handle401Error(
return this.http request: HttpRequest<any>,
.get<any>(environment.apiURL + 'UserAuthentication/RegenereChatToken', { next: HttpHandler
/* refreshToken: SessionStore.user.RefreshToken, */ ): Observable<HttpEvent<any>> {
}) if (!this.isRefreshing) {
.pipe( this.isRefreshing = true;
catchError((error) => { this.refreshChatTokenSubject.next(null);
// Handle token refresh failure
console.log('ChatToken refresh failed:', error); return this.refreshToken().pipe(
return throwError(error); switchMap((token: any) => {
}) this.isRefreshing = false;
);
} let data = {
status: token['status'],
data: {
userId: token['data'].userId,
authToken: token['data'].authToken
}
}
SessionStore.user.ChatData = data
SessionStore.save()
/* this.setheader() */
setheader() { this.refreshChatTokenSubject.next(token.Authorization);
try { return next.handle(this.addToken(request, token.Authorization));
})
);
} else {
return this.refreshChatTokenSubject.pipe(
filter((token) => token != null),
take(1),
switchMap((jwt) => {
return next.handle(this.addToken(request, jwt));
})
);
}
}
if (this.p.userPermission(this.p.permissionList.Chat.access) && SessionStore.user.ChatData) { private addToken(request: HttpRequest<any>, token: string) {
this.headers = new HttpHeaders();; let headers = new HttpHeaders();
if (this.p.userPermission(this.p.permissionList.Chat.access)) {
// console.log('X-User-Id', SessionStore.user.ChatData.data.userId)
this.headers = this.headers.set('X-User-Id', SessionStore.user.ChatData.data.userId); console.log('X-Auth-Token', SessionStore.user.ChatData.data.authToken)
this.headers = this.headers.set('X-Auth-Token', SessionStore.user.ChatData.data.authToken); headers = headers.set('X-User-Id', SessionStore.user.ChatData.data.userId);
this.options = { headers = headers.set('X-Auth-Token', SessionStore.user.ChatData.data.authToken);
headers: this.headers,
}; return request.clone({
setHeaders: {
Authorization: `Bearer ${token}`,
...headers.keys().reduce((acc, key) => ({ ...acc, [key]: headers.get(key) }), {}),
},
});
}
/* private addToken(request: HttpRequest<any>, token: string) {
return request.clone({
setHeaders: {
Authorization: `Bearer ${token}`,
},
});
} */
private refreshToken(): Observable<any> {
return this.http
.get<any>(environment.apiURL + 'UserAuthentication/RegenereChatToken', {
/* refreshToken: SessionStore.user.RefreshToken, */
})
.pipe(
catchError((error) => {
// Handle token refresh failure
console.log('ChatToken refresh failed:', error);
return throwError(error);
})
);
}
setheader() {
try {
if (this.p.userPermission(this.p.permissionList.Chat.access) && SessionStore.user.ChatData) {
this.headers = new HttpHeaders();;
if (this.p.userPermission(this.p.permissionList.Chat.access)) {
//
this.headers = this.headers.set('X-User-Id', SessionStore.user.ChatData.data.userId);
this.headers = this.headers.set('X-Auth-Token', SessionStore.user.ChatData.data.authToken);
this.options = {
headers: this.headers,
};
}
}
} catch (error) {
} }
}
} catch (error) {
} }
}
} }
export const tokenInterceptor = { export const chatTokenInterceptor = {
provide: HTTP_INTERCEPTORS, provide: HTTP_INTERCEPTORS,
useClass: ChatTokenInterceptor, useClass: ChatTokenInterceptor,
multi: true multi: true
}; };
+6 -2
View File
@@ -119,9 +119,13 @@ export class TokenInterceptor implements HttpInterceptor {
if (environment.production) { if (environment.production) {
window.location.pathname = '/auth' window.location.pathname = '/auth'
} else { } else {
/* const pathBeforeGoOut = window.location.pathname */ const pathBeforeGoOut = window.location.pathname
console.log('Before auth',window.location.pathname)
this.router.navigateByUrl('/auth', { replaceUrl: true }).then(() =>{ this.router.navigateByUrl('/auth', { replaceUrl: true }).then(() =>{
this.httpErrorHandle.httpsSucessMessagge('sessonExpired') if(pathBeforeGoOut != "/auth") {
this.httpErrorHandle.httpsSucessMessagge('sessonExpired')
}
}) })
} }
return of(false); return of(false);
-55
View File
@@ -392,61 +392,6 @@ export class ChatService {
async refreshtoken() { async refreshtoken() {
if(this.headers && SessionStore.user.ChatData) {
this.headers = this.headers.set('Authorization', 'Bearer ' + SessionStore.user.Authorization);
let options = {
headers: this.headers
};
try {
let res = await this.http.get(environment.apiURL + 'UserAuthentication/RegenereChatToken', options).toPromise();
let data = {
status: res['status'],
data: {
userId: res['data'].userId,
authToken: res['data'].authToken
}
}
SessionStore.user.ChatData = data
SessionStore.save()
this.setheader()
this.timerEventTriggerDateLastUpdate = new Date();
} catch (error) {
if(this.NetworkServiceService.getCurrentNetworkStatus() == ConnectionStatus.Offline) {
this.RochetChatConnectorService.registerCallback({
requestId: 'refreshtoken',
type: 'reConnect',
funx: async () => {
this.resetTimer();
await this.refreshtoken();
return true
}
})
} else {
if(SessionStore.user.Authorization != '') {
setTimeout(async () => {
this.resetTimer();
await this.refreshtoken();
}, 60000)
}
}
}
} else if(!SessionStore.user.ChatData) {
// do nothing
} else if (!this.headers) {
this.setheader()
this.refreshtoken()
}
} }