From c0e068a51cb0406a2063bc27d0095d3e83e178bd Mon Sep 17 00:00:00 2001 From: Albert <Albert.Bruns@mgm-tp.com> Date: Tue, 4 Feb 2025 14:08:04 +0100 Subject: [PATCH] OZG-7472-7632 ods buttons --- .../libs/test-utils/src/lib/jest.helper.ts | 8 +- .../annehmen-button.component.html | 45 +- .../annehmen-button.component.spec.ts | 122 +++-- .../bescheiden-button.component.html | 45 +- .../bescheiden-button.component.spec.ts | 459 +++++++++--------- .../src/lib/vorgang-detail.module.ts | 2 + 6 files changed, 373 insertions(+), 308 deletions(-) diff --git a/alfa-client/libs/test-utils/src/lib/jest.helper.ts b/alfa-client/libs/test-utils/src/lib/jest.helper.ts index 1f05a4791c..60df8592af 100644 --- a/alfa-client/libs/test-utils/src/lib/jest.helper.ts +++ b/alfa-client/libs/test-utils/src/lib/jest.helper.ts @@ -23,7 +23,8 @@ */ import { ComponentFixture } from '@angular/core/testing'; import { expect } from '@jest/globals'; -import { getElementFromFixture } from './helper'; +import { TooltipDirective } from '@ods/system'; +import { getDebugElementFromFixtureByCss, getElementFromFixture } from './helper'; export function notExistsAsHtmlElement(fixture: ComponentFixture<any>, domElement: string): void { expect(getElementFromFixture(fixture, domElement)).not.toBeInstanceOf(HTMLElement); @@ -32,3 +33,8 @@ export function notExistsAsHtmlElement(fixture: ComponentFixture<any>, domElemen export function existsAsHtmlElement(fixture: ComponentFixture<any>, domElement: string): void { expect(getElementFromFixture(fixture, domElement)).toBeInstanceOf(HTMLElement); } + +export function tooltipExistsWithText(fixture: ComponentFixture<any>, domElement: string, tooltipText: string) { + const tooltipInstance = getDebugElementFromFixtureByCss(fixture, domElement).injector.get(TooltipDirective); + expect(tooltipInstance.componentRef.instance.text).toBe(tooltipText); +} diff --git a/alfa-client/libs/vorgang-detail/src/lib/buttons/annehmen-button/annehmen-button.component.html b/alfa-client/libs/vorgang-detail/src/lib/buttons/annehmen-button/annehmen-button.component.html index 97c685caf7..b93172bd7e 100644 --- a/alfa-client/libs/vorgang-detail/src/lib/buttons/annehmen-button/annehmen-button.component.html +++ b/alfa-client/libs/vorgang-detail/src/lib/buttons/annehmen-button/annehmen-button.component.html @@ -23,24 +23,27 @@ unter der Lizenz sind dem Lizenztext zu entnehmen. --> -<ng-container *ngIf="vorgang | hasLink: linkRel.ANNEHMEN"> - <ozgcloud-stroked-button-with-spinner - *ngIf="!showAsIconButton" - data-test-id="annehmen-button" - text="Annehmen" - icon="check_circle_outline" - [stateResource]="commandStateResource$ | async" - (clickEmitter)="annehmen()" - > - </ozgcloud-stroked-button-with-spinner> - - <ozgcloud-icon-button-with-spinner - *ngIf="showAsIconButton" - data-test-id="annehmen-icon-button" - icon="check_circle_outline" - toolTip="Vorgang annehmen" - [stateResource]="commandStateResource$ | async" - (clickEmitter)="annehmen()" - > - </ozgcloud-icon-button-with-spinner> -</ng-container> +@if(vorgang | hasLink: linkRel.ANNEHMEN){ + @if(showAsIconButton){ + <ods-button-with-spinner + [stateResource]="commandStateResource$ | async" + (clickEmitter)="annehmen()" + toolTip="Vorgang annehmen" + variant="icon" + size="fit" + data-test-id="annehmen-icon-button" + > + <ods-check-icon icon class="fill-primary"/> + </ods-button-with-spinner> + } @else { + <ods-button-with-spinner + [stateResource]="commandStateResource$ | async" + (clickEmitter)="annehmen()" + toolTip="Vorgang annehmen" + variant="outline" + data-test-id="annehmen-button" + > + <ods-check-icon icon class="fill-primary"/> + </ods-button-with-spinner> + } +} \ No newline at end of file diff --git a/alfa-client/libs/vorgang-detail/src/lib/buttons/annehmen-button/annehmen-button.component.spec.ts b/alfa-client/libs/vorgang-detail/src/lib/buttons/annehmen-button/annehmen-button.component.spec.ts index 43b5fa53e7..9d201f9cc3 100644 --- a/alfa-client/libs/vorgang-detail/src/lib/buttons/annehmen-button/annehmen-button.component.spec.ts +++ b/alfa-client/libs/vorgang-detail/src/lib/buttons/annehmen-button/annehmen-button.component.spec.ts @@ -21,14 +21,13 @@ * Die sprachspezifischen Genehmigungen und Beschränkungen * unter der Lizenz sind dem Lizenztext zu entnehmen. */ -import { ComponentFixture, TestBed } from '@angular/core/testing'; -import { HasLinkPipe, createStateResource } from '@alfa-client/tech-shared'; -import { mock } from '@alfa-client/test-utils'; -import { - IconButtonWithSpinnerComponent, - OzgcloudStrokedButtonWithSpinnerComponent, -} from '@alfa-client/ui'; +import { CommandResource } from '@alfa-client/command-shared'; +import { createStateResource, HasLinkPipe, StateResource } from '@alfa-client/tech-shared'; +import { getElementComponentFromFixtureByCss, mock, notExistsAsHtmlElement, triggerEvent } from '@alfa-client/test-utils'; import { VorgangCommandService, VorgangWithEingangLinkRel } from '@alfa-client/vorgang-shared'; +import { ComponentFixture, TestBed } from '@angular/core/testing'; +import { ButtonWithSpinnerComponent } from '@ods/component'; +import { CheckIconComponent, TooltipDirective } from '@ods/system'; import { createCommandResource } from 'libs/command-shared/test/command'; import { getDataTestIdOf } from 'libs/tech-shared/test/data-test'; import { createVorgangWithEingangResource } from 'libs/vorgang-shared/test/vorgang'; @@ -52,9 +51,10 @@ describe('AnnehmenButtonComponent', () => { await TestBed.configureTestingModule({ declarations: [ AnnehmenButtonComponent, - MockComponent(OzgcloudStrokedButtonWithSpinnerComponent), - MockComponent(IconButtonWithSpinnerComponent), HasLinkPipe, + TooltipDirective, + MockComponent(ButtonWithSpinnerComponent), + MockComponent(CheckIconComponent), ], providers: [ { @@ -75,69 +75,95 @@ describe('AnnehmenButtonComponent', () => { expect(component).toBeTruthy(); }); - describe('ngOnInit', () => { - it('should call service', () => { - component.ngOnInit(); + describe('component', () => { + describe('ngOnInit', () => { + it('should call service', () => { + component.ngOnInit(); - expect(vorgangCommandService.getAnnehmenCommand).toHaveBeenCalled(); + expect(vorgangCommandService.getAnnehmenCommand).toHaveBeenCalled(); + }); }); - }); - describe('annehmen', () => { - it('should call vorgang service', () => { - component.annehmen(); + describe('annehmen', () => { + it('should call vorgang service', () => { + component.annehmen(); - expect(vorgangCommandService.annehmen).toHaveBeenCalled(); + expect(vorgangCommandService.annehmen).toHaveBeenCalled(); + }); }); }); - describe('annehmen button', () => { + describe('template', () => { + const state: StateResource<CommandResource> = createStateResource(createCommandResource()); + beforeEach(() => { - component.showAsIconButton = false; + component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.ANNEHMEN]); + component.commandStateResource$ = of(state); fixture.detectChanges(); }); - it('should be hidden', () => { - component.vorgang = createVorgangWithEingangResource(); + describe('annehmen button', () => { + beforeEach(() => { + component.showAsIconButton = false; + fixture.detectChanges(); + }); - fixture.detectChanges(); - const buttonElement = fixture.nativeElement.querySelector(annehmenButton); + it('should not exist', () => { + component.vorgang = createVorgangWithEingangResource(); - expect(buttonElement).not.toBeInstanceOf(HTMLElement); - }); + fixture.detectChanges(); - it('should be visible', () => { - component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.ANNEHMEN]); + notExistsAsHtmlElement(fixture, annehmenButton); + }); - fixture.detectChanges(); - const buttonElement = fixture.nativeElement.querySelector(annehmenButton); + it('should exist with input', () => { + fixture.detectChanges(); - expect(buttonElement).toBeInstanceOf(HTMLElement); - }); - }); + const button: ButtonWithSpinnerComponent = getElementComponentFromFixtureByCss(fixture, annehmenButton); - describe('annehmen icon button', () => { - beforeEach(() => { - component.showAsIconButton = true; - fixture.detectChanges(); - }); + expect(button).toBeTruthy(); + expect(button.stateResource).toBe(state); + }); - it('should be hidden', () => { - component.vorgang = createVorgangWithEingangResource(); + it('should call annehmen on click', () => { + component.annehmen = jest.fn(); - fixture.detectChanges(); - const buttonElement = fixture.nativeElement.querySelector(annehmenIconButton); + triggerEvent({ fixture, name: 'clickEmitter', elementSelector: annehmenButton }); - expect(buttonElement).not.toBeInstanceOf(HTMLElement); + expect(component.annehmen).toHaveBeenCalled(); + }); }); - it('should be visible', () => { - component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.ANNEHMEN]); + describe('annehmen icon button', () => { + beforeEach(() => { + component.showAsIconButton = true; + fixture.detectChanges(); + }); - fixture.detectChanges(); - const buttonElement = fixture.nativeElement.querySelector(annehmenIconButton); + it('should not exist', () => { + component.vorgang = createVorgangWithEingangResource(); + + fixture.detectChanges(); + + notExistsAsHtmlElement(fixture, annehmenIconButton); + }); + + it('should exist with input', () => { + fixture.detectChanges(); + + const button: ButtonWithSpinnerComponent = getElementComponentFromFixtureByCss(fixture, annehmenIconButton); + + expect(button).toBeTruthy(); + expect(button.stateResource).toBe(state); + }); + + it('should call annehmen on click', () => { + component.annehmen = jest.fn(); + + triggerEvent({ fixture, name: 'clickEmitter', elementSelector: annehmenIconButton }); - expect(buttonElement).toBeInstanceOf(HTMLElement); + expect(component.annehmen).toHaveBeenCalled(); + }); }); }); }); diff --git a/alfa-client/libs/vorgang-detail/src/lib/buttons/bescheiden-button/bescheiden-button.component.html b/alfa-client/libs/vorgang-detail/src/lib/buttons/bescheiden-button/bescheiden-button.component.html index fa3f6f038d..287fe3e8e1 100644 --- a/alfa-client/libs/vorgang-detail/src/lib/buttons/bescheiden-button/bescheiden-button.component.html +++ b/alfa-client/libs/vorgang-detail/src/lib/buttons/bescheiden-button/bescheiden-button.component.html @@ -23,24 +23,27 @@ unter der Lizenz sind dem Lizenztext zu entnehmen. --> -<ng-container *ngIf="vorgang | hasLink: linkRel.BESCHEIDEN"> - <ozgcloud-stroked-button-with-spinner - *ngIf="!showAsIconButton" - data-test-id="bescheiden-button" - [text]="buttonText" - svgIcon="stamp" - [stateResource]="commandStateResource$ | async" - (clickEmitter)="bescheiden()" - > - </ozgcloud-stroked-button-with-spinner> - - <ozgcloud-icon-button-with-spinner - *ngIf="showAsIconButton" - data-test-id="bescheiden-icon-button" - svgIcon="stamp" - [toolTip]="toolTipText" - [stateResource]="commandStateResource$ | async" - (clickEmitter)="bescheiden()" - > - </ozgcloud-icon-button-with-spinner> -</ng-container> +@if (vorgang | hasLink: linkRel.BESCHEIDEN) { + @if (showAsIconButton) { + <ods-button-with-spinner + [stateResource]="commandStateResource$ | async" + (clickEmitter)="bescheiden()" + [tooltip]="toolTipText" + variant="icon" + size="fit" + data-test-id="bescheiden-icon-button" + > + <ods-stamp-icon icon class="fill-black" size="medium" /> + </ods-button-with-spinner> + } @else { + <ods-button-with-spinner + [stateResource]="commandStateResource$ | async" + (clickEmitter)="bescheiden()" + [text]="buttonText" + variant="outline" + data-test-id="bescheiden-button" + > + <ods-stamp-icon icon class="fill-primary" size="medium" /> + </ods-button-with-spinner> + } +} diff --git a/alfa-client/libs/vorgang-detail/src/lib/buttons/bescheiden-button/bescheiden-button.component.spec.ts b/alfa-client/libs/vorgang-detail/src/lib/buttons/bescheiden-button/bescheiden-button.component.spec.ts index 01fc62566a..4587f44e18 100644 --- a/alfa-client/libs/vorgang-detail/src/lib/buttons/bescheiden-button/bescheiden-button.component.spec.ts +++ b/alfa-client/libs/vorgang-detail/src/lib/buttons/bescheiden-button/bescheiden-button.component.spec.ts @@ -24,12 +24,16 @@ import { BescheidResource, BescheidService, BescheidWizardDialogResult } from '@alfa-client/bescheid-shared'; import { CommandResource } from '@alfa-client/command-shared'; import { createEmptyStateResource, createStateResource, HasLinkPipe, StateResource } from '@alfa-client/tech-shared'; -import { Mock, mock } from '@alfa-client/test-utils'; import { - IconButtonWithSpinnerComponent, - OzgcloudDialogService, - OzgcloudStrokedButtonWithSpinnerComponent, -} from '@alfa-client/ui'; + getElementComponentFromFixtureByCss, + getMockComponent, + Mock, + mock, + notExistsAsHtmlElement, + tooltipExistsWithText, + triggerEvent, +} from '@alfa-client/test-utils'; +import { OzgcloudDialogService } from '@alfa-client/ui'; import { BescheidenDialogData } from '@alfa-client/vorgang-detail'; import { VorgangCommandService, @@ -39,6 +43,8 @@ import { } from '@alfa-client/vorgang-shared'; import { DialogRef } from '@angular/cdk/dialog'; import { ComponentFixture, TestBed } from '@angular/core/testing'; +import { ButtonWithSpinnerComponent } from '@ods/component'; +import { StampIconComponent, TooltipDirective } from '@ods/system'; import { createCommandResource } from 'libs/command-shared/test/command'; import { getDataTestIdOf } from 'libs/tech-shared/test/data-test'; import { createVorgangWithEingangResource } from 'libs/vorgang-shared/test/vorgang'; @@ -74,8 +80,9 @@ describe('BescheidenButtonComponent', () => { declarations: [ BescheidenButtonComponent, HasLinkPipe, - MockComponent(OzgcloudStrokedButtonWithSpinnerComponent), - MockComponent(IconButtonWithSpinnerComponent), + TooltipDirective, + MockComponent(ButtonWithSpinnerComponent), + MockComponent(StampIconComponent), ], providers: [ { @@ -107,300 +114,318 @@ describe('BescheidenButtonComponent', () => { expect(component).toBeTruthy(); }); - describe('ngOnInit', () => { - it('should call service', () => { - component.ngOnInit(); + describe('component', () => { + describe('ngOnInit', () => { + it('should call service', () => { + component.ngOnInit(); - expect(vorgangCommandService.getBeschiedenCommand).toHaveBeenCalled(); + expect(vorgangCommandService.getBeschiedenCommand).toHaveBeenCalled(); + }); }); - }); - describe('bescheiden button', () => { - beforeEach(() => { - component.showAsIconButton = false; - fixture.detectChanges(); - }); + describe('bescheiden', () => { + describe('should open bescheid wizard', () => { + beforeEach(() => { + component.openBescheidenWizard = jest.fn(); + component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.CREATE_BESCHEID_DRAFT]); + }); - it('should be hidden', () => { - component.vorgang = createVorgangWithEingangResource(); + it('should open bescheid wizard when create bescheid draft link exists', () => { + component.bescheiden(); - fixture.detectChanges(); - const buttonElement = fixture.nativeElement.querySelector(bescheidenButton); + expect(component.openBescheidenWizard).toHaveBeenCalled(); + }); - expect(buttonElement).not.toBeInstanceOf(HTMLElement); - }); + it('should open bescheid wizard when bescheid draft exists', () => { + component.bescheiden(); - it('should be visible', () => { - component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.BESCHEIDEN]); + expect(component.openBescheidenWizard).toHaveBeenCalled(); + }); + }); - fixture.detectChanges(); - const buttonElement = fixture.nativeElement.querySelector(bescheidenButton); + describe('should do bescheiden', () => { + const command: CommandResource = createCommandResource(); + const comandStateResource$: Observable<StateResource<CommandResource>> = of(createStateResource(command)); - expect(buttonElement).toBeInstanceOf(HTMLElement); - }); + beforeEach(() => { + vorgangCommandService.bescheiden.mockReturnValue(comandStateResource$); + }); - it('should get "Bescheid" text', () => { - component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.BESCHEIDEN]); + it('should call vorgangCommandService.bescheiden', () => { + component.bescheiden(); + + expect(vorgangCommandService.bescheiden).toHaveBeenCalled(); + }); + + it('should assign response', () => { + component.commandStateResource$ = of(createEmptyStateResource<CommandResource>()); - const buttonText: string = component.buttonText; + component.bescheiden(); - expect(buttonText).toBe('Bescheiden'); + expect(component.commandStateResource$).toBe(comandStateResource$); + }); + }); }); - it('should get "Bescheiden fortsetzen" text', () => { - component.vorgang = createVorgangWithEingangResource([ - VorgangWithEingangLinkRel.BESCHEIDEN, - VorgangWithEingangLinkRel.BESCHEID_DRAFT, - ]); + // TODO: Use this version after completed Bescheid refactoring and delete the other version below. + // describe('openBescheidenWizard', () => { + // let dialogRefMock: DialogRefMock<BescheidWizardDialogResult>; + // + // beforeEach(() => { + // dialogRefMock = createDialogRefMock<BescheidWizardDialogResult>(); + // ozgcloudDialogService.openWizard.mockReturnValue(dialogRefMock); + // }); + // + // it('should open wizard dialog', () => { + // const vorgang = createVorgangWithEingangResource(); + // component.vorgang = vorgang; + // + // component.openBescheidenWizard(); + // + // expect(ozgcloudDialogService.openWizard).toHaveBeenCalledWith(BescheidWizardContainerComponent, { + // vorgangWithEingangResource: vorgang, + // }); + // }); + // + // it('should handleBescheidWizardClosed', () => { + // component.handleBescheidWizardClosed = jest.fn(); + // const dialogResult: BescheidWizardDialogResult = { reloadVorgang: true }; + // dialogRefMock.closed = of(dialogResult); + // + // component.openBescheidenWizard(); + // + // expect(component.handleBescheidWizardClosed).toHaveBeenCalledWith(dialogResult); + // }); + // }); + + describe('openBescheidenWizard', () => { + it('should init', () => { + component.openBescheidenWizard(); + + expect(bescheidService.init).toBeCalled(); + }); - const buttonText: string = component.buttonText; + it('should open bescheiden dialog with existing draft', () => { + component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.BESCHEID_DRAFT]); + component.openBescheidenDialogWithExistingDraft = jest.fn(); - expect(buttonText).toBe('Bescheiden fortsetzen'); - }); - }); + component.openBescheidenWizard(); - describe('tool tip', () => { - it('should get "Vorgang bescheiden" text', () => { - component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.BESCHEIDEN]); + expect(component.openBescheidenDialogWithExistingDraft).toHaveBeenCalled(); + }); - const toolTipText: string = component.toolTipText; + it('should open bescheiden dialog with new draft', () => { + component.vorgang = createVorgangWithEingangResource(); + component.openBescheidDialogWithNewDraft = jest.fn(); - expect(toolTipText).toBe('Vorgang bescheiden'); + component.openBescheidenWizard(); + + expect(component.openBescheidDialogWithNewDraft).toHaveBeenCalled(); + }); }); - it('should get "Vorgang bescheiden fortsetzen" text', () => { - component.vorgang = createVorgangWithEingangResource([ - VorgangWithEingangLinkRel.BESCHEIDEN, - VorgangWithEingangLinkRel.BESCHEID_DRAFT, - ]); + describe('openBescheidDialogWithNewDraft', () => { + it('should open wizard', () => { + component.vorgang = createVorgangWithEingangResource(); + component.openDialog = jest.fn(); - const toolTipText: string = component.toolTipText; + component.openBescheidDialogWithNewDraft(); - expect(toolTipText).toBe('Vorgang bescheiden fortsetzen'); + expect(component.openDialog).toHaveBeenCalledWith({ + vorgangWithEingangResource: component.vorgang, + bescheidDraftResource: null, + }); + }); }); - }); - describe('bescheiden', () => { - describe('should open bescheid wizard', () => { + describe('openBescheidenDialogWithExistingDraft', () => { + const bescheidDraftResource: BescheidResource = createBescheidResource(); + const bescheidDraftStateResource: StateResource<BescheidResource> = createStateResource(bescheidDraftResource); + const vorgangWithEingangResource: VorgangWithEingangResource = createVorgangWithEingangResource([ + VorgangWithEingangLinkRel.BESCHEID_DRAFT, + ]); + beforeEach(() => { - component.openBescheidenWizard = jest.fn(); - component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.CREATE_BESCHEID_DRAFT]); + component.vorgang = vorgangWithEingangResource; + bescheidService.getBescheidDraftIfExists.mockReturnValue(of(bescheidDraftStateResource)); }); - it('should open bescheid wizard when create bescheid draft link exists', () => { - component.bescheiden(); + it('should open wizard if bescheid draft loaded', () => { + component.openBescheidenDialogWithExistingDraft(); - expect(component.openBescheidenWizard).toHaveBeenCalled(); + expect(ozgcloudDialogService.openWizard).toHaveBeenCalledWith(VorgangDetailBescheidenComponent, { + bescheidDraftResource, + vorgangWithEingangResource, + }); }); - it('should open bescheid wizard when bescheid draft exists', () => { - component.bescheiden(); - - expect(component.openBescheidenWizard).toHaveBeenCalled(); - }); - }); + it('should not open wizard if bescheid draft not loaded', () => { + bescheidService.getBescheidDraftIfExists.mockReturnValue(of(createEmptyStateResource())); - describe('should do bescheiden', () => { - const command: CommandResource = createCommandResource(); - const comandStateResource$: Observable<StateResource<CommandResource>> = of(createStateResource(command)); + component.openBescheidenDialogWithExistingDraft(); - beforeEach(() => { - vorgangCommandService.bescheiden.mockReturnValue(comandStateResource$); + expect(ozgcloudDialogService.openWizard).not.toHaveBeenCalled(); }); - it('should call vorgangCommandService.bescheiden', () => { - component.bescheiden(); + it('should not open wizard on loading bescheid draft', () => { + bescheidService.getBescheidDraftIfExists.mockReturnValue( + of({ ...createStateResource(createBescheidResource()), loading: true }), + ); + + component.openBescheidenDialogWithExistingDraft(); - expect(vorgangCommandService.bescheiden).toHaveBeenCalled(); + expect(ozgcloudDialogService.openWizard).not.toHaveBeenCalled(); }); + }); - it('should assign response', () => { - component.commandStateResource$ = of(createEmptyStateResource<CommandResource>()); + describe('openDialog', () => { + const bescheidDraftResource: BescheidResource = createBescheidResource(); + const bescheidDraftStateResource: StateResource<BescheidResource> = createStateResource(bescheidDraftResource); + const vorgangWithEingangResource: VorgangWithEingangResource = createVorgangWithEingangResource([ + VorgangWithEingangLinkRel.BESCHEID_DRAFT, + ]); - component.bescheiden(); + const dialogData: BescheidenDialogData = { + bescheidDraftResource: bescheidDraftResource, + vorgangWithEingangResource: vorgangWithEingangResource, + }; - expect(component.commandStateResource$).toBe(comandStateResource$); + beforeEach(() => { + component.vorgang = vorgangWithEingangResource; + bescheidService.getBescheidDraftIfExists.mockReturnValue(of(bescheidDraftStateResource)); }); - }); - }); - describe('bescheiden icon button', () => { - beforeEach(() => { - component.showAsIconButton = true; - fixture.detectChanges(); + it('should call ozgcloudDialogService.openWizard', () => { + component.openDialog(dialogData); + + expect(ozgcloudDialogService.openWizard).toHaveBeenCalledWith(VorgangDetailBescheidenComponent, dialogData); + }); }); - it('should be hidden', () => { - component.vorgang = createVorgangWithEingangResource(); + describe('handleBescheidWizardClosed', () => { + it('should reload current vorgang', () => { + component.handleBescheidWizardClosed({ reloadVorgang: true }); - fixture.detectChanges(); - const buttonElement = fixture.nativeElement.querySelector(bescheidenIconButton); + expect(vorgangService.reloadCurrentVorgang).toHaveBeenCalled(); + }); - expect(buttonElement).not.toBeInstanceOf(HTMLElement); - }); + it('should not reload current vorgang', () => { + component.handleBescheidWizardClosed({ reloadVorgang: false }); - it('should be visible', () => { - component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.BESCHEIDEN]); + expect(vorgangService.reloadCurrentVorgang).not.toHaveBeenCalled(); + }); - fixture.detectChanges(); - const buttonElement = fixture.nativeElement.querySelector(bescheidenIconButton); + it.each([null, undefined])( + 'should not reload current vorgang if result nil', + (dialogResult: BescheidWizardDialogResult) => { + component.handleBescheidWizardClosed(dialogResult); - expect(buttonElement).toBeInstanceOf(HTMLElement); + expect(vorgangService.reloadCurrentVorgang).not.toHaveBeenCalled(); + }, + ); }); }); - // TODO: Use this version after completed Bescheid refactoring and delete the other version below. - // describe('openBescheidenWizard', () => { - // let dialogRefMock: DialogRefMock<BescheidWizardDialogResult>; - // - // beforeEach(() => { - // dialogRefMock = createDialogRefMock<BescheidWizardDialogResult>(); - // ozgcloudDialogService.openWizard.mockReturnValue(dialogRefMock); - // }); - // - // it('should open wizard dialog', () => { - // const vorgang = createVorgangWithEingangResource(); - // component.vorgang = vorgang; - // - // component.openBescheidenWizard(); - // - // expect(ozgcloudDialogService.openWizard).toHaveBeenCalledWith(BescheidWizardContainerComponent, { - // vorgangWithEingangResource: vorgang, - // }); - // }); - // - // it('should handleBescheidWizardClosed', () => { - // component.handleBescheidWizardClosed = jest.fn(); - // const dialogResult: BescheidWizardDialogResult = { reloadVorgang: true }; - // dialogRefMock.closed = of(dialogResult); - // - // component.openBescheidenWizard(); - // - // expect(component.handleBescheidWizardClosed).toHaveBeenCalledWith(dialogResult); - // }); - // }); - - describe('openBescheidenWizard', () => { - it('should init', () => { - component.openBescheidenWizard(); - - expect(bescheidService.init).toBeCalled(); - }); - - it('should open bescheiden dialog with existing draft', () => { - component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.BESCHEID_DRAFT]); - component.openBescheidenDialogWithExistingDraft = jest.fn(); + describe('template', () => { + const state: StateResource<CommandResource> = createStateResource(createCommandResource()); - component.openBescheidenWizard(); + beforeEach(() => { + component.vorgang = createVorgangWithEingangResource([VorgangWithEingangLinkRel.BESCHEIDEN]); + component.commandStateResource$ = of(state); - expect(component.openBescheidenDialogWithExistingDraft).toHaveBeenCalled(); + fixture.detectChanges(); }); - it('should open bescheiden dialog with new draft', () => { - component.vorgang = createVorgangWithEingangResource(); - component.openBescheidDialogWithNewDraft = jest.fn(); + describe('bescheiden button', () => { + beforeEach(() => { + component.showAsIconButton = false; + fixture.detectChanges(); + }); - component.openBescheidenWizard(); + it('should not exits', () => { + component.vorgang = createVorgangWithEingangResource(); - expect(component.openBescheidDialogWithNewDraft).toHaveBeenCalled(); - }); - }); + fixture.detectChanges(); - describe('openBescheidDialogWithNewDraft', () => { - it('should open wizard', () => { - component.vorgang = createVorgangWithEingangResource(); - component.openDialog = jest.fn(); + notExistsAsHtmlElement(fixture, bescheidenButton); + }); - component.openBescheidDialogWithNewDraft(); + it('should exist with input', () => { + const button: ButtonWithSpinnerComponent = getElementComponentFromFixtureByCss(fixture, bescheidenButton); - expect(component.openDialog).toHaveBeenCalledWith({ - vorgangWithEingangResource: component.vorgang, - bescheidDraftResource: null, + expect(button).toBeTruthy(); + expect(button.stateResource).toBe(state); }); - }); - }); - describe('openBescheidenDialogWithExistingDraft', () => { - const bescheidDraftResource: BescheidResource = createBescheidResource(); - const bescheidDraftStateResource: StateResource<BescheidResource> = createStateResource(bescheidDraftResource); - const vorgangWithEingangResource: VorgangWithEingangResource = createVorgangWithEingangResource([ - VorgangWithEingangLinkRel.BESCHEID_DRAFT, - ]); + it('should get "Bescheid" text', () => { + const button: ButtonWithSpinnerComponent = getMockComponent(fixture, ButtonWithSpinnerComponent); + expect(button.text).toBe('Bescheiden'); + }); - beforeEach(() => { - component.vorgang = vorgangWithEingangResource; - bescheidService.getBescheidDraftIfExists.mockReturnValue(of(bescheidDraftStateResource)); - }); + it('should get "Bescheiden fortsetzen" text', () => { + component.vorgang = createVorgangWithEingangResource([ + VorgangWithEingangLinkRel.BESCHEIDEN, + VorgangWithEingangLinkRel.BESCHEID_DRAFT, + ]); - it('should open wizard if bescheid draft loaded', () => { - component.openBescheidenDialogWithExistingDraft(); + fixture.detectChanges(); - expect(ozgcloudDialogService.openWizard).toHaveBeenCalledWith(VorgangDetailBescheidenComponent, { - bescheidDraftResource, - vorgangWithEingangResource, + const button: ButtonWithSpinnerComponent = getMockComponent(fixture, ButtonWithSpinnerComponent); + expect(button.text).toBe('Bescheiden fortsetzen'); }); - }); - it('should not open wizard if bescheid draft not loaded', () => { - bescheidService.getBescheidDraftIfExists.mockReturnValue(of(createEmptyStateResource())); + it('should call bescheiden on click', () => { + component.bescheiden = jest.fn(); - component.openBescheidenDialogWithExistingDraft(); + triggerEvent({ fixture, name: 'clickEmitter', elementSelector: bescheidenButton }); - expect(ozgcloudDialogService.openWizard).not.toHaveBeenCalled(); + expect(component.bescheiden).toHaveBeenCalled(); + }); }); - it('should not open wizard on loading bescheid draft', () => { - bescheidService.getBescheidDraftIfExists.mockReturnValue( - of({ ...createStateResource(createBescheidResource()), loading: true }), - ); - - component.openBescheidenDialogWithExistingDraft(); + describe('bescheiden icon button', () => { + beforeEach(() => { + component.showAsIconButton = true; + fixture.detectChanges(); + }); - expect(ozgcloudDialogService.openWizard).not.toHaveBeenCalled(); - }); - }); + it('should not exist', () => { + component.vorgang = createVorgangWithEingangResource(); - describe('openDialog', () => { - const bescheidDraftResource: BescheidResource = createBescheidResource(); - const bescheidDraftStateResource: StateResource<BescheidResource> = createStateResource(bescheidDraftResource); - const vorgangWithEingangResource: VorgangWithEingangResource = createVorgangWithEingangResource([ - VorgangWithEingangLinkRel.BESCHEID_DRAFT, - ]); + fixture.detectChanges(); - const dialogData: BescheidenDialogData = { - bescheidDraftResource: bescheidDraftResource, - vorgangWithEingangResource: vorgangWithEingangResource, - }; + notExistsAsHtmlElement(fixture, bescheidenIconButton); + }); - beforeEach(() => { - component.vorgang = vorgangWithEingangResource; - bescheidService.getBescheidDraftIfExists.mockReturnValue(of(bescheidDraftStateResource)); - }); + it('should exist with input', () => { + const button: ButtonWithSpinnerComponent = getElementComponentFromFixtureByCss(fixture, bescheidenIconButton); - it('should call ozgcloudDialogService.openWizard', () => { - component.openDialog(dialogData); + expect(button).toBeTruthy(); + expect(button.stateResource).toBe(state); + }); - expect(ozgcloudDialogService.openWizard).toHaveBeenCalledWith(VorgangDetailBescheidenComponent, dialogData); - }); - }); + it('should have "Vorgang bescheiden" tooltip', () => { + tooltipExistsWithText(fixture, bescheidenIconButton, 'Vorgang bescheiden'); + }); - describe('handleBescheidWizardClosed', () => { - it('should reload current vorgang', () => { - component.handleBescheidWizardClosed({ reloadVorgang: true }); + it('should have "Vorgang bescheiden fortsetzen" tooltip', () => { + component.vorgang = createVorgangWithEingangResource([ + VorgangWithEingangLinkRel.BESCHEIDEN, + VorgangWithEingangLinkRel.BESCHEID_DRAFT, + ]); - expect(vorgangService.reloadCurrentVorgang).toHaveBeenCalled(); - }); + fixture.detectChanges(); - it('should not reload current vorgang', () => { - component.handleBescheidWizardClosed({ reloadVorgang: false }); + tooltipExistsWithText(fixture, bescheidenIconButton, 'Vorgang bescheiden fortsetzen'); + }); - expect(vorgangService.reloadCurrentVorgang).not.toHaveBeenCalled(); - }); + it('should call bescheiden on click', () => { + component.bescheiden = jest.fn(); - it.each([null, undefined])('should not reload current vorgang if result nil', (dialogResult: BescheidWizardDialogResult) => { - component.handleBescheidWizardClosed(dialogResult); + triggerEvent({ fixture, name: 'clickEmitter', elementSelector: bescheidenIconButton }); - expect(vorgangService.reloadCurrentVorgang).not.toHaveBeenCalled(); + expect(component.bescheiden).toHaveBeenCalled(); + }); }); }); }); diff --git a/alfa-client/libs/vorgang-detail/src/lib/vorgang-detail.module.ts b/alfa-client/libs/vorgang-detail/src/lib/vorgang-detail.module.ts index 579b092e9c..269d972319 100644 --- a/alfa-client/libs/vorgang-detail/src/lib/vorgang-detail.module.ts +++ b/alfa-client/libs/vorgang-detail/src/lib/vorgang-detail.module.ts @@ -70,6 +70,7 @@ import { SendIconComponent, SpinnerIconComponent, StampIconComponent, + TooltipDirective, } from '@ods/system'; import { AktenzeichenEditDialogComponent } from './aktenzeichen-edit-dialog/aktenzeichen-edit-dialog.component'; import { AktenzeichenEditableComponent } from './aktenzeichen-editable/aktenzeichen-editable.component'; @@ -179,6 +180,7 @@ const routes: Routes = [ MoreIconComponent, FileIconComponent, ForwardByOzgcloudButtonContainerComponent, + TooltipDirective, ], declarations: [ VorgangDetailPageComponent, -- GitLab