@vc-shell/framework 1.0.80 → 1.0.82

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.
@@ -1,4 +1,4 @@
1
- import { computed, Ref, ref, ComputedRef, onUnmounted, getCurrentInstance, inject, watch } from "vue";
1
+ import { computed, Ref, ref, ComputedRef } from "vue";
2
2
  import ClientOAuth2 from "client-oauth2";
3
3
  import {
4
4
  UserDetail,
@@ -7,10 +7,12 @@ import {
7
7
  SecurityResult,
8
8
  ValidatePasswordResetTokenRequest,
9
9
  IdentityResult,
10
+ ExternalSignInClient,
11
+ ChangePasswordRequest,
12
+ LoginType,
13
+ ExternalSignInProviderInfo,
10
14
  } from "./../../api";
11
15
  import { AuthData, RequestPasswordResult, SignInResults } from "./../../types";
12
- import * as _ from "lodash-es";
13
- import fetchIntercept from "fetch-intercept";
14
16
  import { useLocalStorage } from "@vueuse/core";
15
17
  //The Platform Manager uses the same key to store authorization data in the
16
18
  //local storage, so we can exchange authorization data between the Platform Manager
@@ -24,24 +26,12 @@ const authClient = new ClientOAuth2({
24
26
  accessTokenUri: `/connect/token`,
25
27
  scopes: ["offline_access"],
26
28
  });
27
- const activeAuthenticationType = ref();
28
29
  const securityClient = new SecurityClient();
29
-
30
- export interface LoginTypes {
31
- enabled?: boolean;
32
- hasLoginForm?: boolean;
33
- authenticationType?: string;
34
- priority?: number;
35
- }
36
- export interface LoginProviders {
37
- authenticationType?: string;
38
- displayName?: string;
39
- }
30
+ const externalSecurityClient = new ExternalSignInClient();
40
31
 
41
32
  interface IUseUser {
42
33
  user: ComputedRef<UserDetail | null>;
43
34
  loading: ComputedRef<boolean>;
44
- isExternalSignedIn: Ref<boolean>;
45
35
  getAccessToken: () => Promise<string | null>;
46
36
  loadUser: () => Promise<UserDetail>;
47
37
  signIn: (username: string, password: string) => Promise<SignInResults>;
@@ -51,29 +41,18 @@ interface IUseUser {
51
41
  resetPasswordByToken: (userId: string, password: string, token: string) => Promise<SecurityResult>;
52
42
  requestPasswordReset: (loginOrEmail: string) => Promise<RequestPasswordResult>;
53
43
  changeUserPassword: (oldPassword: string, newPassword: string) => Promise<SecurityResult>;
54
- getExternalLoginProviders: () => Promise<LoginProviders[]>;
44
+ getExternalLoginProviders: () => Promise<ExternalSignInProviderInfo[]>;
55
45
  externalSignIn: (authenticationType?: string | undefined, returnUrl?: string | undefined) => void;
56
- externalSignOut: (authenticationType?: string | undefined) => void;
57
- getLoginTypes: () => Promise<LoginTypes[]>;
58
- isAzureAdAuthAvailable: () => Promise<boolean>;
59
- getAzureAdAuthCaption: () => Promise<string>;
46
+ getLoginType: () => Promise<LoginType[]>;
47
+ isAuthenticated: () => Promise<boolean>;
60
48
  }
61
49
 
62
50
  export function useUser(): IUseUser {
63
- const base = inject("platformUrl");
64
- const isExternalSignedIn = useLocalStorage("VC_EXTERNAL_LOGIN", false);
65
-
66
- watch(
67
- () => isExternalSignedIn,
68
- (newVal) => {
69
- if (newVal.value) {
70
- initInterceptor();
71
- } else {
72
- fetchIntercept.clear();
73
- }
74
- },
75
- { immediate: true }
76
- );
51
+ const externalSignInStorage = useLocalStorage<{ providerType: string }>("externalSignIn", null);
52
+
53
+ const isAuthenticated = async () => {
54
+ return !!((externalSignInStorage.value && externalSignInStorage.value.providerType) ?? (await getAccessToken()));
55
+ };
77
56
 
78
57
  async function validateToken(userId: string, token: string): Promise<boolean> {
79
58
  let result = false;
@@ -132,13 +111,14 @@ export function useUser(): IUseUser {
132
111
  async function signOut(): Promise<void> {
133
112
  console.debug(`[@vc-shell/framework#useUser:signOut] - Entry point`);
134
113
 
135
- if (!isExternalSignedIn.value) {
114
+ if (externalSignInStorage.value && externalSignInStorage.value.providerType) {
115
+ externalSignOut(externalSignInStorage.value.providerType);
116
+ storeAuthData({});
117
+ externalSignInStorage.value = null;
118
+ } else {
136
119
  user.value = undefined;
137
120
  authData.value = undefined;
138
121
  storeAuthData({});
139
- } else {
140
- externalSignOut(activeAuthenticationType.value);
141
- activeAuthenticationType.value = undefined;
142
122
  }
143
123
  }
144
124
 
@@ -200,6 +180,7 @@ export function useUser(): IUseUser {
200
180
  function storeAuthData(authData: AuthData) {
201
181
  localStorage.setItem(VC_AUTH_DATA_KEY, JSON.stringify({ ...(authData || {}) }));
202
182
  }
183
+
203
184
  async function readAuthData(): Promise<AuthData> {
204
185
  return (await JSON.parse(localStorage.getItem(VC_AUTH_DATA_KEY) || "{}")) as AuthData;
205
186
  }
@@ -225,27 +206,15 @@ export function useUser(): IUseUser {
225
206
  const token = await getAccessToken();
226
207
  let result;
227
208
 
228
- // TODO it's temporary workaround to get valid errors
229
209
  if (token) {
230
210
  try {
231
211
  loading.value = true;
232
- const res = await fetch("/api/platform/security/currentuser/changepassword", {
233
- method: "POST",
234
- headers: {
235
- "Content-Type": "application/json-patch+json",
236
- Accept: "text/plain",
237
- authorization: `Bearer ${token}`,
238
- },
239
- body: JSON.stringify({
240
- oldPassword,
241
- newPassword,
242
- }),
212
+ const command = new ChangePasswordRequest({
213
+ oldPassword,
214
+ newPassword,
243
215
  });
244
- if (res.status !== 500) {
245
- result = await res.text().then((response) => {
246
- return JSON.parse(response);
247
- });
248
- }
216
+
217
+ result = await securityClient.changeCurrentUserPassword(command);
249
218
  } catch (e) {
250
219
  return { succeeded: false, errors: [e.message] } as SecurityResult;
251
220
  } finally {
@@ -253,54 +222,42 @@ export function useUser(): IUseUser {
253
222
  }
254
223
  }
255
224
 
256
- return result as SecurityResult;
225
+ return result;
257
226
  }
258
227
 
259
- async function getLoginTypes(): Promise<LoginTypes[]> {
260
- let result = null as LoginTypes[];
228
+ async function getLoginType(): Promise<LoginType[]> {
229
+ let result = null as LoginType[];
261
230
  try {
262
- const fetchResult = await fetch("/api/platform/security/logintypes", {
263
- method: "GET",
264
- headers: {},
265
- });
266
-
267
- const response = await fetchResult.text();
268
- if (response && response.trim()) {
269
- result = JSON.parse(response) as LoginTypes[];
270
- }
231
+ result = await securityClient.getLoginTypes();
271
232
  } catch (e) {
272
233
  console.error(e);
273
-
274
234
  throw e;
275
235
  }
276
236
 
277
237
  return result;
278
238
  }
279
239
 
280
- async function getExternalLoginProviders(): Promise<LoginProviders[]> {
281
- let result = null as LoginProviders[];
240
+ async function getExternalLoginProviders(): Promise<ExternalSignInProviderInfo[]> {
241
+ let result = null as ExternalSignInProviderInfo[];
282
242
  try {
283
- const fetchResult = await fetch(base + "externalsignin/providers", {
284
- method: "GET",
285
- });
286
-
287
- const response = await fetchResult.text();
288
- if (response && response.trim()) {
289
- result = JSON.parse(response) as LoginProviders[];
290
- }
243
+ result = await externalSecurityClient.getExternalLoginProviders();
291
244
  } catch (e) {
292
245
  console.error(e);
293
-
294
- throw e;
295
246
  }
296
247
 
297
248
  return result;
298
249
  }
299
250
 
300
- async function externalSignIn(authenticationType?: string | undefined, returnUrl?: string | undefined) {
301
- activeAuthenticationType.value = authenticationType;
251
+ async function externalSignIn(authenticationType: string | undefined, returnUrl: string | undefined) {
302
252
  try {
303
- let url_ = base + "externalsignin?";
253
+ let url_ = "externalsignin?";
254
+
255
+ const signInData = {
256
+ providerType: authenticationType,
257
+ };
258
+
259
+ externalSignInStorage.value = signInData;
260
+
304
261
  if (authenticationType === null) throw new Error("The parameter 'authenticationType' cannot be null.");
305
262
  else {
306
263
  if (authenticationType !== undefined)
@@ -308,78 +265,29 @@ export function useUser(): IUseUser {
308
265
  if (returnUrl !== undefined) url_ += "returnUrl=" + encodeURIComponent("" + returnUrl) + "&";
309
266
  }
310
267
  url_ = url_.replace(/[?&]$/, "");
311
- isExternalSignedIn.value = true;
312
268
 
313
269
  window.location.href = url_;
314
270
  } catch (e) {
315
- isExternalSignedIn.value = false;
316
271
  console.error(e);
317
272
 
318
273
  throw e;
319
274
  }
320
275
  }
321
276
 
322
- async function externalSignOut(authenticationType?: string | undefined): Promise<void> {
277
+ async function externalSignOut(authenticationType: string | undefined): Promise<void> {
323
278
  try {
324
- let url_ = base + "externalsignin/signout?";
325
- if (authenticationType === null) throw new Error("The parameter 'authenticationType' cannot be null.");
326
- else {
327
- if (authenticationType !== undefined)
328
- url_ += "authenticationType=" + encodeURIComponent("" + authenticationType) + "&";
329
- }
330
- url_ = url_.replace(/[?&]$/, "");
331
-
332
- await fetch(url_, {
333
- method: "GET",
334
- headers: {},
335
- });
279
+ const url = "externalsignin/signout?authenticationType=" + authenticationType;
280
+ window.location.href = url;
336
281
  } catch (e) {
337
282
  console.error(e);
338
-
339
283
  throw e;
340
284
  }
341
- isExternalSignedIn.value = false;
342
- }
343
-
344
- async function isAzureAdAuthAvailable(): Promise<boolean> {
345
- const loginTypes = await getLoginTypes();
346
- if (loginTypes) {
347
- return (
348
- loginTypes.filter((x) => x.authenticationType === "AzureAD").length > 0 &&
349
- loginTypes.find((x) => x.authenticationType === "AzureAD").enabled
350
- );
351
- }
352
- return false;
353
- }
354
-
355
- async function getAzureAdAuthCaption(): Promise<string> {
356
- const loginProviders = await getExternalLoginProviders();
357
- if (loginProviders) {
358
- return loginProviders.find((x) => x.authenticationType === "AzureAD").displayName;
359
- }
360
- return null;
361
- }
362
-
363
- /* Intercepting requests to explicitly remove auth token when we use AzureAd authentication */
364
- function initInterceptor() {
365
- console.log("[@vc-shell/framework#useUser:initInterceptor]: Entry point");
366
- // store external login in localStorage
367
- return fetchIntercept.register({
368
- request: function (_url, config) {
369
- if (isExternalSignedIn.value) {
370
- const edited = _.omit(config.headers, "authorization");
371
- config.headers = edited;
372
- }
373
-
374
- return [_url, config];
375
- },
376
- });
377
285
  }
378
286
 
379
287
  return {
380
288
  user: computed(() => user.value),
381
289
  loading: computed(() => loading.value),
382
- isExternalSignedIn,
290
+ isAuthenticated,
383
291
  getAccessToken,
384
292
  loadUser,
385
293
  signIn,
@@ -391,9 +299,6 @@ export function useUser(): IUseUser {
391
299
  changeUserPassword,
392
300
  getExternalLoginProviders,
393
301
  externalSignIn,
394
- externalSignOut,
395
- getLoginTypes,
396
- isAzureAdAuthAvailable,
397
- getAzureAdAuthCaption,
302
+ getLoginType,
398
303
  };
399
304
  }
@@ -27,9 +27,10 @@ export declare class ExternalSignInClient extends AuthApiBase {
27
27
  });
28
28
  /**
29
29
  * @param authenticationType (optional)
30
+ * @param returnUrl (optional)
30
31
  * @return Success
31
32
  */
32
- signIn(authenticationType?: string | undefined): Promise<void>;
33
+ signIn(authenticationType?: string | undefined, returnUrl?: string | undefined): Promise<void>;
33
34
  protected processSignIn(response: Response): Promise<void>;
34
35
  /**
35
36
  * @param authenticationType (optional)
@@ -46,8 +47,8 @@ export declare class ExternalSignInClient extends AuthApiBase {
46
47
  /**
47
48
  * @return Success
48
49
  */
49
- getExternalLoginProviders(): Promise<void>;
50
- protected processGetExternalLoginProviders(response: Response): Promise<void>;
50
+ getExternalLoginProviders(): Promise<ExternalSignInProviderInfo[]>;
51
+ protected processGetExternalLoginProviders(response: Response): Promise<ExternalSignInProviderInfo[]>;
51
52
  }
52
53
  export declare class AppsClient extends AuthApiBase {
53
54
  private http;
@@ -503,8 +504,8 @@ export declare class SecurityClient extends AuthApiBase {
503
504
  /**
504
505
  * @return Success
505
506
  */
506
- getLoginTypes(): Promise<void>;
507
- protected processGetLoginTypes(response: Response): Promise<void>;
507
+ getLoginTypes(): Promise<LoginType[]>;
508
+ protected processGetLoginTypes(response: Response): Promise<LoginType[]>;
508
509
  /**
509
510
  * @return Success
510
511
  */
@@ -625,6 +626,7 @@ export declare class ApplicationUser implements IApplicationUser {
625
626
  passwordExpired?: boolean;
626
627
  lastPasswordChangedDate?: Date | undefined;
627
628
  lastPasswordChangeRequestDate?: Date | undefined;
629
+ lastLoginDate?: Date | undefined;
628
630
  id?: string | undefined;
629
631
  userName?: string | undefined;
630
632
  normalizedUserName?: string | undefined;
@@ -665,6 +667,7 @@ export interface IApplicationUser {
665
667
  passwordExpired?: boolean;
666
668
  lastPasswordChangedDate?: Date | undefined;
667
669
  lastPasswordChangeRequestDate?: Date | undefined;
670
+ lastLoginDate?: Date | undefined;
668
671
  id?: string | undefined;
669
672
  userName?: string | undefined;
670
673
  normalizedUserName?: string | undefined;
@@ -1109,6 +1112,18 @@ export declare enum EntryState {
1109
1112
  Deleted = "Deleted",
1110
1113
  Modified = "Modified"
1111
1114
  }
1115
+ export declare class ExternalSignInProviderInfo implements IExternalSignInProviderInfo {
1116
+ authenticationType?: string | undefined;
1117
+ displayName?: string | undefined;
1118
+ constructor(data?: IExternalSignInProviderInfo);
1119
+ init(_data?: any): void;
1120
+ static fromJS(data: any): ExternalSignInProviderInfo;
1121
+ toJSON(data?: any): any;
1122
+ }
1123
+ export interface IExternalSignInProviderInfo {
1124
+ authenticationType?: string | undefined;
1125
+ displayName?: string | undefined;
1126
+ }
1112
1127
  export declare class IdentityError implements IIdentityError {
1113
1128
  code?: string | undefined;
1114
1129
  description?: string | undefined;
@@ -1211,6 +1226,22 @@ export interface ILoginRequest {
1211
1226
  password?: string | undefined;
1212
1227
  rememberMe?: boolean;
1213
1228
  }
1229
+ export declare class LoginType implements ILoginType {
1230
+ enabled?: boolean;
1231
+ hasLoginForm?: boolean;
1232
+ authenticationType?: string | undefined;
1233
+ priority?: number;
1234
+ constructor(data?: ILoginType);
1235
+ init(_data?: any): void;
1236
+ static fromJS(data: any): LoginType;
1237
+ toJSON(data?: any): any;
1238
+ }
1239
+ export interface ILoginType {
1240
+ enabled?: boolean;
1241
+ hasLoginForm?: boolean;
1242
+ authenticationType?: string | undefined;
1243
+ priority?: number;
1244
+ }
1214
1245
  export declare class ModuleAutoInstallPushNotification implements IModuleAutoInstallPushNotification {
1215
1246
  started?: Date | undefined;
1216
1247
  finished?: Date | undefined;