RED-3586, RED-3593: Redo dossier states
This commit is contained in:
parent
61ecb52969
commit
460701a17b
@ -1,7 +1,7 @@
|
|||||||
<section class="dialog">
|
<section class="dialog">
|
||||||
<div
|
<div
|
||||||
[translateParams]="{
|
[translateParams]="{
|
||||||
type: data.dossierState ? 'edit' : 'create',
|
type: type,
|
||||||
name: data.dossierState?.name
|
name: data.dossierState?.name
|
||||||
}"
|
}"
|
||||||
[translate]="'add-edit-dossier-state.title'"
|
[translate]="'add-edit-dossier-state.title'"
|
||||||
|
|||||||
@ -1,8 +1,11 @@
|
|||||||
import { ChangeDetectionStrategy, Component, Inject, Injector } from '@angular/core';
|
import { ChangeDetectionStrategy, Component, Inject, Injector } from '@angular/core';
|
||||||
import { BaseDialogComponent } from '@iqser/common-ui';
|
import { BaseDialogComponent, LoadingService, Toaster } from '@iqser/common-ui';
|
||||||
import { FormBuilder, FormGroup, Validators } from '@angular/forms';
|
import { FormBuilder, FormGroup, Validators } from '@angular/forms';
|
||||||
import { MAT_DIALOG_DATA, MatDialogRef } from '@angular/material/dialog';
|
import { MAT_DIALOG_DATA, MatDialogRef } from '@angular/material/dialog';
|
||||||
import { IDossierState } from '@red/domain';
|
import { IDossierState } from '@red/domain';
|
||||||
|
import { firstValueFrom } from 'rxjs';
|
||||||
|
import { DossierStatesService } from '@services/entity-services/dossier-states.service';
|
||||||
|
import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
|
||||||
|
|
||||||
interface DialogData {
|
interface DialogData {
|
||||||
readonly dossierState: IDossierState;
|
readonly dossierState: IDossierState;
|
||||||
@ -18,6 +21,9 @@ interface DialogData {
|
|||||||
export class AddEditDossierStateDialogComponent extends BaseDialogComponent {
|
export class AddEditDossierStateDialogComponent extends BaseDialogComponent {
|
||||||
constructor(
|
constructor(
|
||||||
private readonly _formBuilder: FormBuilder,
|
private readonly _formBuilder: FormBuilder,
|
||||||
|
private readonly _loadingService: LoadingService,
|
||||||
|
private readonly _toaster: Toaster,
|
||||||
|
private readonly _dossierStateService: DossierStatesService,
|
||||||
protected readonly _injector: Injector,
|
protected readonly _injector: Injector,
|
||||||
protected readonly _dialogRef: MatDialogRef<AddEditDossierStateDialogComponent>,
|
protected readonly _dialogRef: MatDialogRef<AddEditDossierStateDialogComponent>,
|
||||||
@Inject(MAT_DIALOG_DATA) readonly data: DialogData,
|
@Inject(MAT_DIALOG_DATA) readonly data: DialogData,
|
||||||
@ -27,13 +33,23 @@ export class AddEditDossierStateDialogComponent extends BaseDialogComponent {
|
|||||||
this.initialFormValue = this.form.getRawValue();
|
this.initialFormValue = this.form.getRawValue();
|
||||||
}
|
}
|
||||||
|
|
||||||
save(): void {
|
get type(): 'edit' | 'create' {
|
||||||
|
return this.data.dossierState ? 'edit' : 'create';
|
||||||
|
}
|
||||||
|
|
||||||
|
async save(): Promise<void> {
|
||||||
const dossierState: IDossierState = {
|
const dossierState: IDossierState = {
|
||||||
dossierStatusId: this.data.dossierState?.dossierStatusId,
|
dossierStatusId: this.data.dossierState?.dossierStatusId,
|
||||||
dossierTemplateId: this.data.dossierTemplateId,
|
dossierTemplateId: this.data.dossierTemplateId,
|
||||||
...this.form.getRawValue(),
|
...this.form.getRawValue(),
|
||||||
};
|
};
|
||||||
this._dialogRef.close(dossierState);
|
this._loadingService.start();
|
||||||
|
try {
|
||||||
|
await firstValueFrom(this._dossierStateService.createOrUpdate(dossierState));
|
||||||
|
this._toaster.success(_('add-edit-dossier-state.success'), { params: { type: this.type } });
|
||||||
|
this._dialogRef.close();
|
||||||
|
} catch (e) {}
|
||||||
|
this._loadingService.stop();
|
||||||
}
|
}
|
||||||
|
|
||||||
#getForm(): FormGroup {
|
#getForm(): FormGroup {
|
||||||
|
|||||||
@ -12,12 +12,12 @@
|
|||||||
<form [formGroup]="form">
|
<form [formGroup]="form">
|
||||||
<div class="flex">
|
<div class="flex">
|
||||||
<div class="iqser-input-group w-300">
|
<div class="iqser-input-group w-300">
|
||||||
<label translate="confirm-delete-dossier-state.form.status"></label>
|
<label translate="confirm-delete-dossier-state.form.state"></label>
|
||||||
<mat-select
|
<mat-select
|
||||||
[placeholder]="'confirm-delete-dossier-state.form.status-placeholder' | translate"
|
[placeholder]="'confirm-delete-dossier-state.form.state-placeholder' | translate"
|
||||||
formControlName="replaceDossierStatusId"
|
formControlName="replaceDossierStatusId"
|
||||||
>
|
>
|
||||||
<mat-option>{{ 'confirm-delete-dossier-state.form.status-placeholder' | translate }}</mat-option>
|
<mat-option>{{ 'confirm-delete-dossier-state.form.state-placeholder' | translate }}</mat-option>
|
||||||
<mat-option *ngFor="let state of data.otherStates" [value]="state.dossierStatusId">
|
<mat-option *ngFor="let state of data.otherStates" [value]="state.dossierStatusId">
|
||||||
{{ state.name }}
|
{{ state.name }}
|
||||||
</mat-option>
|
</mat-option>
|
||||||
@ -29,10 +29,10 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="dialog-actions">
|
<div class="dialog-actions">
|
||||||
<button (click)="dialogRef.close(afterCloseValue)" color="primary" mat-flat-button>
|
<button (click)="save()" color="primary" mat-flat-button>
|
||||||
{{ label | translate }}
|
{{ label | translate }}
|
||||||
</button>
|
</button>
|
||||||
<div (click)="dialogRef.close()" [translate]="'confirm-delete-dossier-state.cancel'" class="all-caps-label cancel"></div>
|
<div [translate]="'confirm-delete-dossier-state.cancel'" class="all-caps-label cancel" mat-dialog-close></div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<iqser-circle-button class="dialog-close" icon="iqser:close" mat-dialog-close></iqser-circle-button>
|
<iqser-circle-button class="dialog-close" icon="iqser:close" mat-dialog-close></iqser-circle-button>
|
||||||
|
|||||||
@ -1,12 +1,18 @@
|
|||||||
import { ChangeDetectionStrategy, Component, Inject } from '@angular/core';
|
import { ChangeDetectionStrategy, Component, Inject } from '@angular/core';
|
||||||
import { IDossierState } from '@red/domain';
|
import { DossierState } from '@red/domain';
|
||||||
import { MAT_DIALOG_DATA, MatDialogRef } from '@angular/material/dialog';
|
import { MAT_DIALOG_DATA, MatDialogRef } from '@angular/material/dialog';
|
||||||
import { FormBuilder, FormGroup } from '@angular/forms';
|
import { FormBuilder, FormGroup } from '@angular/forms';
|
||||||
import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
|
import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
|
||||||
|
import { firstValueFrom, forkJoin } from 'rxjs';
|
||||||
|
import { DossierStatesService } from '@services/entity-services/dossier-states.service';
|
||||||
|
import { LoadingService, Toaster } from '@iqser/common-ui';
|
||||||
|
import { ActiveDossiersService } from '@services/dossiers/active-dossiers.service';
|
||||||
|
import { ArchivedDossiersService } from '@services/dossiers/archived-dossiers.service';
|
||||||
|
import { take } from 'rxjs/operators';
|
||||||
|
|
||||||
interface DialogData {
|
interface DialogData {
|
||||||
readonly toBeDeletedState: IDossierState;
|
readonly toBeDeletedState: DossierState;
|
||||||
readonly otherStates: IDossierState[];
|
readonly otherStates: DossierState[];
|
||||||
readonly dossierCount: number;
|
readonly dossierCount: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -21,7 +27,12 @@ export class ConfirmDeleteDossierStateDialogComponent {
|
|||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
private readonly _formBuilder: FormBuilder,
|
private readonly _formBuilder: FormBuilder,
|
||||||
readonly dialogRef: MatDialogRef<ConfirmDeleteDossierStateDialogComponent>,
|
private readonly _loadingService: LoadingService,
|
||||||
|
private readonly _toaster: Toaster,
|
||||||
|
private readonly _dossierStateService: DossierStatesService,
|
||||||
|
private readonly _dialogRef: MatDialogRef<ConfirmDeleteDossierStateDialogComponent>,
|
||||||
|
private readonly _activeDossiersService: ActiveDossiersService,
|
||||||
|
private readonly _archivedDossiersService: ArchivedDossiersService,
|
||||||
@Inject(MAT_DIALOG_DATA) readonly data: DialogData,
|
@Inject(MAT_DIALOG_DATA) readonly data: DialogData,
|
||||||
) {
|
) {
|
||||||
this.form = this.#getForm();
|
this.form = this.#getForm();
|
||||||
@ -42,8 +53,15 @@ export class ConfirmDeleteDossierStateDialogComponent {
|
|||||||
return this.replaceDossierStatusId ? _('confirm-delete-dossier-state.delete-replace') : _('confirm-delete-dossier-state.delete');
|
return this.replaceDossierStatusId ? _('confirm-delete-dossier-state.delete-replace') : _('confirm-delete-dossier-state.delete');
|
||||||
}
|
}
|
||||||
|
|
||||||
get afterCloseValue(): string | true {
|
async save(): Promise<void> {
|
||||||
return this.replaceDossierStatusId ?? true;
|
this._loadingService.start();
|
||||||
|
await firstValueFrom(this._dossierStateService.deleteState(this.data.toBeDeletedState, this.replaceDossierStatusId));
|
||||||
|
await firstValueFrom(
|
||||||
|
forkJoin([this._activeDossiersService.loadAll().pipe(take(1)), this._archivedDossiersService.loadAll().pipe(take(1))]),
|
||||||
|
);
|
||||||
|
this._toaster.success(_('confirm-delete-dossier-state.success'));
|
||||||
|
this._dialogRef.close();
|
||||||
|
this._loadingService.stop();
|
||||||
}
|
}
|
||||||
|
|
||||||
#getForm(): FormGroup {
|
#getForm(): FormGroup {
|
||||||
|
|||||||
@ -1,101 +1,98 @@
|
|||||||
<ng-container *ngIf="dossierStateService.all">
|
<section>
|
||||||
<section>
|
<div class="page-header">
|
||||||
<div class="page-header">
|
<redaction-dossier-template-breadcrumbs class="flex-1"></redaction-dossier-template-breadcrumbs>
|
||||||
<redaction-dossier-template-breadcrumbs class="flex-1"></redaction-dossier-template-breadcrumbs>
|
|
||||||
|
|
||||||
<div class="actions flex-1">
|
<div class="actions flex-1">
|
||||||
<redaction-dossier-template-actions></redaction-dossier-template-actions>
|
<redaction-dossier-template-actions></redaction-dossier-template-actions>
|
||||||
|
|
||||||
|
<iqser-circle-button
|
||||||
|
[routerLink]="['../..']"
|
||||||
|
[tooltip]="'common.close' | translate"
|
||||||
|
icon="iqser:close"
|
||||||
|
tooltipPosition="below"
|
||||||
|
></iqser-circle-button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="content-inner">
|
||||||
|
<div class="overlay-shadow"></div>
|
||||||
|
|
||||||
|
<redaction-admin-side-nav type="dossierTemplates"></redaction-admin-side-nav>
|
||||||
|
|
||||||
|
<div class="content-container">
|
||||||
|
<iqser-table
|
||||||
|
[headerTemplate]="headerTemplate"
|
||||||
|
[itemSize]="80"
|
||||||
|
[noDataText]="'dossier-states-listing.no-data.title' | translate"
|
||||||
|
[noMatchText]="'dossier-states-listing.no-match.title' | translate"
|
||||||
|
[tableColumnConfigs]="tableColumnConfigs"
|
||||||
|
emptyColumnWidth="1fr"
|
||||||
|
noDataIcon="red:attribute"
|
||||||
|
></iqser-table>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="right-container">
|
||||||
|
<redaction-simple-doughnut-chart
|
||||||
|
*ngIf="chartData$ | async as chartData"
|
||||||
|
[config]="chartData"
|
||||||
|
[radius]="80"
|
||||||
|
[strokeWidth]="15"
|
||||||
|
[subtitle]="'dossier-states-listing.chart.dossier-states' | translate: { count: chartData.length }"
|
||||||
|
[totalType]="'simpleLabel'"
|
||||||
|
></redaction-simple-doughnut-chart>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<ng-template #headerTemplate>
|
||||||
|
<div class="table-header-actions">
|
||||||
|
<iqser-input-with-action
|
||||||
|
[(value)]="searchService.searchValue"
|
||||||
|
[placeholder]="'dossier-states-listing.search' | translate"
|
||||||
|
></iqser-input-with-action>
|
||||||
|
|
||||||
|
<iqser-icon-button
|
||||||
|
(action)="openAddEditStateDialog($event)"
|
||||||
|
*ngIf="permissionsService.canPerformDossierStatesActions"
|
||||||
|
[label]="'dossier-states-listing.add-new' | translate"
|
||||||
|
[type]="iconButtonTypes.primary"
|
||||||
|
icon="iqser:plus"
|
||||||
|
></iqser-icon-button>
|
||||||
|
</div>
|
||||||
|
</ng-template>
|
||||||
|
|
||||||
|
<ng-template #tableItemTemplate let-entity="entity">
|
||||||
|
<div *ngIf="cast(entity) as state">
|
||||||
|
<div class="cell">
|
||||||
|
<div class="flex-align-items-center">
|
||||||
|
<div [style.background-color]="state.color" class="dossier-state-square"></div>
|
||||||
|
<div class="state-name">{{ state.name }}</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="cell small-label">
|
||||||
|
<span>{{ state.rank }}</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="cell small-label">
|
||||||
|
<span>{{ state.dossierCount }}</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="cell">
|
||||||
|
<div *ngIf="permissionsService.canPerformDossierStatesActions" class="action-buttons">
|
||||||
<iqser-circle-button
|
<iqser-circle-button
|
||||||
[routerLink]="['../..']"
|
(action)="openAddEditStateDialog($event, state)"
|
||||||
[tooltip]="'common.close' | translate"
|
[tooltip]="'dossier-states-listing.action.edit' | translate"
|
||||||
icon="iqser:close"
|
[type]="circleButtonTypes.dark"
|
||||||
tooltipPosition="below"
|
icon="iqser:edit"
|
||||||
|
></iqser-circle-button>
|
||||||
|
<iqser-circle-button
|
||||||
|
(action)="openConfirmDeleteStateDialog($event, state)"
|
||||||
|
[tooltip]="'dossier-states-listing.action.delete' | translate"
|
||||||
|
[type]="circleButtonTypes.dark"
|
||||||
|
icon="iqser:trash"
|
||||||
></iqser-circle-button>
|
></iqser-circle-button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<div class="content-inner">
|
</ng-template>
|
||||||
<div class="overlay-shadow"></div>
|
|
||||||
|
|
||||||
<redaction-admin-side-nav type="dossierTemplates"></redaction-admin-side-nav>
|
|
||||||
|
|
||||||
<div class="content-container">
|
|
||||||
<iqser-table
|
|
||||||
[headerTemplate]="headerTemplate"
|
|
||||||
[itemSize]="80"
|
|
||||||
[noDataText]="'dossier-states-listing.no-data.title' | translate"
|
|
||||||
[noMatchText]="'dossier-states-listing.no-match.title' | translate"
|
|
||||||
[selectionEnabled]="true"
|
|
||||||
[tableColumnConfigs]="tableColumnConfigs"
|
|
||||||
emptyColumnWidth="1fr"
|
|
||||||
noDataIcon="red:attribute"
|
|
||||||
></iqser-table>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="right-container">
|
|
||||||
<redaction-simple-doughnut-chart
|
|
||||||
*ngIf="chartData"
|
|
||||||
[config]="chartData"
|
|
||||||
[radius]="80"
|
|
||||||
[strokeWidth]="15"
|
|
||||||
[subtitle]="'dossier-states-listing.chart.dossier-states' | translate: { count: chartData.length }"
|
|
||||||
[totalType]="'simpleLabel'"
|
|
||||||
></redaction-simple-doughnut-chart>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</section>
|
|
||||||
|
|
||||||
<ng-template #headerTemplate>
|
|
||||||
<div class="table-header-actions">
|
|
||||||
<iqser-input-with-action
|
|
||||||
[(value)]="searchService.searchValue"
|
|
||||||
[placeholder]="'dossier-states-listing.search' | translate"
|
|
||||||
></iqser-input-with-action>
|
|
||||||
|
|
||||||
<iqser-icon-button
|
|
||||||
(action)="openAddEditStateDialog($event)"
|
|
||||||
*ngIf="currentUser.isAdmin"
|
|
||||||
[label]="'dossier-states-listing.add-new' | translate"
|
|
||||||
[type]="iconButtonTypes.primary"
|
|
||||||
icon="iqser:plus"
|
|
||||||
></iqser-icon-button>
|
|
||||||
</div>
|
|
||||||
</ng-template>
|
|
||||||
|
|
||||||
<ng-template #tableItemTemplate let-entity="entity">
|
|
||||||
<div *ngIf="cast(entity) as state">
|
|
||||||
<div class="cell">
|
|
||||||
<div class="flex-align-items-center">
|
|
||||||
<div [style.background-color]="state.color" class="dossier-state-square"></div>
|
|
||||||
<div class="state-name">{{ state.name }}</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="cell small-label">
|
|
||||||
<span>{{ state.rank }}</span>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="cell small-label">
|
|
||||||
<span>{{ state.dossierCount }}</span>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="cell">
|
|
||||||
<div *ngIf="currentUser.isAdmin" class="action-buttons">
|
|
||||||
<iqser-circle-button
|
|
||||||
(action)="openAddEditStateDialog($event, state)"
|
|
||||||
[tooltip]="'dossier-states-listing.action.edit' | translate"
|
|
||||||
[type]="circleButtonTypes.dark"
|
|
||||||
icon="iqser:edit"
|
|
||||||
></iqser-circle-button>
|
|
||||||
<iqser-circle-button
|
|
||||||
(action)="openConfirmDeleteStateDialog($event, state)"
|
|
||||||
[tooltip]="'dossier-states-listing.action.delete' | translate"
|
|
||||||
[type]="circleButtonTypes.dark"
|
|
||||||
icon="iqser:trash"
|
|
||||||
></iqser-circle-button>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</ng-template>
|
|
||||||
</ng-container>
|
|
||||||
|
|||||||
@ -3,6 +3,7 @@
|
|||||||
.dossier-state-square {
|
.dossier-state-square {
|
||||||
height: 16px;
|
height: 16px;
|
||||||
width: 16px;
|
width: 16px;
|
||||||
|
min-width: 16px;
|
||||||
margin-right: 16px;
|
margin-right: 16px;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -4,22 +4,19 @@ import {
|
|||||||
DefaultListingServices,
|
DefaultListingServices,
|
||||||
IconButtonTypes,
|
IconButtonTypes,
|
||||||
ListingComponent,
|
ListingComponent,
|
||||||
LoadingService,
|
|
||||||
SortingOrders,
|
SortingOrders,
|
||||||
TableColumnConfig,
|
TableColumnConfig,
|
||||||
Toaster,
|
|
||||||
} from '@iqser/common-ui';
|
} from '@iqser/common-ui';
|
||||||
import { DossierState, IDossierState } from '@red/domain';
|
import { DossierState, IDossierState } from '@red/domain';
|
||||||
import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
|
import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
|
||||||
import { ActiveDossiersService } from '@services/dossiers/active-dossiers.service';
|
import { firstValueFrom, map, Observable } from 'rxjs';
|
||||||
import { DossierStateService } from '@services/entity-services/dossier-state.service';
|
|
||||||
import { firstValueFrom } from 'rxjs';
|
|
||||||
import { AdminDialogService } from '../../services/admin-dialog.service';
|
import { AdminDialogService } from '../../services/admin-dialog.service';
|
||||||
import { UserService } from '@services/user.service';
|
|
||||||
import { HttpStatusCode } from '@angular/common/http';
|
|
||||||
import { DoughnutChartConfig } from '@shared/components/simple-doughnut-chart/simple-doughnut-chart.component';
|
import { DoughnutChartConfig } from '@shared/components/simple-doughnut-chart/simple-doughnut-chart.component';
|
||||||
import { ActivatedRoute } from '@angular/router';
|
import { ActivatedRoute } from '@angular/router';
|
||||||
import { DossierTemplatesService } from '@services/entity-services/dossier-templates.service';
|
import { DossierStatesMapService } from '@services/entity-services/dossier-states-map.service';
|
||||||
|
import { tap } from 'rxjs/operators';
|
||||||
|
import { PermissionsService } from '@services/permissions.service';
|
||||||
|
import { DossierStatesService } from '@services/entity-services/dossier-states.service';
|
||||||
|
|
||||||
@Component({
|
@Component({
|
||||||
templateUrl: './dossier-states-listing-screen.component.html',
|
templateUrl: './dossier-states-listing-screen.component.html',
|
||||||
@ -33,29 +30,29 @@ import { DossierTemplatesService } from '@services/entity-services/dossier-templ
|
|||||||
export class DossierStatesListingScreenComponent extends ListingComponent<DossierState> implements OnInit, OnDestroy {
|
export class DossierStatesListingScreenComponent extends ListingComponent<DossierState> implements OnInit, OnDestroy {
|
||||||
readonly iconButtonTypes = IconButtonTypes;
|
readonly iconButtonTypes = IconButtonTypes;
|
||||||
readonly circleButtonTypes = CircleButtonTypes;
|
readonly circleButtonTypes = CircleButtonTypes;
|
||||||
readonly currentUser = this._userService.currentUser;
|
|
||||||
readonly tableHeaderLabel = _('dossier-states-listing.table-header.title');
|
readonly tableHeaderLabel = _('dossier-states-listing.table-header.title');
|
||||||
readonly tableColumnConfigs: TableColumnConfig<DossierState>[] = [
|
readonly tableColumnConfigs: TableColumnConfig<DossierState>[] = [
|
||||||
{ label: _('dossier-states-listing.table-col-names.name'), sortByKey: 'name' },
|
{ label: _('dossier-states-listing.table-col-names.name'), sortByKey: 'name' },
|
||||||
{ label: _('dossier-states-listing.table-col-names.rank'), sortByKey: 'rank' },
|
{ label: _('dossier-states-listing.table-col-names.rank'), sortByKey: 'rank' },
|
||||||
{ label: _('dossier-states-listing.table-col-names.dossiers-count') },
|
{ label: _('dossier-states-listing.table-col-names.dossiers-count') },
|
||||||
];
|
];
|
||||||
chartData: DoughnutChartConfig[];
|
chartData$: Observable<DoughnutChartConfig[]>;
|
||||||
readonly #dossierTemplateId: string;
|
readonly #dossierTemplateId: string;
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
protected readonly _injector: Injector,
|
protected readonly _injector: Injector,
|
||||||
private readonly _loadingService: LoadingService,
|
|
||||||
private readonly _activeDossiersService: ActiveDossiersService,
|
|
||||||
readonly dossierStateService: DossierStateService,
|
|
||||||
private readonly _dialogService: AdminDialogService,
|
private readonly _dialogService: AdminDialogService,
|
||||||
private readonly _userService: UserService,
|
|
||||||
private readonly _toaster: Toaster,
|
|
||||||
private readonly _route: ActivatedRoute,
|
private readonly _route: ActivatedRoute,
|
||||||
private readonly _dossierTemplatesService: DossierTemplatesService,
|
private readonly _dossierStatesMapService: DossierStatesMapService,
|
||||||
|
private readonly _dossierStatesService: DossierStatesService,
|
||||||
|
readonly permissionsService: PermissionsService,
|
||||||
) {
|
) {
|
||||||
super(_injector);
|
super(_injector);
|
||||||
this.#dossierTemplateId = _route.snapshot.paramMap.get('dossierTemplateId');
|
this.#dossierTemplateId = _route.snapshot.paramMap.get('dossierTemplateId');
|
||||||
|
this.chartData$ = this._dossierStatesMapService.get$(this.#dossierTemplateId).pipe(
|
||||||
|
tap(states => this.entitiesService.setEntities(states)),
|
||||||
|
map(states => this.#chartData(states)),
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
async ngOnInit(): Promise<void> {
|
async ngOnInit(): Promise<void> {
|
||||||
@ -63,7 +60,7 @@ export class DossierStatesListingScreenComponent extends ListingComponent<Dossie
|
|||||||
column: 'rank',
|
column: 'rank',
|
||||||
order: SortingOrders.asc,
|
order: SortingOrders.asc,
|
||||||
});
|
});
|
||||||
await this.#loadData();
|
await firstValueFrom(this._dossierStatesService.loadAllForTemplate(this.#dossierTemplateId));
|
||||||
}
|
}
|
||||||
|
|
||||||
openAddEditStateDialog($event: MouseEvent, dossierState?: IDossierState) {
|
openAddEditStateDialog($event: MouseEvent, dossierState?: IDossierState) {
|
||||||
@ -71,66 +68,24 @@ export class DossierStatesListingScreenComponent extends ListingComponent<Dossie
|
|||||||
dossierState,
|
dossierState,
|
||||||
dossierTemplateId: this.#dossierTemplateId,
|
dossierTemplateId: this.#dossierTemplateId,
|
||||||
};
|
};
|
||||||
this._dialogService.openDialog('addEditDossierState', $event, data, async (newValue: IDossierState) => {
|
this._dialogService.openDialog('addEditDossierState', $event, data);
|
||||||
await this.#createNewDossierStateAndRefreshView(newValue);
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
openConfirmDeleteStateDialog($event: MouseEvent, dossierState: IDossierState) {
|
openConfirmDeleteStateDialog($event: MouseEvent, dossierState: DossierState) {
|
||||||
const templateId = this.#dossierTemplateId;
|
|
||||||
const data = {
|
const data = {
|
||||||
toBeDeletedState: dossierState,
|
toBeDeletedState: dossierState,
|
||||||
otherStates: this.entitiesService.all.filter(state => state.dossierStatusId !== dossierState.dossierStatusId),
|
otherStates: this.entitiesService.all.filter(state => state.id !== dossierState.id),
|
||||||
dossierCount: dossierState.dossierCount,
|
dossierCount: dossierState.dossierCount,
|
||||||
};
|
};
|
||||||
this._dialogService.openDialog('deleteDossierState', $event, data, async (value: string | true) => {
|
this._dialogService.openDialog('deleteDossierState', $event, data);
|
||||||
if (value) {
|
|
||||||
if (typeof value === 'string') {
|
|
||||||
await firstValueFrom(this.dossierStateService.deleteAndReplace(dossierState.dossierStatusId, value));
|
|
||||||
} else {
|
|
||||||
await firstValueFrom(this.dossierStateService.delete(dossierState.dossierStatusId));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
await firstValueFrom(this._dossierTemplatesService.refreshDossierTemplate(templateId));
|
|
||||||
await this.#loadData();
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async #createNewDossierStateAndRefreshView(newValue: IDossierState): Promise<void> {
|
#chartData(states: DossierState[]): DoughnutChartConfig[] {
|
||||||
this._loadingService.start();
|
return states.map(state => ({
|
||||||
await firstValueFrom(this.dossierStateService.updateDossierState(newValue)).catch(error => {
|
value: state.dossierCount,
|
||||||
if (error.status === HttpStatusCode.Conflict) {
|
label: state.name,
|
||||||
this._toaster.error(_('dossier-states-listing.error.conflict'));
|
key: state.name,
|
||||||
} else {
|
color: state.color,
|
||||||
this._toaster.error(_('dossier-states-listing.error.generic'));
|
}));
|
||||||
}
|
|
||||||
});
|
|
||||||
await firstValueFrom(this._dossierTemplatesService.refreshDossierTemplate(this.#dossierTemplateId));
|
|
||||||
await this.#loadData();
|
|
||||||
}
|
|
||||||
|
|
||||||
async #loadData(): Promise<void> {
|
|
||||||
this._loadingService.start();
|
|
||||||
// TODO: Move this in service; dossiers states service should be a mapping service
|
|
||||||
await firstValueFrom(this._activeDossiersService.loadAll());
|
|
||||||
|
|
||||||
try {
|
|
||||||
const dossierStates = this.dossierStateService.all.filter(d => d.dossierTemplateId === this.#dossierTemplateId);
|
|
||||||
this.#setStatesCount(dossierStates);
|
|
||||||
this.chartData = dossierStates.map(state => ({
|
|
||||||
value: state.dossierCount,
|
|
||||||
label: state.name,
|
|
||||||
key: state.name,
|
|
||||||
color: state.color,
|
|
||||||
}));
|
|
||||||
|
|
||||||
this.entitiesService.setEntities(dossierStates || []);
|
|
||||||
} catch (e) {}
|
|
||||||
this._loadingService.stop();
|
|
||||||
}
|
|
||||||
|
|
||||||
#setStatesCount(dossierStates: DossierState[]): void {
|
|
||||||
dossierStates.forEach(state => (state.dossierCount = this._activeDossiersService.getCountWithState(state.dossierStatusId)));
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -9,5 +9,5 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="cell">
|
<div class="cell">
|
||||||
<redaction-dossier-status [dossier]="dossier"></redaction-dossier-status>
|
<redaction-dossier-state [dossier]="dossier"></redaction-dossier-state>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@ -10,7 +10,7 @@ export class ConfigService {
|
|||||||
{ label: _('archived-dossiers-listing.table-col-names.name'), sortByKey: 'searchKey', width: '2fr' },
|
{ label: _('archived-dossiers-listing.table-col-names.name'), sortByKey: 'searchKey', width: '2fr' },
|
||||||
{ label: _('archived-dossiers-listing.table-col-names.last-modified'), sortByKey: 'archivedTime' },
|
{ label: _('archived-dossiers-listing.table-col-names.last-modified'), sortByKey: 'archivedTime' },
|
||||||
{ label: _('archived-dossiers-listing.table-col-names.owner'), class: 'user-column' },
|
{ label: _('archived-dossiers-listing.table-col-names.owner'), class: 'user-column' },
|
||||||
{ label: _('archived-dossiers-listing.table-col-names.dossier-status'), class: 'flex-end', width: '2fr' },
|
{ label: _('archived-dossiers-listing.table-col-names.dossier-state'), class: 'flex-end', width: '2fr' },
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -42,7 +42,7 @@
|
|||||||
|
|
||||||
<div class="flex fields-container">
|
<div class="flex fields-container">
|
||||||
<div class="iqser-input-group w-300">
|
<div class="iqser-input-group w-300">
|
||||||
<label translate="edit-dossier-dialog.general-info.form.dossier-status.label"></label>
|
<label translate="edit-dossier-dialog.general-info.form.dossier-state.label"></label>
|
||||||
<mat-select [placeholder]="statusPlaceholder" formControlName="dossierStatusId">
|
<mat-select [placeholder]="statusPlaceholder" formControlName="dossierStatusId">
|
||||||
<mat-option *ngFor="let stateId of states" [value]="stateId">
|
<mat-option *ngFor="let stateId of states" [value]="stateId">
|
||||||
<div class="flex-align-items-center">
|
<div class="flex-align-items-center">
|
||||||
|
|||||||
@ -1,7 +1,7 @@
|
|||||||
import { ChangeDetectionStrategy, Component, Input, OnInit } from '@angular/core';
|
import { ChangeDetectionStrategy, Component, Input, OnInit } from '@angular/core';
|
||||||
import { FormBuilder, FormGroup, Validators } from '@angular/forms';
|
import { FormBuilder, FormGroup, Validators } from '@angular/forms';
|
||||||
import * as moment from 'moment';
|
import * as moment from 'moment';
|
||||||
import { Dossier, DossierState, IDossierRequest, IDossierTemplate } from '@red/domain';
|
import { Dossier, IDossierRequest, IDossierTemplate } from '@red/domain';
|
||||||
import { EditDossierSaveResult, EditDossierSectionInterface } from '../edit-dossier-section.interface';
|
import { EditDossierSaveResult, EditDossierSectionInterface } from '../edit-dossier-section.interface';
|
||||||
import { DossiersDialogService } from '../../../services/dossiers-dialog.service';
|
import { DossiersDialogService } from '../../../services/dossiers-dialog.service';
|
||||||
import { PermissionsService } from '@services/permissions.service';
|
import { PermissionsService } from '@services/permissions.service';
|
||||||
@ -13,12 +13,12 @@ import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
|
|||||||
import { DossierTemplatesService } from '@services/entity-services/dossier-templates.service';
|
import { DossierTemplatesService } from '@services/entity-services/dossier-templates.service';
|
||||||
import { DossierStatsService } from '@services/dossiers/dossier-stats.service';
|
import { DossierStatsService } from '@services/dossiers/dossier-stats.service';
|
||||||
import { firstValueFrom } from 'rxjs';
|
import { firstValueFrom } from 'rxjs';
|
||||||
import { DossierStateService } from '@services/entity-services/dossier-state.service';
|
|
||||||
import { DOSSIER_TEMPLATE_ID } from '@utils/constants';
|
import { DOSSIER_TEMPLATE_ID } from '@utils/constants';
|
||||||
import { TranslateService } from '@ngx-translate/core';
|
import { TranslateService } from '@ngx-translate/core';
|
||||||
import { DossiersService } from '@services/dossiers/dossiers.service';
|
import { DossiersService } from '@services/dossiers/dossiers.service';
|
||||||
import { TrashDossiersService } from '@services/entity-services/trash-dossiers.service';
|
import { TrashDossiersService } from '@services/entity-services/trash-dossiers.service';
|
||||||
import { ArchivedDossiersService } from '@services/dossiers/archived-dossiers.service';
|
import { ArchivedDossiersService } from '@services/dossiers/archived-dossiers.service';
|
||||||
|
import { DossierStatesMapService } from '@services/entity-services/dossier-states-map.service';
|
||||||
|
|
||||||
@Component({
|
@Component({
|
||||||
selector: 'redaction-edit-dossier-general-info',
|
selector: 'redaction-edit-dossier-general-info',
|
||||||
@ -36,11 +36,10 @@ export class EditDossierGeneralInfoComponent implements OnInit, EditDossierSecti
|
|||||||
hasDueDate: boolean;
|
hasDueDate: boolean;
|
||||||
dossierTemplates: IDossierTemplate[];
|
dossierTemplates: IDossierTemplate[];
|
||||||
states: string[];
|
states: string[];
|
||||||
currentStatus: DossierState;
|
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
readonly permissionsService: PermissionsService,
|
readonly permissionsService: PermissionsService,
|
||||||
private readonly _dossierStateService: DossierStateService,
|
private readonly _dossierStatesMapService: DossierStatesMapService,
|
||||||
private readonly _dossierTemplatesService: DossierTemplatesService,
|
private readonly _dossierTemplatesService: DossierTemplatesService,
|
||||||
private readonly _dossiersService: DossiersService,
|
private readonly _dossiersService: DossiersService,
|
||||||
private readonly _trashDossiersService: TrashDossiersService,
|
private readonly _trashDossiersService: TrashDossiersService,
|
||||||
@ -80,20 +79,22 @@ export class EditDossierGeneralInfoComponent implements OnInit, EditDossierSecti
|
|||||||
return this.hasDueDate && this.form.get('dueDate').value === null;
|
return this.hasDueDate && this.form.get('dueDate').value === null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
get #statusPlaceholder(): string {
|
||||||
|
return this._translateService.instant(
|
||||||
|
this.states.length === 1
|
||||||
|
? 'edit-dossier-dialog.general-info.form.dossier-state.no-state-placeholder'
|
||||||
|
: 'edit-dossier-dialog.general-info.form.dossier-state.placeholder',
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
ngOnInit() {
|
ngOnInit() {
|
||||||
this.states = [
|
this.states = [null, ...this._dossierStatesMapService.get(this.dossier.dossierTemplateId).map(s => s.id)];
|
||||||
null,
|
|
||||||
...this._dossierStateService.all.filter(s => s.dossierTemplateId === this.dossier.dossierTemplateId).map(s => s.id),
|
|
||||||
];
|
|
||||||
this.statusPlaceholder = this.#statusPlaceholder;
|
this.statusPlaceholder = this.#statusPlaceholder;
|
||||||
this.#filterInvalidDossierTemplates();
|
this.#filterInvalidDossierTemplates();
|
||||||
this.form = this.#getForm();
|
this.form = this.#getForm();
|
||||||
if (!this.permissionsService.canEditDossier(this.dossier)) {
|
if (!this.permissionsService.canEditDossier(this.dossier)) {
|
||||||
this.form.disable();
|
this.form.disable();
|
||||||
}
|
}
|
||||||
if (this.dossier.dossierStatusId) {
|
|
||||||
this.currentStatus = this._dossierStateService.find(this.dossier.dossierStatusId);
|
|
||||||
}
|
|
||||||
this.hasDueDate = !!this.dossier.dueDate;
|
this.hasDueDate = !!this.dossier.dueDate;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -168,6 +169,17 @@ export class EditDossierGeneralInfoComponent implements OnInit, EditDossierSecti
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
getStateName(stateId: string): string {
|
||||||
|
return (
|
||||||
|
this._dossierStatesMapService.get(this.dossier.dossierTemplateId, stateId)?.name ||
|
||||||
|
this._translateService.instant('edit-dossier-dialog.general-info.form.dossier-state.placeholder')
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
getStateColor(stateId: string): string {
|
||||||
|
return this._dossierStatesMapService.get(this.dossier.dossierTemplateId, stateId).color;
|
||||||
|
}
|
||||||
|
|
||||||
#getForm(): FormGroup {
|
#getForm(): FormGroup {
|
||||||
const formFieldWithArchivedCheck = value => ({ value, disabled: !this.dossier.isActive });
|
const formFieldWithArchivedCheck = value => ({ value, disabled: !this.dossier.isActive });
|
||||||
return this._formBuilder.group({
|
return this._formBuilder.group({
|
||||||
@ -185,25 +197,6 @@ export class EditDossierGeneralInfoComponent implements OnInit, EditDossierSecti
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
get #statusPlaceholder(): string {
|
|
||||||
return this._translateService.instant(
|
|
||||||
this.states.length === 1
|
|
||||||
? 'edit-dossier-dialog.general-info.form.dossier-status.no-status-placeholder'
|
|
||||||
: 'edit-dossier-dialog.general-info.form.dossier-status.placeholder',
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
getStateName(stateId: string): string {
|
|
||||||
return (
|
|
||||||
this._dossierStateService.find(stateId)?.name ||
|
|
||||||
this._translateService.instant('edit-dossier-dialog.general-info.form.dossier-status.placeholder')
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
getStateColor(stateId: string): string {
|
|
||||||
return this._dossierStateService.find(stateId).color;
|
|
||||||
}
|
|
||||||
|
|
||||||
#filterInvalidDossierTemplates() {
|
#filterInvalidDossierTemplates() {
|
||||||
this.dossierTemplates = this._dossierTemplatesService.all.filter(r => {
|
this.dossierTemplates = this._dossierTemplatesService.all.filter(r => {
|
||||||
if (this.dossier?.dossierTemplateId === r.dossierTemplateId) {
|
if (this.dossier?.dossierTemplateId === r.dossierTemplateId) {
|
||||||
|
|||||||
@ -8,8 +8,8 @@ import { workflowFileStatusTranslations } from '../../../../../../translations/f
|
|||||||
import { TranslateChartService } from '@services/translate-chart.service';
|
import { TranslateChartService } from '@services/translate-chart.service';
|
||||||
import { filter, map, switchMap } from 'rxjs/operators';
|
import { filter, map, switchMap } from 'rxjs/operators';
|
||||||
import { DossierStatsService } from '@services/dossiers/dossier-stats.service';
|
import { DossierStatsService } from '@services/dossiers/dossier-stats.service';
|
||||||
import { DossierStateService } from '@services/entity-services/dossier-state.service';
|
|
||||||
import { TranslateService } from '@ngx-translate/core';
|
import { TranslateService } from '@ngx-translate/core';
|
||||||
|
import { DossierStatesMapService } from '@services/entity-services/dossier-states-map.service';
|
||||||
|
|
||||||
@Component({
|
@Component({
|
||||||
selector: 'redaction-dossiers-listing-details',
|
selector: 'redaction-dossiers-listing-details',
|
||||||
@ -26,7 +26,7 @@ export class DossiersListingDetailsComponent {
|
|||||||
readonly activeDossiersService: ActiveDossiersService,
|
readonly activeDossiersService: ActiveDossiersService,
|
||||||
private readonly _dossierStatsMap: DossierStatsService,
|
private readonly _dossierStatsMap: DossierStatsService,
|
||||||
private readonly _translateChartService: TranslateChartService,
|
private readonly _translateChartService: TranslateChartService,
|
||||||
private readonly _dossierStateService: DossierStateService,
|
private readonly _dossierStatesMapService: DossierStatesMapService,
|
||||||
private readonly _translateService: TranslateService,
|
private readonly _translateService: TranslateService,
|
||||||
) {
|
) {
|
||||||
this.documentsChartData$ = this.activeDossiersService.all$.pipe(
|
this.documentsChartData$ = this.activeDossiersService.all$.pipe(
|
||||||
@ -40,24 +40,12 @@ export class DossiersListingDetailsComponent {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private _toDossierChartData(): DoughnutChartConfig[] {
|
private _toDossierChartData(): DoughnutChartConfig[] {
|
||||||
this._dossierStateService.all.forEach(
|
const configArray: DoughnutChartConfig[] = this._dossierStatesMapService.stats;
|
||||||
state => (state.dossierCount = this.activeDossiersService.getCountWithState(state.dossierStatusId)),
|
const undefinedStateLength =
|
||||||
);
|
this.activeDossiersService.all.length - configArray.map(v => v.value).reduce((acc, val) => acc + val, 0);
|
||||||
const configArray: DoughnutChartConfig[] = [
|
|
||||||
...this._dossierStateService.all
|
|
||||||
.reduce((acc, { color, dossierCount, name }) => {
|
|
||||||
const key = name + '-' + color;
|
|
||||||
const item = acc.get(key) ?? Object.assign({}, { value: 0, label: name, color: color });
|
|
||||||
|
|
||||||
return acc.set(key, { ...item, value: item.value + dossierCount });
|
|
||||||
}, new Map<string, DoughnutChartConfig>())
|
|
||||||
.values(),
|
|
||||||
];
|
|
||||||
|
|
||||||
const notAssignedLength = this.activeDossiersService.all.length - configArray.map(v => v.value).reduce((acc, val) => acc + val, 0);
|
|
||||||
configArray.push({
|
configArray.push({
|
||||||
value: notAssignedLength,
|
value: undefinedStateLength,
|
||||||
label: this._translateService.instant('edit-dossier-dialog.general-info.form.dossier-status.placeholder'),
|
label: this._translateService.instant('edit-dossier-dialog.general-info.form.dossier-state.placeholder'),
|
||||||
color: '#E2E4E9',
|
color: '#E2E4E9',
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@ -21,7 +21,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="cell">
|
<div class="cell">
|
||||||
<redaction-dossier-status [dossier]="dossier"></redaction-dossier-status>
|
<redaction-dossier-state [dossier]="dossier"></redaction-dossier-state>
|
||||||
|
|
||||||
<redaction-dossiers-listing-actions [dossier]="dossier" [stats]="stats"></redaction-dossiers-listing-actions>
|
<redaction-dossiers-listing-actions [dossier]="dossier" [stats]="stats"></redaction-dossiers-listing-actions>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
import { Injectable, TemplateRef } from '@angular/core';
|
import { Injectable, TemplateRef } from '@angular/core';
|
||||||
import { ButtonConfig, IFilterGroup, INestedFilter, keyChecker, NestedFilter, TableColumnConfig } from '@iqser/common-ui';
|
import { ButtonConfig, IFilterGroup, INestedFilter, keyChecker, NestedFilter, TableColumnConfig } from '@iqser/common-ui';
|
||||||
import { Dossier, StatusSorter, User } from '@red/domain';
|
import { Dossier, StatusSorter, User, WorkflowFileStatus } from '@red/domain';
|
||||||
import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
|
import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
|
||||||
import { TranslateService } from '@ngx-translate/core';
|
import { TranslateService } from '@ngx-translate/core';
|
||||||
import { UserPreferenceService } from '@services/user-preference.service';
|
import { UserPreferenceService } from '@services/user-preference.service';
|
||||||
@ -10,7 +10,7 @@ import { dossierMemberChecker, dossierStateChecker, dossierTemplateChecker, Reda
|
|||||||
import { workloadTranslations } from '../../translations/workload-translations';
|
import { workloadTranslations } from '../../translations/workload-translations';
|
||||||
import { DossierTemplatesService } from '@services/entity-services/dossier-templates.service';
|
import { DossierTemplatesService } from '@services/entity-services/dossier-templates.service';
|
||||||
import { DossierStatsService } from '@services/dossiers/dossier-stats.service';
|
import { DossierStatsService } from '@services/dossiers/dossier-stats.service';
|
||||||
import { DossierStateService } from '@services/entity-services/dossier-state.service';
|
import { DossierStatesMapService } from '@services/entity-services/dossier-states-map.service';
|
||||||
|
|
||||||
@Injectable()
|
@Injectable()
|
||||||
export class ConfigService {
|
export class ConfigService {
|
||||||
@ -20,7 +20,7 @@ export class ConfigService {
|
|||||||
private readonly _userService: UserService,
|
private readonly _userService: UserService,
|
||||||
private readonly _dossierTemplatesService: DossierTemplatesService,
|
private readonly _dossierTemplatesService: DossierTemplatesService,
|
||||||
private readonly _dossierStatsService: DossierStatsService,
|
private readonly _dossierStatsService: DossierStatsService,
|
||||||
private readonly _dossierStateService: DossierStateService,
|
private readonly _dossierStatesMapService: DossierStatesMapService,
|
||||||
) {}
|
) {}
|
||||||
|
|
||||||
get tableConfig(): TableColumnConfig<Dossier>[] {
|
get tableConfig(): TableColumnConfig<Dossier>[] {
|
||||||
@ -30,7 +30,7 @@ export class ConfigService {
|
|||||||
{ label: _('dossier-listing.table-col-names.needs-work') },
|
{ label: _('dossier-listing.table-col-names.needs-work') },
|
||||||
{ label: _('dossier-listing.table-col-names.owner'), class: 'user-column' },
|
{ label: _('dossier-listing.table-col-names.owner'), class: 'user-column' },
|
||||||
{ label: _('dossier-listing.table-col-names.documents-status'), class: 'flex-end', width: 'auto' },
|
{ label: _('dossier-listing.table-col-names.documents-status'), class: 'flex-end', width: 'auto' },
|
||||||
{ label: _('dossier-listing.table-col-names.dossier-status'), class: 'flex-end' },
|
{ label: _('dossier-listing.table-col-names.dossier-state'), class: 'flex-end' },
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -66,6 +66,8 @@ export class ConfigService {
|
|||||||
const allDistinctDossierTemplates = new Set<string>();
|
const allDistinctDossierTemplates = new Set<string>();
|
||||||
const allDistinctDossierStates = new Set<string>();
|
const allDistinctDossierStates = new Set<string>();
|
||||||
|
|
||||||
|
const stateToTemplateMap = new Map<string, string>();
|
||||||
|
|
||||||
const filterGroups: IFilterGroup[] = [];
|
const filterGroups: IFilterGroup[] = [];
|
||||||
|
|
||||||
entities?.forEach(entry => {
|
entities?.forEach(entry => {
|
||||||
@ -73,6 +75,7 @@ export class ConfigService {
|
|||||||
allDistinctDossierTemplates.add(entry.dossierTemplateId);
|
allDistinctDossierTemplates.add(entry.dossierTemplateId);
|
||||||
if (entry.dossierStatusId) {
|
if (entry.dossierStatusId) {
|
||||||
allDistinctDossierStates.add(entry.dossierStatusId);
|
allDistinctDossierStates.add(entry.dossierStatusId);
|
||||||
|
stateToTemplateMap.set(entry.dossierStatusId, entry.dossierTemplateId);
|
||||||
}
|
}
|
||||||
const stats = this._dossierStatsService.get(entry.dossierId);
|
const stats = this._dossierStatsService.get(entry.dossierId);
|
||||||
|
|
||||||
@ -100,13 +103,13 @@ export class ConfigService {
|
|||||||
id =>
|
id =>
|
||||||
new NestedFilter({
|
new NestedFilter({
|
||||||
id: id,
|
id: id,
|
||||||
label: this._dossierStateService.find(id).name,
|
label: this._dossierStatesMapService.get(stateToTemplateMap.get(id), id).name,
|
||||||
}),
|
}),
|
||||||
);
|
);
|
||||||
|
|
||||||
filterGroups.push({
|
filterGroups.push({
|
||||||
slug: 'dossierStatesFilters',
|
slug: 'dossierStatesFilters',
|
||||||
label: this._translateService.instant('filters.dossier-status'),
|
label: this._translateService.instant('filters.dossier-state'),
|
||||||
icon: 'red:status',
|
icon: 'red:status',
|
||||||
hide: dossierStatesFilters.length <= 1,
|
hide: dossierStatesFilters.length <= 1,
|
||||||
filters: dossierStatesFilters,
|
filters: dossierStatesFilters,
|
||||||
@ -114,7 +117,7 @@ export class ConfigService {
|
|||||||
});
|
});
|
||||||
|
|
||||||
const statusFilters = [...allDistinctFileStatus].map(
|
const statusFilters = [...allDistinctFileStatus].map(
|
||||||
status =>
|
(status: WorkflowFileStatus) =>
|
||||||
new NestedFilter({
|
new NestedFilter({
|
||||||
id: status,
|
id: status,
|
||||||
label: this._translateService.instant(workflowFileStatusTranslations[status]),
|
label: this._translateService.instant(workflowFileStatusTranslations[status]),
|
||||||
|
|||||||
@ -0,0 +1,6 @@
|
|||||||
|
<div class="flex-align-items-center dossier-state-container">
|
||||||
|
<div class="dossier-state-text">
|
||||||
|
{{ (dossierState$ | async)?.name || ('edit-dossier-dialog.general-info.form.dossier-state.placeholder' | translate) }}
|
||||||
|
</div>
|
||||||
|
<redaction-small-chip [color]="(dossierState$ | async)?.color || '#E2E4E9'"></redaction-small-chip>
|
||||||
|
</div>
|
||||||
@ -1,6 +1,6 @@
|
|||||||
@use 'variables';
|
@use 'variables';
|
||||||
|
|
||||||
.dossier-status-container {
|
.dossier-state-container {
|
||||||
justify-content: flex-end;
|
justify-content: flex-end;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
}
|
}
|
||||||
@ -9,7 +9,7 @@ redaction-small-chip {
|
|||||||
margin-left: 8px;
|
margin-left: 8px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.dossier-status-text {
|
.dossier-state-text {
|
||||||
font-size: 13px;
|
font-size: 13px;
|
||||||
line-height: 16px;
|
line-height: 16px;
|
||||||
color: variables.$grey-1;
|
color: variables.$grey-1;
|
||||||
@ -0,0 +1,21 @@
|
|||||||
|
import { ChangeDetectionStrategy, Component, Input, OnChanges } from '@angular/core';
|
||||||
|
import { Dossier, DossierState } from '@red/domain';
|
||||||
|
import { DossierStatesMapService } from '@services/entity-services/dossier-states-map.service';
|
||||||
|
import { Observable } from 'rxjs';
|
||||||
|
|
||||||
|
@Component({
|
||||||
|
selector: 'redaction-dossier-state [dossier]',
|
||||||
|
templateUrl: './dossier-state.component.html',
|
||||||
|
styleUrls: ['./dossier-state.component.scss'],
|
||||||
|
changeDetection: ChangeDetectionStrategy.OnPush,
|
||||||
|
})
|
||||||
|
export class DossierStateComponent implements OnChanges {
|
||||||
|
@Input() dossier: Dossier;
|
||||||
|
dossierState$: Observable<DossierState>;
|
||||||
|
|
||||||
|
constructor(private readonly _dossierStatesMapService: DossierStatesMapService) {}
|
||||||
|
|
||||||
|
ngOnChanges(): void {
|
||||||
|
this.dossierState$ = this._dossierStatesMapService.watch$(this.dossier.dossierTemplateId, this.dossier.dossierStatusId);
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -1,6 +0,0 @@
|
|||||||
<div class="flex-align-items-center dossier-status-container">
|
|
||||||
<div class="dossier-status-text">
|
|
||||||
{{ currentState?.name || ('edit-dossier-dialog.general-info.form.dossier-status.placeholder' | translate) }}
|
|
||||||
</div>
|
|
||||||
<redaction-small-chip [color]="currentState?.color || '#E2E4E9'"></redaction-small-chip>
|
|
||||||
</div>
|
|
||||||
@ -1,28 +0,0 @@
|
|||||||
import { ChangeDetectionStrategy, Component, Input, OnChanges, OnInit } from '@angular/core';
|
|
||||||
import { Dossier, DossierState } from '@red/domain';
|
|
||||||
import { DossierStateService } from '@services/entity-services/dossier-state.service';
|
|
||||||
|
|
||||||
@Component({
|
|
||||||
selector: 'redaction-dossier-status [dossier]',
|
|
||||||
templateUrl: './dossier-status.component.html',
|
|
||||||
styleUrls: ['./dossier-status.component.scss'],
|
|
||||||
changeDetection: ChangeDetectionStrategy.OnPush,
|
|
||||||
})
|
|
||||||
export class DossierStatusComponent implements OnInit, OnChanges {
|
|
||||||
@Input() dossier: Dossier;
|
|
||||||
currentState: DossierState;
|
|
||||||
|
|
||||||
constructor(private readonly _dossierStateService: DossierStateService) {}
|
|
||||||
|
|
||||||
ngOnInit(): void {
|
|
||||||
this.#setState();
|
|
||||||
}
|
|
||||||
|
|
||||||
ngOnChanges(): void {
|
|
||||||
this.#setState();
|
|
||||||
}
|
|
||||||
|
|
||||||
#setState(): void {
|
|
||||||
this.currentState = this._dossierStateService.find(this.dossier.dossierStatusId);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@ -27,7 +27,7 @@ import { TeamMembersComponent } from './components/team-members/team-members.com
|
|||||||
import { EditorComponent } from './components/editor/editor.component';
|
import { EditorComponent } from './components/editor/editor.component';
|
||||||
import { ExpandableFileActionsComponent } from './components/expandable-file-actions/expandable-file-actions.component';
|
import { ExpandableFileActionsComponent } from './components/expandable-file-actions/expandable-file-actions.component';
|
||||||
import { ProcessingIndicatorComponent } from '@shared/components/processing-indicator/processing-indicator.component';
|
import { ProcessingIndicatorComponent } from '@shared/components/processing-indicator/processing-indicator.component';
|
||||||
import { DossierStatusComponent } from '@shared/components/dossier-status/dossier-status.component';
|
import { DossierStateComponent } from '@shared/components/dossier-state/dossier-state.component';
|
||||||
import { DossiersListingDossierNameComponent } from '@shared/components/dossiers-listing-dossier-name/dossiers-listing-dossier-name.component';
|
import { DossiersListingDossierNameComponent } from '@shared/components/dossiers-listing-dossier-name/dossiers-listing-dossier-name.component';
|
||||||
|
|
||||||
const buttons = [FileDownloadBtnComponent, UserButtonComponent];
|
const buttons = [FileDownloadBtnComponent, UserButtonComponent];
|
||||||
@ -45,7 +45,7 @@ const components = [
|
|||||||
TeamMembersComponent,
|
TeamMembersComponent,
|
||||||
ExpandableFileActionsComponent,
|
ExpandableFileActionsComponent,
|
||||||
ProcessingIndicatorComponent,
|
ProcessingIndicatorComponent,
|
||||||
DossierStatusComponent,
|
DossierStateComponent,
|
||||||
DossiersListingDossierNameComponent,
|
DossiersListingDossierNameComponent,
|
||||||
|
|
||||||
...buttons,
|
...buttons,
|
||||||
|
|||||||
@ -1,7 +1,7 @@
|
|||||||
import { Injectable, Injector } from '@angular/core';
|
import { Injectable, Injector } from '@angular/core';
|
||||||
import { switchMap, tap } from 'rxjs/operators';
|
import { switchMap, tap } from 'rxjs/operators';
|
||||||
import { timer } from 'rxjs';
|
import { timer } from 'rxjs';
|
||||||
import { CHANGED_CHECK_INTERVAL } from '../../utils/constants';
|
import { CHANGED_CHECK_INTERVAL } from '@utils/constants';
|
||||||
import { DossiersService } from './dossiers.service';
|
import { DossiersService } from './dossiers.service';
|
||||||
|
|
||||||
export interface IDossiersStats {
|
export interface IDossiersStats {
|
||||||
|
|||||||
@ -3,20 +3,20 @@ import { Dossier, DossierStats, IChangesDetails, IDossier, IDossierChanges, IDos
|
|||||||
import { combineLatest, EMPTY, forkJoin, Observable, of, Subject, throwError } from 'rxjs';
|
import { combineLatest, EMPTY, forkJoin, Observable, of, Subject, throwError } from 'rxjs';
|
||||||
import { catchError, filter, map, mapTo, pluck, switchMap, tap } from 'rxjs/operators';
|
import { catchError, filter, map, mapTo, pluck, switchMap, tap } from 'rxjs/operators';
|
||||||
import { Injector } from '@angular/core';
|
import { Injector } from '@angular/core';
|
||||||
import { DossierStateService } from '../entity-services/dossier-state.service';
|
import { DossierStatesService } from '../entity-services/dossier-states.service';
|
||||||
import { DossierStatsService } from './dossier-stats.service';
|
import { DossierStatsService } from './dossier-stats.service';
|
||||||
import { IDossiersStats } from './active-dossiers.service';
|
import { IDossiersStats } from './active-dossiers.service';
|
||||||
import { HttpErrorResponse, HttpStatusCode } from '@angular/common/http';
|
import { HttpErrorResponse, HttpStatusCode } from '@angular/common/http';
|
||||||
import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
|
import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
|
||||||
|
|
||||||
const DOSSIER_EXISTS_MSG = _('add-dossier-dialog.errors.dossier-already-exists');
|
const CONFLICT_MSG = _('add-dossier-dialog.errors.dossier-already-exists');
|
||||||
const GENERIC_MSG = _('add-dossier-dialog.errors.generic');
|
const GENERIC_MSG = _('add-dossier-dialog.errors.generic');
|
||||||
|
|
||||||
export abstract class DossiersService extends EntitiesService<Dossier, IDossier> {
|
export abstract class DossiersService extends EntitiesService<Dossier, IDossier> {
|
||||||
readonly dossierFileChanges$ = new Subject<string>();
|
readonly dossierFileChanges$ = new Subject<string>();
|
||||||
readonly generalStats$ = this.all$.pipe(switchMap(entities => this.#generalStats$(entities)));
|
readonly generalStats$ = this.all$.pipe(switchMap(entities => this.#generalStats$(entities)));
|
||||||
protected readonly _dossierStatsService = this._injector.get(DossierStatsService);
|
protected readonly _dossierStatsService = this._injector.get(DossierStatsService);
|
||||||
protected readonly _dossierStateService = this._injector.get(DossierStateService);
|
protected readonly _dossierStateService = this._injector.get(DossierStatesService);
|
||||||
protected readonly _toaster = this._injector.get(Toaster);
|
protected readonly _toaster = this._injector.get(Toaster);
|
||||||
|
|
||||||
protected constructor(protected readonly _injector: Injector, protected readonly _path: string, readonly routerPath: string) {
|
protected constructor(protected readonly _injector: Injector, protected readonly _path: string, readonly routerPath: string) {
|
||||||
@ -26,7 +26,7 @@ export abstract class DossiersService extends EntitiesService<Dossier, IDossier>
|
|||||||
@Validate()
|
@Validate()
|
||||||
createOrUpdate(@RequiredParam() dossier: IDossierRequest): Observable<Dossier> {
|
createOrUpdate(@RequiredParam() dossier: IDossierRequest): Observable<Dossier> {
|
||||||
const showToast = (error: HttpErrorResponse) => {
|
const showToast = (error: HttpErrorResponse) => {
|
||||||
this._toaster.error(error.status === HttpStatusCode.Conflict ? DOSSIER_EXISTS_MSG : GENERIC_MSG);
|
this._toaster.error(error.status === HttpStatusCode.Conflict ? CONFLICT_MSG : GENERIC_MSG);
|
||||||
return EMPTY;
|
return EMPTY;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@ -1,41 +0,0 @@
|
|||||||
import { Injectable, Injector } from '@angular/core';
|
|
||||||
import { EntitiesService, mapEach, RequiredParam, Validate } from '@iqser/common-ui';
|
|
||||||
import { DossierState, IDossierState } from '@red/domain';
|
|
||||||
import { forkJoin, Observable, switchMap } from 'rxjs';
|
|
||||||
import { DossierTemplatesService } from '@services/entity-services/dossier-templates.service';
|
|
||||||
import { defaultIfEmpty, map, tap } from 'rxjs/operators';
|
|
||||||
|
|
||||||
@Injectable({
|
|
||||||
providedIn: 'root',
|
|
||||||
})
|
|
||||||
export class DossierStateService extends EntitiesService<DossierState, IDossierState> {
|
|
||||||
constructor(protected readonly _injector: Injector, private readonly _dossierTemplatesService: DossierTemplatesService) {
|
|
||||||
super(_injector, DossierState, 'dossier-status');
|
|
||||||
}
|
|
||||||
|
|
||||||
@Validate()
|
|
||||||
updateDossierState(@RequiredParam() body: IDossierState) {
|
|
||||||
return this._post<unknown>(body, this._defaultModelPath);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Validate()
|
|
||||||
loadAllForTemplate(@RequiredParam() templateId: string) {
|
|
||||||
return this.loadAll(`${this._defaultModelPath}/dossier-template/${templateId}`);
|
|
||||||
}
|
|
||||||
|
|
||||||
loadAllForAllTemplates(): Observable<DossierState[]> {
|
|
||||||
return this._dossierTemplatesService.all$.pipe(
|
|
||||||
mapEach(template => template.dossierTemplateId),
|
|
||||||
mapEach(id => this.loadAllForTemplate(id)),
|
|
||||||
switchMap(all => forkJoin(all).pipe(defaultIfEmpty([] as DossierState[][]))),
|
|
||||||
map(value => value.flatMap(item => item)),
|
|
||||||
tap(value => this.setEntities(value)),
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Validate()
|
|
||||||
deleteAndReplace(@RequiredParam() dossierStatusId: string, @RequiredParam() replaceDossierStatusId: string) {
|
|
||||||
const url = `${this._defaultModelPath}/${dossierStatusId}?replaceDossierStatusId=${replaceDossierStatusId}`;
|
|
||||||
return this.delete({}, url);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@ -0,0 +1,26 @@
|
|||||||
|
import { Injectable } from '@angular/core';
|
||||||
|
import { DossierState, IDossierState } from '@red/domain';
|
||||||
|
import { EntitiesMapService } from '@iqser/common-ui';
|
||||||
|
import { DOSSIER_TEMPLATE_ID } from '@utils/constants';
|
||||||
|
import { DoughnutChartConfig } from '@shared/components/simple-doughnut-chart/simple-doughnut-chart.component';
|
||||||
|
import { flatMap } from 'lodash';
|
||||||
|
|
||||||
|
@Injectable({ providedIn: 'root' })
|
||||||
|
export class DossierStatesMapService extends EntitiesMapService<DossierState, IDossierState> {
|
||||||
|
constructor() {
|
||||||
|
super(DOSSIER_TEMPLATE_ID);
|
||||||
|
}
|
||||||
|
|
||||||
|
get stats(): DoughnutChartConfig[] {
|
||||||
|
const allStates = flatMap(Array.from(this._map.values()).map(obs => obs.value));
|
||||||
|
return Array.from(
|
||||||
|
allStates
|
||||||
|
.reduce((acc, { color, name, dossierCount }) => {
|
||||||
|
const key = name + '-' + color;
|
||||||
|
const item = acc.get(key) ?? Object.assign({}, { value: 0, label: name, color: color });
|
||||||
|
return acc.set(key, { ...item, value: item.value + dossierCount });
|
||||||
|
}, new Map<string, DoughnutChartConfig>())
|
||||||
|
.values(),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -0,0 +1,60 @@
|
|||||||
|
import { Injectable, Injector } from '@angular/core';
|
||||||
|
import { EntitiesService, mapEach, RequiredParam, Toaster, Validate } from '@iqser/common-ui';
|
||||||
|
import { DossierState, IDossierState } from '@red/domain';
|
||||||
|
import { EMPTY, forkJoin, Observable, switchMap } from 'rxjs';
|
||||||
|
import { DossierTemplatesService } from '@services/entity-services/dossier-templates.service';
|
||||||
|
import { catchError, defaultIfEmpty, tap } from 'rxjs/operators';
|
||||||
|
import { DossierStatesMapService } from '@services/entity-services/dossier-states-map.service';
|
||||||
|
import { HttpErrorResponse, HttpStatusCode } from '@angular/common/http';
|
||||||
|
import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
|
||||||
|
|
||||||
|
const CONFLICT_MSG = _('dossier-states-listing.error.conflict');
|
||||||
|
const GENERIC_MSG = _('dossier-states-listing.error.generic');
|
||||||
|
|
||||||
|
@Injectable({
|
||||||
|
providedIn: 'root',
|
||||||
|
})
|
||||||
|
export class DossierStatesService extends EntitiesService<DossierState, IDossierState> {
|
||||||
|
constructor(
|
||||||
|
protected readonly _injector: Injector,
|
||||||
|
private readonly _toaster: Toaster,
|
||||||
|
private readonly _dossierTemplatesService: DossierTemplatesService,
|
||||||
|
private readonly _dossierStatesMapService: DossierStatesMapService,
|
||||||
|
) {
|
||||||
|
super(_injector, DossierState, 'dossier-status');
|
||||||
|
}
|
||||||
|
|
||||||
|
@Validate()
|
||||||
|
createOrUpdate(@RequiredParam() state: IDossierState): Observable<DossierState[]> {
|
||||||
|
const showToast = (error: HttpErrorResponse) => {
|
||||||
|
this._toaster.error(error.status === HttpStatusCode.Conflict ? CONFLICT_MSG : GENERIC_MSG);
|
||||||
|
return EMPTY;
|
||||||
|
};
|
||||||
|
return this._post<unknown>(state, this._defaultModelPath).pipe(
|
||||||
|
catchError(showToast),
|
||||||
|
switchMap(() => this.loadAllForTemplate(state.dossierTemplateId)),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Validate()
|
||||||
|
loadAllForTemplate(@RequiredParam() templateId: string) {
|
||||||
|
return this.loadAll(`${this._defaultModelPath}/dossier-template/${templateId}`).pipe(
|
||||||
|
tap(states => this._dossierStatesMapService.set(templateId, states)),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
loadAllForAllTemplates(): Observable<DossierState[][]> {
|
||||||
|
return this._dossierTemplatesService.all$.pipe(
|
||||||
|
mapEach(template => template.dossierTemplateId),
|
||||||
|
mapEach(id => this.loadAllForTemplate(id)),
|
||||||
|
switchMap(all => forkJoin(all).pipe(defaultIfEmpty([] as DossierState[][]))),
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
deleteState(dossierState: IDossierState, replaceDossierStatusId?: string): Observable<unknown> {
|
||||||
|
const queryParams = replaceDossierStatusId ? [{ key: 'replaceDossierStatusId', value: replaceDossierStatusId }] : null;
|
||||||
|
return super
|
||||||
|
.delete(dossierState.dossierStatusId, this._defaultModelPath, queryParams)
|
||||||
|
.pipe(switchMap(() => this.loadAllForTemplate(dossierState.dossierTemplateId)));
|
||||||
|
}
|
||||||
|
}
|
||||||
@ -19,6 +19,10 @@ export class PermissionsService {
|
|||||||
return dossiersServiceResolver(this._injector);
|
return dossiersServiceResolver(this._injector);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
canPerformDossierStatesActions(user = this._userService.currentUser): boolean {
|
||||||
|
return user.isAdmin;
|
||||||
|
}
|
||||||
|
|
||||||
isReviewerOrApprover(file: File): boolean {
|
isReviewerOrApprover(file: File): boolean {
|
||||||
const dossier = this._getDossier(file);
|
const dossier = this._getDossier(file);
|
||||||
return this.isFileAssignee(file) || this.isApprover(dossier);
|
return this.isFileAssignee(file) || this.isApprover(dossier);
|
||||||
|
|||||||
@ -84,6 +84,7 @@
|
|||||||
"rank": ""
|
"rank": ""
|
||||||
},
|
},
|
||||||
"save": "",
|
"save": "",
|
||||||
|
"success": "",
|
||||||
"title": ""
|
"title": ""
|
||||||
},
|
},
|
||||||
"add-edit-dossier-template": {
|
"add-edit-dossier-template": {
|
||||||
@ -327,7 +328,7 @@
|
|||||||
"title": ""
|
"title": ""
|
||||||
},
|
},
|
||||||
"table-col-names": {
|
"table-col-names": {
|
||||||
"dossier-status": "",
|
"dossier-state": "",
|
||||||
"last-modified": "",
|
"last-modified": "",
|
||||||
"name": "",
|
"name": "",
|
||||||
"owner": ""
|
"owner": ""
|
||||||
@ -460,9 +461,10 @@
|
|||||||
"delete": "",
|
"delete": "",
|
||||||
"delete-replace": "",
|
"delete-replace": "",
|
||||||
"form": {
|
"form": {
|
||||||
"status": "",
|
"state": "",
|
||||||
"status-placeholder": ""
|
"state-placeholder": ""
|
||||||
},
|
},
|
||||||
|
"success": "",
|
||||||
"suggestion": "",
|
"suggestion": "",
|
||||||
"title": "",
|
"title": "",
|
||||||
"warning": ""
|
"warning": ""
|
||||||
@ -769,7 +771,7 @@
|
|||||||
},
|
},
|
||||||
"table-col-names": {
|
"table-col-names": {
|
||||||
"documents-status": "",
|
"documents-status": "",
|
||||||
"dossier-status": "",
|
"dossier-state": "",
|
||||||
"name": "Name",
|
"name": "Name",
|
||||||
"needs-work": "Arbeitsvorrat",
|
"needs-work": "Arbeitsvorrat",
|
||||||
"owner": "Besitzer"
|
"owner": "Besitzer"
|
||||||
@ -1065,9 +1067,9 @@
|
|||||||
"label": "Beschreibung",
|
"label": "Beschreibung",
|
||||||
"placeholder": "Beschreibung eingeben"
|
"placeholder": "Beschreibung eingeben"
|
||||||
},
|
},
|
||||||
"dossier-status": {
|
"dossier-state": {
|
||||||
"label": "",
|
"label": "",
|
||||||
"no-status-placeholder": "",
|
"no-state-placeholder": "",
|
||||||
"placeholder": ""
|
"placeholder": ""
|
||||||
},
|
},
|
||||||
"due-date": "Termin",
|
"due-date": "Termin",
|
||||||
@ -1359,7 +1361,7 @@
|
|||||||
"filters": {
|
"filters": {
|
||||||
"assigned-people": "Beauftragt",
|
"assigned-people": "Beauftragt",
|
||||||
"documents-status": "",
|
"documents-status": "",
|
||||||
"dossier-status": "",
|
"dossier-state": "",
|
||||||
"dossier-templates": "Regelsätze",
|
"dossier-templates": "Regelsätze",
|
||||||
"empty": "Leer",
|
"empty": "Leer",
|
||||||
"filter-by": "Filter:",
|
"filter-by": "Filter:",
|
||||||
|
|||||||
@ -83,8 +83,9 @@
|
|||||||
"name-placeholder": "Enter Name",
|
"name-placeholder": "Enter Name",
|
||||||
"rank": "Rank"
|
"rank": "Rank"
|
||||||
},
|
},
|
||||||
"save": "Save Status",
|
"save": "Save State",
|
||||||
"title": "{type, select, edit{Edit {name}} create{Create} other{}} Dossier Status"
|
"success": "Successfully {type, select, edit{updated} create{created} other{}} the dossier state!",
|
||||||
|
"title": "{type, select, edit{Edit {name}} create{Create} other{}} Dossier State"
|
||||||
},
|
},
|
||||||
"add-edit-dossier-template": {
|
"add-edit-dossier-template": {
|
||||||
"error": {
|
"error": {
|
||||||
@ -327,7 +328,7 @@
|
|||||||
"title": "No archived dossiers match your current filters."
|
"title": "No archived dossiers match your current filters."
|
||||||
},
|
},
|
||||||
"table-col-names": {
|
"table-col-names": {
|
||||||
"dossier-status": "Dossier Status",
|
"dossier-state": "Dossier State",
|
||||||
"last-modified": "Archived Time",
|
"last-modified": "Archived Time",
|
||||||
"name": "Name",
|
"name": "Name",
|
||||||
"owner": "Owner"
|
"owner": "Owner"
|
||||||
@ -460,12 +461,13 @@
|
|||||||
"delete": "Delete",
|
"delete": "Delete",
|
||||||
"delete-replace": "Delete and Replace",
|
"delete-replace": "Delete and Replace",
|
||||||
"form": {
|
"form": {
|
||||||
"status": "Replace Status",
|
"state": "Replace State",
|
||||||
"status-placeholder": "Choose another status"
|
"state-placeholder": "Choose another state"
|
||||||
},
|
},
|
||||||
"suggestion": "Would you like to replace the states of the Dossiers with another status?",
|
"success": "Successfully deleted state!",
|
||||||
"title": "Delete Dossier Status",
|
"suggestion": "Would you like to replace the dossiers' states with another state?",
|
||||||
"warning": "The {name} status is assigned to {count} {count, plural, one{Dossier} other{Dossiers}}."
|
"title": "Delete Dossier State",
|
||||||
|
"warning": "The {name} state is assigned to {count} {count, plural, one{dossier} other{dossiers}}."
|
||||||
},
|
},
|
||||||
"confirm-delete-users": {
|
"confirm-delete-users": {
|
||||||
"cancel": "Keep {usersCount, plural, one{User} other{Users}}",
|
"cancel": "Keep {usersCount, plural, one{User} other{Users}}",
|
||||||
@ -769,7 +771,7 @@
|
|||||||
},
|
},
|
||||||
"table-col-names": {
|
"table-col-names": {
|
||||||
"documents-status": "Documents Status",
|
"documents-status": "Documents Status",
|
||||||
"dossier-status": "Dossier Status",
|
"dossier-state": "Dossier State",
|
||||||
"name": "Name",
|
"name": "Name",
|
||||||
"needs-work": "Workload",
|
"needs-work": "Workload",
|
||||||
"owner": "Owner"
|
"owner": "Owner"
|
||||||
@ -881,16 +883,16 @@
|
|||||||
"dossier-states": "Dossier States",
|
"dossier-states": "Dossier States",
|
||||||
"dossier-states-listing": {
|
"dossier-states-listing": {
|
||||||
"action": {
|
"action": {
|
||||||
"delete": "Delete Status",
|
"delete": "Delete State",
|
||||||
"edit": "Edit Status"
|
"edit": "Edit State"
|
||||||
},
|
},
|
||||||
"add-new": "New Status",
|
"add-new": "New State",
|
||||||
"chart": {
|
"chart": {
|
||||||
"dossier-states": "{count, plural, one{Dossier State} other{Dossier States}}"
|
"dossier-states": "{count, plural, one{Dossier State} other{Dossier States}}"
|
||||||
},
|
},
|
||||||
"error": {
|
"error": {
|
||||||
"conflict": "Dossier State with this name already exists!",
|
"conflict": "Dossier state with this name already exists!",
|
||||||
"generic": "Failed to add Dossier State"
|
"generic": "Failed to save dossier state!"
|
||||||
},
|
},
|
||||||
"no-data": {
|
"no-data": {
|
||||||
"title": "There are no dossier states."
|
"title": "There are no dossier states."
|
||||||
@ -1065,9 +1067,9 @@
|
|||||||
"label": "Description",
|
"label": "Description",
|
||||||
"placeholder": "Enter Description"
|
"placeholder": "Enter Description"
|
||||||
},
|
},
|
||||||
"dossier-status": {
|
"dossier-state": {
|
||||||
"label": "Dossier Status",
|
"label": "Dossier State",
|
||||||
"no-status-placeholder": "This dossier template has no states",
|
"no-state-placeholder": "This dossier template has no states",
|
||||||
"placeholder": "Undefined"
|
"placeholder": "Undefined"
|
||||||
},
|
},
|
||||||
"due-date": "Due Date",
|
"due-date": "Due Date",
|
||||||
@ -1359,7 +1361,7 @@
|
|||||||
"filters": {
|
"filters": {
|
||||||
"assigned-people": "Assignee(s)",
|
"assigned-people": "Assignee(s)",
|
||||||
"documents-status": "Documents Status",
|
"documents-status": "Documents Status",
|
||||||
"dossier-status": "Dossier Status",
|
"dossier-state": "Dossier State",
|
||||||
"dossier-templates": "Dossier Templates",
|
"dossier-templates": "Dossier Templates",
|
||||||
"empty": "Empty",
|
"empty": "Empty",
|
||||||
"filter-by": "Filter:",
|
"filter-by": "Filter:",
|
||||||
|
|||||||
@ -1,23 +1,25 @@
|
|||||||
import { IListable } from '@iqser/common-ui';
|
import { Entity } from '@iqser/common-ui';
|
||||||
import { IDossierState } from './dossier-state';
|
import { IDossierState } from './dossier-state';
|
||||||
|
|
||||||
export class DossierState implements IDossierState, IListable {
|
export class DossierState extends Entity<IDossierState> {
|
||||||
readonly description: string;
|
readonly description: string;
|
||||||
readonly dossierStatusId: string;
|
readonly dossierStatusId: string;
|
||||||
readonly dossierTemplateId: string;
|
readonly dossierTemplateId: string;
|
||||||
readonly name: string;
|
readonly name: string;
|
||||||
readonly color: string;
|
readonly color: string;
|
||||||
readonly rank?: number;
|
readonly rank?: number;
|
||||||
dossierCount?: number;
|
readonly routerLink = undefined;
|
||||||
|
readonly dossierCount: number;
|
||||||
|
|
||||||
constructor(dossierState: IDossierState) {
|
constructor(dossierState: IDossierState) {
|
||||||
|
super(dossierState);
|
||||||
this.description = dossierState.description;
|
this.description = dossierState.description;
|
||||||
this.dossierStatusId = dossierState.dossierStatusId;
|
this.dossierStatusId = dossierState.dossierStatusId;
|
||||||
this.dossierTemplateId = dossierState.dossierTemplateId;
|
this.dossierTemplateId = dossierState.dossierTemplateId;
|
||||||
this.name = dossierState.name;
|
this.name = dossierState.name;
|
||||||
this.color = dossierState.color;
|
this.color = dossierState.color;
|
||||||
this.dossierCount = dossierState.dossierCount;
|
|
||||||
this.rank = dossierState.rank;
|
this.rank = dossierState.rank;
|
||||||
|
this.dossierCount = dossierState.dossierCount || 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
get id(): string {
|
get id(): string {
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user