alfenory-authv2-ui 0.0.18 → 0.0.19

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.
Files changed (26) hide show
  1. package/fesm2022/alfenory-authv2-ui.mjs +655 -43
  2. package/fesm2022/alfenory-authv2-ui.mjs.map +1 -1
  3. package/lib/components/index.d.ts +1 -0
  4. package/lib/components/login/login.d.ts +1 -1
  5. package/lib/components/usergroup-attributes/index.d.ts +1 -0
  6. package/lib/components/usergroup-attributes/usergroup-attributes-basic.d.ts +10 -0
  7. package/lib/components/usergroup-attributes/usergroup-attributes-list-detail.d.ts +14 -0
  8. package/lib/components/usergroup-attributes/usergroup-attributes-list.d.ts +9 -0
  9. package/lib/components/usergroup-attributes/usergroup-attributes-update-field-base.d.ts +11 -0
  10. package/lib/components/usergroup-attributes/usergroup-attributes-update-number.d.ts +7 -0
  11. package/lib/components/usergroup-attributes/usergroup-attributes-update-select.d.ts +7 -0
  12. package/lib/components/usergroup-attributes/usergroup-attributes-update-textarea.d.ts +6 -0
  13. package/lib/components/usergroup-attributes/usergroup-attributes-update-textfield.d.ts +6 -0
  14. package/lib/components/usergroup-attributes/usergroup-attributes-update.d.ts +15 -0
  15. package/lib/components/usergroup-attributes/usergroup-attributes.d.ts +37 -0
  16. package/lib/models/get-filter-query-parameter.model.d.ts +6 -0
  17. package/lib/models/get-filter-query-relation.enum.d.ts +6 -0
  18. package/lib/models/index.d.ts +3 -0
  19. package/lib/models/localstorage-keys.model.d.ts +2 -1
  20. package/lib/models/usergroup-attribute.model.d.ts +26 -0
  21. package/lib/providers/basic-provider-alfenoryauthv2.service.d.ts +7 -0
  22. package/lib/providers/basic-provider.d.ts +20 -0
  23. package/lib/providers/index.d.ts +1 -0
  24. package/lib/providers/localstorage.service.d.ts +4 -2
  25. package/lib/providers/usergroup-attributes.service.d.ts +11 -0
  26. package/package.json +2 -1
@@ -1,5 +1,5 @@
1
1
  import * as i0 from '@angular/core';
2
- import { InjectionToken, inject, Injectable, computed, Component, input, ElementRef, effect, Directive } from '@angular/core';
2
+ import { InjectionToken, inject, Injectable, computed, Component, Directive, input, output, effect, signal, ElementRef } from '@angular/core';
3
3
  import { signalStore, withState, withMethods, patchState } from '@ngrx/signals';
4
4
  import { Router } from '@angular/router';
5
5
  import { catchError, of, tap, switchMap } from 'rxjs';
@@ -7,9 +7,10 @@ import { HttpClient, HttpHeaders, HttpParams } from '@angular/common/http';
7
7
  import * as i1 from '@angular/common';
8
8
  import { CommonModule } from '@angular/common';
9
9
  import * as i1$1 from '@ngx-translate/core';
10
- import { TranslateModule } from '@ngx-translate/core';
11
- import * as i3 from '@angular/forms';
12
- import { FormGroup, FormControl, Validators, ReactiveFormsModule } from '@angular/forms';
10
+ import { TranslateModule, TranslateService, TranslatePipe } from '@ngx-translate/core';
11
+ import * as i1$2 from '@angular/forms';
12
+ import { FormGroup, FormControl, Validators, ReactiveFormsModule, FormsModule } from '@angular/forms';
13
+ import { NgbModal } from '@ng-bootstrap/ng-bootstrap';
13
14
 
14
15
  const API_URL = new InjectionToken('API_URL');
15
16
  ;
@@ -21,8 +22,25 @@ var LocalStorageKeys;
21
22
  LocalStorageKeys["memberships"] = "AUTH_MEMBERSHIPS";
22
23
  LocalStorageKeys["currentMembership"] = "AUTH_CURRENT_MEMBERSHIP";
23
24
  LocalStorageKeys["privileges"] = "AUTH_PRIVILEGES";
25
+ LocalStorageKeys["usergroupId"] = "AUTH_USERGROUP_ID";
24
26
  })(LocalStorageKeys || (LocalStorageKeys = {}));
25
27
 
28
+ var GetFilterQueryRelation;
29
+ (function (GetFilterQueryRelation) {
30
+ GetFilterQueryRelation["eq"] = "eq";
31
+ GetFilterQueryRelation["contains"] = "contains";
32
+ GetFilterQueryRelation["in"] = "in";
33
+ GetFilterQueryRelation["gt"] = "gt";
34
+ })(GetFilterQueryRelation || (GetFilterQueryRelation = {}));
35
+
36
+ var UsergroupAttributeEditType;
37
+ (function (UsergroupAttributeEditType) {
38
+ UsergroupAttributeEditType[UsergroupAttributeEditType["InputNumber"] = 1] = "InputNumber";
39
+ UsergroupAttributeEditType[UsergroupAttributeEditType["InputString"] = 2] = "InputString";
40
+ UsergroupAttributeEditType[UsergroupAttributeEditType["InputArea"] = 3] = "InputArea";
41
+ UsergroupAttributeEditType[UsergroupAttributeEditType["selectTypes"] = 4] = "selectTypes";
42
+ })(UsergroupAttributeEditType || (UsergroupAttributeEditType = {}));
43
+
26
44
  class ConnectionService {
27
45
  http = inject(HttpClient);
28
46
  apiUrl = inject(API_URL);
@@ -41,10 +59,10 @@ class ConnectionService {
41
59
  getURL(customUrl) {
42
60
  return `${this.apiUrl}/${customUrl}`;
43
61
  }
44
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: ConnectionService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
45
- static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: ConnectionService, providedIn: 'root' });
62
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: ConnectionService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
63
+ static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: ConnectionService, providedIn: 'root' });
46
64
  }
47
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: ConnectionService, decorators: [{
65
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: ConnectionService, decorators: [{
48
66
  type: Injectable,
49
67
  args: [{
50
68
  providedIn: 'root'
@@ -65,7 +83,7 @@ class BasicLocalStorageService {
65
83
  return localStorage.getItem(key);
66
84
  }
67
85
  getNumber(key, defaultValue) {
68
- return parseInt(this.getString(key) ?? (defaultValue ?? '0'));
86
+ return parseInt(this.getString(key) ?? defaultValue ?? '0');
69
87
  }
70
88
  getJson(key, defaultValue) {
71
89
  const resp = localStorage.getItem(key);
@@ -83,29 +101,35 @@ class BasicLocalStorageService {
83
101
  removeKey(key) {
84
102
  localStorage.removeItem(key);
85
103
  }
86
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: BasicLocalStorageService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
87
- static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: BasicLocalStorageService, providedIn: 'root' });
104
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: BasicLocalStorageService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
105
+ static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: BasicLocalStorageService, providedIn: 'root' });
88
106
  }
89
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: BasicLocalStorageService, decorators: [{
107
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: BasicLocalStorageService, decorators: [{
90
108
  type: Injectable,
91
109
  args: [{
92
- providedIn: 'root'
110
+ providedIn: 'root',
93
111
  }]
94
112
  }] });
95
113
 
96
114
  class LocalStorageService extends BasicLocalStorageService {
97
115
  getAuthToken() {
98
- return this.getString(LocalStorageKeys.authToken) ?? null;
116
+ return this.getString(LocalStorageKeys.authToken);
99
117
  }
100
118
  setAuthToken(token) {
101
119
  this.setString(LocalStorageKeys.authToken, token);
102
120
  }
103
121
  getUserId() {
104
- return this.getString(LocalStorageKeys.userId) ?? null;
122
+ return this.getString(LocalStorageKeys.userId);
105
123
  }
106
124
  setUserId(userId) {
107
125
  this.setString(LocalStorageKeys.userId, userId);
108
126
  }
127
+ getUsergroupId() {
128
+ return this.getString(LocalStorageKeys.usergroupId);
129
+ }
130
+ setUsergroupId(usergroupId) {
131
+ this.setString(LocalStorageKeys.usergroupId, usergroupId);
132
+ }
109
133
  setMemberships(memberships) {
110
134
  this.setJson(LocalStorageKeys.memberships, memberships);
111
135
  }
@@ -122,11 +146,13 @@ class LocalStorageService extends BasicLocalStorageService {
122
146
  this.setString(LocalStorageKeys.currentMembership, membershipId);
123
147
  }
124
148
  getCurrentMembershipId() {
125
- return this.getString(LocalStorageKeys.currentMembership) ?? null;
149
+ return this.getString(LocalStorageKeys.currentMembership);
126
150
  }
127
151
  getHeaderWithAuth() {
128
152
  let headers = new HttpHeaders();
129
- headers = headers.set('Authorization', 'Bearer ' + this.getAuthToken());
153
+ if (this.getAuthToken()) {
154
+ headers = headers.set('Authorization', 'Bearer ' + this.getAuthToken());
155
+ }
130
156
  const params = new HttpParams();
131
157
  return { headers, params };
132
158
  }
@@ -136,14 +162,15 @@ class LocalStorageService extends BasicLocalStorageService {
136
162
  this.removeKey(LocalStorageKeys.privileges);
137
163
  this.removeKey(LocalStorageKeys.memberships);
138
164
  this.removeKey(LocalStorageKeys.currentMembership);
165
+ this.removeKey(LocalStorageKeys.usergroupId);
139
166
  }
140
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: LocalStorageService, deps: null, target: i0.ɵɵFactoryTarget.Injectable });
141
- static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: LocalStorageService, providedIn: 'root' });
167
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: LocalStorageService, deps: null, target: i0.ɵɵFactoryTarget.Injectable });
168
+ static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: LocalStorageService, providedIn: 'root' });
142
169
  }
143
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: LocalStorageService, decorators: [{
170
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: LocalStorageService, decorators: [{
144
171
  type: Injectable,
145
172
  args: [{
146
- providedIn: 'root'
173
+ providedIn: 'root',
147
174
  }]
148
175
  }] });
149
176
 
@@ -171,10 +198,10 @@ class AuthService {
171
198
  return of({ success: false });
172
199
  }));
173
200
  }
174
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: AuthService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
175
- static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: AuthService, providedIn: 'root' });
201
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: AuthService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
202
+ static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: AuthService, providedIn: 'root' });
176
203
  }
177
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: AuthService, decorators: [{
204
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: AuthService, decorators: [{
178
205
  type: Injectable,
179
206
  args: [{
180
207
  providedIn: 'root'
@@ -186,14 +213,14 @@ const AuthStore = signalStore({ providedIn: 'root' }, withState({
186
213
  isAuthenticated: false,
187
214
  loginError: false,
188
215
  sessionRunoutError: false,
189
- hasNewPriv: false
216
+ hasNewPriv: false,
190
217
  }), withMethods((store) => {
191
218
  const router = inject(Router);
192
219
  const authservice = inject(AuthService);
193
220
  const localstorageService = inject(LocalStorageService);
194
221
  return {
195
222
  loadMemberships() {
196
- authservice.getMemberships().subscribe(val => {
223
+ authservice.getMemberships().subscribe((val) => {
197
224
  const memberships = val.data ?? [];
198
225
  localstorageService.setMemberships(memberships);
199
226
  if (memberships.length === 0) {
@@ -208,7 +235,12 @@ const AuthStore = signalStore({ providedIn: 'root' }, withState({
208
235
  });
209
236
  },
210
237
  login(username, password) {
211
- patchState(store, { loading: true, loginError: false, sessionRunoutError: false, isAuthenticated: false });
238
+ patchState(store, {
239
+ loading: true,
240
+ loginError: false,
241
+ sessionRunoutError: false,
242
+ isAuthenticated: false,
243
+ });
212
244
  authservice.doLogin(username, password).subscribe((val) => {
213
245
  if (val.success && val.data) {
214
246
  patchState(store, { loading: false, isAuthenticated: true });
@@ -223,10 +255,11 @@ const AuthStore = signalStore({ providedIn: 'root' }, withState({
223
255
  setMembershipId(membership) {
224
256
  localstorageService.setCurrentMembershipId(membership.id);
225
257
  localstorageService.setUserId(membership.user_id);
258
+ localstorageService.setUsergroupId(membership.usergroup_id);
226
259
  this.loadPrivileges(membership);
227
260
  },
228
261
  loadPrivileges(membership) {
229
- authservice.getPrivsForMembership(membership.id).subscribe(val => {
262
+ authservice.getPrivsForMembership(membership.id).subscribe((val) => {
230
263
  localstorageService.setPrivs(val.data ?? []);
231
264
  patchState(store, { hasNewPriv: true });
232
265
  setTimeout(() => patchState(store, { hasNewPriv: false }), 1000);
@@ -243,7 +276,7 @@ const AuthStore = signalStore({ providedIn: 'root' }, withState({
243
276
  patchState(store, {
244
277
  loading: false,
245
278
  isAuthenticated: false,
246
- sessionRunoutError: localstorageService.getAuthToken() ? true : false
279
+ sessionRunoutError: localstorageService.getAuthToken() ? true : false,
247
280
  });
248
281
  localstorageService.removeAll();
249
282
  router.navigate(['/auth/login']);
@@ -261,7 +294,7 @@ const AuthStore = signalStore({ providedIn: 'root' }, withState({
261
294
  hasPriv(priv) {
262
295
  const privs = localstorageService.getPrivs();
263
296
  if (privs) {
264
- return privs.find(val => val === priv) !== undefined;
297
+ return privs.find((val) => val === priv) !== undefined;
265
298
  }
266
299
  return false;
267
300
  },
@@ -273,7 +306,7 @@ const AuthStore = signalStore({ providedIn: 'root' }, withState({
273
306
  localstorageService.removeAll();
274
307
  }
275
308
  });
276
- }
309
+ },
277
310
  };
278
311
  }));
279
312
 
@@ -311,10 +344,10 @@ class Login {
311
344
  this.authStore.login(this.usernameControl.value?.trim(), this.passwordControl.value?.trim());
312
345
  }
313
346
  }
314
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: Login, deps: [], target: i0.ɵɵFactoryTarget.Component });
315
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "19.2.15", type: Login, isStandalone: true, selector: "alfenoryauthv2-ui-login", ngImport: i0, template: "@if (isLoading()) {\r\n <div class=\"spinner-border\" role=\"status\">\r\n <span class=\"sr-only\"></span>\r\n </div>\r\n} \r\n@else {\r\n<div class=\"card\">\r\n <div class=\"card-header\">\r\n <h1>{{'alfenoryauthv2.login.header' | translate}}</h1>\r\n </div>\r\n <div class=\"card-body\">\r\n @if (errorType() !== 0) \r\n {\r\n <div class=\"alert alert-danger\" role=\"alert\">\r\n <b>{{'general.messages.error' | translate}}</b>\r\n @if (errorType() === 1) {\r\n {{'alfenoryauthv2.login.loginerror' | translate}}\r\n } \r\n @if (errorType() === 2) {\r\n {{'alfenoryauthv2.login.sessionrunouterror_text' | translate}}\r\n } \r\n </div>\r\n }\r\n <form [formGroup]=\"formGroup\" (ngSubmit)=\"onSubmit()\"> \r\n <div class=\"form-floating mb-3\">\r\n <input type=\"email\" class=\"form-control\" formControlName=\"username\" id=\"username\" name=\"username\" autocomplete=\"username\" placeholder=\"Email\" [ngClass]=\"{'is-invalid' : usernameControl.touched && usernameControl.errors}\">\r\n <label for=\"username\">{{'alfenoryauthv2.login.email' | translate}}</label>\r\n <div class=\"invalid-feedback\">\r\n {{'general.messages.required' | translate}}\r\n </div>\r\n </div>\r\n <div class=\"form-floating mb-3\">\r\n <input type=\"password\" class=\"form-control\" formControlName=\"password\" id=\"password\" name=\"password\" autocomplete=\"current-password\" placeholder=\"Passwort\" [ngClass]=\"{'is-invalid' : passwordControl.touched && passwordControl.errors}\">\r\n <label for=\"password\">{{'alfenoryauthv2.login.password' | translate}}</label>\r\n <div class=\"invalid-feedback\">\r\n {{'general.messages.required' | translate}}\r\n </div>\r\n </div>\r\n <button class=\"btn btn-primary\" type=\"submit\">\r\n {{'alfenoryauthv2.login.submit' | translate}}\r\n </button>\r\n </form>\r\n </div>\r\n</div>\r\n}", dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "ngmodule", type: TranslateModule }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }, { kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i3.ɵNgNoValidate, selector: "form:not([ngNoForm]):not([ngNativeValidate])" }, { kind: "directive", type: i3.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i3.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i3.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i3.FormGroupDirective, selector: "[formGroup]", inputs: ["formGroup"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: i3.FormControlName, selector: "[formControlName]", inputs: ["formControlName", "disabled", "ngModel"], outputs: ["ngModelChange"] }] });
347
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: Login, deps: [], target: i0.ɵɵFactoryTarget.Component });
348
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "19.2.20", type: Login, isStandalone: true, selector: "alfenoryauthv2-ui-login", ngImport: i0, template: "@if (isLoading()) {\r\n <div class=\"spinner-border\" role=\"status\">\r\n <span class=\"sr-only\"></span>\r\n </div>\r\n} \r\n@else {\r\n<div class=\"card\">\r\n <div class=\"card-header\">\r\n <h1>{{'alfenoryauthv2.login.header' | translate}}</h1>\r\n </div>\r\n <div class=\"card-body\">\r\n @if (errorType() !== 0) \r\n {\r\n <div class=\"alert alert-danger\" role=\"alert\">\r\n <b>{{'general.messages.error' | translate}}</b>\r\n @if (errorType() === 1) {\r\n {{'alfenoryauthv2.login.loginerror' | translate}}\r\n } \r\n @if (errorType() === 2) {\r\n {{'alfenoryauthv2.login.sessionrunouterror_text' | translate}}\r\n } \r\n </div>\r\n }\r\n <form [formGroup]=\"formGroup\" (ngSubmit)=\"onSubmit()\"> \r\n <div class=\"form-floating mb-3\">\r\n <input type=\"email\" class=\"form-control\" formControlName=\"username\" id=\"username\" name=\"username\" autocomplete=\"username\" placeholder=\"Email\" [ngClass]=\"{'is-invalid' : usernameControl.touched && usernameControl.errors}\">\r\n <label for=\"username\">{{'alfenoryauthv2.login.email' | translate}}</label>\r\n <div class=\"invalid-feedback\">\r\n {{'general.messages.required' | translate}}\r\n </div>\r\n </div>\r\n <div class=\"form-floating mb-3\">\r\n <input type=\"password\" class=\"form-control\" formControlName=\"password\" id=\"password\" name=\"password\" autocomplete=\"current-password\" placeholder=\"Passwort\" [ngClass]=\"{'is-invalid' : passwordControl.touched && passwordControl.errors}\">\r\n <label for=\"password\">{{'alfenoryauthv2.login.password' | translate}}</label>\r\n <div class=\"invalid-feedback\">\r\n {{'general.messages.required' | translate}}\r\n </div>\r\n </div>\r\n <button class=\"btn btn-primary\" type=\"submit\">\r\n {{'alfenoryauthv2.login.submit' | translate}}\r\n </button>\r\n </form>\r\n </div>\r\n</div>\r\n}", dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "ngmodule", type: TranslateModule }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }, { kind: "ngmodule", type: ReactiveFormsModule }, { kind: "directive", type: i1$2.ɵNgNoValidate, selector: "form:not([ngNoForm]):not([ngNativeValidate])" }, { kind: "directive", type: i1$2.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$2.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$2.NgControlStatusGroup, selector: "[formGroupName],[formArrayName],[ngModelGroup],[formGroup],form:not([ngNoForm]),[ngForm]" }, { kind: "directive", type: i1$2.FormGroupDirective, selector: "[formGroup]", inputs: ["formGroup"], outputs: ["ngSubmit"], exportAs: ["ngForm"] }, { kind: "directive", type: i1$2.FormControlName, selector: "[formControlName]", inputs: ["formControlName", "disabled", "ngModel"], outputs: ["ngModelChange"] }] });
316
349
  }
317
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: Login, decorators: [{
350
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: Login, decorators: [{
318
351
  type: Component,
319
352
  args: [{ selector: 'alfenoryauthv2-ui-login', imports: [CommonModule, TranslateModule, ReactiveFormsModule], template: "@if (isLoading()) {\r\n <div class=\"spinner-border\" role=\"status\">\r\n <span class=\"sr-only\"></span>\r\n </div>\r\n} \r\n@else {\r\n<div class=\"card\">\r\n <div class=\"card-header\">\r\n <h1>{{'alfenoryauthv2.login.header' | translate}}</h1>\r\n </div>\r\n <div class=\"card-body\">\r\n @if (errorType() !== 0) \r\n {\r\n <div class=\"alert alert-danger\" role=\"alert\">\r\n <b>{{'general.messages.error' | translate}}</b>\r\n @if (errorType() === 1) {\r\n {{'alfenoryauthv2.login.loginerror' | translate}}\r\n } \r\n @if (errorType() === 2) {\r\n {{'alfenoryauthv2.login.sessionrunouterror_text' | translate}}\r\n } \r\n </div>\r\n }\r\n <form [formGroup]=\"formGroup\" (ngSubmit)=\"onSubmit()\"> \r\n <div class=\"form-floating mb-3\">\r\n <input type=\"email\" class=\"form-control\" formControlName=\"username\" id=\"username\" name=\"username\" autocomplete=\"username\" placeholder=\"Email\" [ngClass]=\"{'is-invalid' : usernameControl.touched && usernameControl.errors}\">\r\n <label for=\"username\">{{'alfenoryauthv2.login.email' | translate}}</label>\r\n <div class=\"invalid-feedback\">\r\n {{'general.messages.required' | translate}}\r\n </div>\r\n </div>\r\n <div class=\"form-floating mb-3\">\r\n <input type=\"password\" class=\"form-control\" formControlName=\"password\" id=\"password\" name=\"password\" autocomplete=\"current-password\" placeholder=\"Passwort\" [ngClass]=\"{'is-invalid' : passwordControl.touched && passwordControl.errors}\">\r\n <label for=\"password\">{{'alfenoryauthv2.login.password' | translate}}</label>\r\n <div class=\"invalid-feedback\">\r\n {{'general.messages.required' | translate}}\r\n </div>\r\n </div>\r\n <button class=\"btn btn-primary\" type=\"submit\">\r\n {{'alfenoryauthv2.login.submit' | translate}}\r\n </button>\r\n </form>\r\n </div>\r\n</div>\r\n}" }]
320
353
  }] });
@@ -327,14 +360,83 @@ class Logout {
327
360
  ngOnInit() {
328
361
  this.authStore.logout();
329
362
  }
330
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: Logout, deps: [], target: i0.ɵɵFactoryTarget.Component });
331
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "19.2.15", type: Logout, isStandalone: true, selector: "alfenoryauthv2-ui-logout", ngImport: i0, template: "@if(isLoading()) {\r\n <div class=\"spinner-border\" role=\"status\">\r\n <span class=\"sr-only\"></span>\r\n </div>\r\n} @else { \r\n <div class=\"card\">\r\n <div class=\"card-header\">\r\n <h1>{{'alfenoryauthv2.logout.logout' | translate}}</h1>\r\n </div>\r\n <div class=\"card-body\">\r\n <p>{{'alfenoryauthv2.logout.success_logouttext' | translate}}</p>\r\n <a href=\"/auth/login\">{{ 'alfenoryauthv2.logout.login-link' | translate }}</a>\r\n </div> \r\n </div>\r\n}", dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: TranslateModule }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }] });
363
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: Logout, deps: [], target: i0.ɵɵFactoryTarget.Component });
364
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "19.2.20", type: Logout, isStandalone: true, selector: "alfenoryauthv2-ui-logout", ngImport: i0, template: "@if(isLoading()) {\r\n <div class=\"spinner-border\" role=\"status\">\r\n <span class=\"sr-only\"></span>\r\n </div>\r\n} @else { \r\n <div class=\"card\">\r\n <div class=\"card-header\">\r\n <h1>{{'alfenoryauthv2.logout.logout' | translate}}</h1>\r\n </div>\r\n <div class=\"card-body\">\r\n <p>{{'alfenoryauthv2.logout.success_logouttext' | translate}}</p>\r\n <a href=\"/auth/login\">{{ 'alfenoryauthv2.logout.login-link' | translate }}</a>\r\n </div> \r\n </div>\r\n}", dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: TranslateModule }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }] });
332
365
  }
333
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: Logout, decorators: [{
366
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: Logout, decorators: [{
334
367
  type: Component,
335
368
  args: [{ selector: 'alfenoryauthv2-ui-logout', imports: [CommonModule, TranslateModule], template: "@if(isLoading()) {\r\n <div class=\"spinner-border\" role=\"status\">\r\n <span class=\"sr-only\"></span>\r\n </div>\r\n} @else { \r\n <div class=\"card\">\r\n <div class=\"card-header\">\r\n <h1>{{'alfenoryauthv2.logout.logout' | translate}}</h1>\r\n </div>\r\n <div class=\"card-body\">\r\n <p>{{'alfenoryauthv2.logout.success_logouttext' | translate}}</p>\r\n <a href=\"/auth/login\">{{ 'alfenoryauthv2.logout.login-link' | translate }}</a>\r\n </div> \r\n </div>\r\n}" }]
336
369
  }] });
337
370
 
371
+ class BasicProvider {
372
+ apiUrl = inject(API_URL);
373
+ localstorage = inject(LocalStorageService);
374
+ connectionService = inject(ConnectionService);
375
+ get authHeader() {
376
+ return this.localstorage.getHeaderWithAuth();
377
+ }
378
+ getQueryFilter(filterParams) {
379
+ if (filterParams.length === 0) {
380
+ return '';
381
+ }
382
+ return filterParams.map((val) => `filter[${val.key}][${val.relation}]=${val.value}`).join('&');
383
+ }
384
+ getQueryUrl(filterQueryParams) {
385
+ const queryFilter = this.getQueryFilter(filterQueryParams);
386
+ return `${this.url}${queryFilter ? '?' : ''}${queryFilter}`;
387
+ }
388
+ getWithFilterQueryParams(params) {
389
+ return this.connectionService
390
+ .get(this.getQueryUrl(params), this.authHeader)
391
+ .pipe(switchMap((val) => of(val.data)));
392
+ }
393
+ //eslint-disable-next-line @typescript-eslint/no-explicit-any
394
+ createBasic(url, obj) {
395
+ return this.connectionService.post(url, obj, this.authHeader);
396
+ }
397
+ //eslint-disable-next-line @typescript-eslint/no-explicit-any
398
+ updateBasic(url, obj) {
399
+ return this.connectionService.patch(url, obj, this.authHeader);
400
+ }
401
+ removeBasic(url) {
402
+ return this.connectionService.delete(url, this.authHeader);
403
+ }
404
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: BasicProvider, deps: [], target: i0.ɵɵFactoryTarget.Directive });
405
+ static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "19.2.20", type: BasicProvider, isStandalone: true, ngImport: i0 });
406
+ }
407
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: BasicProvider, decorators: [{
408
+ type: Directive
409
+ }] });
410
+
411
+ class BasicProviderAlfenoryAuthV2 extends BasicProvider {
412
+ get basicUrlAuthUrl() {
413
+ return `v1/auth/${this.localstorage.getCurrentMembershipId() ?? ''}`;
414
+ }
415
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: BasicProviderAlfenoryAuthV2, deps: null, target: i0.ɵɵFactoryTarget.Directive });
416
+ static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "19.2.20", type: BasicProviderAlfenoryAuthV2, isStandalone: true, usesInheritance: true, ngImport: i0 });
417
+ }
418
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: BasicProviderAlfenoryAuthV2, decorators: [{
419
+ type: Directive
420
+ }] });
421
+
422
+ class UsergroupAttributesService extends BasicProviderAlfenoryAuthV2 {
423
+ get url() {
424
+ return `${this.basicUrlAuthUrl}/${this.localstorage.getUsergroupId()}/attributes`;
425
+ }
426
+ urlWithId(id) {
427
+ return `${this.url}/${id}`;
428
+ }
429
+ create(usergroupAttribute) {
430
+ return this.createBasic(this.url, usergroupAttribute);
431
+ }
432
+ update(usergroupAttribute) {
433
+ return this.updateBasic(this.urlWithId(usergroupAttribute.id), usergroupAttribute);
434
+ }
435
+ remove(id) {
436
+ return this.removeBasic(this.urlWithId(id));
437
+ }
438
+ }
439
+
338
440
  class SwitchMembership {
339
441
  authStore = inject(AuthStore);
340
442
  localStorageService = inject(LocalStorageService);
@@ -342,14 +444,524 @@ class SwitchMembership {
342
444
  switch(membership) {
343
445
  this.authStore.setMembershipId(membership);
344
446
  }
345
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: SwitchMembership, deps: [], target: i0.ɵɵFactoryTarget.Component });
346
- static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "19.2.15", type: SwitchMembership, isStandalone: true, selector: "alfenoryauthv2-ui-switch-membership", ngImport: i0, template: "<div class=\"list-group\">\r\n <div class=\"list-group-item\">\r\n <h1>{{'alfenoryauthv2.switchmembership.header' | translate}}</h1>\r\n </div>\r\n <div class=\"list-group-item\">\r\n <p>{{'alfenoryauthv2.switchmembership.text' | translate}}</p>\r\n @for (membership of memberships(); track membership.id) {\r\n <div class=\"pt-2\">\r\n <button class=\"btn btn-outline-primary\" (click)=\"switch(membership)\">{{membership.ug.name}}</button>\r\n </div>\r\n }\r\n </div>\r\n</div>", dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: TranslateModule }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }] });
447
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: SwitchMembership, deps: [], target: i0.ɵɵFactoryTarget.Component });
448
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "19.2.20", type: SwitchMembership, isStandalone: true, selector: "alfenoryauthv2-ui-switch-membership", ngImport: i0, template: "<div class=\"list-group\">\r\n <div class=\"list-group-item\">\r\n <h1>{{'alfenoryauthv2.switchmembership.header' | translate}}</h1>\r\n </div>\r\n <div class=\"list-group-item\">\r\n <p>{{'alfenoryauthv2.switchmembership.text' | translate}}</p>\r\n @for (membership of memberships(); track membership.id) {\r\n <div class=\"pt-2\">\r\n <button class=\"btn btn-outline-primary\" (click)=\"switch(membership)\">{{membership.ug.name}}</button>\r\n </div>\r\n }\r\n </div>\r\n</div>", dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: TranslateModule }, { kind: "pipe", type: i1$1.TranslatePipe, name: "translate" }] });
347
449
  }
348
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: SwitchMembership, decorators: [{
450
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: SwitchMembership, decorators: [{
349
451
  type: Component,
350
452
  args: [{ selector: 'alfenoryauthv2-ui-switch-membership', imports: [CommonModule, TranslateModule], template: "<div class=\"list-group\">\r\n <div class=\"list-group-item\">\r\n <h1>{{'alfenoryauthv2.switchmembership.header' | translate}}</h1>\r\n </div>\r\n <div class=\"list-group-item\">\r\n <p>{{'alfenoryauthv2.switchmembership.text' | translate}}</p>\r\n @for (membership of memberships(); track membership.id) {\r\n <div class=\"pt-2\">\r\n <button class=\"btn btn-outline-primary\" (click)=\"switch(membership)\">{{membership.ug.name}}</button>\r\n </div>\r\n }\r\n </div>\r\n</div>" }]
351
453
  }] });
352
454
 
455
+ class UsergroupAttributeBasic {
456
+ attribute = input.required();
457
+ translateService = inject(TranslateService);
458
+ label = computed(() => this.translateService.instant(`alfenoryauthv2.usergroupattributes.${this.attribute().key}`));
459
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeBasic, deps: [], target: i0.ɵɵFactoryTarget.Directive });
460
+ static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "19.2.20", type: UsergroupAttributeBasic, isStandalone: true, inputs: { attribute: { classPropertyName: "attribute", publicName: "attribute", isSignal: true, isRequired: true, transformFunction: null } }, ngImport: i0 });
461
+ }
462
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeBasic, decorators: [{
463
+ type: Directive
464
+ }] });
465
+
466
+ class UsergroupAttributeUpdateFieldBase extends UsergroupAttributeBasic {
467
+ valueChanges = output();
468
+ value = '';
469
+ oldValue = '';
470
+ constructor() {
471
+ super();
472
+ effect(() => {
473
+ this.value = this.attribute().value ?? '';
474
+ this.oldValue = this.value;
475
+ });
476
+ }
477
+ triggerValueChange() {
478
+ if (this.oldValue !== this.value) {
479
+ this.valueChanges.emit(this.value);
480
+ }
481
+ }
482
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdateFieldBase, deps: [], target: i0.ɵɵFactoryTarget.Directive });
483
+ static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "19.2.20", type: UsergroupAttributeUpdateFieldBase, isStandalone: true, outputs: { valueChanges: "valueChanges" }, usesInheritance: true, ngImport: i0 });
484
+ }
485
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdateFieldBase, decorators: [{
486
+ type: Directive
487
+ }], ctorParameters: () => [] });
488
+
489
+ class UsergroupAttributeUpdateTextfield extends UsergroupAttributeUpdateFieldBase {
490
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdateTextfield, deps: null, target: i0.ɵɵFactoryTarget.Component });
491
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "19.2.20", type: UsergroupAttributeUpdateTextfield, isStandalone: true, selector: "alfenoryauthv2-usergroup-attributes-update-textfield", usesInheritance: true, ngImport: i0, template: `
492
+ <div class="form-floating">
493
+ <input
494
+ id="attributeTextField"
495
+ type="text"
496
+ class="form-control"
497
+ [(ngModel)]="value"
498
+ (change)="triggerValueChange()"
499
+ />
500
+ <label for="attributeTextField">{{ label() }}</label>
501
+ </div>
502
+ `, isInline: true, dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$2.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$2.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$2.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }] });
503
+ }
504
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdateTextfield, decorators: [{
505
+ type: Component,
506
+ args: [{
507
+ selector: 'alfenoryauthv2-usergroup-attributes-update-textfield',
508
+ template: `
509
+ <div class="form-floating">
510
+ <input
511
+ id="attributeTextField"
512
+ type="text"
513
+ class="form-control"
514
+ [(ngModel)]="value"
515
+ (change)="triggerValueChange()"
516
+ />
517
+ <label for="attributeTextField">{{ label() }}</label>
518
+ </div>
519
+ `,
520
+ imports: [FormsModule],
521
+ }]
522
+ }] });
523
+
524
+ class UsergroupAttributeUpdateNumber extends UsergroupAttributeUpdateFieldBase {
525
+ triggerValueChange() {
526
+ this.valueChanges.emit(`${this.value}`);
527
+ }
528
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdateNumber, deps: null, target: i0.ɵɵFactoryTarget.Component });
529
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "19.2.20", type: UsergroupAttributeUpdateNumber, isStandalone: true, selector: "alfenoryauthv2-usergroup-attributes-update-number", usesInheritance: true, ngImport: i0, template: `
530
+ <div class="form-floating">
531
+ <input
532
+ id="attributeTextField"
533
+ type="number"
534
+ class="form-control"
535
+ [(ngModel)]="value"
536
+ (change)="triggerValueChange()"
537
+ />
538
+ <label for="attributeTextField">{{ label() }}</label>
539
+ </div>
540
+ `, isInline: true, dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$2.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$2.NumberValueAccessor, selector: "input[type=number][formControlName],input[type=number][formControl],input[type=number][ngModel]" }, { kind: "directive", type: i1$2.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$2.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }] });
541
+ }
542
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdateNumber, decorators: [{
543
+ type: Component,
544
+ args: [{
545
+ selector: 'alfenoryauthv2-usergroup-attributes-update-number',
546
+ template: `
547
+ <div class="form-floating">
548
+ <input
549
+ id="attributeTextField"
550
+ type="number"
551
+ class="form-control"
552
+ [(ngModel)]="value"
553
+ (change)="triggerValueChange()"
554
+ />
555
+ <label for="attributeTextField">{{ label() }}</label>
556
+ </div>
557
+ `,
558
+ imports: [FormsModule],
559
+ }]
560
+ }] });
561
+
562
+ class UsergroupAttributeUpdateTextarea extends UsergroupAttributeUpdateFieldBase {
563
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdateTextarea, deps: null, target: i0.ɵɵFactoryTarget.Component });
564
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "19.2.20", type: UsergroupAttributeUpdateTextarea, isStandalone: true, selector: "alfenoryauthv2-usergroup-attributes-update-textarea", usesInheritance: true, ngImport: i0, template: `
565
+ <div class="form-floating">
566
+ <textarea
567
+ id="attributeTextField"
568
+ class="form-control"
569
+ [(ngModel)]="value"
570
+ (change)="triggerValueChange()"
571
+ ></textarea>
572
+ <label for="attributeTextField">{{ label() }}</label>
573
+ </div>
574
+ `, isInline: true, dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$2.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$2.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$2.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }] });
575
+ }
576
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdateTextarea, decorators: [{
577
+ type: Component,
578
+ args: [{
579
+ selector: 'alfenoryauthv2-usergroup-attributes-update-textarea',
580
+ template: `
581
+ <div class="form-floating">
582
+ <textarea
583
+ id="attributeTextField"
584
+ class="form-control"
585
+ [(ngModel)]="value"
586
+ (change)="triggerValueChange()"
587
+ ></textarea>
588
+ <label for="attributeTextField">{{ label() }}</label>
589
+ </div>
590
+ `,
591
+ imports: [FormsModule],
592
+ }]
593
+ }] });
594
+
595
+ class UsergroupAttributeUpdateSelect extends UsergroupAttributeUpdateFieldBase {
596
+ selectableValues = computed(() => {
597
+ const mapping = this.attribute().typeMapping;
598
+ if ('selectableValues' in mapping) {
599
+ return mapping.selectableValues;
600
+ }
601
+ return [];
602
+ });
603
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdateSelect, deps: null, target: i0.ɵɵFactoryTarget.Component });
604
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "19.2.20", type: UsergroupAttributeUpdateSelect, isStandalone: true, selector: "alfenoryauthv2-usergroup-attributes-update-select", usesInheritance: true, ngImport: i0, template: `
605
+ <div class="form-floating">
606
+ <select
607
+ id="attributeTextField"
608
+ class="form-control"
609
+ [(ngModel)]="value"
610
+ (change)="triggerValueChange()"
611
+ >
612
+ @for (value of selectableValues(); track value) {
613
+ <option [value]="value">
614
+ {{ 'alfenoryauthv2.usergroupattributes.selectable_' + value | translate }}
615
+ </option>
616
+ }
617
+ </select>
618
+ <label for="attributeTextField">{{ label() }}</label>
619
+ </div>
620
+ `, isInline: true, dependencies: [{ kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$2.NgSelectOption, selector: "option", inputs: ["ngValue", "value"] }, { kind: "directive", type: i1$2.ɵNgSelectMultipleOption, selector: "option", inputs: ["ngValue", "value"] }, { kind: "directive", type: i1$2.SelectControlValueAccessor, selector: "select:not([multiple])[formControlName],select:not([multiple])[formControl],select:not([multiple])[ngModel]", inputs: ["compareWith"] }, { kind: "directive", type: i1$2.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$2.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "pipe", type: TranslatePipe, name: "translate" }] });
621
+ }
622
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdateSelect, decorators: [{
623
+ type: Component,
624
+ args: [{
625
+ selector: 'alfenoryauthv2-usergroup-attributes-update-select',
626
+ template: `
627
+ <div class="form-floating">
628
+ <select
629
+ id="attributeTextField"
630
+ class="form-control"
631
+ [(ngModel)]="value"
632
+ (change)="triggerValueChange()"
633
+ >
634
+ @for (value of selectableValues(); track value) {
635
+ <option [value]="value">
636
+ {{ 'alfenoryauthv2.usergroupattributes.selectable_' + value | translate }}
637
+ </option>
638
+ }
639
+ </select>
640
+ <label for="attributeTextField">{{ label() }}</label>
641
+ </div>
642
+ `,
643
+ imports: [FormsModule, TranslatePipe],
644
+ }]
645
+ }] });
646
+
647
+ class UsergroupAttributeUpdate {
648
+ attribute = input.required();
649
+ usergroupAttributeService = inject(UsergroupAttributesService);
650
+ EditType = UsergroupAttributeEditType;
651
+ value = '';
652
+ didSave = output();
653
+ doSave() {
654
+ if (this.value) {
655
+ if (this.attribute().id) {
656
+ this.usergroupAttributeService.update(this.toModel());
657
+ }
658
+ else {
659
+ this.usergroupAttributeService.create(this.toModel());
660
+ }
661
+ }
662
+ else {
663
+ if (this.attribute().id) {
664
+ this.usergroupAttributeService.remove(this.attribute().id);
665
+ }
666
+ }
667
+ this.didSave.emit();
668
+ }
669
+ updateValue(val) {
670
+ this.value = val;
671
+ }
672
+ toModel() {
673
+ return {
674
+ ...this.attribute(),
675
+ value: this.value,
676
+ };
677
+ }
678
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdate, deps: [], target: i0.ɵɵFactoryTarget.Component });
679
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "19.2.20", type: UsergroupAttributeUpdate, isStandalone: true, selector: "alfenoryauthv2-usergroup-attributes-update", inputs: { attribute: { classPropertyName: "attribute", publicName: "attribute", isSignal: true, isRequired: true, transformFunction: null } }, outputs: { didSave: "didSave" }, ngImport: i0, template: `
680
+ @switch (this.attribute().typeMapping.editType) {
681
+ @case (EditType.InputArea) {
682
+ <alfenoryauthv2-usergroup-attributes-update-textarea
683
+ [attribute]="attribute()"
684
+ (valueChanges)="updateValue($event)"
685
+ />
686
+ }
687
+ @case (EditType.InputNumber) {
688
+ <alfenoryauthv2-usergroup-attributes-update-number
689
+ [attribute]="attribute()"
690
+ (valueChanges)="updateValue($event)"
691
+ />
692
+ }
693
+ @case (EditType.selectTypes) {
694
+ <alfenoryauthv2-usergroup-attributes-update-select
695
+ [attribute]="attribute()"
696
+ (valueChanges)="updateValue($event)"
697
+ />
698
+ }
699
+ @default {
700
+ <alfenoryauthv2-usergroup-attributes-update-textfield
701
+ [attribute]="attribute()"
702
+ (valueChanges)="updateValue($event)"
703
+ />
704
+ }
705
+ }
706
+
707
+ <button
708
+ class="btn btn-outline-primary"
709
+ (click)="doSave()"
710
+ title="{{ 'general.messages.save' | translate }}"
711
+ >
712
+ <i class="bi-save"></i>
713
+ </button>
714
+ `, isInline: true, dependencies: [{ kind: "component", type: UsergroupAttributeUpdateTextfield, selector: "alfenoryauthv2-usergroup-attributes-update-textfield" }, { kind: "component", type: UsergroupAttributeUpdateNumber, selector: "alfenoryauthv2-usergroup-attributes-update-number" }, { kind: "component", type: UsergroupAttributeUpdateTextarea, selector: "alfenoryauthv2-usergroup-attributes-update-textarea" }, { kind: "component", type: UsergroupAttributeUpdateSelect, selector: "alfenoryauthv2-usergroup-attributes-update-select" }, { kind: "pipe", type: TranslatePipe, name: "translate" }] });
715
+ }
716
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributeUpdate, decorators: [{
717
+ type: Component,
718
+ args: [{
719
+ selector: 'alfenoryauthv2-usergroup-attributes-update',
720
+ template: `
721
+ @switch (this.attribute().typeMapping.editType) {
722
+ @case (EditType.InputArea) {
723
+ <alfenoryauthv2-usergroup-attributes-update-textarea
724
+ [attribute]="attribute()"
725
+ (valueChanges)="updateValue($event)"
726
+ />
727
+ }
728
+ @case (EditType.InputNumber) {
729
+ <alfenoryauthv2-usergroup-attributes-update-number
730
+ [attribute]="attribute()"
731
+ (valueChanges)="updateValue($event)"
732
+ />
733
+ }
734
+ @case (EditType.selectTypes) {
735
+ <alfenoryauthv2-usergroup-attributes-update-select
736
+ [attribute]="attribute()"
737
+ (valueChanges)="updateValue($event)"
738
+ />
739
+ }
740
+ @default {
741
+ <alfenoryauthv2-usergroup-attributes-update-textfield
742
+ [attribute]="attribute()"
743
+ (valueChanges)="updateValue($event)"
744
+ />
745
+ }
746
+ }
747
+
748
+ <button
749
+ class="btn btn-outline-primary"
750
+ (click)="doSave()"
751
+ title="{{ 'general.messages.save' | translate }}"
752
+ >
753
+ <i class="bi-save"></i>
754
+ </button>
755
+ `,
756
+ imports: [
757
+ UsergroupAttributeUpdateTextfield,
758
+ UsergroupAttributeUpdateNumber,
759
+ UsergroupAttributeUpdateTextarea,
760
+ UsergroupAttributeUpdateSelect,
761
+ TranslatePipe,
762
+ ],
763
+ }]
764
+ }] });
765
+
766
+ class UsergroupAttributesListDetail {
767
+ attribute = input.required();
768
+ keyName = computed(() => `alfenoryauthv2.usergroupattributes.${this.attribute()?.key}`);
769
+ translateService = inject(TranslateService);
770
+ modalService = inject(NgbModal);
771
+ value = computed(() => this.getValue());
772
+ didSaveValue = output();
773
+ getValue() {
774
+ switch (this.attribute().typeMapping.editType) {
775
+ case UsergroupAttributeEditType.InputArea:
776
+ return this.translateService.instant('alfenoryauthv2.usergroup-attribute.long-text');
777
+ case UsergroupAttributeEditType.selectTypes:
778
+ return this.translateService.instant(`alfenoryauthv2.usergroup-attribute.${this.attribute().value === '' ? 'novalue' : this.attribute().value}`);
779
+ default:
780
+ return this.attribute().value;
781
+ }
782
+ }
783
+ openUpdate() {
784
+ const component = this.modalService.open(UsergroupAttributeUpdate);
785
+ component.componentInstance.usergroupAttribute = signal(this.attribute());
786
+ component.closed.subscribe(() => this.didSaveValue.emit());
787
+ }
788
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributesListDetail, deps: [], target: i0.ɵɵFactoryTarget.Component });
789
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "19.2.20", type: UsergroupAttributesListDetail, isStandalone: true, selector: "alfenoryauthv2-usergroup-attributes-list-detail", inputs: { attribute: { classPropertyName: "attribute", publicName: "attribute", isSignal: true, isRequired: true, transformFunction: null } }, outputs: { didSaveValue: "didSaveValue" }, ngImport: i0, template: `
790
+ <div>{{ keyName() }} : {{ value() }}</div>
791
+
792
+ <button
793
+ class="btn btn-outline-primary"
794
+ title="{{ 'general.messages.update' | translate }}"
795
+ (click)="openUpdate()"
796
+ >
797
+ <i class="bi-pen"></i>
798
+ </button>
799
+ `, isInline: true, dependencies: [{ kind: "pipe", type: TranslatePipe, name: "translate" }] });
800
+ }
801
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributesListDetail, decorators: [{
802
+ type: Component,
803
+ args: [{
804
+ selector: 'alfenoryauthv2-usergroup-attributes-list-detail',
805
+ template: `
806
+ <div>{{ keyName() }} : {{ value() }}</div>
807
+
808
+ <button
809
+ class="btn btn-outline-primary"
810
+ title="{{ 'general.messages.update' | translate }}"
811
+ (click)="openUpdate()"
812
+ >
813
+ <i class="bi-pen"></i>
814
+ </button>
815
+ `,
816
+ imports: [TranslatePipe],
817
+ }]
818
+ }] });
819
+
820
+ class UsergroupAttributesList {
821
+ attributes = input();
822
+ didSaveValue = output();
823
+ handleDidSaveValue() {
824
+ this.didSaveValue.emit();
825
+ }
826
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributesList, deps: [], target: i0.ɵɵFactoryTarget.Component });
827
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "19.2.20", type: UsergroupAttributesList, isStandalone: true, selector: "alfenoryauthv2-usergroup-attributes-list", inputs: { attributes: { classPropertyName: "attributes", publicName: "attributes", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { didSaveValue: "didSaveValue" }, ngImport: i0, template: `
828
+ <div class="list-group">
829
+ <div class="list-group-item fw-bold">
830
+ {{ 'alfenoryauthv2.usergroup-attributes.usergroup-attribute' | translate }}
831
+ </div>
832
+ @for (attribute of attributes(); track attribute.id) {
833
+ <alfenoryauthv2-usergroup-attributes-list-detail
834
+ class="list-group-item d-flex justify-content-between"
835
+ [attribute]="attribute"
836
+ (didSaveValue)="handleDidSaveValue()"
837
+ />
838
+ } @empty {
839
+ <div class="list-group-item">
840
+ {{ 'general.messages.emptylist' | translate }}
841
+ </div>
842
+ }
843
+ </div>
844
+ `, isInline: true, dependencies: [{ kind: "pipe", type: TranslatePipe, name: "translate" }, { kind: "component", type: UsergroupAttributesListDetail, selector: "alfenoryauthv2-usergroup-attributes-list-detail", inputs: ["attribute"], outputs: ["didSaveValue"] }] });
845
+ }
846
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributesList, decorators: [{
847
+ type: Component,
848
+ args: [{
849
+ selector: 'alfenoryauthv2-usergroup-attributes-list',
850
+ template: `
851
+ <div class="list-group">
852
+ <div class="list-group-item fw-bold">
853
+ {{ 'alfenoryauthv2.usergroup-attributes.usergroup-attribute' | translate }}
854
+ </div>
855
+ @for (attribute of attributes(); track attribute.id) {
856
+ <alfenoryauthv2-usergroup-attributes-list-detail
857
+ class="list-group-item d-flex justify-content-between"
858
+ [attribute]="attribute"
859
+ (didSaveValue)="handleDidSaveValue()"
860
+ />
861
+ } @empty {
862
+ <div class="list-group-item">
863
+ {{ 'general.messages.emptylist' | translate }}
864
+ </div>
865
+ }
866
+ </div>
867
+ `,
868
+ imports: [TranslatePipe, UsergroupAttributesListDetail],
869
+ }]
870
+ }] });
871
+
872
+ class UsergroupAttributes {
873
+ editableUsergroupAttributesTypes = input.required();
874
+ authStore = inject(AuthStore);
875
+ attributesService = inject(UsergroupAttributesService);
876
+ attributes = signal([]);
877
+ isLoading = signal(false);
878
+ hasPrivilege = computed(() => this.authStore.hasPriv('usergroupattribute.get'));
879
+ constructor() {
880
+ this.authStore.checkValid();
881
+ effect(() => {
882
+ if (this.hasPrivilege()) {
883
+ this.loadUsergroupAttributes();
884
+ }
885
+ });
886
+ }
887
+ loadUsergroupAttributes() {
888
+ this.isLoading.set(true);
889
+ this.attributesService.getWithFilterQueryParams([]).subscribe((ugAts) => {
890
+ this.isLoading.set(false);
891
+ this.attributes.set(ugAts
892
+ //setUsergroupAttributes with Mapping
893
+ .map((val) => this.toUsergroupAttributeWithType(val))
894
+ //filter where to mapping are found
895
+ .filter((val) => val !== undefined));
896
+ this.addMissingTypeMappings();
897
+ });
898
+ }
899
+ toUsergroupAttributeWithType(usergroupAttribute) {
900
+ const attributeTypeMapping = this.editableUsergroupAttributesTypes().find((val) => val.key === usergroupAttribute.key);
901
+ if (attributeTypeMapping) {
902
+ return {
903
+ ...usergroupAttribute,
904
+ typeMapping: attributeTypeMapping,
905
+ };
906
+ }
907
+ return undefined;
908
+ }
909
+ addMissingTypeMappings() {
910
+ const currentAttributes = this.attributes();
911
+ const existingKeys = new Set(currentAttributes.map((a) => a.key));
912
+ const newElements = this.editableUsergroupAttributesTypes()
913
+ .filter((type) => !existingKeys.has(type.key))
914
+ .map((type) => ({
915
+ key: type.key,
916
+ value: '',
917
+ id: '',
918
+ typeMapping: type,
919
+ }));
920
+ if (newElements.length > 0) {
921
+ this.attributes.set([...currentAttributes, ...newElements]);
922
+ }
923
+ }
924
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributes, deps: [], target: i0.ɵɵFactoryTarget.Component });
925
+ static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "19.2.20", type: UsergroupAttributes, isStandalone: true, selector: "ng-component", inputs: { editableUsergroupAttributesTypes: { classPropertyName: "editableUsergroupAttributesTypes", publicName: "editableUsergroupAttributesTypes", isSignal: true, isRequired: true, transformFunction: null } }, ngImport: i0, template: `
926
+ @if (hasPrivilege()) {
927
+ @if (isLoading()) {
928
+ <div class="spinner-border" role="status">
929
+ <span class="visually-hidden">Loading...</span>
930
+ </div>
931
+ } @else {
932
+ <alfenoryauthv2-usergroup-attributes-list
933
+ [attributes]="attributes()"
934
+ (didSaveValue)="loadUsergroupAttributes()"
935
+ />
936
+ }
937
+ } @else {
938
+ <p>{{ 'general.messages.nopriv' | translate }}</p>
939
+ }
940
+ `, isInline: true, dependencies: [{ kind: "pipe", type: TranslatePipe, name: "translate" }, { kind: "component", type: UsergroupAttributesList, selector: "alfenoryauthv2-usergroup-attributes-list", inputs: ["attributes"], outputs: ["didSaveValue"] }] });
941
+ }
942
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: UsergroupAttributes, decorators: [{
943
+ type: Component,
944
+ args: [{
945
+ template: `
946
+ @if (hasPrivilege()) {
947
+ @if (isLoading()) {
948
+ <div class="spinner-border" role="status">
949
+ <span class="visually-hidden">Loading...</span>
950
+ </div>
951
+ } @else {
952
+ <alfenoryauthv2-usergroup-attributes-list
953
+ [attributes]="attributes()"
954
+ (didSaveValue)="loadUsergroupAttributes()"
955
+ />
956
+ }
957
+ } @else {
958
+ <p>{{ 'general.messages.nopriv' | translate }}</p>
959
+ }
960
+ `,
961
+ imports: [TranslatePipe, UsergroupAttributesList],
962
+ }]
963
+ }], ctorParameters: () => [] });
964
+
353
965
  class HideIfNoPriv {
354
966
  hideIfNoPriv = input();
355
967
  authService = inject(AuthStore);
@@ -367,10 +979,10 @@ class HideIfNoPriv {
367
979
  const isVisible = this.authService.checkValid() && this.authService.hasOneOfPrivs(privileges);
368
980
  this.elementRef.nativeElement.style.display = isVisible ? '' : 'none';
369
981
  }
370
- static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: HideIfNoPriv, deps: [], target: i0.ɵɵFactoryTarget.Directive });
371
- static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "19.2.15", type: HideIfNoPriv, isStandalone: true, selector: "[hideIfNoPriv]", inputs: { hideIfNoPriv: { classPropertyName: "hideIfNoPriv", publicName: "hideIfNoPriv", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0 });
982
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: HideIfNoPriv, deps: [], target: i0.ɵɵFactoryTarget.Directive });
983
+ static ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "17.1.0", version: "19.2.20", type: HideIfNoPriv, isStandalone: true, selector: "[hideIfNoPriv]", inputs: { hideIfNoPriv: { classPropertyName: "hideIfNoPriv", publicName: "hideIfNoPriv", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0 });
372
984
  }
373
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.15", ngImport: i0, type: HideIfNoPriv, decorators: [{
985
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.20", ngImport: i0, type: HideIfNoPriv, decorators: [{
374
986
  type: Directive,
375
987
  args: [{
376
988
  selector: '[hideIfNoPriv]'
@@ -381,5 +993,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.15", ngImpo
381
993
  * Generated bundle index. Do not edit.
382
994
  */
383
995
 
384
- export { API_URL, AuthService, AuthStore, BasicLocalStorageService, ConnectionService, HideIfNoPriv, LocalStorageKeys, LocalStorageService, Login, Logout, SwitchMembership, authGuard };
996
+ export { API_URL, AuthService, AuthStore, BasicLocalStorageService, ConnectionService, GetFilterQueryRelation, HideIfNoPriv, LocalStorageKeys, LocalStorageService, Login, Logout, SwitchMembership, UsergroupAttributeEditType, UsergroupAttributes, UsergroupAttributesService, authGuard };
385
997
  //# sourceMappingURL=alfenory-authv2-ui.mjs.map