feat(Deltagarlista): Lade till startdatum, slutdatum, avbrott samt Visa händelser, som öppnar en modal med en deltagares händelser (TV-606)

Squashed commit of the following:

commit 932d0ce27b416652e241803e04dd9e98c6ca5757
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Wed Sep 22 08:17:56 2021 +0200

    fix lint and fails

commit b988fb7dc443d336e1e572d1a1f2993f7ed8f43b
Merge: 7eb75ec 5846c2c
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Wed Sep 22 07:54:00 2021 +0200

    Merge branch 'develop' into feature/TV-606-deltagarlista-add-columns

commit 7eb75ec659a3a25386f76dd9aed1806fd603c35b
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Wed Sep 22 07:53:54 2021 +0200

    refactor

commit 3bfe1fe1d7d17f8ba3dcdc6d587d957ff584ef6c
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Tue Sep 21 11:53:20 2021 +0200

    Update deltagare-list-handelser-dialog.component.scss

commit 4c7275e24ca9fdf70fb26db8e67a747c2a26b825
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Tue Sep 21 11:51:08 2021 +0200

    set dialog width to auto

commit 1feb3b6f5779a810881a7592325dd9f1bf33d490
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Tue Sep 21 11:43:51 2021 +0200

    added captions to tables

commit 4b4137cd9ae8e4084ea6172119449d247c591c40
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Tue Sep 21 11:06:16 2021 +0200

    Update server.js

commit 203609c380f2d47ce248b94ed06e0dfde293ef24
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Tue Sep 21 11:05:05 2021 +0200

    full name in dialog heading

commit 265c38aefe8d1380c7cc0ae1b87a12d276671ced
Merge: e734ab5 2dd9d3d
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Tue Sep 21 10:58:29 2021 +0200

    Merge branch 'develop' into feature/TV-606-deltagarlista-add-columns

commit e734ab5c6fe00923642da70dfe92cdbafc0f0c79
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Tue Sep 21 10:58:26 2021 +0200

    formatting

commit 1a13a9fc6d9329e6b5d6fce7c77352ac75123a5a
Merge: aa1552d 91eeb1d
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Tue Sep 21 10:49:07 2021 +0200

    Merge branch 'develop' into feature/TV-606-deltagarlista-add-columns

commit aa1552d0ad85b3213a0e062ee3f786849013566a
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Tue Sep 21 09:33:10 2021 +0200

    add colums to handelser

commit 584ecd2cb2b5265cc885dcab713582083dbe19bb
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Mon Sep 20 15:46:38 2021 +0200

    fix test and lint

commit 890e741c69a6408a72ca7899cc5cd76eccbdb498
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Mon Sep 20 15:39:18 2021 +0200

    add dialog and fix mock apis

commit fc8ee963619a8cd24e482c56180536219c83ec28
Merge: 422563b 8da6899
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Mon Sep 20 14:14:49 2021 +0200

    Merge branch 'develop' into feature/TV-606-deltagarlista-add-columns

commit 422563b5ecc8cc923b2e6791b5c533913ae6e4bd
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Mon Sep 20 13:01:45 2021 +0200

    wip

commit 2d83fa6e8a4d7459e8661bf7036388021bec460e
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Mon Sep 20 11:26:38 2021 +0200

    added columns to deltagare list

commit a9df57d4492ec3f08de8f20a3032c8a1a84fd8a4
Author: Daniel Appelgren <daniel.appelgren@arbetsformedlingen.se>
Date:   Mon Sep 20 10:21:27 2021 +0200

    wip
This commit is contained in:
Daniel Appelgren
2021-09-22 08:19:25 +02:00
parent 5846c2c5a4
commit 68c5c8d4a8
24 changed files with 382 additions and 70 deletions

View File

@@ -1,4 +1,4 @@
import { ButtonSize, ButtonType, ButtonVariation } from '@af/digi-ng/_button/button'; import { ButtonSize, ButtonType } from '@af/digi-ng/_button/button';
import { FormSelectItem } from '@af/digi-ng/_form/form-select'; import { FormSelectItem } from '@af/digi-ng/_form/form-select';
import { import {
ChangeDetectionStrategy, ChangeDetectionStrategy,

View File

@@ -0,0 +1,33 @@
<div class="deltagare-list-handelser">
<p>
Genomförandereferens: <strong>{{deltagare?.genomforandeReferens}}</strong>
</p>
<digi-table af-size="s">
<table>
<caption class="msfa__a11y-sr-only">Lista med alla händelser för {{deltagare?.fullName}}</caption>
<thead>
<tr>
<th scope="col" class="deltagare-list-handelser__heading-row">Inkom</th>
<th scope="col" class="deltagare-list-handelser__heading-row">Händelse</th>
<th scope="col" class="deltagare-list-handelser__heading-row">Datum för händelse</th>
<th scope="col" class="deltagare-list-handelser__heading-row">Datum förklaring</th>
</tr>
</thead>
<tbody>
<tr *ngFor="let handelse of deltagareHandelser$ | async">
<td class="deltagare-list-handelser__table-cell">{{handelse.receivedDate | date}}</td>
<td class="deltagare-list-handelser__table-cell" *ngIf="!handelse.isAvbrott; else isAvbrottCell">
{{handelse.description}}</td>
<td class="deltagare-list-handelser__table-cell">{{handelse.tidpunkt | date }}</td>
<td class="deltagare-list-handelser__table-cell">{{handelse.tidpunktDescription}}</td>
<ng-template #isAvbrottCell>
<td class="deltagare-list-handelser__avbrott-cell">
<msfa-icon [icon]="iconType.WARNING" size="l"></msfa-icon>
{{handelse.description}}</td>
</ng-template>
</tr>
</tbody>
</table>
</digi-table>
</div>

View File

@@ -0,0 +1,26 @@
.deltagare-list-handelser {
&__heading-row {
white-space: nowrap;
}
&__table-cell {
white-space: nowrap;
}
&__avbrott-cell {
color: var(--digi--ui--color--danger);
}
}
// DA: Digins maxbredd är hårt satt till 540px (!?) Bör vara auto tycker jag.
// Vi kanske bör ersätta med egen dialog längre fram?
::ng-deep .digi-ng-dialog-base__content {
width: auto;
max-width: 90vw !important;
}
::ng-deep .digi-ng-dialog__inner {
width: auto !important;
max-width: 90vw !important;
}

View File

@@ -0,0 +1,28 @@
import { ComponentFixture, TestBed } from '@angular/core/testing';
import { DeltagareListHandelserDialogComponent } from './deltagare-list-handelser-dialog.component';
import { HttpClientTestingModule } from '@angular/common/http/testing';
import { CUSTOM_ELEMENTS_SCHEMA } from '@angular/core';
describe('DeltagareListHandelserDialogComponent', () => {
let component: DeltagareListHandelserDialogComponent;
let fixture: ComponentFixture<DeltagareListHandelserDialogComponent>;
beforeEach(async () => {
await TestBed.configureTestingModule({
schemas: [CUSTOM_ELEMENTS_SCHEMA],
imports: [HttpClientTestingModule],
declarations: [DeltagareListHandelserDialogComponent],
}).compileComponents();
});
beforeEach(() => {
fixture = TestBed.createComponent(DeltagareListHandelserDialogComponent);
component = fixture.componentInstance;
fixture.detectChanges();
});
it('should create', () => {
expect(component).toBeTruthy();
});
});

View File

@@ -0,0 +1,28 @@
import { ChangeDetectionStrategy, Component, Input, OnInit } from '@angular/core';
import { DeltagareHandelserApiService } from '@msfa-services/api/deltagare-handelser-api.service';
import { DeltagareHandelse } from '@msfa-models/deltagare-handelse.model';
import { Observable } from 'rxjs';
import { IconType } from '@msfa-enums/icon-type.enum';
import { DeltagareCompact } from '@msfa-models/deltagare.model';
@Component({
selector: 'msfa-deltagare-list-handelser-dialog',
templateUrl: './deltagare-list-handelser-dialog.component.html',
styleUrls: ['./deltagare-list-handelser-dialog.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush,
})
export class DeltagareListHandelserDialogComponent implements OnInit {
@Input() deltagare: DeltagareCompact;
iconType = IconType;
deltagareHandelser$: Observable<DeltagareHandelse[]>;
constructor(private deltagareHandelserApiService: DeltagareHandelserApiService) {}
ngOnInit(): void {
if (this.deltagare) {
this.deltagareHandelser$ = this.deltagareHandelserApiService.fetchDeltagareHandelser(
this.deltagare.genomforandeReferens
);
}
}
}

View File

@@ -1,41 +1,76 @@
<div class="deltagare-list"> <div class="deltagare-list">
<digi-table af-variation="secondary"> <digi-table af-variation="secondary">
<table> <table class="deltagare-list__table">
<caption class="msfa__a11y-sr-only">Tabell med de deltagare som tillhör organistaionen.</caption>
<thead> <thead>
<tr> <tr>
<th scope="col" class="deltagare-list__column-head" *ngFor="let column of columnHeaders"> <th scope="col" class="deltagare-list__column-head" *ngFor="let column of columnHeaders">
<button <button
class="deltagare-list__sort-button" class="deltagare-list__sort-button"
[attr.id]="'sort-button-' + column.key" [attr.id]="'sort-button-' + column.key"
(click)="handleSort(column.key)" (click)="handleSort(column.key)"
> >
{{column.label}} {{column.label}}
<ng-container *ngIf="sort.key === column.key"> <ng-container *ngIf="sort.key === column.key">
<digi-icon-caret-up <digi-icon-caret-up
class="deltagare-list__sort-icon" class="deltagare-list__sort-icon"
*ngIf="sort.order === orderType.ASC" *ngIf="sort.order === orderType.ASC"
></digi-icon-caret-up> ></digi-icon-caret-up>
<digi-icon-caret-down <digi-icon-caret-down
class="deltagare-list__sort-icon" class="deltagare-list__sort-icon"
*ngIf="sort.order === orderType.DESC" *ngIf="sort.order === orderType.DESC"
></digi-icon-caret-down> ></digi-icon-caret-down>
</ng-container> </ng-container>
</button> </button>
</th> </th>
</tr> </tr>
</thead> </thead>
<tbody> <tbody>
<tr class="deltagare-list__row" *ngFor="let singleDeltagare of deltagare"> <tr class="deltagare-list__row" *ngFor="let singleDeltagare of deltagare">
<th scope="row"> <th scope="row">
<a [routerLink]="singleDeltagare.id" class="deltagare-list__link">{{ singleDeltagare.fullName }}</a> <a [routerLink]="singleDeltagare.id" class="deltagare-list__link">{{ singleDeltagare.fullName }}</a>
</th> </th>
<td>{{ singleDeltagare.tjanst }}</td> <td>{{ singleDeltagare.tjanst }}</td>
<td>{{ singleDeltagare.utforandeVerksamhet }}</td> <td>{{ singleDeltagare.utforandeVerksamhet }}</td>
</tr> <td>{{ singleDeltagare.startdatumAvrop | date }}</td>
<td>
{{ singleDeltagare.slutdatumAvrop | date }}
<div class="deltagare-list__avbrott-alert" *ngIf="singleDeltagare.hasAvbrott">
<msfa-icon [icon]="iconType.WARNING" size="l"></msfa-icon>
Avbrott
</div>
</td>
<td>
<digi-button
af-variation="tertiary"
af-size="s"
(click)="openHandelser(singleDeltagare)"
aria-controls="deltagareHandelser"
>
<digi-icon-info-circle-reg class="deltagare-list__info-icon" slot="icon"></digi-icon-info-circle-reg>
Visa händelser
</digi-button>
</td>
</tr>
</tbody> </tbody>
</table> </table>
</digi-table> </digi-table>
<digi-ng-dialog
[afActive]="handelserDialogIsOpen$ | async"
(afOnPrimaryClick)="closeHandelser()"
(afOnInactive)="closeHandelser()"
*ngIf="handelserDialogDeltagare$ | async; let deltagare"
[afHeading]="'Händelser för ' + deltagare.fullName"
afHeadingLevel="h2"
[afPrimaryButtonText]="'Stäng'"
id="deltagareHandelser"
>
<msfa-deltagare-list-handelser-dialog
[deltagare]="deltagare"
></msfa-deltagare-list-handelser-dialog>
</digi-ng-dialog>
<digi-navigation-pagination <digi-navigation-pagination
*ngIf="totalPage > 1" *ngIf="totalPage > 1"
class="deltagare-list__pagination" class="deltagare-list__pagination"

View File

@@ -1,6 +1,11 @@
@import 'variables/gutters'; @import 'variables/gutters';
.deltagare-list { .deltagare-list {
&__table {
font-size: var(--digi--typography--font-size--s);
}
&__column-head { &__column-head {
padding: 0; padding: 0;
} }
@@ -11,8 +16,7 @@
border-width: 0; border-width: 0;
width: 100%; width: 100%;
text-align: left; text-align: left;
padding: var(--digi--layout--gutter--s) $digi--layout--gutter--l var(--digi--layout--gutter--s) padding: var(--digi--layout--gutter--s) $digi--layout--gutter--l var(--digi--layout--gutter--s) var(--digi--layout--gutter);
var(--digi--layout--gutter);
margin: 0; margin: 0;
font-size: inherit; font-size: inherit;
font-weight: inherit; font-weight: inherit;
@@ -32,4 +36,15 @@
display: block; display: block;
margin-top: var(--digi--layout--gutter); margin-top: var(--digi--layout--gutter);
} }
&__avbrott-alert {
display: inline-block;
color: var(--digi--ui--color--danger);
}
&__info-icon {
--digi-icon--height: 1rem;
--digi-icon--width: 1rem;
}
} }

View File

@@ -3,6 +3,10 @@ import { SortOrder } from '@msfa-enums/sort-order.enum';
import { DeltagareCompact } from '@msfa-models/deltagare.model'; import { DeltagareCompact } from '@msfa-models/deltagare.model';
import { PaginationMeta } from '@msfa-models/pagination-meta.model'; import { PaginationMeta } from '@msfa-models/pagination-meta.model';
import { Sort } from '@msfa-models/sort.model'; import { Sort } from '@msfa-models/sort.model';
import { IconType } from '@msfa-enums/icon-type.enum';
import { ErrorSeverity } from '@msfa-enums/error-severity.enum';
import { BehaviorSubject } from 'rxjs';
import { map } from 'rxjs/operators';
@Component({ @Component({
selector: 'msfa-deltagare-list', selector: 'msfa-deltagare-list',
@@ -16,6 +20,12 @@ export class DeltagareListComponent {
@Input() sort: Sort<keyof DeltagareCompact>; @Input() sort: Sort<keyof DeltagareCompact>;
@Output() sorted = new EventEmitter<keyof DeltagareCompact>(); @Output() sorted = new EventEmitter<keyof DeltagareCompact>();
@Output() paginated = new EventEmitter<number>(); @Output() paginated = new EventEmitter<number>();
handelserDialogDeltagare$ = new BehaviorSubject<DeltagareCompact | null>(null);
handelserDialogIsOpen$ = this.handelserDialogDeltagare$.pipe(map(genomforandereferens => !!genomforandereferens));
iconType = IconType;
errorSeverity = ErrorSeverity;
columnHeaders: { label: string; key: keyof DeltagareCompact }[] = [ columnHeaders: { label: string; key: keyof DeltagareCompact }[] = [
{ label: 'Namn', key: 'fullName' }, { label: 'Namn', key: 'fullName' },
@@ -27,6 +37,18 @@ export class DeltagareListComponent {
label: 'Utförande verksamhet', label: 'Utförande verksamhet',
key: 'utforandeVerksamhet', key: 'utforandeVerksamhet',
}, },
{
label: 'Startdatum',
key: 'startdatumAvrop',
},
{
label: 'Slutdatum',
key: 'slutdatumAvrop',
},
{
label: 'Status',
key: 'genomforandeReferens',
},
]; ];
orderType = SortOrder; orderType = SortOrder;
@@ -59,4 +81,12 @@ export class DeltagareListComponent {
setNewPage(page: number): void { setNewPage(page: number): void {
this.paginated.emit(page); this.paginated.emit(page);
} }
openHandelser(deltagareCompact: DeltagareCompact): void {
this.handelserDialogDeltagare$.next(deltagareCompact);
}
closeHandelser(): void {
this.handelserDialogDeltagare$.next(null);
}
} }

View File

@@ -2,11 +2,14 @@ import { CommonModule } from '@angular/common';
import { CUSTOM_ELEMENTS_SCHEMA, NgModule } from '@angular/core'; import { CUSTOM_ELEMENTS_SCHEMA, NgModule } from '@angular/core';
import { RouterModule } from '@angular/router'; import { RouterModule } from '@angular/router';
import { DeltagareListComponent } from './deltagare-list.component'; import { DeltagareListComponent } from './deltagare-list.component';
import { IconModule } from '@msfa-shared/components/icon/icon.module';
import { DigiNgDialogModule } from '@af/digi-ng/_dialog/dialog';
import { DeltagareListHandelserDialogComponent } from './deltagare-list-handelser-dialog/deltagare-list-handelser-dialog.component';
@NgModule({ @NgModule({
schemas: [CUSTOM_ELEMENTS_SCHEMA], schemas: [CUSTOM_ELEMENTS_SCHEMA],
declarations: [DeltagareListComponent], declarations: [DeltagareListComponent, DeltagareListHandelserDialogComponent],
imports: [CommonModule, RouterModule], imports: [CommonModule, RouterModule, IconModule, DigiNgDialogModule],
exports: [DeltagareListComponent], exports: [DeltagareListComponent],
}) })
export class DeltagareListModule {} export class DeltagareListModule {}

View File

@@ -4,10 +4,11 @@ import { LayoutModule } from '@msfa-shared/components/layout/layout.module';
import { DeltagareListModule } from './components/deltagare-list/deltagare-list.module'; import { DeltagareListModule } from './components/deltagare-list/deltagare-list.module';
import { DeltagareRoutingModule } from './deltagare-routing.module'; import { DeltagareRoutingModule } from './deltagare-routing.module';
import { DeltagareComponent } from './deltagare.component'; import { DeltagareComponent } from './deltagare.component';
import { DigiNgSkeletonBaseModule } from '@af/digi-ng/_skeleton/skeleton-base';
@NgModule({ @NgModule({
schemas: [CUSTOM_ELEMENTS_SCHEMA], schemas: [CUSTOM_ELEMENTS_SCHEMA],
declarations: [DeltagareComponent], declarations: [DeltagareComponent],
imports: [CommonModule, DeltagareRoutingModule, LayoutModule, DeltagareListModule], imports: [CommonModule, DeltagareRoutingModule, LayoutModule, DeltagareListModule, DigiNgSkeletonBaseModule],
}) })
export class DeltagareModule {} export class DeltagareModule {}

View File

@@ -1,18 +1,12 @@
import { Component, OnInit, ChangeDetectionStrategy } from '@angular/core'; import { Component, ChangeDetectionStrategy } from '@angular/core';
@Component({ @Component({
selector: 'msfa-periodisk-redovisning', selector: 'msfa-periodisk-redovisning',
templateUrl: './periodisk-redovisning.component.html', templateUrl: './periodisk-redovisning.component.html',
styleUrls: ['./periodisk-redovisning.component.scss'], styleUrls: ['./periodisk-redovisning.component.scss'],
changeDetection: ChangeDetectionStrategy.OnPush changeDetection: ChangeDetectionStrategy.OnPush,
}) })
export class PeriodiskRedovisningComponent implements OnInit { export class PeriodiskRedovisningComponent {
currentStep = 1; currentStep = 1;
sendRequest = false; sendRequest = false;
constructor() { }
ngOnInit(): void {
}
} }

View File

@@ -3,10 +3,9 @@ import { CUSTOM_ELEMENTS_SCHEMA, NgModule } from '@angular/core';
import { ReactiveFormsModule } from '@angular/forms'; import { ReactiveFormsModule } from '@angular/forms';
import { RouterModule } from '@angular/router'; import { RouterModule } from '@angular/router';
import { LayoutModule } from '@msfa-shared/components/layout/layout.module'; import { LayoutModule } from '@msfa-shared/components/layout/layout.module';
import { ReportLayoutModule } from '../../../../shared/report-layout/report-layout-module'; import { ReportLayoutModule } from '../../../../shared/report-layout/report-layout.module';
import { PeriodiskRedovisningComponent } from './periodisk-redovisning.component'; import { PeriodiskRedovisningComponent } from './periodisk-redovisning.component';
@NgModule({ @NgModule({
schemas: [CUSTOM_ELEMENTS_SCHEMA], schemas: [CUSTOM_ELEMENTS_SCHEMA],
declarations: [PeriodiskRedovisningComponent], declarations: [PeriodiskRedovisningComponent],
@@ -15,8 +14,8 @@ import { PeriodiskRedovisningComponent } from './periodisk-redovisning.component
RouterModule.forChild([{ path: '', component: PeriodiskRedovisningComponent }]), RouterModule.forChild([{ path: '', component: PeriodiskRedovisningComponent }]),
LayoutModule, LayoutModule,
ReactiveFormsModule, ReactiveFormsModule,
ReportLayoutModule ReportLayoutModule,
], ],
exports: [PeriodiskRedovisningComponent] exports: [PeriodiskRedovisningComponent],
}) })
export class PeriodiskRedovisningModule { } export class PeriodiskRedovisningModule {}

View File

@@ -1,6 +1,8 @@
import { ComponentFixture, TestBed } from '@angular/core/testing'; import { ComponentFixture, TestBed } from '@angular/core/testing';
import { ReportLayoutComponent } from './report-layout.component'; import { ReportLayoutComponent } from './report-layout.component';
import { HttpClientTestingModule } from '@angular/common/http/testing';
import { ReportLayoutModule } from './report-layout.module';
import { RouterTestingModule } from '@angular/router/testing';
describe('ReportLayoutComponent', () => { describe('ReportLayoutComponent', () => {
let component: ReportLayoutComponent; let component: ReportLayoutComponent;
@@ -8,9 +10,8 @@ describe('ReportLayoutComponent', () => {
beforeEach(async () => { beforeEach(async () => {
await TestBed.configureTestingModule({ await TestBed.configureTestingModule({
declarations: [ ReportLayoutComponent ] imports: [ReportLayoutModule, RouterTestingModule, HttpClientTestingModule],
}) }).compileComponents();
.compileComponents();
}); });
beforeEach(() => { beforeEach(() => {

View File

@@ -4,11 +4,12 @@ import { LayoutModule } from '@msfa-shared/components/layout/layout.module';
import { ReportLayoutComponent } from './report-layout.component'; import { ReportLayoutComponent } from './report-layout.component';
import { DigiNgProgressProgressbarModule } from '@af/digi-ng/_progress/progressbar'; import { DigiNgProgressProgressbarModule } from '@af/digi-ng/_progress/progressbar';
import { HideTextModule } from '@msfa-shared/components/hide-text/hide-text.module'; import { HideTextModule } from '@msfa-shared/components/hide-text/hide-text.module';
import { RouterModule } from '@angular/router';
@NgModule({ @NgModule({
schemas: [CUSTOM_ELEMENTS_SCHEMA], schemas: [CUSTOM_ELEMENTS_SCHEMA],
declarations: [ReportLayoutComponent], declarations: [ReportLayoutComponent],
imports: [CommonModule, LayoutModule, DigiNgProgressProgressbarModule, HideTextModule], imports: [CommonModule, RouterModule, LayoutModule, DigiNgProgressProgressbarModule, HideTextModule],
exports: [ReportLayoutComponent] exports: [ReportLayoutComponent],
}) })
export class ReportLayoutModule {} export class ReportLayoutModule {}

View File

@@ -9,7 +9,6 @@ import {
Output, Output,
Renderer2, Renderer2,
ViewChild, ViewChild,
ChangeDetectorRef,
} from '@angular/core'; } from '@angular/core';
import { ControlValueAccessor, NG_VALUE_ACCESSOR } from '@angular/forms'; import { ControlValueAccessor, NG_VALUE_ACCESSOR } from '@angular/forms';
import { DropdownTriggerForDirective } from '@msfa-shared/components/dropdown/dropdown-trigger-for.directive'; import { DropdownTriggerForDirective } from '@msfa-shared/components/dropdown/dropdown-trigger-for.directive';
@@ -55,7 +54,7 @@ export class MultiselectComponent implements AfterViewInit, ControlValueAccessor
private propagateChange: PropagateChangeFn; private propagateChange: PropagateChangeFn;
private propagateTouched: PropagateTouchedFn; private propagateTouched: PropagateTouchedFn;
constructor(private renderer: Renderer2, private changeDetectionRef: ChangeDetectorRef) {} constructor(private renderer: Renderer2) {}
// Allows Angular to update the model. // Allows Angular to update the model.
// Update the model and changes needed for the view here. // Update the model and changes needed for the view here.

View File

@@ -16,6 +16,10 @@ export interface DeltagareCompactResponse {
tjanst: string; tjanst: string;
utforandeVerksamhet: string; utforandeVerksamhet: string;
utforandeAdress: string; utforandeAdress: string;
hasAvbrott: boolean;
genomforandeReferens: string;
startdatumAvrop: Date;
slutdatumAvrop: Date;
} }
export interface DeltagareResponse { export interface DeltagareResponse {

View File

@@ -0,0 +1,11 @@
export interface DeltagareHandelse {
description: string;
receivedDate: Date;
isAvbrott: boolean;
tidpunkt: Date;
tidpunktDescription: string;
}
export interface DeltagareHandelseApiResponse {
data: DeltagareHandelse[];
}

View File

@@ -18,6 +18,10 @@ export interface DeltagareCompact {
tjanst: string; tjanst: string;
utforandeVerksamhet: string; utforandeVerksamhet: string;
utforandeAdress: string; utforandeAdress: string;
hasAvbrott: boolean;
genomforandeReferens: string;
startdatumAvrop: Date;
slutdatumAvrop: Date;
} }
export interface Deltagare { export interface Deltagare {
@@ -45,7 +49,18 @@ export interface DeltagareCompactData {
} }
export function mapResponseToDeltagareCompact(data: DeltagareCompactResponse): DeltagareCompact { export function mapResponseToDeltagareCompact(data: DeltagareCompactResponse): DeltagareCompact {
const { sokandeId, fornamn, efternamn, tjanst, utforandeVerksamhet, utforandeAdress } = data; const {
sokandeId,
fornamn,
efternamn,
tjanst,
utforandeVerksamhet,
utforandeAdress,
hasAvbrott,
genomforandeReferens,
startdatumAvrop,
slutdatumAvrop,
} = data;
return { return {
id: sokandeId.toString(), id: sokandeId.toString(),
firstName: fornamn, firstName: fornamn,
@@ -54,6 +69,10 @@ export function mapResponseToDeltagareCompact(data: DeltagareCompactResponse): D
tjanst, tjanst,
utforandeVerksamhet, utforandeVerksamhet,
utforandeAdress, utforandeAdress,
hasAvbrott,
genomforandeReferens,
startdatumAvrop,
slutdatumAvrop,
}; };
} }

View File

@@ -0,0 +1,26 @@
import { Injectable } from '@angular/core';
import { Observable } from 'rxjs';
import { map } from 'rxjs/operators';
import { HttpClient } from '@angular/common/http';
import { DeltagareHandelse, DeltagareHandelseApiResponse } from '@msfa-models/deltagare-handelse.model';
import { environment } from '@msfa-environment';
@Injectable({
providedIn: 'root',
})
export class DeltagareHandelserApiService {
private _apiBaseUrl = `${environment.api.url}/deltagareHandelser`;
constructor(private httpClient: HttpClient) {}
fetchDeltagareHandelser(genomforandereferens: string): Observable<DeltagareHandelse[]> {
return this.httpClient
.get<DeltagareHandelseApiResponse>(`${this._apiBaseUrl}?genomforandereferens=${genomforandereferens}`)
.pipe(
map(({ data }) => {
if (data) {
return data;
}
})
);
}
}

View File

@@ -58,6 +58,7 @@ function generateAvrop(amount = 10, deltagare, handledare) {
sparNamn: track.name, sparNamn: track.name,
handledareCiamUserId: null, handledareCiamUserId: null,
recievedTimestamp: faker.date.recent(), recievedTimestamp: faker.date.recent(),
hasAvbrott: currentDeltagare.hasAvbrott,
}); });
} }

View File

@@ -0,0 +1,36 @@
import faker from 'faker';
faker.locale = 'sv';
const HANDELSER = [
'Gemensam planering inkommen',
'Gemensam planering godkänd',
'Slutredovisning inkommen',
'Slutredovisning godkänd',
'Slutredovisning ej godkänd',
'Avbrott handläggs',
'Avbrott bifall',
'Avbrott avslag',
'Byte av leverantör bifall',
];
const TIDPUNKT_DESCRIPTION = ['Handläggning startad', 'Inrapporteringsdatum slutredovisning'];
function generateHandelser(amount = 10) {
const handelser = [];
for (let id = 1; id <= amount; ++id) {
const handelse = HANDELSER[Math.floor(Math.random() * HANDELSER.length)];
handelser.push({
description: handelse,
receivedDate: faker.date.recent(),
isAvbrott: handelse.indexOf('Avbrott') >= 0,
tidpunkt: faker.date.recent(),
tidpunktDescription: TIDPUNKT_DESCRIPTION[Math.floor(Math.random() * TIDPUNKT_DESCRIPTION.length)],
});
}
return handelser;
}
export default {
generate: generateHandelser,
};

View File

@@ -111,6 +111,7 @@ function generateDeltagare(amount = 10) {
workExperiences: { workExperiences: {
arbetslivserfarenheter: chooseRandom(WORK_EXPERIENCES, faker.datatype.number(WORK_EXPERIENCES.length)), arbetslivserfarenheter: chooseRandom(WORK_EXPERIENCES, faker.datatype.number(WORK_EXPERIENCES.length)),
}, },
hasAvbrott: Math.random() < 0.2,
}; };
if (Math.random() > 0.8) { if (Math.random() > 0.8) {
deltagare.contact.adresser.push({ deltagare.contact.adresser.push({

View File

@@ -4,6 +4,7 @@ import avrop from './avrop.js';
import currentUser from './current-user.js'; import currentUser from './current-user.js';
import userinfo from './userinfo.js'; import userinfo from './userinfo.js';
import deltagare from './deltagare.js'; import deltagare from './deltagare.js';
import deltagareHandelser from './deltagare-handelser.js';
import employees from './employees.js'; import employees from './employees.js';
import handledare from './handledare.js'; import handledare from './handledare.js';
import languages from './languages.js'; import languages from './languages.js';
@@ -21,6 +22,7 @@ const AUTHORIZATIONS = ['Hantera användare', 'Hantera origisation', 'Hantera ek
const generatedEmployees = employees.generate(50); const generatedEmployees = employees.generate(50);
const generatedDeltagare = deltagare.generate(50); const generatedDeltagare = deltagare.generate(50);
const generatedDeltagareHandelser = deltagareHandelser.generate(10);
const generatedHandledare = handledare.generate(generatedEmployees.slice(0, 6)); const generatedHandledare = handledare.generate(generatedEmployees.slice(0, 6));
const generatedAvrop = avrop.generate(10, generatedDeltagare.slice(0, 25), generatedHandledare); const generatedAvrop = avrop.generate(10, generatedDeltagare.slice(0, 25), generatedHandledare);
const generatedTjanster = tjanster.generate(); const generatedTjanster = tjanster.generate();
@@ -111,6 +113,7 @@ const apiData = {
utforandeVerksamheter, utforandeVerksamheter,
kommuner: avropKommuner, kommuner: avropKommuner,
deltagare: generatedDeltagare, deltagare: generatedDeltagare,
deltagareHandelser: generatedDeltagareHandelser,
handledare: generatedHandledare, handledare: generatedHandledare,
participants: participants.generate(50).map(participant => ({ participants: participants.generate(50).map(participant => ({
...participant, ...participant,

View File

@@ -123,14 +123,32 @@ router.render = (req, res) => {
} }
if (pathname === '/deltagare') { if (pathname === '/deltagare') {
data = data.map(({ sokandeId, fornamn, efternamn, tjansteNamn, utforandeverksamhet, adress }) => ({ // NOTE: this is reading from avrop.js
sokandeId: sokandeId.toString(), data = data.map(
fornamn, ({
efternamn, sokandeId,
tjanst: tjansteNamn, fornamn,
utforandeVerksamhet: utforandeverksamhet, efternamn,
utforandeAdress: adress, tjansteNamn,
})); utforandeverksamhet,
adress,
startdatumAvrop,
slutdatumAvrop,
hasAvbrott,
genomforandeReferens,
}) => ({
sokandeId: sokandeId.toString(),
fornamn,
efternamn,
tjanst: tjansteNamn,
utforandeVerksamhet: utforandeverksamhet,
utforandeAdress: adress,
startdatumAvrop,
slutdatumAvrop,
hasAvbrott,
genomforandeReferens,
})
);
} }
res.jsonp({ res.jsonp({