diff --git a/demo-shell-ng2/app/components/activiti/activiti-demo.component.html b/demo-shell-ng2/app/components/activiti/activiti-demo.component.html
index 4f00688632..8fdcae6d86 100644
--- a/demo-shell-ng2/app/components/activiti/activiti-demo.component.html
+++ b/demo-shell-ng2/app/components/activiti/activiti-demo.component.html
@@ -119,7 +119,9 @@
+ (editReport)="onEditReport($event)"
+ (reportSaved)="onReportSaved()"
+ (reportDeleted)="onReportDeleted()">
diff --git a/demo-shell-ng2/app/components/activiti/activiti-demo.component.ts b/demo-shell-ng2/app/components/activiti/activiti-demo.component.ts
index 0fee1a1127..7c030da7f1 100644
--- a/demo-shell-ng2/app/components/activiti/activiti-demo.component.ts
+++ b/demo-shell-ng2/app/components/activiti/activiti-demo.component.ts
@@ -104,8 +104,8 @@ export class ActivitiDemoComponent implements AfterViewInit {
this.dataTasks = new ObjectDataTableAdapter(
[],
[
- {type: 'text', key: 'name', title: 'Name', cssClass: 'full-width name-column', sortable: true},
- {type: 'text', key: 'created', title: 'Created', cssClass: 'hidden', sortable: true}
+ { type: 'text', key: 'name', title: 'Name', cssClass: 'full-width name-column', sortable: true },
+ { type: 'text', key: 'created', title: 'Created', cssClass: 'hidden', sortable: true }
]
);
this.dataTasks.setSorting(new DataSorting('created', 'desc'));
@@ -113,8 +113,8 @@ export class ActivitiDemoComponent implements AfterViewInit {
this.dataProcesses = new ObjectDataTableAdapter(
[],
[
- {type: 'text', key: 'name', title: 'Name', cssClass: 'full-width name-column', sortable: true},
- {type: 'text', key: 'started', title: 'Started', cssClass: 'hidden', sortable: true}
+ { type: 'text', key: 'name', title: 'Name', cssClass: 'full-width name-column', sortable: true },
+ { type: 'text', key: 'started', title: 'Started', cssClass: 'hidden', sortable: true }
]
);
this.dataProcesses.setSorting(new DataSorting('started', 'desc'));
@@ -154,7 +154,7 @@ export class ActivitiDemoComponent implements AfterViewInit {
}
onTaskFilterClick(event: FilterRepresentationModel) {
- if(event){
+ if (event) {
this.taskFilter = event;
}
}
@@ -202,6 +202,21 @@ export class ActivitiDemoComponent implements AfterViewInit {
this.analyticsreportlist.reload();
}
+ onReportSaved() {
+ this.analyticsreportlist.reload();
+ }
+
+ onReportDeleted() {
+ this.analyticsreportlist.reload();
+ this.selectFirstElementInReportList();
+ }
+
+ selectFirstElementInReportList(){
+ if (! this.analyticsreportlist.isReportsEmpty()) {
+ this.analyticsreportlist.selectReport(this.analyticsreportlist.reports[0]);
+ }
+ }
+
navigateStartProcess() {
this.resetProcessFilters();
this.reloadProcessFilters();
diff --git a/ng2-components/ng2-activiti-analytics/README.md b/ng2-components/ng2-activiti-analytics/README.md
index bc9bae8974..9c7eb99a83 100644
--- a/ng2-components/ng2-activiti-analytics/README.md
+++ b/ng2-components/ng2-activiti-analytics/README.md
@@ -251,6 +251,8 @@ platformBrowserDynamic().bootstrapModule(AppModule);
| --- | --- |
|`onSuccess` | The event is emitted when the report parameters are loaded |
|`onError` | The event is emitted when an error occur during the loading |
+|`reportSaved` | The event is emitted when a report is saved |
+|`reportDeleted` | The event is emitted when a report is deleted |
#### Options
diff --git a/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.css b/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.css
index 947c5d475a..f703726852 100644
--- a/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.css
+++ b/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.css
@@ -63,3 +63,29 @@
.report-container-setting {
padding-left: 10px;
}
+
+.option_button_details{
+ padding-top: 20px;
+}
+
+.mdl-dialog__title.choose_name{
+ padding: 0px;
+}
+
+.mdl-dialog.options-name-dialog {
+ width: 30%;
+}
+
+.export-message{
+ background-color: lightgray;
+}
+
+.save-export-input{
+ width:100%;
+}
+
+.delete-parameter {
+ position: absolute;
+ margin-left: 60%;
+ padding-top: 5px;
+}
diff --git a/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.html b/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.html
index 91b38999f5..f2bfcdcbe2 100644
--- a/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.html
+++ b/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.html
@@ -2,8 +2,8 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
{{'ANALYTICS.MESSAGES.UNKNOWN-WIDGET-TYPE' | translate}}: {{field.type}}
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ {{'ANALYTICS.MESSAGES.UNKNOWN-WIDGET-TYPE' | translate}}: {{field.type}}
+
-
-
-
ReportForm valid : {{ reportForm.valid }}
-
ReportForm status : {{ reportForm.errors | json }}
-
ReportForm FormGroup valid : {{reportForm && reportForm.controls.dateRange.valid | json }}
-
+
+
+
+
+
+
+
+
+
ReportForm valid : {{ reportForm.valid }}
+
ReportForm status : {{ reportForm.errors | json }}
+
ReportForm FormGroup valid : {{reportForm && reportForm.controls.dateRange.valid | json }}
+
diff --git a/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.spec.ts b/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.spec.ts
index 4354d1bb25..6d46a4ac98 100644
--- a/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.spec.ts
+++ b/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.spec.ts
@@ -55,7 +55,9 @@ describe('AnalyticsReportParametersComponent', () => {
let translateService = TestBed.get(AlfrescoTranslationService);
spyOn(translateService, 'addTranslationFolder').and.stub();
- spyOn(translateService, 'get').and.callFake((key) => { return Observable.of(key); });
+ spyOn(translateService, 'get').and.callFake((key) => {
+ return Observable.of(key);
+ });
componentHandler = jasmine.createSpyObj('componentHandler', [
'upgradeAllRegistered'
@@ -80,17 +82,22 @@ describe('AnalyticsReportParametersComponent', () => {
jasmine.Ajax.uninstall();
});
- it('Should initialize the Report form with a Form Group ', () => {
- expect(component.reportForm.get('dateRange')).toBeDefined();
- expect(component.reportForm.get('dateRange').get('startDate')).toBeDefined();
- expect(component.reportForm.get('dateRange').get('endDate')).toBeDefined();
+ it('Should initialize the Report form with a Form Group ', (done) => {
+ let fakeReportParam = new ReportParametersModel(analyticParamsMock.reportDefParamTask);
+ component.onSuccessReportParams.subscribe(() => {
+ fixture.detectChanges();
+ expect(component.reportForm.get('taskGroup')).toBeDefined();
+ expect(component.reportForm.get('taskGroup').get('taskName')).toBeDefined();
+ done();
+ });
+ component.onSuccessReportParams.emit(fakeReportParam);
});
it('Should render a dropdown with all the status when the definition parameter type is \'status\' ', (done) => {
component.onSuccessReportParams.subscribe(() => {
fixture.detectChanges();
let dropDown: any = element.querySelector('#select-status');
- expect(element.querySelector('h4').innerHTML).toEqual('Fake Task overview status');
+ expect(element.querySelector('h4').textContent.trim()).toEqual('Fake Task overview status');
expect(dropDown).toBeDefined();
expect(dropDown.length).toEqual(4);
expect(dropDown[0].innerHTML).toEqual('Choose One');
@@ -400,5 +407,148 @@ describe('AnalyticsReportParametersComponent', () => {
let numberConvert = component.convertNumber('2');
expect(numberConvert).toEqual(2);
});
+
+ describe('When the form is rendered correctly', () => {
+ let values: any = {
+ dateRange: {
+ startDate: '2016-09-01', endDate: '2016-10-05'
+ },
+ statusGroup: {
+ status: 'All'
+ },
+ processDefGroup: {
+ processDefinitionId: 'FakeProcess:1:22'
+ },
+ taskGroup: {
+ taskName: 'FakeTaskName'
+ },
+ durationGroup: {
+ duration: 22
+ },
+ dateIntervalGroup: {
+ dateRangeInterval: 120
+ },
+ processInstanceGroup: {
+ slowProcessInstanceInteger: 2
+ },
+ typeFilteringGroup: {
+ typeFiltering: true
+ }
+ };
+
+ beforeEach(async(() => {
+ let reportId = 1;
+ let change = new SimpleChange(null, reportId);
+ component.ngOnChanges({ 'reportId': change });
+ fixture.detectChanges();
+ jasmine.Ajax.requests.mostRecent().respondWith({
+ status: 200,
+ contentType: 'json',
+ responseText: analyticParamsMock.reportDefParamStatus
+ });
+ fixture.whenStable().then(() => {
+ component.toggleParameters();
+ component.reportId = '1';
+ spyOn(component, 'isFormValid').and.returnValue(true);
+ fixture.detectChanges();
+ });
+ }));
+
+ it('Should be able to change the report title', async(() => {
+ let title: HTMLElement = element.querySelector('h4');
+ title.click();
+ fixture.detectChanges();
+ let reportName: HTMLInputElement =
element.querySelector('#reportName');
+ expect(reportName).not.toBeNull();
+ reportName.focus();
+ component.reportParameters.name = 'FAKE_TEST_NAME';
+ reportName.value = 'FAKE_TEST_NAME';
+ reportName.blur();
+ jasmine.Ajax.requests.mostRecent().respondWith({
+ status: 200,
+ contentType: 'json',
+ responseText: analyticParamsMock.reportDefParamStatus
+ });
+ fixture.detectChanges();
+ fixture.whenStable().then(() => {
+ fixture.detectChanges();
+ let titleChanged: HTMLElement = element.querySelector('h4');
+ expect(titleChanged.textContent.trim()).toEqual('FAKE_TEST_NAME');
+ });
+ }));
+
+ it('Should show a dialog to allowing report save', async(() => {
+ component.saveReportSuccess.subscribe(() => {
+ let reportDialogTitle: HTMLElement = element.querySelector('#report-dialog');
+ expect(reportDialogTitle.getAttribute('open')).toBeNull();
+ });
+
+ component.submit(values);
+ fixture.detectChanges();
+ let saveButton: HTMLButtonElement = element.querySelector('#save-button');
+ expect(saveButton).toBeDefined();
+ expect(saveButton).not.toBeNull();
+ saveButton.click();
+ fixture.detectChanges();
+ fixture.whenStable().then(() => {
+ fixture.detectChanges();
+ let reportDialogTitle: HTMLElement = element.querySelector('#report-dialog-title');
+ let saveTitleSubMessage: HTMLElement = element.querySelector('#save-title-submessage');
+ let inputSaveName: HTMLInputElement = element.querySelector('#repName');
+ let performActionButton: HTMLButtonElement = element.querySelector('#action-dialog-button');
+ let todayDate = component.getTodayDate();
+ expect(reportDialogTitle).not.toBeNull();
+ expect(saveTitleSubMessage).not.toBeNull();
+ expect(inputSaveName.value.trim()).toEqual(analyticParamsMock.reportDefParamStatus.name + ' ( ' + todayDate + ' )');
+ expect(performActionButton).not.toBeNull();
+ performActionButton.click();
+ jasmine.Ajax.requests.mostRecent().respondWith({
+ status: 200,
+ contentType: 'json'
+ });
+ });
+ }));
+
+ it('Should show a dialog to allowing report export', async(() => {
+ component.submit(values);
+ spyOn(component, 'generateDownloadElement').and.stub();
+ fixture.detectChanges();
+ let exportButton: HTMLButtonElement = element.querySelector('#export-button');
+ expect(exportButton).toBeDefined();
+ expect(exportButton).not.toBeNull();
+ exportButton.click();
+ fixture.detectChanges();
+ fixture.whenStable().then(() => {
+ fixture.detectChanges();
+ let reportDialogTitle: HTMLElement = element.querySelector('#report-dialog-title');
+ let inputSaveName: HTMLInputElement = element.querySelector('#repName');
+ let performActionButton: HTMLButtonElement = element.querySelector('#action-dialog-button');
+ let todayDate = component.getTodayDate();
+ expect(reportDialogTitle).not.toBeNull();
+ expect(inputSaveName.value.trim()).toEqual(analyticParamsMock.reportDefParamStatus.name + ' ( ' + todayDate + ' )');
+ expect(performActionButton).not.toBeNull();
+ performActionButton.click();
+ jasmine.Ajax.requests.mostRecent().respondWith({
+ status: 200,
+ contentType: 'json'
+ });
+ });
+ }));
+
+ it('Should raise an event for report deleted', async(() => {
+ let deleteButton: HTMLButtonElement = element.querySelector('#delete-button');
+ expect(deleteButton).toBeDefined();
+ expect(deleteButton).not.toBeNull();
+
+ component.deleteReportSuccess.subscribe((reportId) => {
+ expect(reportId).not.toBeNull();
+ });
+ deleteButton.click();
+ jasmine.Ajax.requests.mostRecent().respondWith({
+ status: 200,
+ contentType: 'json'
+ });
+ }));
+ });
});
});
diff --git a/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.ts b/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.ts
index b1e3297328..b7c5e45386 100644
--- a/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.ts
+++ b/ng2-components/ng2-activiti-analytics/src/components/analytics-report-parameters.component.ts
@@ -24,7 +24,8 @@ import {
Output,
SimpleChanges,
OnDestroy,
- AfterViewChecked
+ AfterViewChecked,
+ ViewChild
} from '@angular/core';
import { FormGroup, FormBuilder, FormControl } from '@angular/forms';
import * as moment from 'moment';
@@ -38,6 +39,7 @@ import {
} from '../models/report.model';
declare var componentHandler;
+declare let dialogPolyfill: any;
@Component({
moduleId: module.id,
@@ -47,7 +49,7 @@ declare var componentHandler;
})
export class AnalyticsReportParametersComponent implements OnInit, OnChanges, OnDestroy, AfterViewChecked {
- public static FORMAT_DATE_ACTIVITI: string = 'YYYY-MM-DD';
+ public static FORMAT_DATE_ACTIVITI: string = 'YYYY-MM-DD';
@Input()
appId: string;
@@ -70,6 +72,15 @@ export class AnalyticsReportParametersComponent implements OnInit, OnChanges, On
@Output()
onFormValueChanged = new EventEmitter();
+ @Output()
+ saveReportSuccess = new EventEmitter();
+
+ @Output()
+ deleteReportSuccess = new EventEmitter();
+
+ @ViewChild('reportNameDialog')
+ reportNameDialog: any;
+
onDropdownChanged = new EventEmitter();
onSuccessReportParams = new EventEmitter();
@@ -84,6 +95,9 @@ export class AnalyticsReportParametersComponent implements OnInit, OnChanges, On
private reportParamsSub;
private paramOpts;
private isEditable: boolean = false;
+ private action: string;
+ private reportParamQuery: ReportQuery;
+ private reportName: string;
private hideParameters: boolean = true;
constructor(private translateService: AlfrescoTranslationService,
@@ -96,8 +110,6 @@ export class AnalyticsReportParametersComponent implements OnInit, OnChanges, On
}
ngOnInit() {
- this.initForm();
-
this.dropDownSub = this.onDropdownChanged.subscribe((field) => {
let paramDependOn: ReportParameterDetailsModel = this.reportParameters.definition.parameters.find(p => p.dependsOn === field.id);
if (paramDependOn) {
@@ -108,10 +120,9 @@ export class AnalyticsReportParametersComponent implements OnInit, OnChanges, On
this.paramOpts = this.onSuccessReportParams.subscribe((report: ReportParametersModel) => {
if (report.hasParameters()) {
this.retrieveParameterOptions(report.definition.parameters, this.appId);
+ this.generateFormGroupFromParameter(report.definition.parameters);
}
});
-
- this.reportForm.valueChanges.subscribe(data => this.onValueChanged(data));
}
ngOnChanges(changes: SimpleChanges) {
@@ -127,31 +138,54 @@ export class AnalyticsReportParametersComponent implements OnInit, OnChanges, On
}
}
- initForm() {
- this.reportForm = this.formBuilder.group({
- dateRange: new FormGroup({}),
- statusGroup: new FormGroup({
- status: new FormControl()
- }),
- processInstanceGroup: new FormGroup({
- slowProcessInstanceInteger: new FormControl()
- }),
- taskGroup: new FormGroup({
- taskName: new FormControl()
- }),
- typeFilteringGroup: new FormGroup({
- typeFiltering: new FormControl()
- }),
- dateIntervalGroup: new FormGroup({
- dateRangeInterval: new FormControl()
- }),
- durationGroup: new FormGroup({
- duration: new FormControl()
- }),
- processDefGroup: new FormGroup({
- processDefinitionId: new FormControl()
- })
+ private generateFormGroupFromParameter(parameters: ReportParameterDetailsModel[]) {
+ let formBuilderGroup: any = {};
+ parameters.forEach((param: ReportParameterDetailsModel) => {
+ switch (param.type) {
+ case 'dateRange' :
+ formBuilderGroup.dateRange = new FormGroup({});
+ break;
+ case 'processDefinition':
+ formBuilderGroup.processDefGroup = new FormGroup({
+ processDefinitionId: new FormControl()
+ });
+ break;
+ case 'duration':
+ formBuilderGroup.durationGroup = new FormGroup({
+ duration: new FormControl()
+ });
+ break;
+ case 'dateInterval':
+ formBuilderGroup.dateIntervalGroup = new FormGroup({
+ dateRangeInterval: new FormControl()
+ });
+ break;
+ case 'boolean':
+ formBuilderGroup.typeFilteringGroup = new FormGroup({
+ typeFiltering: new FormControl()
+ });
+ break;
+ case 'task':
+ formBuilderGroup.taskGroup = new FormGroup({
+ taskName: new FormControl()
+ });
+ break;
+ case 'integer':
+ formBuilderGroup.processInstanceGroup = new FormGroup({
+ slowProcessInstanceInteger: new FormControl()
+ });
+ break;
+ case 'status':
+ formBuilderGroup.statusGroup = new FormGroup({
+ status: new FormControl()
+ });
+ break;
+ default:
+ return;
+ }
});
+ this.reportForm = this.formBuilder.group(formBuilderGroup);
+ this.reportForm.valueChanges.subscribe(data => this.onValueChanged(data));
}
public getReportParams(reportId: string) {
@@ -193,8 +227,8 @@ export class AnalyticsReportParametersComponent implements OnInit, OnChanges, On
}
public submit(values: any) {
- let reportParamQuery = this.convertFormValuesToReportParamQuery(values);
- this.onSuccess.emit(reportParamQuery);
+ this.reportParamQuery = this.convertFormValuesToReportParamQuery(values);
+ this.onSuccess.emit(this.reportParamQuery);
}
onValueChanged(values: any) {
@@ -209,21 +243,41 @@ export class AnalyticsReportParametersComponent implements OnInit, OnChanges, On
.format(AnalyticsReportParametersComponent.FORMAT_DATE_ACTIVITI) + 'T00:00:00.000Z';
}
+ public getTodayDate() {
+ return moment().format(AnalyticsReportParametersComponent.FORMAT_DATE_ACTIVITI);
+ }
+
public convertNumber(value: string): number {
return value != null ? parseInt(value, 10) : 0;
}
convertFormValuesToReportParamQuery(values: any): ReportQuery {
let reportParamQuery: ReportQuery = new ReportQuery();
- reportParamQuery.dateRange.startDate = this.convertMomentDate(values.dateRange.startDate);
- reportParamQuery.dateRange.endDate = this.convertMomentDate(values.dateRange.endDate);
- reportParamQuery.status = values.statusGroup.status;
- reportParamQuery.processDefinitionId = values.processDefGroup.processDefinitionId;
- reportParamQuery.taskName = values.taskGroup.taskName;
- reportParamQuery.duration = values.durationGroup.duration;
- reportParamQuery.dateRangeInterval = values.dateIntervalGroup.dateRangeInterval;
- reportParamQuery.slowProcessInstanceInteger = this.convertNumber(values.processInstanceGroup.slowProcessInstanceInteger);
- reportParamQuery.typeFiltering = values.typeFilteringGroup.typeFiltering;
+ if (values.dateRange) {
+ reportParamQuery.dateRange.startDate = this.convertMomentDate(values.dateRange.startDate);
+ reportParamQuery.dateRange.endDate = this.convertMomentDate(values.dateRange.endDate);
+ }
+ if (values.statusGroup) {
+ reportParamQuery.status = values.statusGroup.status;
+ }
+ if (values.processDefGroup) {
+ reportParamQuery.processDefinitionId = values.processDefGroup.processDefinitionId;
+ }
+ if (values.taskGroup) {
+ reportParamQuery.taskName = values.taskGroup.taskName;
+ }
+ if (values.durationGroup) {
+ reportParamQuery.duration = values.durationGroup.duration;
+ }
+ if (values.dateIntervalGroup) {
+ reportParamQuery.dateRangeInterval = values.dateIntervalGroup.dateRangeInterval;
+ }
+ if (values.processInstanceGroup) {
+ reportParamQuery.slowProcessInstanceInteger = this.convertNumber(values.processInstanceGroup.slowProcessInstanceInteger);
+ }
+ if (values.typeFilteringGroup) {
+ reportParamQuery.typeFiltering = values.typeFilteringGroup.typeFiltering;
+ }
return reportParamQuery;
}
@@ -236,7 +290,7 @@ export class AnalyticsReportParametersComponent implements OnInit, OnChanges, On
}
public editEnable() {
- this.isEditable = true;
+ this.isEditable = true;
}
public editDisable() {
@@ -256,6 +310,74 @@ export class AnalyticsReportParametersComponent implements OnInit, OnChanges, On
);
}
+ public showDialog(event: string) {
+ if (!this.reportNameDialog.nativeElement.showModal) {
+ dialogPolyfill.registerDialog(this.reportNameDialog.nativeElement);
+ }
+ this.reportNameDialog.nativeElement.showModal();
+ this.action = event;
+ this.reportName = this.reportParameters.name + ' ( ' + this.getTodayDate() + ' )';
+ }
+
+ closeDialog() {
+ if (this.reportNameDialog) {
+ this.reportNameDialog.nativeElement.close();
+ }
+ }
+
+ performAction(action: string, reportParamQuery: ReportQuery) {
+ reportParamQuery.reportName = this.reportName;
+ this.closeDialog();
+ if (action === 'Save') {
+ this.doSave(reportParamQuery);
+ } else if (action === 'Export') {
+ this.doExport(reportParamQuery);
+ }
+ this.resetActions();
+ }
+
+ resetActions() {
+ this.action = '';
+ this.reportName = '';
+ }
+
+ isFormValid() {
+ return this.reportForm && this.reportForm.valid && this.reportForm.dirty;
+ }
+
+ isSaveAction() {
+ return this.action === 'Save';
+ }
+
+ doExport(paramQuery: ReportQuery) {
+ this.analyticsService.exportReportToCsv(this.reportId, paramQuery).subscribe(
+ (data: any) => {
+ let blob: Blob = new Blob([data], { type: 'text/csv' });
+ let downloadUrl = window.URL.createObjectURL(blob);
+ this.generateDownloadElement(downloadUrl, paramQuery);
+ });
+ }
+
+ private generateDownloadElement(downloadUrl: string, paramQuery: ReportQuery) {
+ let downloadElement = window.document.createElement('a');
+ downloadElement.setAttribute('id', 'export-download');
+ downloadElement.setAttribute('href', downloadUrl);
+ downloadElement.setAttribute('download', paramQuery.reportName);
+ downloadElement.click();
+ }
+
+ doSave(paramQuery: ReportQuery) {
+ this.analyticsService.saveReport(this.reportId, paramQuery).subscribe(() => {
+ this.saveReportSuccess.emit();
+ });
+ }
+
+ deleteReport(reportId: string) {
+ this.analyticsService.deleteReport(reportId).subscribe(() => {
+ this.deleteReportSuccess.emit(reportId);
+ }, error => this.logService.error(error));
+ }
+
ngAfterViewChecked() {
// workaround for MDL issues with dynamic components
if (componentHandler) {
diff --git a/ng2-components/ng2-activiti-analytics/src/components/analytics.component.html b/ng2-components/ng2-activiti-analytics/src/components/analytics.component.html
index 0cfae9ccdc..3f16077c5c 100644
--- a/ng2-components/ng2-activiti-analytics/src/components/analytics.component.html
+++ b/ng2-components/ng2-activiti-analytics/src/components/analytics.component.html
@@ -2,6 +2,8 @@
diff --git a/ng2-components/ng2-activiti-analytics/src/components/analytics.component.ts b/ng2-components/ng2-activiti-analytics/src/components/analytics.component.ts
index 21572dd43e..959d82329a 100644
--- a/ng2-components/ng2-activiti-analytics/src/components/analytics.component.ts
+++ b/ng2-components/ng2-activiti-analytics/src/components/analytics.component.ts
@@ -41,6 +41,12 @@ export class AnalyticsComponent implements OnChanges {
@Output()
editReport = new EventEmitter();
+ @Output()
+ reportSaved = new EventEmitter();
+
+ @Output()
+ reportDeleted = new EventEmitter();
+
@ViewChild('analyticsgenerator')
analyticsgenerator: AnalyticsGeneratorComponent;
@@ -71,4 +77,12 @@ export class AnalyticsComponent implements OnChanges {
this.editReport.emit(name);
}
+ public onSaveReportSuccess() {
+ this.reportSaved.emit();
+ }
+
+ public onDeleteReportSuccess() {
+ this.reportDeleted.emit();
+ }
+
}
diff --git a/ng2-components/ng2-activiti-analytics/src/components/widgets/dropdown/dropdown.widget.ts b/ng2-components/ng2-activiti-analytics/src/components/widgets/dropdown/dropdown.widget.ts
index 4e9450b361..9f6ca1434f 100644
--- a/ng2-components/ng2-activiti-analytics/src/components/widgets/dropdown/dropdown.widget.ts
+++ b/ng2-components/ng2-activiti-analytics/src/components/widgets/dropdown/dropdown.widget.ts
@@ -16,7 +16,7 @@
*/
import { Component, Input, Output, EventEmitter } from '@angular/core';
-import { FormGroup, Validators } from '@angular/forms';
+import { FormGroup, Validators, FormControl } from '@angular/forms';
import { WidgetComponent } from './../widget.component';
@Component({
@@ -54,7 +54,20 @@ export class DropdownWidget extends WidgetComponent {
ngOnInit() {
if (this.required) {
- this.formGroup.get(this.controllerName).setValidators(Validators.required);
+ this.formGroup.get(this.controllerName).setValidators(Validators.compose(this.buildValidatorList()));
}
}
+
+ validateDropDown(controller: FormControl) {
+ return controller.value !== 'null' ? null : { controllerName: false };
+ }
+
+ buildValidatorList() {
+ let validatorList = [];
+ validatorList.push(Validators.required);
+ if (this.showDefaultOption) {
+ validatorList.push(this.validateDropDown);
+ }
+ return validatorList;
+ }
}
diff --git a/ng2-components/ng2-activiti-analytics/src/i18n/en.json b/ng2-components/ng2-activiti-analytics/src/i18n/en.json
index 9e5cd9ca95..19d67e515d 100644
--- a/ng2-components/ng2-activiti-analytics/src/i18n/en.json
+++ b/ng2-components/ng2-activiti-analytics/src/i18n/en.json
@@ -43,5 +43,9 @@
},
"PROCESS-STATUS": "Process status",
"TASK-STATUS": "Task status"
+ },
+ "DIALOG":{
+ "SAVE_MESSAGE" : "The current parameter settings will be stored, and a new report will be shown in the reports list. When that particular report is clicked, the report will be generated using these saved parameter values.",
+ "EXPORT_MESSAGE":""
}
}
diff --git a/ng2-components/ng2-activiti-analytics/src/models/report.model.ts b/ng2-components/ng2-activiti-analytics/src/models/report.model.ts
index df82947ac2..5014a3c0e3 100644
--- a/ng2-components/ng2-activiti-analytics/src/models/report.model.ts
+++ b/ng2-components/ng2-activiti-analytics/src/models/report.model.ts
@@ -106,6 +106,7 @@ export class ParameterValueModel {
}
export class ReportQuery {
+ reportName: string;
processDefinitionId: string;
status: string;
taskName: string;
@@ -116,6 +117,7 @@ export class ReportQuery {
duration: number;
constructor(obj?: any) {
+ this.reportName = obj && obj.reportName || null;
this.processDefinitionId = obj && obj.processDefinitionId || null;
this.status = obj && obj.status || null;
this.taskName = obj && obj.taskName || null;
@@ -125,15 +127,18 @@ export class ReportQuery {
this.duration = obj && obj.duration || 0;
this.dateRange = new ReportDateRange(obj);
}
+
}
export class ReportDateRange {
startDate: string;
endDate: string;
+ rangeId: string;
constructor(obj?: any) {
this.startDate = obj && obj.startDate || null;
this.endDate = obj && obj.endDate || null;
+ this.rangeId = obj && obj.rangeId || null;
}
}
diff --git a/ng2-components/ng2-activiti-analytics/src/services/analytics.service.ts b/ng2-components/ng2-activiti-analytics/src/services/analytics.service.ts
index c1b3242e4d..50ac073941 100644
--- a/ng2-components/ng2-activiti-analytics/src/services/analytics.service.ts
+++ b/ng2-components/ng2-activiti-analytics/src/services/analytics.service.ts
@@ -184,6 +184,28 @@ export class AnalyticsService {
}).catch(err => this.handleError(err));
}
+ exportReportToCsv(reportId: string, paramsQuery: any): Observable {
+ return Observable.fromPromise(this.apiService.getInstance().activiti.reportApi.exportToCsv(reportId, paramsQuery))
+ .map((res: any) => {
+ this.logService.info('export');
+ return res;
+ }).catch(err => this.handleError(err));
+ }
+
+ saveReport(reportId: string, paramsQuery: any): Observable {
+ return Observable.fromPromise(this.apiService.getInstance().activiti.reportApi.saveReport(reportId, paramsQuery))
+ .map(() => {
+ this.logService.info('save');
+ }).catch(err => this.handleError(err));
+ }
+
+ deleteReport(reportId: string): Observable {
+ return Observable.fromPromise(this.apiService.getInstance().activiti.reportApi.deleteReport(reportId))
+ .map(() => {
+ this.logService.info('delete');
+ }).catch(err => this.handleError(err));
+ }
+
private handleError(error: Response) {
this.logService.error(error);
return Observable.throw(error.json().error || 'Server error');