diff --git a/alfa-client/libs/admin/keycloak-shared/src/lib/keycloak-formservice.ts b/alfa-client/libs/admin/keycloak-shared/src/lib/keycloak-formservice.ts index ecd71702a2a6d3e6176dc5890bdc9cd61dc7fe7c..f0aae76ba36f97b4d3508ad517764a02b2b3b5f2 100644 --- a/alfa-client/libs/admin/keycloak-shared/src/lib/keycloak-formservice.ts +++ b/alfa-client/libs/admin/keycloak-shared/src/lib/keycloak-formservice.ts @@ -75,6 +75,10 @@ export abstract class KeycloakFormService<T> { abstract _doSubmit(): Observable<StateResource<T>>; + public delete(): Observable<StateResource<T>> { + return null; + } + _patch(valueToPatch: T): void { this.form.reset(); diff --git a/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-button/user-form-delete-button.component.html b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-button/user-form-delete-button.component.html new file mode 100644 index 0000000000000000000000000000000000000000..54add448551525bd2ece9b4c74c838430b68972b --- /dev/null +++ b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-button/user-form-delete-button.component.html @@ -0,0 +1,6 @@ +<ods-button-with-spinner + (clickEmitter)="delete()" + variant="outline" + text="Löschen" + dataTestId="delete-button" +/> \ No newline at end of file diff --git a/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-button/user-form-delete-button.component.spec.ts b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-button/user-form-delete-button.component.spec.ts new file mode 100644 index 0000000000000000000000000000000000000000..71daffb081b873e23d68a0fa5adf96239da4a6c9 --- /dev/null +++ b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-button/user-form-delete-button.component.spec.ts @@ -0,0 +1,62 @@ +import { ComponentFixture, TestBed } from '@angular/core/testing'; + +import { dispatchEventFromFixture, existsAsHtmlElement, Mock, mock } from '@alfa-client/test-utils'; +import { DialogService } from '@alfa-client/ui'; +import { ButtonWithSpinnerComponent } from '@ods/component'; +import { MockComponent } from 'ng-mocks'; +import { getDataTestIdAttributeOf } from '../../../../../../tech-shared/test/data-test'; +import { UserFormDeleteDialogComponent } from '../user-form-delete-dialog/user-form-delete-dialog.component'; +import { UserFormDeleteButtonComponent } from './user-form-delete-button.component'; + +describe('UserFormDeleteButtonComponent', () => { + let component: UserFormDeleteButtonComponent; + let fixture: ComponentFixture<UserFormDeleteButtonComponent>; + + const deleteButton: string = getDataTestIdAttributeOf('delete-button'); + + let dialogService: Mock<DialogService>; + + beforeEach(async () => { + dialogService = mock(DialogService); + + await TestBed.configureTestingModule({ + imports: [UserFormDeleteButtonComponent], + declarations: [MockComponent(ButtonWithSpinnerComponent)], + providers: [{ provide: DialogService, useValue: dialogService }], + }).compileComponents(); + + fixture = TestBed.createComponent(UserFormDeleteButtonComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); + + describe('component', () => { + describe('delete', () => { + it('should open dialog', () => { + component.delete(); + + expect(dialogService.open).toHaveBeenCalledWith(UserFormDeleteDialogComponent); + }); + }); + }); + + describe('template', () => { + describe('button with spinner', () => { + it('should exist', () => { + existsAsHtmlElement(fixture, deleteButton); + }); + + it('should call delete on click', () => { + component.delete = jest.fn(); + + dispatchEventFromFixture(fixture, deleteButton, 'clickEmitter'); + + expect(component.delete).toHaveBeenCalled(); + }); + }); + }); +}); diff --git a/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-button/user-form-delete-button.component.ts b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-button/user-form-delete-button.component.ts new file mode 100644 index 0000000000000000000000000000000000000000..abe8a9be6d38ed1443b8fca282cc1b0f1b6b41d0 --- /dev/null +++ b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-button/user-form-delete-button.component.ts @@ -0,0 +1,18 @@ +import { DialogService } from '@alfa-client/ui'; +import { Component, inject } from '@angular/core'; +import { ButtonWithSpinnerComponent } from '@ods/component'; +import { UserFormDeleteDialogComponent } from '../user-form-delete-dialog/user-form-delete-dialog.component'; + +@Component({ + selector: 'admin-user-form-delete-button', + standalone: true, + imports: [ButtonWithSpinnerComponent], + templateUrl: './user-form-delete-button.component.html', +}) +export class UserFormDeleteButtonComponent { + private readonly dialogService = inject(DialogService); + + public delete(): void { + this.dialogService.openWidely(UserFormDeleteDialogComponent); + } +} diff --git a/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-dialog/user-form-delete-dialog.component.html b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-dialog/user-form-delete-dialog.component.html new file mode 100644 index 0000000000000000000000000000000000000000..51bec494bace9b21847aadd47aaa5e0f0851e6d6 --- /dev/null +++ b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-dialog/user-form-delete-dialog.component.html @@ -0,0 +1 @@ +<p>user-form-delete-dialog works!</p> diff --git a/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-dialog/user-form-delete-dialog.component.spec.ts b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-dialog/user-form-delete-dialog.component.spec.ts new file mode 100644 index 0000000000000000000000000000000000000000..b7c73d98cad4c17a15bb8b87f0577da60ac8fbee --- /dev/null +++ b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-dialog/user-form-delete-dialog.component.spec.ts @@ -0,0 +1,23 @@ +import { ComponentFixture, TestBed } from '@angular/core/testing'; + +import { UserFormDeleteDialogComponent } from './user-form-delete-dialog.component'; + +describe('UserFormDeleteDialogComponent', () => { + let component: UserFormDeleteDialogComponent; + let fixture: ComponentFixture<UserFormDeleteDialogComponent>; + + beforeEach(async () => { + await TestBed.configureTestingModule({ + imports: [UserFormDeleteDialogComponent] + }) + .compileComponents(); + + fixture = TestBed.createComponent(UserFormDeleteDialogComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); +}); diff --git a/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-dialog/user-form-delete-dialog.component.ts b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-dialog/user-form-delete-dialog.component.ts new file mode 100644 index 0000000000000000000000000000000000000000..42b9a86ebcad8d8284f82063fd80a3a3cad018cf --- /dev/null +++ b/alfa-client/libs/admin/user/src/lib/user-form/user-form-delete-dialog/user-form-delete-dialog.component.ts @@ -0,0 +1,9 @@ +import { Component } from '@angular/core'; + +@Component({ + selector: 'admin-user-form-delete-dialog', + standalone: true, + imports: [], + templateUrl: './user-form-delete-dialog.component.html', +}) +export class UserFormDeleteDialogComponent {} diff --git a/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.html b/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.html index dcab3c25b5a05434e0eedd7f56e889914253b5d7..944e7a1c13b0512ed9ef2a39f7471dbada63007d 100644 --- a/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.html +++ b/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.html @@ -32,6 +32,11 @@ [formGroupParent]="formService.form" [formGroupOrganisationsEinheiten]="formService.getOrganisationsEinheitenGroup()" /> - <admin-user-form-save-button /> + <div class="flex justify-between"> + <admin-user-form-save-button /> + @if(formService.isPatch()){ + <admin-user-form-delete-button data-test-id="delete-button-host"/> + } + </div> </div> </ods-spinner> diff --git a/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.spec.ts b/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.spec.ts index 085f2fe196fdb6d881240f4485527e72123b51ba..6d3e2413240c63953cfb608858fab4df2f8e9552 100644 --- a/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.spec.ts +++ b/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.spec.ts @@ -23,7 +23,7 @@ */ import { User } from '@admin-client/user-shared'; import { createEmptyStateResource, createStateResource, StateResource } from '@alfa-client/tech-shared'; -import { getMockComponent, mock, Mock, notExistsAsHtmlElement } from '@alfa-client/test-utils'; +import { existsAsHtmlElement, getMockComponent, mock, Mock, notExistsAsHtmlElement } from '@alfa-client/test-utils'; import { CommonModule } from '@angular/common'; import { ComponentFixture, TestBed } from '@angular/core/testing'; import { FormGroup, ReactiveFormsModule } from '@angular/forms'; @@ -34,6 +34,7 @@ import { MockComponent } from 'ng-mocks'; import { of } from 'rxjs'; import { getDataTestIdOf } from '../../../../../tech-shared/test/data-test'; import { UserFormDataComponent } from './user-form-data/user-form-data.component'; +import { UserFormDeleteButtonComponent } from './user-form-delete-button/user-form-delete-button.component'; import { UserFormHeadlineComponent } from './user-form-headline/user-form-headline.component'; import { UserFormOrganisationsEinheitListComponent } from './user-form-organisations-einheit-list/user-form-organisations-einheit-list.component'; import { UserFormRolesComponent } from './user-form-roles/user-form-roles.component'; @@ -47,6 +48,7 @@ describe('UserFormComponent', () => { let formService: Mock<UserFormService>; const userContent: string = getDataTestIdOf('user-content'); + const deleteButton: string = getDataTestIdOf('delete-button-host'); beforeEach(async () => { formService = <any>{ @@ -66,8 +68,8 @@ describe('UserFormComponent', () => { MockComponent(UserFormOrganisationsEinheitListComponent), MockComponent(UserFormRolesComponent), MockComponent(UserFormHeadlineComponent), + MockComponent(UserFormDeleteButtonComponent), ], - providers: [{ provide: UserFormService, useValue: formService }], }) .overrideComponent(UserFormComponent, { set: { @@ -130,7 +132,6 @@ describe('UserFormComponent', () => { it('should exist with input', () => { const formDataComponent: UserFormDataComponent = getMockComponent(fixture, UserFormDataComponent); - expect(formDataComponent).toBeTruthy(); expect(formDataComponent.formGroupParent).toBe(component.formService.form); }); }); @@ -151,7 +152,6 @@ describe('UserFormComponent', () => { UserFormOrganisationsEinheitListComponent, ); - expect(organisationsEinheitListComponent).toBeTruthy(); expect(organisationsEinheitListComponent.formGroupParent).toBe(component.formService.form); expect(organisationsEinheitListComponent.formGroupOrganisationsEinheiten).toBe( component.formService.getOrganisationsEinheitenGroup(), @@ -167,4 +167,20 @@ describe('UserFormComponent', () => { notExistsAsHtmlElement(fixture, userContent); }); }); + + describe('admin delete button', () => { + it('should exist', () => { + formService.isPatch.mockReturnValue(true); + fixture.detectChanges(); + + existsAsHtmlElement(fixture, deleteButton); + }); + + it('should not exist', () => { + formService.isPatch.mockReturnValue(false); + fixture.detectChanges(); + + notExistsAsHtmlElement(fixture, deleteButton); + }); + }); }); diff --git a/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.ts b/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.ts index 03199641945f4841fcd0360b025262c2136d9ef3..d671aee05003b1b27f84bee9f03eeda63cf1f1b2 100644 --- a/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.ts +++ b/alfa-client/libs/admin/user/src/lib/user-form/user-form.component.ts @@ -29,6 +29,7 @@ import { FormsModule, ReactiveFormsModule } from '@angular/forms'; import { SpinnerComponent } from '@ods/component'; import { Observable } from 'rxjs'; import { UserFormDataComponent } from './user-form-data/user-form-data.component'; +import { UserFormDeleteButtonComponent } from './user-form-delete-button/user-form-delete-button.component'; import { UserFormHeadlineComponent } from './user-form-headline/user-form-headline.component'; import { UserFormOrganisationsEinheitListComponent } from './user-form-organisations-einheit-list/user-form-organisations-einheit-list.component'; import { UserFormRolesComponent } from './user-form-roles/user-form-roles.component'; @@ -44,12 +45,13 @@ import { UserFormService } from './user.formservice'; FormsModule, ReactiveFormsModule, AsyncPipe, + SpinnerComponent, UserFormDataComponent, UserFormRolesComponent, UserFormOrganisationsEinheitListComponent, UserFormHeadlineComponent, UserFormSaveButtonComponent, - SpinnerComponent, + UserFormDeleteButtonComponent, ], }) export class UserFormComponent implements OnInit {