This commit is contained in:
Jovan Krunić
2026-09-17 17:56:15 +02:00
parent e3b6f14536
commit e0ef20e96c
3 changed files with 80 additions and 84 deletions
@@ -90,12 +90,18 @@ export class AuthHelperService {
key as keyof SCUserConfiguration;
user[userKey] = JSONPath({
path: this.userConfigurationMap[userKey] as string,
path:
this.userConfigurationMap[
userKey
] as string,
json: userInfo,
})[0];
}
if (user.givenName && user.familyName) {
if (
user.givenName &&
user.familyName
) {
user.name =
`${user.givenName} ${user.familyName}`;
}
@@ -103,7 +109,8 @@ export class AuthHelperService {
return user;
}
public async deleteOriginPath(): Promise<void> {
public async deleteOriginPath():
Promise<void> {
await this.storageProvider.delete(
AUTH_ORIGIN_PATH,
);
@@ -129,9 +136,11 @@ export class AuthHelperService {
}
}
public async endBrowserSession(): Promise<void> {
public async endBrowserSession():
Promise<void> {
const endSessionEndpoint =
await this.authService.getEndSessionEndpoint();
await this.authService
.getEndSessionEndpoint();
if (!endSessionEndpoint) {
return;
@@ -139,25 +148,41 @@ export class AuthHelperService {
const alert =
await this.alertController.create({
header: this.translateService.instant(
`${AUTH_MESSAGE_PREFIX}.log_out_alert.header`,
),
message: this.translateService.instant(
`${AUTH_MESSAGE_PREFIX}.log_out_alert.message`,
),
header:
this.translateService.instant(
`${AUTH_MESSAGE_PREFIX}.log_out_alert.header`,
),
message:
this.translateService.instant(
`${AUTH_MESSAGE_PREFIX}.log_out_alert.message`,
),
buttons: [
{
text:
this.translateService.instant('no'),
this.translateService.instant(
'no',
),
role: 'cancel',
cssClass: 'default',
},
{
text:
this.translateService.instant('yes'),
this.translateService.instant(
'yes',
),
role: 'confirm',
cssClass: 'preferred',
handler: () => {
this.browser.open(
handler: async () => {
/*
* Only now, after explicit confirmation,
* open the IdP end-session endpoint.
*/
await this.browser.open(
endSessionEndpoint,
);
},
@@ -53,7 +53,6 @@ import {
} from './auth.provider.methods';
import {requestorFactory} from './factories/requestor.factory';
import {storageFactory} from './factories/storage.factory';
import {SimpleBrowser} from '../../util/browser.factory';
const TOKEN_RESPONSE_KEY = 'token_response';
const AUTH_EXPIRY_BUFFER = -5 * 60;
@@ -184,7 +183,6 @@ export class AuthService {
constructor(
private readonly platform: Platform,
private readonly configProvider: ConfigProvider,
private readonly browser: SimpleBrowser,
) {
this.storage =
storageFactory(platform);
@@ -420,12 +418,9 @@ export class AuthService {
}
public async signOut(
state?: string,
_state?: string,
revokeTokens = false,
): Promise<void> {
const currentToken =
this.tokenSubject.value;
try {
if (revokeTokens) {
await this.revokeTokens();
@@ -435,23 +430,17 @@ export class AuthService {
TOKEN_RESPONSE_KEY,
);
const endSessionEndpoint =
await this.getEndSessionEndpoint();
if (
endSessionEndpoint &&
currentToken
) {
await this.performEndSessionRequest(
endSessionEndpoint,
currentToken,
state,
);
return;
}
await this.internalEndSessionCallback();
/*
* Local logout only.
*
* The optional logout from the identity provider is
* deliberately handled by AuthHelperService after the
* confirmation dialog.
*/
this.notify({
action:
AuthActions.SignOutSuccess,
});
} catch (error) {
this.notify({
action:
@@ -886,43 +875,6 @@ export class AuthService {
.completeAuthorizationRequestIfPossible();
}
private async performEndSessionRequest(
endpoint: string,
token: TokenResponse,
state?: string,
): Promise<void> {
const url =
new URL(endpoint);
if (token.idToken) {
url.searchParams.set(
'id_token_hint',
token.idToken,
);
}
if (
this.authConfig
.end_session_redirect_url
) {
url.searchParams.set(
'post_logout_redirect_uri',
this.authConfig
.end_session_redirect_url,
);
}
if (state) {
url.searchParams.set(
'state',
state,
);
}
await this.browser.open(
url.toString(),
);
}
private async internalEndSessionCallback():
Promise<void> {
@@ -1,5 +1,5 @@
/*
* Copyright (C) 2023 StApps
* Copyright (C) 2022 StApps
* This program is free software: you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the Free
* Software Foundation, version 3.
@@ -12,12 +12,14 @@
* You should have received a copy of the GNU General Public License along with
* this program. If not, see <https://www.gnu.org/licenses/>.
*/
import {Component} from '@angular/core';
import {AuthHelperService} from '../../auth/auth-helper.service';
import {ActivatedRoute} from '@angular/router';
import {AuthHelperService} from '../../auth/auth-helper.service';
import {AuthService} from '../../auth/auth.service';
import {ScheduleProvider} from '../../calendar/schedule.provider';
import {profilePageSections} from '../../../../config/profile-page-sections';
import {AuthService} from '../../auth/auth.service';
@Component({
selector: 'app-home',
@@ -34,23 +36,40 @@ export class ProfilePageComponent {
readonly scheduleProvider: ScheduleProvider,
) {}
async signIn() {
const originPath = this.activatedRoute.snapshot.queryParamMap.get('origin_path');
async signIn(): Promise<void> {
const originPath =
this.activatedRoute.snapshot
.queryParamMap
.get('origin_path');
await (
originPath
? this.authHelper.setOriginPath(originPath)
: this.authHelper.deleteOriginPath()
? this.authHelper
.setOriginPath(originPath)
: this.authHelper
.deleteOriginPath()
);
await this.authService.signIn();
}
async signOut() {
async signOut(): Promise<void> {
/*
* First log out locally.
*/
await this.authService.signOut();
/*
* Then ask whether the user also wants to terminate
* the session at the identity provider.
*
* The IdP end-session endpoint is opened only if
* the user confirms with "Yes".
*/
await this.authHelper.endBrowserSession();
}
ionViewWillEnter() {
ionViewWillEnter(): void {
void this.authService.loadUserInfo();
}
}