From edcaebe9ac409fb8f3f036cff3d74a9bd17e9f51 Mon Sep 17 00:00:00 2001 From: Vladyslav_Prykhodko Date: Mon, 7 Sep 2020 17:19:12 +0300 Subject: [PATCH] Refactoring layout oauth2 templated --- ui-ngx/src/app/core/http/admin.service.ts | 6 +- .../modules/home/pages/admin/admin.module.ts | 4 +- .../edit-redirect-uri-panel.component.html | 49 ++ .../edit-redirect-uri-panel.component.scss | 18 + .../edit-redirect-uri-panel.component.ts | 76 +++ .../admin/oauth2-settings.component.html | 570 +++++++++--------- .../admin/oauth2-settings.component.scss | 1 + .../pages/admin/oauth2-settings.component.ts | 112 +++- .../src/app/shared/models/settings.models.ts | 5 +- .../assets/locale/locale.constant-en_US.json | 2 +- 10 files changed, 529 insertions(+), 314 deletions(-) create mode 100644 ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.html create mode 100644 ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.scss create mode 100644 ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.ts diff --git a/ui-ngx/src/app/core/http/admin.service.ts b/ui-ngx/src/app/core/http/admin.service.ts index ddc2069d4a..1fb6f717c3 100644 --- a/ui-ngx/src/app/core/http/admin.service.ts +++ b/ui-ngx/src/app/core/http/admin.service.ts @@ -63,8 +63,12 @@ export class AdminService { return this.http.get(`/api/oauth2/config`, defaultHttpOptionsFromConfig(config)); } + public getOAuth2Template(config?: RequestConfig): Observable { + return this.http.get(`/api/oauth2/config/template`, defaultHttpOptionsFromConfig(config)); + } + public saveOAuth2Settings(OAuth2Setting: OAuth2Settings, - config?: RequestConfig): Observable { + config?: RequestConfig): Observable { return this.http.post('/api/oauth2/config', OAuth2Setting, defaultHttpOptionsFromConfig(config)); } diff --git a/ui-ngx/src/app/modules/home/pages/admin/admin.module.ts b/ui-ngx/src/app/modules/home/pages/admin/admin.module.ts index 73fef6a32f..189550d1c2 100644 --- a/ui-ngx/src/app/modules/home/pages/admin/admin.module.ts +++ b/ui-ngx/src/app/modules/home/pages/admin/admin.module.ts @@ -24,6 +24,7 @@ import { GeneralSettingsComponent } from '@modules/home/pages/admin/general-sett import { SecuritySettingsComponent } from '@modules/home/pages/admin/security-settings.component'; import { HomeComponentsModule } from '@modules/home/components/home-components.module'; import { OAuth2SettingsComponent } from '@modules/home/pages/admin/oauth2-settings.component'; +import { EditRedirectUriPanelComponent } from './edit-redirect-uri-panel.component'; @NgModule({ declarations: @@ -31,7 +32,8 @@ import { OAuth2SettingsComponent } from '@modules/home/pages/admin/oauth2-settin GeneralSettingsComponent, MailServerComponent, SecuritySettingsComponent, - OAuth2SettingsComponent + OAuth2SettingsComponent, + EditRedirectUriPanelComponent ], imports: [ CommonModule, diff --git a/ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.html b/ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.html new file mode 100644 index 0000000000..6f4efc061c --- /dev/null +++ b/ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.html @@ -0,0 +1,49 @@ + +
+
+ + admin.oauth2.redirect-uri-template + + + {{ 'admin.oauth2.redirect-uri-template-required' | translate }} + + + {{ 'admin.oauth2.uri-pattern-error' | translate }} + + +
+
+ + + +
+
diff --git a/ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.scss b/ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.scss new file mode 100644 index 0000000000..43b16cf165 --- /dev/null +++ b/ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.scss @@ -0,0 +1,18 @@ +/** + * Copyright © 2016-2020 The Thingsboard Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +:host { + background-color: #f9f9f9; +} diff --git a/ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.ts b/ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.ts new file mode 100644 index 0000000000..44f6bff0f3 --- /dev/null +++ b/ui-ngx/src/app/modules/home/pages/admin/edit-redirect-uri-panel.component.ts @@ -0,0 +1,76 @@ +/// +/// Copyright © 2016-2020 The Thingsboard Authors +/// +/// Licensed under the Apache License, Version 2.0 (the "License"); +/// you may not use this file except in compliance with the License. +/// You may obtain a copy of the License at +/// +/// http://www.apache.org/licenses/LICENSE-2.0 +/// +/// Unless required by applicable law or agreed to in writing, software +/// distributed under the License is distributed on an "AS IS" BASIS, +/// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +/// See the License for the specific language governing permissions and +/// limitations under the License. +/// + +import { Component, Inject, InjectionToken, OnInit, SkipSelf } from '@angular/core'; +import { ErrorStateMatcher } from '@angular/material/core'; +import { Store } from '@ngrx/store'; +import { AppState } from '@core/core.state'; +import { FormBuilder, FormControl, FormGroup, FormGroupDirective, NgForm, Validators } from '@angular/forms'; +import { PageComponent } from '@shared/components/page.component'; +import { OverlayRef } from '@angular/cdk/overlay'; + +export const EDIT_REDIRECT_URI_PANEL_DATA = new InjectionToken('EditRedirectUriPanelData'); + +export interface EditRedirectUriPanelData { + redirectURI: any; +} + +@Component({ + selector: 'tb-edit-redirect-uri-panel', + templateUrl: './edit-redirect-uri-panel.component.html', + providers: [{provide: ErrorStateMatcher, useExisting: EditRedirectUriPanelComponent}], + styleUrls: ['./edit-redirect-uri-panel.component.scss'] +}) +export class EditRedirectUriPanelComponent extends PageComponent implements OnInit, ErrorStateMatcher { + + private URL_REGEXP = /^[A-Za-z][A-Za-z\d.+-]*:\/*(?:\w+(?::\w+)?@)?[^\s/]+(?::\d+)?(?:\/[\w#!:.?+=&%@\-/]*)?$/; + + redirectURIFormGroup: FormGroup; + + result: any = null; + + submitted = false; + + constructor(protected store: Store, + @Inject(EDIT_REDIRECT_URI_PANEL_DATA) public data: EditRedirectUriPanelData, + @SkipSelf() private errorStateMatcher: ErrorStateMatcher, + public overlayRef: OverlayRef, + public fb: FormBuilder) { + super(store); + } + + ngOnInit(): void { + this.redirectURIFormGroup = this.fb.group({ + value: [this.data.redirectURI, [Validators.required, Validators.pattern(this.URL_REGEXP)]] + }); + } + + isErrorState(control: FormControl | null, form: FormGroupDirective | NgForm | null): boolean { + const originalErrorState = this.errorStateMatcher.isErrorState(control, form); + const customErrorState = !!(control && control.invalid && this.submitted); + return originalErrorState || customErrorState; + } + + cancel(): void { + this.overlayRef.dispose(); + } + + update(): void { + this.submitted = true; + this.result = this.redirectURIFormGroup.get('value').value; + this.overlayRef.dispose(); + } +} diff --git a/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.html b/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.html index f1c3bfaf62..bb77210ba8 100644 --- a/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.html +++ b/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.html @@ -40,300 +40,316 @@ {{ domain.get('domainName').value ? domain.get('domainName').value : ("admin.new-domain" | translate) }} - + + - - admin.domain-name - - - {{ 'admin.error-verification-url' | translate }} - - - {{ 'admin.domain-name-unique' | translate }} - - - - - admin.oauth2.redirect-uri-template - - - {{ 'admin.oauth2.redirect-uri-template-required' | translate }} - - - {{ 'admin.oauth2.uri-pattern-error' | translate }} - - - - -
- -
-
- -
- - admin.oauth2.registration-id - - - {{ 'admin.oauth2.registration-id-required' | translate }} - - - {{ 'admin.oauth2.registration-id-unique' | translate }} - - - -
- - admin.oauth2.client-id - - - {{ 'admin.oauth2.client-id-required' | translate }} - - - - - admin.oauth2.client-secret - - - {{ 'admin.oauth2.client-secret-required' | translate }} - - -
- -
- - admin.oauth2.access-token-uri - - - {{ 'admin.oauth2.access-token-uri-required' | translate }} - - - {{ 'admin.oauth2.uri-pattern-error' | translate }} - - - - - admin.oauth2.authorization-uri - - - {{ 'admin.oauth2.authorization-uri-required' | translate }} - - - {{ 'admin.oauth2.uri-pattern-error' | translate }} - - -
- - - admin.oauth2.scope - - - {{scope}} - cancel - - - - - {{ 'admin.oauth2.jwk-set-uri-required' | translate }} - - - -
- - admin.oauth2.jwk-set-uri - - - {{ 'admin.oauth2.jwk-set-uri-required' | translate }} - - - {{ 'admin.oauth2.uri-pattern-error' | translate }} - - - - - admin.oauth2.user-info-uri - - - {{ 'admin.oauth2.user-info-uri-required' | translate }} - - - {{ 'admin.oauth2.uri-pattern-error' | translate }} - - -
- - - admin.oauth2.client-authentication-method - - - {{ clientAuthenticationMethod | uppercase }} - - - - - - admin.oauth2.user-name-attribute-name - - - {{ 'admin.oauth2.user-name-attribute-name-required' | translate }} - - - -
-
- - {{ 'admin.oauth2.allow-user-creation' | translate }} - - - {{ 'admin.oauth2.activate-user' | translate }} - -
- - - admin.oauth2.type - - - {{ converterTypeExternalUser }} - - - - -
- - admin.oauth2.email-attribute-key - - - {{ 'admin.oauth2.email-attribute-key-required' | translate }} - + + + admin.domain-name + + + {{ 'admin.error-verification-url' | translate }} + + + {{ 'admin.domain-name-unique' | translate }} + + + + +
+ + + + {{ registration.get('providerName').value }} + + + + + + + +
+ + Login Provider + + + {{ provider | uppercase }} + +
- admin.oauth2.first-name-attribute-key - - - - - admin.oauth2.last-name-attribute-key - - -
- -
- - admin.oauth2.tenant-name-strategy - - - {{ tenantNameStrategy }} - - - - - - admin.oauth2.tenant-name-pattern - - - {{ 'admin.oauth2.tenant-name-pattern-required' | translate }} + admin.oauth2.client-id + + + {{ 'admin.oauth2.client-id-required' | translate }} -
- - admin.oauth2.customer-name-pattern - - - -
- admin.oauth2.default-dashboard-name - + admin.oauth2.client-secret + + + {{ 'admin.oauth2.client-secret-required' | translate }} + - - - {{ 'admin.oauth2.always-fullscreen' | translate}} -
-
- -
- - admin.oauth2.url - - - {{ 'admin.oauth2.url-required' | translate }} - - - {{ 'admin.oauth2.url-pattern' | translate }} - - + + +
+ + admin.oauth2.access-token-uri + + + {{ 'admin.oauth2.access-token-uri-required' | translate }} + + + {{ 'admin.oauth2.uri-pattern-error' | translate }} + + + + + admin.oauth2.authorization-uri + + + {{ 'admin.oauth2.authorization-uri-required' | translate }} + + + {{ 'admin.oauth2.uri-pattern-error' | translate }} + + +
+ +
+ + admin.oauth2.jwk-set-uri + + + {{ 'admin.oauth2.jwk-set-uri-required' | translate }} + + + {{ 'admin.oauth2.uri-pattern-error' | translate }} + + + + + admin.oauth2.user-info-uri + + + {{ 'admin.oauth2.user-info-uri-required' | translate }} + + + {{ 'admin.oauth2.uri-pattern-error' | translate }} + + +
+ + + admin.oauth2.client-authentication-method + + + {{ clientAuthenticationMethod | uppercase }} + + + + +
+ + admin.oauth2.login-button-label + + + {{ 'admin.oauth2.login-button-label-required' | translate }} + + + + + admin.oauth2.login-button-icon + + +
+ + + admin.oauth2.scope + + + {{scope}} + cancel + + + + + {{ 'admin.oauth2.jwk-set-uri-required' | translate }} + + + +
+ + + admin.oauth2.user-name-attribute-name + + + {{ 'admin.oauth2.user-name-attribute-name-required' | translate }} + + + +
+
+ + {{ 'admin.oauth2.allow-user-creation' | translate }} + + + {{ 'admin.oauth2.activate-user' | translate }} + +
+ + + admin.oauth2.type + + + {{ converterTypeExternalUser }} + + + + +
+ + admin.oauth2.email-attribute-key + + + {{ 'admin.oauth2.email-attribute-key-required' | translate }} + + + +
+ + admin.oauth2.first-name-attribute-key + + + + + admin.oauth2.last-name-attribute-key + + +
+ +
+ + admin.oauth2.tenant-name-strategy + + + {{ tenantNameStrategy }} + + + + + + admin.oauth2.tenant-name-pattern + + + {{ 'admin.oauth2.tenant-name-pattern-required' | translate }} + + +
+ + + admin.oauth2.customer-name-pattern + + + +
+ + admin.oauth2.default-dashboard-name + + + + + {{ 'admin.oauth2.always-fullscreen' | translate}} + +
+
+ +
+ + admin.oauth2.url + + + {{ 'admin.oauth2.url-required' | translate }} + + + {{ 'admin.oauth2.url-pattern' | translate }} + + + +
+ + common.username + + + + + common.password + + +
+
+
+
+
-
- - common.username - - - - - common.password - - -
-
- -
- - admin.oauth2.login-button-label - - - {{ 'admin.oauth2.login-button-label-required' | translate }} - - - - - admin.oauth2.login-button-icon - - -
-
- + + +
+
+ +
+
- - -
- -
+ diff --git a/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.scss b/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.scss index 95f47b7023..d174ba2dcf 100644 --- a/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.scss +++ b/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.scss @@ -20,6 +20,7 @@ .registration-card{ margin-bottom: 8px; + border: 1px solid rgba(0, 0, 0, 0.2); } .container{ diff --git a/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.ts b/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.ts index ab472643a6..0459213ee9 100644 --- a/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.ts +++ b/ui-ngx/src/app/modules/home/pages/admin/oauth2-settings.component.ts @@ -14,7 +14,7 @@ /// limitations under the License. /// -import { Component, Inject, OnDestroy, OnInit } from '@angular/core'; +import { ChangeDetectorRef, Component, Inject, OnDestroy, OnInit, ViewContainerRef } from '@angular/core'; import { AbstractControl, FormArray, FormBuilder, FormGroup, Validators } from '@angular/forms'; import { ClientAuthenticationMethod, @@ -32,9 +32,16 @@ import { HasConfirmForm } from '@core/guards/confirm-on-exit.guard'; import { COMMA, ENTER } from '@angular/cdk/keycodes'; import { MatChipInputEvent } from '@angular/material/chips'; import { WINDOW } from '@core/services/window.service'; -import { Subscription } from 'rxjs'; +import { forkJoin, Subscription } from 'rxjs'; import { DialogService } from '@core/services/dialog.service'; import { TranslateService } from '@ngx-translate/core'; +import { ConnectedPosition, Overlay, OverlayConfig, OverlayRef } from '@angular/cdk/overlay'; +import { ComponentPortal, PortalInjector } from '@angular/cdk/portal'; +import { + EDIT_REDIRECT_URI_PANEL_DATA, + EditRedirectUriPanelComponent, + EditRedirectUriPanelData +} from './edit-redirect-uri-panel.component'; @Component({ selector: 'tb-oauth2-settings', @@ -45,6 +52,7 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha private URL_REGEXP = /^[A-Za-z][A-Za-z\d.+-]*:\/*(?:\w+(?::\w+)?@)?[^\s/]+(?::\d+)?(?:\/[\w#!:.?+=&%@\-/]*)?$/; private subscriptions: Subscription[] = []; + private templates = []; readonly separatorKeysCodes: number[] = [ENTER, COMMA]; @@ -55,8 +63,13 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha converterTypesExternalUser: MapperConfigType[] = ['BASIC', 'CUSTOM']; tenantNameStrategies: TenantNameStrategy[] = ['DOMAIN', 'EMAIL', 'CUSTOM']; + templateProvider = ['Custom']; + constructor(protected store: Store, private adminService: AdminService, + private overlay: Overlay, + private viewContainerRef: ViewContainerRef, + private cd: ChangeDetectorRef, private fb: FormBuilder, private dialogService: DialogService, private translate: TranslateService, @@ -66,8 +79,12 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha ngOnInit(): void { this.buildOAuth2SettingsForm(); - this.adminService.getOAuth2Settings().subscribe( - (oauth2Settings) => { + forkJoin([ + this.adminService.getOAuth2Template(), + this.adminService.getOAuth2Settings() + ]).subscribe( + ([templates, oauth2Settings]) => { + this.initTemplates(templates); this.oauth2Settings = oauth2Settings; this.initOAuth2Settings(this.oauth2Settings); this.oauth2SettingsForm.reset(this.oauth2Settings); @@ -79,7 +96,13 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha super.ngOnDestroy(); this.subscriptions.forEach((subscription) => { subscription.unsubscribe(); - }) + }); + } + + private initTemplates(templates: any): void { + this.templates = templates; + templates.map(provider => this.templateProvider.push(provider.name)); + this.templateProvider.sort(); } get clientsDomainsParams(): FormArray { @@ -114,7 +137,7 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha url: [null, [Validators.required, Validators.pattern(this.URL_REGEXP)]], username: [null], password: [null] - }) + }); } private buildOAuth2SettingsForm(): void { @@ -136,7 +159,7 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha const listDomainName = []; control.root.value.clientsDomainsParams.forEach((domain) => { listDomainName.push(domain.domainName); - }) + }); if (listDomainName.indexOf(control.value) > -1) { return {unique: true}; } @@ -144,21 +167,6 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha return null; } - private uniqueRegistrationIdValidator(control: AbstractControl): { [key: string]: boolean } | null { - if (control.value !== null && control?.root) { - const listRegistration = []; - control.root.value.clientsDomainsParams.forEach((domain) => { - domain.clientRegistrations.forEach((client) => { - listRegistration.push(client.registrationId); - }) - }) - if (listRegistration.indexOf(control.value) > -1) { - return {unique: true}; - } - } - return null; - } - private buildSettingsDomain(domainParams?: DomainParams): FormGroup { let url = this.window.location.protocol + '//' + this.window.location.hostname; const port = this.window.location.port; @@ -174,7 +182,7 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha this.subscriptions.push(formDomain.get('domainName').valueChanges.subscribe((domain) => { if (!domain) { - domain = this.window.location.hostname + domain = this.window.location.hostname; } const uri = this.window.location.protocol + `//${domain}/login/oauth2/code/`; formDomain.get('redirectUriTemplate').patchValue(uri); @@ -183,7 +191,7 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha if (domainParams) { domainParams.clientRegistrations.forEach((registration) => { this.clientDomainRegistrations(formDomain).push(this.buildSettingsRegistration(registration)); - }) + }); } else { this.clientDomainRegistrations(formDomain).push(this.buildSettingsRegistration()); } @@ -193,7 +201,7 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha private buildSettingsRegistration(registrationData?: ClientRegistration): FormGroup { const clientRegistration = this.fb.group({ - registrationId: [null, [Validators.required, this.uniqueRegistrationIdValidator]], + providerName: ['Custom', [Validators.required]], loginButtonLabel: [null, [Validators.required]], loginButtonIcon: [null], clientId: ['', [Validators.required]], @@ -227,8 +235,8 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha if (registrationData) { registrationData.scope.forEach(() => { - (clientRegistration.get('scope') as FormArray).push(this.fb.control('')) - }) + (clientRegistration.get('scope') as FormArray).push(this.fb.control('')); + }); if (registrationData.mapperConfig.type !== 'BASIC') { clientRegistration.get('mapperConfig.type').patchValue('CUSTOM'); } @@ -288,7 +296,7 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha if (data) { this.clientsDomainsParams.removeAt(index); } - }) + }); } clientDomainRegistrations(control: AbstractControl): FormArray { @@ -305,15 +313,57 @@ export class OAuth2SettingsComponent extends PageComponent implements OnInit, Ha $event.preventDefault(); } - const registrationId = this.clientDomainRegistrations(controler).at(index).get('registrationId').value; + const providerName = this.clientDomainRegistrations(controler).at(index).get('providerName').value; this.dialogService.confirm( - this.translate.instant('admin.oauth2.delete-registration-title', {name: registrationId || ''}), + this.translate.instant('admin.oauth2.delete-registration-title', {name: providerName || ''}), this.translate.instant('admin.oauth2.delete-registration-text'), null, this.translate.instant('action.delete') ).subscribe((data) => { if (data) { this.clientDomainRegistrations(controler).removeAt(index); } - }) + }); + } + + editRedirectURI($event: MouseEvent, index: number) { + if ($event) { + $event.stopPropagation(); + $event.preventDefault(); + } + const target = $event.target || $event.currentTarget; + const config = new OverlayConfig(); + config.backdropClass = 'cdk-overlay-transparent-backdrop'; + config.hasBackdrop = true; + const connectedPosition: ConnectedPosition = { + originX: 'end', + originY: 'bottom', + overlayX: 'end', + overlayY: 'top' + }; + config.positionStrategy = this.overlay.position().flexibleConnectedTo(target as HTMLElement) + .withPositions([connectedPosition]); + + const overlayRef = this.overlay.create(config); + overlayRef.backdropClick().subscribe(() => { + overlayRef.dispose(); + }); + + const redirectURI = this.clientsDomainsParams.at(index).get('redirectUriTemplate').value; + + const injectionTokens = new WeakMap([ + [EDIT_REDIRECT_URI_PANEL_DATA, { + redirectURI + } as EditRedirectUriPanelData], + [OverlayRef, overlayRef] + ]); + const injector = new PortalInjector(this.viewContainerRef.injector, injectionTokens); + const componentRef = overlayRef.attach(new ComponentPortal(EditRedirectUriPanelComponent, + this.viewContainerRef, injector)); + componentRef.onDestroy(() => { + if (componentRef.instance.result !== null) { + const attributeValue = componentRef.instance.result; + this.clientsDomainsParams.at(index).get('redirectUriTemplate').patchValue(attributeValue, {emitEvent: true}); + } + }); } } diff --git a/ui-ngx/src/app/shared/models/settings.models.ts b/ui-ngx/src/app/shared/models/settings.models.ts index c4a1504f0f..2016a309c6 100644 --- a/ui-ngx/src/app/shared/models/settings.models.ts +++ b/ui-ngx/src/app/shared/models/settings.models.ts @@ -76,7 +76,6 @@ export interface DomainParams { } export interface ClientRegistration { - registrationId: string; loginButtonLabel: string; loginButtonIcon: string; clientId: string; @@ -86,9 +85,9 @@ export interface ClientRegistration { scope: string[]; jwkSetUri: string; userInfoUri: string; - clientAuthenticationMethod: ClientAuthenticationMethod + clientAuthenticationMethod: ClientAuthenticationMethod; userNameAttributeName: string; - mapperConfig: MapperConfig + mapperConfig: MapperConfig; } export interface MapperConfig { diff --git a/ui-ngx/src/assets/locale/locale.constant-en_US.json b/ui-ngx/src/assets/locale/locale.constant-en_US.json index c8967f0636..aea8c1cfe4 100644 --- a/ui-ngx/src/assets/locale/locale.constant-en_US.json +++ b/ui-ngx/src/assets/locale/locale.constant-en_US.json @@ -125,7 +125,7 @@ "error-verification-url": "A domain name shouldn't contain symbols '/' and ':'. Example: thingsboard.io", "add-domain": "Add domain", "new-domain": "New domain", - "add-registration": "Add registration", + "add-provider": "Add provider", "settings": "Settings", "oauth2": { "settings": "OAuth2 Settings",