@abp/ng.oauth 9.3.6 → 10.0.0-rc.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/fesm2022/abp-ng.oauth.mjs +305 -89
- package/fesm2022/abp-ng.oauth.mjs.map +1 -1
- package/index.d.ts +50 -10
- package/package.json +3 -3
|
@@ -1,13 +1,12 @@
|
|
|
1
1
|
import * as i0 from '@angular/core';
|
|
2
|
-
import { inject, Injectable, Inject, signal, provideAppInitializer, makeEnvironmentProviders, NgModule } from '@angular/core';
|
|
3
|
-
import
|
|
4
|
-
import { EnvironmentService, NAVIGATE_TO_MANAGE_PROFILE, AuthService, CORE_OPTIONS, IS_EXTERNAL_REQUEST, TENANT_KEY, AbpLocalStorageService, ConfigStateService, HttpErrorReporterService, SessionStateService, AbpWindowService, noop, AbstractAuthErrorFilter, AuthGuard, authGuard, ApiInterceptor, PIPE_TO_LOGIN_FN_KEY, CHECK_AUTHENTICATION_STATE_FN_KEY, AuthErrorFilterService } from '@abp/ng.core';
|
|
2
|
+
import { inject, Injectable, PLATFORM_ID, RESPONSE_INIT, REQUEST, Optional, Inject, DOCUMENT, Injector, signal, provideAppInitializer, makeEnvironmentProviders, NgModule } from '@angular/core';
|
|
3
|
+
import { EnvironmentService, NAVIGATE_TO_MANAGE_PROFILE, AuthService, CORE_OPTIONS, SessionStateService, HttpWaitService, TENANT_KEY, IS_EXTERNAL_REQUEST, APP_STARTED_WITH_SSR, AbpLocalStorageService, AbpCookieStorageService, ConfigStateService, HttpErrorReporterService, AbpWindowService, noop, AbstractAuthErrorFilter, AuthGuard, authGuard, asyncAuthGuard, ApiInterceptor, PIPE_TO_LOGIN_FN_KEY, CHECK_AUTHENTICATION_STATE_FN_KEY, AuthErrorFilterService } from '@abp/ng.core';
|
|
5
4
|
import { HttpHeaders, HTTP_INTERCEPTORS } from '@angular/common/http';
|
|
6
|
-
import
|
|
7
|
-
import {
|
|
5
|
+
import { OAuthService, OAuthStorage, OAuthErrorEvent, OAuthInfoEvent, OAuthModule } from 'angular-oauth2-oidc';
|
|
6
|
+
import { firstValueFrom, timer, map, filter, take, timeout, catchError, of, pipe, tap as tap$1, from, lastValueFrom, EMPTY } from 'rxjs';
|
|
7
|
+
import { isPlatformServer, isPlatformBrowser } from '@angular/common';
|
|
8
8
|
import compare from 'just-compare';
|
|
9
|
-
import { map, filter, finalize, switchMap, tap, take } from 'rxjs/operators';
|
|
10
|
-
import { pipe, of, filter as filter$1, tap as tap$1, take as take$1, from, lastValueFrom, EMPTY } from 'rxjs';
|
|
9
|
+
import { map as map$1, filter as filter$1, finalize, switchMap, tap, take as take$1 } from 'rxjs/operators';
|
|
11
10
|
import { Router } from '@angular/router';
|
|
12
11
|
|
|
13
12
|
const NavigateToManageProfileProvider = {
|
|
@@ -56,31 +55,84 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.0.7", ngImpor
|
|
|
56
55
|
const abpOAuthGuard = (route, state) => {
|
|
57
56
|
const oAuthService = inject(OAuthService);
|
|
58
57
|
const authService = inject(AuthService);
|
|
58
|
+
const platformId = inject(PLATFORM_ID);
|
|
59
|
+
const resInit = inject(RESPONSE_INIT);
|
|
60
|
+
const environmentService = inject(EnvironmentService);
|
|
59
61
|
const hasValidAccessToken = oAuthService.hasValidAccessToken();
|
|
60
62
|
if (hasValidAccessToken) {
|
|
61
63
|
return true;
|
|
62
64
|
}
|
|
63
65
|
const params = { returnUrl: state.url };
|
|
66
|
+
if (isPlatformServer(platformId) && resInit) {
|
|
67
|
+
const ssrAuthorizationUrl = environmentService.getEnvironment().oAuthConfig.ssrAuthorizationUrl;
|
|
68
|
+
const url = buildLoginUrl(ssrAuthorizationUrl, params);
|
|
69
|
+
const headers = new Headers(resInit.headers);
|
|
70
|
+
headers.set('Location', url);
|
|
71
|
+
resInit.status = 302;
|
|
72
|
+
resInit.statusText = 'Found';
|
|
73
|
+
resInit.headers = headers;
|
|
74
|
+
return;
|
|
75
|
+
}
|
|
64
76
|
authService.navigateToLogin(params);
|
|
65
77
|
return false;
|
|
66
78
|
};
|
|
79
|
+
const buildLoginUrl = (path, params) => {
|
|
80
|
+
if (!params || Object.keys(params).length === 0)
|
|
81
|
+
return path;
|
|
82
|
+
const usp = new URLSearchParams();
|
|
83
|
+
for (const [k, v] of Object.entries(params)) {
|
|
84
|
+
if (v == null)
|
|
85
|
+
continue;
|
|
86
|
+
Array.isArray(v) ? v.forEach(x => usp.append(k, String(x))) : usp.set(k, String(v));
|
|
87
|
+
}
|
|
88
|
+
return `${path}?${usp.toString()}`;
|
|
89
|
+
};
|
|
90
|
+
const asyncAbpOAuthGuard = (route, state) => {
|
|
91
|
+
const oAuthService = inject(OAuthService);
|
|
92
|
+
const authService = inject(AuthService);
|
|
93
|
+
const environmentService = inject(EnvironmentService);
|
|
94
|
+
const platformId = inject(PLATFORM_ID);
|
|
95
|
+
const resInit = inject(RESPONSE_INIT);
|
|
96
|
+
const { oAuthConfig } = environmentService.getEnvironment();
|
|
97
|
+
if (oAuthConfig?.responseType === 'code') {
|
|
98
|
+
return firstValueFrom(timer(0, 100).pipe(map(() => oAuthService.hasValidAccessToken()), filter(Boolean), take(1), timeout(3000), catchError(() => {
|
|
99
|
+
if (isPlatformServer(platformId) && resInit) {
|
|
100
|
+
const ssrAuthorizationUrl = environmentService.getEnvironment().oAuthConfig.ssrAuthorizationUrl;
|
|
101
|
+
const url = buildLoginUrl(ssrAuthorizationUrl, { returnUrl: state.url });
|
|
102
|
+
const headers = new Headers(resInit.headers);
|
|
103
|
+
headers.set('Location', url);
|
|
104
|
+
resInit.status = 302;
|
|
105
|
+
resInit.statusText = 'Found';
|
|
106
|
+
resInit.headers = headers;
|
|
107
|
+
return;
|
|
108
|
+
}
|
|
109
|
+
authService.navigateToLogin({ returnUrl: state.url });
|
|
110
|
+
return of(false);
|
|
111
|
+
})));
|
|
112
|
+
}
|
|
113
|
+
if (oAuthService.hasValidAccessToken()) {
|
|
114
|
+
return true;
|
|
115
|
+
}
|
|
116
|
+
authService.navigateToLogin({ returnUrl: state.url });
|
|
117
|
+
return false;
|
|
118
|
+
};
|
|
67
119
|
|
|
68
120
|
class OAuthConfigurationHandler {
|
|
69
|
-
constructor(
|
|
70
|
-
this.oAuthService =
|
|
71
|
-
this.environmentService =
|
|
72
|
-
this.options =
|
|
121
|
+
constructor() {
|
|
122
|
+
this.oAuthService = inject(OAuthService);
|
|
123
|
+
this.environmentService = inject(EnvironmentService);
|
|
124
|
+
this.options = inject(CORE_OPTIONS);
|
|
73
125
|
this.listenToSetEnvironment();
|
|
74
126
|
}
|
|
75
127
|
listenToSetEnvironment() {
|
|
76
128
|
this.environmentService
|
|
77
129
|
.createOnUpdateStream(state => state)
|
|
78
|
-
.pipe(map(environment => environment.oAuthConfig), filter(config => !compare(config, this.options.environment.oAuthConfig)))
|
|
130
|
+
.pipe(map$1(environment => environment.oAuthConfig), filter$1(config => !compare(config, this.options.environment.oAuthConfig)))
|
|
79
131
|
.subscribe((config) => {
|
|
80
132
|
this.oAuthService.configure(config);
|
|
81
133
|
});
|
|
82
134
|
}
|
|
83
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: OAuthConfigurationHandler, deps: [
|
|
135
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: OAuthConfigurationHandler, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
|
|
84
136
|
static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: OAuthConfigurationHandler, providedIn: 'root' }); }
|
|
85
137
|
}
|
|
86
138
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: OAuthConfigurationHandler, decorators: [{
|
|
@@ -88,17 +140,14 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.0.7", ngImpor
|
|
|
88
140
|
args: [{
|
|
89
141
|
providedIn: 'root',
|
|
90
142
|
}]
|
|
91
|
-
}], ctorParameters: () => [
|
|
92
|
-
type: Inject,
|
|
93
|
-
args: [CORE_OPTIONS]
|
|
94
|
-
}] }] });
|
|
143
|
+
}], ctorParameters: () => [] });
|
|
95
144
|
|
|
96
145
|
class OAuthApiInterceptor {
|
|
97
|
-
constructor(
|
|
98
|
-
this.oAuthService =
|
|
99
|
-
this.sessionState =
|
|
100
|
-
this.httpWaitService =
|
|
101
|
-
this.tenantKey =
|
|
146
|
+
constructor() {
|
|
147
|
+
this.oAuthService = inject(OAuthService);
|
|
148
|
+
this.sessionState = inject(SessionStateService);
|
|
149
|
+
this.httpWaitService = inject(HttpWaitService);
|
|
150
|
+
this.tenantKey = inject(TENANT_KEY);
|
|
102
151
|
}
|
|
103
152
|
intercept(request, next) {
|
|
104
153
|
this.httpWaitService.addRequest(request);
|
|
@@ -129,7 +178,7 @@ class OAuthApiInterceptor {
|
|
|
129
178
|
headers['X-Requested-With'] = 'XMLHttpRequest';
|
|
130
179
|
return headers;
|
|
131
180
|
}
|
|
132
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: OAuthApiInterceptor, deps: [
|
|
181
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: OAuthApiInterceptor, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
|
|
133
182
|
static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: OAuthApiInterceptor, providedIn: 'root' }); }
|
|
134
183
|
}
|
|
135
184
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: OAuthApiInterceptor, decorators: [{
|
|
@@ -137,14 +186,10 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.0.7", ngImpor
|
|
|
137
186
|
args: [{
|
|
138
187
|
providedIn: 'root',
|
|
139
188
|
}]
|
|
140
|
-
}]
|
|
141
|
-
type: Inject,
|
|
142
|
-
args: [TENANT_KEY]
|
|
143
|
-
}] }] });
|
|
144
|
-
|
|
145
|
-
const oAuthStorage = localStorage;
|
|
189
|
+
}] });
|
|
146
190
|
|
|
147
|
-
function clearOAuthStorage(
|
|
191
|
+
function clearOAuthStorage(injector) {
|
|
192
|
+
const storage = injector.get(OAuthStorage);
|
|
148
193
|
const keys = [
|
|
149
194
|
'access_token',
|
|
150
195
|
'id_token',
|
|
@@ -162,27 +207,109 @@ function clearOAuthStorage(storage = oAuthStorage) {
|
|
|
162
207
|
keys.forEach(key => storage.removeItem(key));
|
|
163
208
|
}
|
|
164
209
|
|
|
165
|
-
|
|
166
|
-
|
|
210
|
+
class ServerTokenStorageService {
|
|
211
|
+
constructor(req) {
|
|
212
|
+
this.req = req;
|
|
213
|
+
this.cookies = new Map();
|
|
214
|
+
const cookieHeader = this.req?.headers.get('cookie') ?? '';
|
|
215
|
+
for (const part of cookieHeader.split(';')) {
|
|
216
|
+
const i = part.indexOf('=');
|
|
217
|
+
if (i > -1) {
|
|
218
|
+
const k = part.slice(0, i).trim();
|
|
219
|
+
const v = decodeURIComponent(part.slice(i + 1).trim());
|
|
220
|
+
this.cookies.set(k, v);
|
|
221
|
+
}
|
|
222
|
+
}
|
|
223
|
+
}
|
|
224
|
+
getItem(key) {
|
|
225
|
+
const fromCookie = this.cookies.get(key);
|
|
226
|
+
if (fromCookie) {
|
|
227
|
+
return fromCookie;
|
|
228
|
+
}
|
|
229
|
+
return '';
|
|
230
|
+
}
|
|
231
|
+
setItem(_k, _v) { }
|
|
232
|
+
removeItem(_k) { }
|
|
233
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: ServerTokenStorageService, deps: [{ token: REQUEST, optional: true }], target: i0.ɵɵFactoryTarget.Injectable }); }
|
|
234
|
+
static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: ServerTokenStorageService, providedIn: null }); }
|
|
235
|
+
}
|
|
236
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: ServerTokenStorageService, decorators: [{
|
|
237
|
+
type: Injectable,
|
|
238
|
+
args: [{ providedIn: null }]
|
|
239
|
+
}], ctorParameters: () => [{ type: Request, decorators: [{
|
|
240
|
+
type: Optional
|
|
241
|
+
}, {
|
|
242
|
+
type: Inject,
|
|
243
|
+
args: [REQUEST]
|
|
244
|
+
}] }] });
|
|
245
|
+
|
|
246
|
+
class MockStorage {
|
|
247
|
+
constructor() {
|
|
248
|
+
this.data = new Map();
|
|
249
|
+
}
|
|
250
|
+
get length() {
|
|
251
|
+
return this.data.size;
|
|
252
|
+
}
|
|
253
|
+
clear() {
|
|
254
|
+
this.data.clear();
|
|
255
|
+
}
|
|
256
|
+
getItem(key) {
|
|
257
|
+
return this.data.get(key) || null;
|
|
258
|
+
}
|
|
259
|
+
key(index) {
|
|
260
|
+
return Array.from(this.data.keys())[index] || null;
|
|
261
|
+
}
|
|
262
|
+
removeItem(key) {
|
|
263
|
+
this.data.delete(key);
|
|
264
|
+
}
|
|
265
|
+
setItem(key, value) {
|
|
266
|
+
this.data.set(key, value);
|
|
267
|
+
}
|
|
268
|
+
}
|
|
269
|
+
function oAuthStorageFactory() {
|
|
270
|
+
const platformId = inject(PLATFORM_ID);
|
|
271
|
+
const appStartedWithSSR = inject(APP_STARTED_WITH_SSR);
|
|
272
|
+
if (appStartedWithSSR) {
|
|
273
|
+
return isPlatformBrowser(platformId)
|
|
274
|
+
? inject(BrowserTokenStorageService)
|
|
275
|
+
: inject(ServerTokenStorageService);
|
|
276
|
+
}
|
|
277
|
+
return inject(AbpLocalStorageService);
|
|
167
278
|
}
|
|
168
279
|
|
|
169
280
|
class RememberMeService {
|
|
170
281
|
constructor() {
|
|
171
282
|
this.#rememberMe = 'remember_me';
|
|
172
283
|
this.localStorageService = inject(AbpLocalStorageService);
|
|
284
|
+
this.cookieStorageService = inject(AbpCookieStorageService);
|
|
285
|
+
this.appStartedWithSsr = inject(APP_STARTED_WITH_SSR, { optional: true });
|
|
173
286
|
}
|
|
174
287
|
#rememberMe;
|
|
175
288
|
set(remember) {
|
|
289
|
+
if (this.appStartedWithSsr) {
|
|
290
|
+
this.cookieStorageService.setItem(this.#rememberMe, JSON.stringify(remember));
|
|
291
|
+
return;
|
|
292
|
+
}
|
|
176
293
|
this.localStorageService.setItem(this.#rememberMe, JSON.stringify(remember));
|
|
177
294
|
}
|
|
178
295
|
remove() {
|
|
296
|
+
if (this.appStartedWithSsr) {
|
|
297
|
+
this.cookieStorageService.removeItem(this.#rememberMe);
|
|
298
|
+
return;
|
|
299
|
+
}
|
|
179
300
|
this.localStorageService.removeItem(this.#rememberMe);
|
|
180
301
|
}
|
|
181
302
|
get() {
|
|
303
|
+
if (this.appStartedWithSsr) {
|
|
304
|
+
return Boolean(JSON.parse(this.cookieStorageService.getItem(this.#rememberMe) || 'false'));
|
|
305
|
+
}
|
|
182
306
|
return Boolean(JSON.parse(this.localStorageService.getItem(this.#rememberMe) || 'false'));
|
|
183
307
|
}
|
|
184
308
|
getFromToken(accessToken) {
|
|
185
|
-
|
|
309
|
+
let tokenBody = accessToken.split('.')[1].replace(/-/g, '+').replace(/_/g, '/');
|
|
310
|
+
while (tokenBody.length % 4 !== 0) {
|
|
311
|
+
tokenBody += '=';
|
|
312
|
+
}
|
|
186
313
|
try {
|
|
187
314
|
const parsedToken = JSON.parse(atob(tokenBody));
|
|
188
315
|
return Boolean(parsedToken[this.#rememberMe]);
|
|
@@ -224,7 +351,7 @@ const checkAccessToken = function (injector) {
|
|
|
224
351
|
const configState = injector.get(ConfigStateService);
|
|
225
352
|
const oAuth = injector.get(OAuthService);
|
|
226
353
|
if (oAuth.hasValidAccessToken() && !configState.getDeep('currentUser.id')) {
|
|
227
|
-
clearOAuthStorage();
|
|
354
|
+
clearOAuthStorage(this.injector);
|
|
228
355
|
}
|
|
229
356
|
};
|
|
230
357
|
|
|
@@ -251,13 +378,13 @@ class AuthFlowStrategy {
|
|
|
251
378
|
}
|
|
252
379
|
async init() {
|
|
253
380
|
if (this.oAuthConfig.clientId) {
|
|
254
|
-
const shouldClear = shouldStorageClear(this.oAuthConfig.clientId,
|
|
381
|
+
const shouldClear = shouldStorageClear(this.oAuthConfig.clientId, this.injector);
|
|
255
382
|
if (shouldClear)
|
|
256
|
-
clearOAuthStorage(
|
|
383
|
+
clearOAuthStorage(this.injector);
|
|
257
384
|
}
|
|
258
385
|
this.oAuthService.configure(this.oAuthConfig);
|
|
259
386
|
this.oAuthService.events
|
|
260
|
-
.pipe(filter(event => event.type === 'token_refresh_error'))
|
|
387
|
+
.pipe(filter$1(event => event.type === 'token_refresh_error'))
|
|
261
388
|
.subscribe(() => this.navigateToLogin());
|
|
262
389
|
this.navigateToPreviousUrl();
|
|
263
390
|
return this.oAuthService
|
|
@@ -275,31 +402,32 @@ class AuthFlowStrategy {
|
|
|
275
402
|
const { responseType } = this.oAuthConfig;
|
|
276
403
|
if (responseType === 'code') {
|
|
277
404
|
this.oAuthService.events
|
|
278
|
-
.pipe(filter(event => event.type === 'token_received' && !!this.oAuthService.state), take(1), map(() => {
|
|
405
|
+
.pipe(filter$1(event => event.type === 'token_received' && !!this.oAuthService.state), take$1(1), map$1(() => {
|
|
279
406
|
const redirectUri = decodeURIComponent(this.oAuthService.state);
|
|
280
407
|
if (redirectUri && redirectUri !== '/') {
|
|
281
408
|
return redirectUri;
|
|
282
409
|
}
|
|
283
410
|
return '/';
|
|
284
|
-
}), switchMap(redirectUri => this.configState.getOne$('currentUser').pipe(filter(user => !!user?.isAuthenticated), tap(() => this.router.navigateByUrl(redirectUri)))))
|
|
411
|
+
}), switchMap(redirectUri => this.configState.getOne$('currentUser').pipe(filter$1(user => !!user?.isAuthenticated), tap(() => this.router.navigateByUrl(redirectUri)))))
|
|
285
412
|
.subscribe();
|
|
286
413
|
}
|
|
287
414
|
}
|
|
288
415
|
refreshToken() {
|
|
289
|
-
return this.oAuthService.refreshToken().catch(() => clearOAuthStorage());
|
|
416
|
+
return this.oAuthService.refreshToken().catch(() => clearOAuthStorage(this.injector));
|
|
290
417
|
}
|
|
291
418
|
listenToOauthErrors() {
|
|
292
419
|
this.oAuthService.events
|
|
293
|
-
.pipe(filter(event => event instanceof OAuthErrorEvent), tap((err) => {
|
|
420
|
+
.pipe(filter$1(event => event instanceof OAuthErrorEvent), tap((err) => {
|
|
294
421
|
const shouldSkip = this.oAuthErrorFilterService.run(err);
|
|
295
422
|
if (!shouldSkip) {
|
|
296
|
-
clearOAuthStorage();
|
|
423
|
+
clearOAuthStorage(this.injector);
|
|
297
424
|
}
|
|
298
425
|
}), switchMap(() => this.configState.refreshAppState()))
|
|
299
426
|
.subscribe();
|
|
300
427
|
}
|
|
301
428
|
}
|
|
302
|
-
function shouldStorageClear(clientId,
|
|
429
|
+
function shouldStorageClear(clientId, injector) {
|
|
430
|
+
const storage = injector.get(OAuthStorage);
|
|
303
431
|
const key = 'abpOAuthClientId';
|
|
304
432
|
if (!storage.getItem(key)) {
|
|
305
433
|
storage.setItem(key, clientId);
|
|
@@ -312,17 +440,25 @@ function shouldStorageClear(clientId, storage) {
|
|
|
312
440
|
}
|
|
313
441
|
|
|
314
442
|
class AuthCodeFlowStrategy extends AuthFlowStrategy {
|
|
315
|
-
constructor() {
|
|
316
|
-
super(
|
|
443
|
+
constructor(injector) {
|
|
444
|
+
super(injector);
|
|
445
|
+
this.injector = injector;
|
|
317
446
|
this.isInternalAuth = false;
|
|
447
|
+
this.platformId = injector.get(PLATFORM_ID);
|
|
448
|
+
this.appStartedWithSSR = injector.get(APP_STARTED_WITH_SSR);
|
|
449
|
+
this.document = injector.get(DOCUMENT);
|
|
318
450
|
}
|
|
319
451
|
async init() {
|
|
320
452
|
this.checkRememberMeOption();
|
|
321
453
|
this.listenToTokenReceived();
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
454
|
+
if (!this.appStartedWithSSR && isPlatformBrowser(this.platformId)) {
|
|
455
|
+
return super
|
|
456
|
+
.init()
|
|
457
|
+
.then(() => this.oAuthService.tryLogin().catch(noop))
|
|
458
|
+
.then(() => {
|
|
459
|
+
this.oAuthService.setupAutomaticSilentRefresh();
|
|
460
|
+
});
|
|
461
|
+
}
|
|
326
462
|
}
|
|
327
463
|
checkRememberMeOption() {
|
|
328
464
|
const accessToken = this.oAuthService.getAccessToken();
|
|
@@ -344,51 +480,78 @@ class AuthCodeFlowStrategy extends AuthFlowStrategy {
|
|
|
344
480
|
return { ...(lang && culture), ...queryParams };
|
|
345
481
|
}
|
|
346
482
|
setUICulture() {
|
|
347
|
-
|
|
348
|
-
|
|
483
|
+
if (isPlatformBrowser(this.platformId)) {
|
|
484
|
+
const urlParams = new URLSearchParams(window.location.search);
|
|
485
|
+
this.configState.uiCultureFromAuthCodeFlow = urlParams.get('ui-culture');
|
|
486
|
+
}
|
|
349
487
|
}
|
|
350
488
|
replaceURLParams() {
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
489
|
+
if (isPlatformBrowser(this.platformId)) {
|
|
490
|
+
const location = this.windowService.window.location;
|
|
491
|
+
const history = this.windowService.window.history;
|
|
492
|
+
const query = location.search
|
|
493
|
+
.replace(/([?&])iss=[^&]*&?/, '$1')
|
|
494
|
+
.replace(/([?&])culture=[^&]*&?/, '$1')
|
|
495
|
+
.replace(/([?&])ui-culture=[^&]*&?/, '$1')
|
|
496
|
+
.replace(/[?&]+$/, '');
|
|
497
|
+
const href = location.origin + location.pathname + query + location.hash;
|
|
498
|
+
history.replaceState(null, '', href);
|
|
499
|
+
}
|
|
360
500
|
}
|
|
361
501
|
listenToTokenReceived() {
|
|
362
|
-
this.
|
|
363
|
-
.
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
502
|
+
if (isPlatformBrowser(this.platformId) && !this.appStartedWithSSR) {
|
|
503
|
+
this.oAuthService.events
|
|
504
|
+
.pipe(filter(event => event.type === 'token_received'), tap$1(() => {
|
|
505
|
+
//TODO: Investigate how to handle with ssr
|
|
506
|
+
this.setUICulture();
|
|
507
|
+
this.replaceURLParams();
|
|
508
|
+
}), take(1))
|
|
509
|
+
.subscribe();
|
|
510
|
+
}
|
|
368
511
|
}
|
|
369
512
|
navigateToLogin(queryParams) {
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
513
|
+
if (isPlatformBrowser(this.platformId)) {
|
|
514
|
+
if (this.appStartedWithSSR) {
|
|
515
|
+
if (this.document.defaultView) {
|
|
516
|
+
this.document.defaultView.location.replace('/authorize');
|
|
517
|
+
}
|
|
518
|
+
}
|
|
519
|
+
else {
|
|
520
|
+
let additionalState = '';
|
|
521
|
+
if (queryParams?.returnUrl) {
|
|
522
|
+
additionalState = queryParams.returnUrl;
|
|
523
|
+
}
|
|
524
|
+
const cultureParams = this.getCultureParams(queryParams);
|
|
525
|
+
this.oAuthService.initCodeFlow(additionalState, cultureParams);
|
|
526
|
+
}
|
|
373
527
|
}
|
|
374
|
-
const cultureParams = this.getCultureParams(queryParams);
|
|
375
|
-
this.oAuthService.initCodeFlow(additionalState, cultureParams);
|
|
376
528
|
}
|
|
377
529
|
checkIfInternalAuth(queryParams) {
|
|
378
|
-
|
|
379
|
-
|
|
530
|
+
if (isPlatformBrowser(this.platformId)) {
|
|
531
|
+
this.oAuthService.initCodeFlow('', this.getCultureParams(queryParams));
|
|
532
|
+
return false;
|
|
533
|
+
}
|
|
380
534
|
}
|
|
381
535
|
logout(queryParams) {
|
|
382
536
|
this.rememberMeService.remove();
|
|
383
|
-
if (
|
|
384
|
-
this.
|
|
385
|
-
|
|
537
|
+
if (this.appStartedWithSSR) {
|
|
538
|
+
if (this.document.defaultView) {
|
|
539
|
+
this.document.defaultView.location.replace('/logout');
|
|
540
|
+
}
|
|
541
|
+
}
|
|
542
|
+
else {
|
|
543
|
+
if (queryParams?.noRedirectToLogoutUrl) {
|
|
544
|
+
this.router.navigate(['/']);
|
|
545
|
+
return from(this.oAuthService.revokeTokenAndLogout(true));
|
|
546
|
+
}
|
|
547
|
+
return from(this.oAuthService.revokeTokenAndLogout(this.getCultureParams(queryParams)));
|
|
386
548
|
}
|
|
387
|
-
return from(this.oAuthService.revokeTokenAndLogout(this.getCultureParams(queryParams)));
|
|
388
549
|
}
|
|
389
550
|
login(queryParams) {
|
|
390
|
-
|
|
391
|
-
|
|
551
|
+
if (isPlatformBrowser(this.platformId)) {
|
|
552
|
+
this.oAuthService.initCodeFlow('', this.getCultureParams(queryParams));
|
|
553
|
+
return of(null);
|
|
554
|
+
}
|
|
392
555
|
}
|
|
393
556
|
}
|
|
394
557
|
|
|
@@ -399,7 +562,7 @@ class AuthPasswordFlowStrategy extends AuthFlowStrategy {
|
|
|
399
562
|
}
|
|
400
563
|
listenToTokenExpiration() {
|
|
401
564
|
this.oAuthService.events
|
|
402
|
-
.pipe(filter(event => event instanceof OAuthInfoEvent &&
|
|
565
|
+
.pipe(filter$1(event => event instanceof OAuthInfoEvent &&
|
|
403
566
|
event.type === 'token_expires' &&
|
|
404
567
|
event.info === 'access_token'))
|
|
405
568
|
.subscribe(() => {
|
|
@@ -447,7 +610,7 @@ class AuthPasswordFlowStrategy extends AuthFlowStrategy {
|
|
|
447
610
|
}
|
|
448
611
|
refreshToken() {
|
|
449
612
|
return this.oAuthService.refreshToken().catch(() => {
|
|
450
|
-
clearOAuthStorage();
|
|
613
|
+
clearOAuthStorage(this.injector);
|
|
451
614
|
this.rememberMeService.remove();
|
|
452
615
|
});
|
|
453
616
|
}
|
|
@@ -472,18 +635,21 @@ class AbpOAuthService {
|
|
|
472
635
|
get isInternalAuth() {
|
|
473
636
|
return this.strategy.isInternalAuth;
|
|
474
637
|
}
|
|
475
|
-
constructor(
|
|
476
|
-
this.injector =
|
|
638
|
+
constructor() {
|
|
639
|
+
this.injector = inject(Injector);
|
|
640
|
+
this.appStartedWithSsr = this.injector.get(APP_STARTED_WITH_SSR);
|
|
641
|
+
this.platformId = this.injector.get(PLATFORM_ID);
|
|
642
|
+
this.document = this.injector.get(DOCUMENT);
|
|
477
643
|
this.oAuthService = this.injector.get(OAuthService);
|
|
478
644
|
}
|
|
479
645
|
async init() {
|
|
480
646
|
const environmentService = this.injector.get(EnvironmentService);
|
|
481
|
-
const result$ = environmentService.getEnvironment$().pipe(map(env => env?.oAuthConfig), filter(Boolean), tap(oAuthConfig => {
|
|
647
|
+
const result$ = environmentService.getEnvironment$().pipe(map$1(env => env?.oAuthConfig), filter$1(Boolean), tap(oAuthConfig => {
|
|
482
648
|
this.strategy =
|
|
483
649
|
oAuthConfig.responseType === 'code'
|
|
484
650
|
? AUTH_FLOW_STRATEGY.Code(this.injector)
|
|
485
651
|
: AUTH_FLOW_STRATEGY.Password(this.injector);
|
|
486
|
-
}), switchMap(() => from(this.strategy.init())), take(1));
|
|
652
|
+
}), switchMap(() => from(this.strategy.init())), take$1(1));
|
|
487
653
|
return await lastValueFrom(result$);
|
|
488
654
|
}
|
|
489
655
|
logout(queryParams) {
|
|
@@ -522,12 +688,16 @@ class AbpOAuthService {
|
|
|
522
688
|
return this.oAuthService.getAccessToken();
|
|
523
689
|
}
|
|
524
690
|
refreshToken() {
|
|
691
|
+
if (isPlatformBrowser(this.platformId) && this.appStartedWithSsr) {
|
|
692
|
+
this.document.defaultView?.location.replace('/authorize');
|
|
693
|
+
return Promise.resolve();
|
|
694
|
+
}
|
|
525
695
|
return this.oAuthService.refreshToken();
|
|
526
696
|
}
|
|
527
697
|
getAccessTokenExpiration() {
|
|
528
698
|
return this.oAuthService.getAccessTokenExpiration();
|
|
529
699
|
}
|
|
530
|
-
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: AbpOAuthService, deps: [
|
|
700
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: AbpOAuthService, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
|
|
531
701
|
static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: AbpOAuthService, providedIn: 'root' }); }
|
|
532
702
|
}
|
|
533
703
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: AbpOAuthService, decorators: [{
|
|
@@ -535,7 +705,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.0.7", ngImpor
|
|
|
535
705
|
args: [{
|
|
536
706
|
providedIn: 'root',
|
|
537
707
|
}]
|
|
538
|
-
}], ctorParameters: () => [
|
|
708
|
+
}], ctorParameters: () => [] });
|
|
539
709
|
|
|
540
710
|
class OAuthErrorFilterService extends AbstractAuthErrorFilter {
|
|
541
711
|
constructor() {
|
|
@@ -577,6 +747,43 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.0.7", ngImpor
|
|
|
577
747
|
args: [{ providedIn: 'root' }]
|
|
578
748
|
}] });
|
|
579
749
|
|
|
750
|
+
class BrowserTokenStorageService {
|
|
751
|
+
getItem(key) {
|
|
752
|
+
return this.readCookie(key);
|
|
753
|
+
}
|
|
754
|
+
removeItem(key) {
|
|
755
|
+
this.removeCookie(key);
|
|
756
|
+
}
|
|
757
|
+
setItem(key, data) {
|
|
758
|
+
this.writeCookie(key, data);
|
|
759
|
+
}
|
|
760
|
+
readCookie(name) {
|
|
761
|
+
if (typeof document === 'undefined')
|
|
762
|
+
return null;
|
|
763
|
+
const match = document.cookie.match(new RegExp('(^| )' + name + '=([^;]+)'));
|
|
764
|
+
return match ? decodeURIComponent(match[2]) : null;
|
|
765
|
+
}
|
|
766
|
+
writeCookie(name, value, days = 7) {
|
|
767
|
+
if (typeof document === 'undefined')
|
|
768
|
+
return;
|
|
769
|
+
const expires = new Date(Date.now() + days * 86400000).toUTCString();
|
|
770
|
+
document.cookie = `${name}=${encodeURIComponent(value)}; expires=${expires}; path=/; Secure; SameSite=Lax`;
|
|
771
|
+
}
|
|
772
|
+
removeCookie(name) {
|
|
773
|
+
if (typeof document === 'undefined')
|
|
774
|
+
return;
|
|
775
|
+
document.cookie = `${name}=; Max-Age=0; path=/;`;
|
|
776
|
+
}
|
|
777
|
+
static { this.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: BrowserTokenStorageService, deps: [], target: i0.ɵɵFactoryTarget.Injectable }); }
|
|
778
|
+
static { this.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: BrowserTokenStorageService, providedIn: 'root' }); }
|
|
779
|
+
}
|
|
780
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.0.7", ngImport: i0, type: BrowserTokenStorageService, decorators: [{
|
|
781
|
+
type: Injectable,
|
|
782
|
+
args: [{
|
|
783
|
+
providedIn: 'root',
|
|
784
|
+
}]
|
|
785
|
+
}] });
|
|
786
|
+
|
|
580
787
|
function provideAbpOAuth() {
|
|
581
788
|
const providers = [
|
|
582
789
|
{
|
|
@@ -591,6 +798,10 @@ function provideAbpOAuth() {
|
|
|
591
798
|
provide: authGuard,
|
|
592
799
|
useValue: abpOAuthGuard,
|
|
593
800
|
},
|
|
801
|
+
{
|
|
802
|
+
provide: asyncAuthGuard,
|
|
803
|
+
useValue: asyncAbpOAuthGuard,
|
|
804
|
+
},
|
|
594
805
|
{
|
|
595
806
|
provide: ApiInterceptor,
|
|
596
807
|
useClass: OAuthApiInterceptor,
|
|
@@ -613,7 +824,12 @@ function provideAbpOAuth() {
|
|
|
613
824
|
inject(OAuthConfigurationHandler);
|
|
614
825
|
}),
|
|
615
826
|
OAuthModule.forRoot().providers,
|
|
616
|
-
|
|
827
|
+
ServerTokenStorageService,
|
|
828
|
+
BrowserTokenStorageService,
|
|
829
|
+
{
|
|
830
|
+
provide: OAuthStorage,
|
|
831
|
+
useFactory: oAuthStorageFactory,
|
|
832
|
+
},
|
|
617
833
|
{ provide: AuthErrorFilterService, useExisting: OAuthErrorFilterService },
|
|
618
834
|
];
|
|
619
835
|
return makeEnvironmentProviders(providers);
|
|
@@ -641,5 +857,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.0.7", ngImpor
|
|
|
641
857
|
* Generated bundle index. Do not edit.
|
|
642
858
|
*/
|
|
643
859
|
|
|
644
|
-
export { AUTH_FLOW_STRATEGY, AbpOAuthGuard, AbpOAuthModule, AbpOAuthService, AuthCodeFlowStrategy, AuthFlowStrategy, AuthPasswordFlowStrategy, NavigateToManageProfileProvider, OAuthApiInterceptor, OAuthConfigurationHandler, OAuthErrorFilterService, RememberMeService, abpOAuthGuard, checkAccessToken, clearOAuthStorage, isTokenExpired,
|
|
860
|
+
export { AUTH_FLOW_STRATEGY, AbpOAuthGuard, AbpOAuthModule, AbpOAuthService, AuthCodeFlowStrategy, AuthFlowStrategy, AuthPasswordFlowStrategy, BrowserTokenStorageService, MockStorage, NavigateToManageProfileProvider, OAuthApiInterceptor, OAuthConfigurationHandler, OAuthErrorFilterService, RememberMeService, ServerTokenStorageService, abpOAuthGuard, asyncAbpOAuthGuard, buildLoginUrl, checkAccessToken, clearOAuthStorage, isTokenExpired, oAuthStorageFactory, pipeToLogin, provideAbpOAuth };
|
|
645
861
|
//# sourceMappingURL=abp-ng.oauth.mjs.map
|