[ADF-3586] Add processInstanceId input and fix empty response (#3916)

* [ADF-3586] Add processInstanceId input and fix empty response

* [ADF-3586] Fix Task Details Model

* [ADF-3586] Fix Dates on ProcessList Component

* [ADF-3586] Fix Task Details Model

* [ADF-3586] Fix attach form unit tests

* [ADF-3586] Fix moment.js import

* [ADF-3586] Remove fdescribe

* [ADF-3586] Fix Attach Form Component unit test
This commit is contained in:
davidcanonieto
2018-11-19 14:57:26 +00:00
committed by Eugenio Romano
parent f0dff4d011
commit 3d0c7449b4
8 changed files with 81 additions and 43 deletions

View File

@@ -18,6 +18,15 @@
</mat-error> </mat-error>
</mat-form-field> </mat-form-field>
<mat-form-field>
<mat-label>ProcessInstanceId</mat-label>
<input
matInput
class="form-control"
[formControl]="processInstanceId">
<mat-hint>SimpleProcess:1:2</mat-hint>
</mat-form-field>
<mat-form-field> <mat-form-field>
<mat-label>ProcessDefinitionId</mat-label> <mat-label>ProcessDefinitionId</mat-label>
<input <input
@@ -85,6 +94,7 @@
#processList #processList
[appId]="appId" [appId]="appId"
[processDefinitionId]="processDefId" [processDefinitionId]="processDefId"
[processInstanceId]="processInsId"
[state]="state" [state]="state"
[sort]="sort" [sort]="sort"
[page]="page" [page]="page"

View File

@@ -35,6 +35,7 @@ export class ProcessListDemoComponent implements OnInit {
appId: number; appId: number;
processDefId: string; processDefId: string;
processInsId: string;
state: string; state: string;
sort: string; sort: string;
size: number = this.DEFAULT_SIZE; size: number = this.DEFAULT_SIZE;
@@ -75,6 +76,7 @@ export class ProcessListDemoComponent implements OnInit {
this.processListForm = this.formBuilder.group({ this.processListForm = this.formBuilder.group({
processAppId: new FormControl(this.appId, [Validators.required, Validators.pattern('^[0-9]*$'), Validators.min(this.minValue)]), processAppId: new FormControl(this.appId, [Validators.required, Validators.pattern('^[0-9]*$'), Validators.min(this.minValue)]),
processDefinitionId: new FormControl(''), processDefinitionId: new FormControl(''),
processInstanceId: new FormControl(''),
processState: new FormControl(''), processState: new FormControl(''),
processSort: new FormControl(''), processSort: new FormControl(''),
processSize: new FormControl('', [Validators.pattern('^[0-9]*$'), Validators.min(this.minValue)]), processSize: new FormControl('', [Validators.pattern('^[0-9]*$'), Validators.min(this.minValue)]),
@@ -96,6 +98,7 @@ export class ProcessListDemoComponent implements OnInit {
filterProcesses(processFilter: any) { filterProcesses(processFilter: any) {
this.appId = processFilter.processAppId; this.appId = processFilter.processAppId;
this.processDefId = processFilter.processDefinitionId; this.processDefId = processFilter.processDefinitionId;
this.processInsId = processFilter.processInstanceId;
this.state = processFilter.processState; this.state = processFilter.processState;
if (!processFilter.processState) { if (!processFilter.processState) {
this.state = this.stateOptions[0].value; this.state = this.stateOptions[0].value;
@@ -142,6 +145,10 @@ export class ProcessListDemoComponent implements OnInit {
return this.processListForm.get('processDefinitionId'); return this.processListForm.get('processDefinitionId');
} }
get processInstanceId(): AbstractControl {
return this.processListForm.get('processInstanceId');
}
get processState(): AbstractControl { get processState(): AbstractControl {
return this.processListForm.get('processState'); return this.processListForm.get('processState');
} }

View File

@@ -185,15 +185,14 @@ describe('ProcessInstanceListComponent', () => {
expect(dataRow[0]['id']).toEqual('999'); expect(dataRow[0]['id']).toEqual('999');
}); });
it('should throw an exception when the response is wrong', fakeAsync(() => { it('should return an empty list when the response is wrong', fakeAsync(() => {
let emitSpy: jasmine.Spy = spyOn(component.error, 'emit');
let mockError = 'Fake server error'; let mockError = 'Fake server error';
getProcessInstancesSpy.and.returnValue(throwError(mockError)); getProcessInstancesSpy.and.returnValue(throwError(mockError));
component.appId = 1; component.appId = 1;
component.state = 'open'; component.state = 'open';
fixture.detectChanges(); fixture.detectChanges();
tick(); tick();
expect(emitSpy).toHaveBeenCalledWith(mockError); expect(component.isListEmpty()).toBeTruthy();
})); }));
it('should emit onSuccess event when reload() called', fakeAsync(() => { it('should emit onSuccess event when reload() called', fakeAsync(() => {

View File

@@ -44,6 +44,7 @@ import { processPresetsDefaultModel } from '../models/process-preset.model';
import { ProcessService } from '../services/process.service'; import { ProcessService } from '../services/process.service';
import { BehaviorSubject } from 'rxjs'; import { BehaviorSubject } from 'rxjs';
import { ProcessListModel } from '../models/process-list.model'; import { ProcessListModel } from '../models/process-list.model';
import moment from 'moment-es6';
@Component({ @Component({
selector: 'adf-process-instance-list', selector: 'adf-process-instance-list',
@@ -53,6 +54,7 @@ import { ProcessListModel } from '../models/process-list.model';
export class ProcessInstanceListComponent extends DataTableSchema implements OnChanges, AfterContentInit, PaginatedComponent { export class ProcessInstanceListComponent extends DataTableSchema implements OnChanges, AfterContentInit, PaginatedComponent {
static PRESET_KEY = 'adf-process-list.presets'; static PRESET_KEY = 'adf-process-list.presets';
public FORMAT_DATE: string = 'll';
@ContentChild(EmptyCustomContentDirective) emptyCustomContent: EmptyCustomContentDirective; @ContentChild(EmptyCustomContentDirective) emptyCustomContent: EmptyCustomContentDirective;
@@ -208,10 +210,10 @@ export class ProcessInstanceListComponent extends DataTableSchema implements On
private load(requestNode: ProcessFilterParamRepresentationModel) { private load(requestNode: ProcessFilterParamRepresentationModel) {
this.isLoading = true; this.isLoading = true;
this.processService.getProcessInstances(requestNode, this.processDefinitionKey) this.processService.getProcesses(requestNode, this.processDefinitionKey)
.subscribe( .subscribe(
(response) => { (response) => {
this.rows = this.optimizeNames(response.data); this.rows = this.optimizeProcessDetails(response.data);
this.selectFirst(); this.selectFirst();
this.success.emit(response); this.success.emit(response);
this.isLoading = false; this.isLoading = false;
@@ -283,9 +285,12 @@ export class ProcessInstanceListComponent extends DataTableSchema implements On
* Optimize name field * Optimize name field
* @param instances * @param instances
*/ */
private optimizeNames(instances: any[]): any[] { private optimizeProcessDetails(instances: any[]): any[] {
instances = instances.map(instance => { instances = instances.map(instance => {
instance.name = this.getProcessNameOrDescription(instance, 'medium'); instance.name = this.getProcessNameOrDescription(instance, 'medium');
if (instance.started) {
instance.started = moment(instance.started).format(this.FORMAT_DATE);
}
return instance; return instance;
}); });
return instances; return instances;

View File

@@ -17,11 +17,21 @@
import { ProcessInstance } from './process-instance.model'; import { ProcessInstance } from './process-instance.model';
export interface ProcessListModel { export class ProcessListModel {
size: number; size: number;
total: number; total: number;
start: number; start: number;
length: number; length: number;
data: ProcessInstance []; data: ProcessInstance [];
constructor(obj?: any) {
if (obj) {
this.size = obj.size || null;
this.total = obj.total || null;
this.start = obj.start || null;
this.length = obj.length || null;
this.data = obj.data || [];
}
}
} }

View File

@@ -17,7 +17,7 @@
import { AlfrescoApiService, FormValues } from '@alfresco/adf-core'; import { AlfrescoApiService, FormValues } from '@alfresco/adf-core';
import { Injectable } from '@angular/core'; import { Injectable } from '@angular/core';
import { Observable, from, throwError } from 'rxjs'; import { Observable, from, throwError, of } from 'rxjs';
import { TaskDetailsModel } from '../../task-list'; import { TaskDetailsModel } from '../../task-list';
import { ProcessFilterParamRepresentationModel } from '../models/filter-process.model'; import { ProcessFilterParamRepresentationModel } from '../models/filter-process.model';
import { ProcessDefinitionRepresentation } from '../models/process-definition.model'; import { ProcessDefinitionRepresentation } from '../models/process-definition.model';
@@ -58,6 +58,13 @@ export class ProcessService {
); );
} }
getProcesses(requestNode: ProcessFilterParamRepresentationModel, processDefinitionKey?: string): Observable<ProcessListModel> {
return this.getProcessInstances(requestNode, processDefinitionKey || null)
.pipe(catchError(() => {
return of(new ProcessListModel({}));
}));
}
/** /**
* Fetches the Process Audit information as a PDF. * Fetches the Process Audit information as a PDF.
* @param processId ID of the target process * @param processId ID of the target process
@@ -102,9 +109,9 @@ export class ProcessService {
*/ */
getProcessTasks(processInstanceId: string, state?: string): Observable<TaskDetailsModel[]> { getProcessTasks(processInstanceId: string, state?: string): Observable<TaskDetailsModel[]> {
let taskOpts = state ? { let taskOpts = state ? {
processInstanceId: processInstanceId, processInstanceId: processInstanceId,
state: state state: state
} : { } : {
processInstanceId: processInstanceId processInstanceId: processInstanceId
}; };
return from(this.alfrescoApiService.getInstance().activiti.taskApi.listTasks(taskOpts)) return from(this.alfrescoApiService.getInstance().activiti.taskApi.listTasks(taskOpts))
@@ -125,19 +132,19 @@ export class ProcessService {
*/ */
getProcessDefinitions(appId?: number): Observable<ProcessDefinitionRepresentation[]> { getProcessDefinitions(appId?: number): Observable<ProcessDefinitionRepresentation[]> {
let opts = appId ? { let opts = appId ? {
latest: true, latest: true,
appDefinitionId: appId appDefinitionId: appId
} : { } : {
latest: true latest: true
}; };
return from( return from(
this.alfrescoApiService.getInstance().activiti.processApi.getProcessDefinitions(opts) this.alfrescoApiService.getInstance().activiti.processApi.getProcessDefinitions(opts)
) )
.pipe( .pipe(
map(this.extractData), map(this.extractData),
map(processDefs => processDefs.map((pd) => new ProcessDefinitionRepresentation(pd))), map(processDefs => processDefs.map((pd) => new ProcessDefinitionRepresentation(pd))),
catchError(err => this.handleProcessError(err)) catchError(err => this.handleProcessError(err))
); );
} }
/** /**
@@ -166,10 +173,10 @@ export class ProcessService {
return from( return from(
this.alfrescoApiService.getInstance().activiti.processApi.startNewProcessInstance(startRequest) this.alfrescoApiService.getInstance().activiti.processApi.startNewProcessInstance(startRequest)
) )
.pipe( .pipe(
map((pd) => new ProcessInstance(pd)), map((pd) => new ProcessInstance(pd)),
catchError(err => this.handleProcessError(err)) catchError(err => this.handleProcessError(err))
); );
} }
/** /**
@@ -181,9 +188,9 @@ export class ProcessService {
return from<void>( return from<void>(
this.alfrescoApiService.getInstance().activiti.processApi.deleteProcessInstance(processInstanceId) this.alfrescoApiService.getInstance().activiti.processApi.deleteProcessInstance(processInstanceId)
) )
.pipe( .pipe(
catchError(err => this.handleProcessError(err)) catchError(err => this.handleProcessError(err))
); );
} }
/** /**
@@ -195,10 +202,10 @@ export class ProcessService {
return from( return from(
this.alfrescoApiService.getInstance().activiti.processInstanceVariablesApi.getProcessInstanceVariables(processInstanceId) this.alfrescoApiService.getInstance().activiti.processInstanceVariablesApi.getProcessInstanceVariables(processInstanceId)
) )
.pipe( .pipe(
map((processVars: any[]) => processVars.map((pd) => new ProcessInstanceVariable(pd))), map((processVars: any[]) => processVars.map((pd) => new ProcessInstanceVariable(pd))),
catchError(err => this.handleProcessError(err)) catchError(err => this.handleProcessError(err))
); );
} }
/** /**
@@ -211,9 +218,9 @@ export class ProcessService {
return from<ProcessInstanceVariable[]>( return from<ProcessInstanceVariable[]>(
this.alfrescoApiService.getInstance().activiti.processInstanceVariablesApi.createOrUpdateProcessInstanceVariables(processInstanceId, variables) this.alfrescoApiService.getInstance().activiti.processInstanceVariablesApi.createOrUpdateProcessInstanceVariables(processInstanceId, variables)
) )
.pipe( .pipe(
catchError(err => this.handleProcessError(err)) catchError(err => this.handleProcessError(err))
); );
} }
/** /**
@@ -226,9 +233,9 @@ export class ProcessService {
return from<void>( return from<void>(
this.alfrescoApiService.getInstance().activiti.processInstanceVariablesApi.deleteProcessInstanceVariable(processInstanceId, variableName) this.alfrescoApiService.getInstance().activiti.processInstanceVariablesApi.deleteProcessInstanceVariable(processInstanceId, variableName)
) )
.pipe( .pipe(
catchError(err => this.handleProcessError(err)) catchError(err => this.handleProcessError(err))
); );
} }
private extractData(res: any) { private extractData(res: any) {

View File

@@ -155,7 +155,7 @@ describe('StartTaskComponent', () => {
let successSpy = spyOn(component.success, 'emit'); let successSpy = spyOn(component.success, 'emit');
component.appId = 42; component.appId = 42;
component.startTaskModel = new StartTaskModel(startTaskMock); component.startTaskModel = new StartTaskModel(startTaskMock);
component.formKey = 1204; component.formKey = '1204';
fixture.detectChanges(); fixture.detectChanges();
let createTaskButton = <HTMLElement> element.querySelector('#button-start'); let createTaskButton = <HTMLElement> element.querySelector('#button-start');
createTaskButton.click(); createTaskButton.click();
@@ -216,7 +216,7 @@ describe('StartTaskComponent', () => {
let successSpy = spyOn(component.success, 'emit'); let successSpy = spyOn(component.success, 'emit');
component.appId = 42; component.appId = 42;
component.startTaskModel = new StartTaskModel(startTaskMock); component.startTaskModel = new StartTaskModel(startTaskMock);
component.formKey = 1204; component.formKey = '1204';
component.assigneeId = testUser.id; component.assigneeId = testUser.id;
fixture.detectChanges(); fixture.detectChanges();
let createTaskButton = <HTMLElement> element.querySelector('#button-start'); let createTaskButton = <HTMLElement> element.querySelector('#button-start');
@@ -232,7 +232,7 @@ describe('StartTaskComponent', () => {
it('should not assign task when no assignee is selected', () => { it('should not assign task when no assignee is selected', () => {
let successSpy = spyOn(component.success, 'emit'); let successSpy = spyOn(component.success, 'emit');
component.appId = 42; component.appId = 42;
component.formKey = 1204; component.formKey = '1204';
component.assigneeId = null; component.assigneeId = null;
component.startTaskModel = new StartTaskModel(startTaskMock); component.startTaskModel = new StartTaskModel(startTaskMock);
fixture.detectChanges(); fixture.detectChanges();
@@ -250,7 +250,7 @@ describe('StartTaskComponent', () => {
let successSpy = spyOn(component.success, 'emit'); let successSpy = spyOn(component.success, 'emit');
component.appId = 42; component.appId = 42;
component.startTaskModel = new StartTaskModel(startTaskMock); component.startTaskModel = new StartTaskModel(startTaskMock);
component.formKey = 1204; component.formKey = '1204';
component.getAssigneeId(testUser.id); component.getAssigneeId(testUser.id);
fixture.detectChanges(); fixture.detectChanges();
let createTaskButton = <HTMLElement> element.querySelector('#button-start'); let createTaskButton = <HTMLElement> element.querySelector('#button-start');

View File

@@ -63,7 +63,7 @@ export class StartTaskComponent implements OnInit {
assigneeId: number; assigneeId: number;
formKey: number; formKey: string;
taskId: string; taskId: string;
@@ -124,10 +124,10 @@ export class StartTaskComponent implements OnInit {
this.assigneeId = userId; this.assigneeId = userId;
} }
private attachForm(taskId: string, formKey: number): Observable<any> { private attachForm(taskId: string, formKey: string): Observable<any> {
let response = of(); let response = of();
if (taskId && formKey) { if (taskId && formKey) {
response = this.taskService.attachFormToATask(taskId, formKey); response = this.taskService.attachFormToATask(taskId, parseInt(formKey, 10));
} }
return response; return response;
} }