Adds Dataset copy functionality from a DMP to another.

This commit is contained in:
Diamantis Tziotzios 2019-03-28 16:53:17 +02:00
parent 3976722d47
commit c37e421388
8 changed files with 242 additions and 32 deletions

View File

@ -0,0 +1,21 @@
<div class="dataset-copy-dialog">
<div class="confirmation-message">
<mat-form-field class="col-12">
<app-single-auto-complete [formControl]="data.formControl" placeholder="{{'DATASET-WIZARD.DIALOGUE.DMP-SEARCH.PLACEHOLDER' | translate}}"
[configuration]="dmpAutoCompleteConfiguration">
</app-single-auto-complete>
</mat-form-field>
<mat-error *ngIf="data.formControl.hasError('incorrect')">
{{getErrorMessage()}}
</mat-error>
</div>
<div class="row">
<div class="col"></div>
<div class="col-auto">
<button mat-raised-button color="primary" type="button" (click)="cancel()">{{ data.cancelButton }}</button>
</div>
<div class="col-auto">
<button mat-raised-button color="primary" type="button" (click)="confirm()">{{ data.confirmButton }}</button>
</div>
</div>
</div>

View File

@ -0,0 +1,6 @@
.confirmation-message {
padding-bottom: 20px;
}
.dataset-copy-dialog {
width: 350px;
}

View File

@ -0,0 +1,88 @@
import { Component } from "@angular/core";
import { MatDialogRef, MAT_DIALOG_DATA } from "@angular/material";
import { SingleAutoCompleteConfiguration } from "../../../../library/auto-complete/single/single-auto-complete-configuration";
import { Observable } from "rxjs";
import { DataTableRequest } from "../../../../core/model/data-table/data-table-request";
import { DmpCriteria } from "../../../../core/query/dmp/dmp-criteria";
import { DmpListingModel } from "../../../../core/model/dmp/dmp-listing";
import { DmpService } from "../../../../core/services/dmp/dmp.service";
import { Inject } from "@angular/core";
import { DmpModel } from "../../../../core/model/dmp/dmp";
import { TranslateService } from "@ngx-translate/core";
@Component({
selector: 'dataset-copy-dialogue-component',
templateUrl: 'dataset-copy-dialogue.component.html',
styleUrls: ['./dataset-copy-dialogue.component.scss'],
})
export class DatasetCopyDialogueComponent {
dmpAutoCompleteConfiguration: SingleAutoCompleteConfiguration;
dmpModel: DmpModel;
constructor(
public dialogRef: MatDialogRef<DatasetCopyDialogueComponent>,
public dmpService: DmpService,
public language: TranslateService,
@Inject(MAT_DIALOG_DATA) public data: any
) { }
ngOnInit() {
this.dmpAutoCompleteConfiguration = {
filterFn: this.searchDmp.bind(this),
initialItems: (extraData) => this.searchDmp(''),
displayFn: (item) => item['label'],
titleFn: (item) => item['label']
};
}
cancel() {
this.dialogRef.close(this.data);
}
confirm() {
this.datasetProfileValidate().subscribe(x => {
if (this.data.datasetProfileExist) {
this.dialogRef.close(this.data);
}
else if (!this.data.datasetProfileExist) {
this.data.formControl.setErrors({'incorrect': true});
console.log(this.data.formControl.invalid);
}
});
}
searchDmp(query: string): Observable<DmpListingModel[]> {
const fields: Array<string> = new Array<string>();
fields.push('asc');
const dmpDataTableRequest: DataTableRequest<DmpCriteria> = new DataTableRequest(0, null, { fields: fields });
dmpDataTableRequest.criteria = new DmpCriteria();
dmpDataTableRequest.criteria.like = query;
return this.dmpService.getPaged(dmpDataTableRequest, "autocomplete").map(x => x.data);
}
datasetProfileValidate() {
return this.dmpService.getSingle(this.data.formControl.value.id).map(result => result as DmpModel)
.map(result => {
this.dmpModel = result
this.dmpModel.profiles.forEach((element) => {
if (element.id == this.data.datasetProfileId) {
this.data.datasetProfileExist = true;
}
})
});
}
getErrorMessage() {
return this.language.instant('DATASET-WIZARD.DIALOGUE.ERROR-MESSAGE');
}
hasValidDatasetProfile() {
if (this.data.datasetProfileExist) {
return true;
}
else {
return false;
}
}
}

View File

@ -2,11 +2,22 @@
<h3 *ngIf="isNew">{{ 'DATASET-WIZARD.TITLE.NEW' | translate }}</h3>
<div class="row">
<div class="col-auto">
<h3 *ngIf="!isNew">{{datasetWizardModel?.label}} {{ 'GENERAL.NAMES.DATASET' | translate }}<span *ngIf="this.formGroup && this.formGroup.dirty">
- {{ 'GENERAL.STATUSES.EDIT' | translate }}</span></h3>
<h3 *ngIf="this.formGroup && this.formGroup.get('status').value == DatasetStatus.Finalized && viewOnly">{{'GENERAL.STATUSES.FINALISED'
| translate }}</h3>
<h3 *ngIf="!isNew">{{datasetWizardModel?.label}} {{ 'GENERAL.NAMES.DATASET' | translate }}
<span *ngIf="this.formGroup && this.formGroup.dirty">
- {{ 'GENERAL.STATUSES.EDIT' | translate }}</span>
</h3>
<h3 *ngIf="this.formGroup && this.formGroup.get('status').value == DatasetStatus.Finalized && viewOnly">{{'GENERAL.STATUSES.FINALISED' | translate }}</h3>
</div>
<div class="col"></div>
<mat-menu #actionsMenu="matMenu">
<button mat-menu-item (click)="openDmpSearchDialogue()">
<mat-icon>file_copy</mat-icon>{{'DATASET-WIZARD.ACTIONS.COPY-DATASET' | translate}}
</button>
</mat-menu>
<button mat-icon-button [matMenuTriggerFor]="actionsMenu">
<mat-icon>more_vert</mat-icon>
</button>
<!-- <div class="col"></div>
<div class="col-auto" *ngIf=" !viewOnly">
<button *ngIf="!editMode" class="col-auto" mat-icon-button (click)="enableForm()">
@ -18,18 +29,15 @@
</div> -->
</div>
<div *ngIf="this.datasetProfileDefinitionModel || this.datasetWizardModel?.datasetProfileDefinition">
<button mat-raised-button color="primary" *ngIf="!isNew && !viewOnly" class="deleteButton"
(click)="openConfirm(formGroup.get('label').value, formGroup.get('id').value)" type="button">{{
'DATASET-WIZARD.ACTIONS.DELETE' | translate }}</button>
<button mat-raised-button color="primary" *ngIf="datasetWizardModel&&datasetWizardModel?.status != 1 && !viewOnly"
class="saveButton" (click)="save();" type="button">{{
'DATASET-WIZARD.ACTIONS.SAVE' | translate }}</button>
<button mat-raised-button color="primary" *ngIf="!isNew && !viewOnly && !isCopy" class="deleteButton" (click)="openConfirm(formGroup.get('label').value, formGroup.get('id').value)"
type="button">{{ 'DATASET-WIZARD.ACTIONS.DELETE' | translate }}</button>
<button mat-raised-button color="primary" *ngIf="datasetWizardModel&&datasetWizardModel?.status != 1 && !viewOnly" class="saveButton"
(click)="save();" type="button">{{ 'DATASET-WIZARD.ACTIONS.SAVE' | translate }}</button>
<button mat-raised-button color="primary" *ngIf="datasetWizardModel&&datasetWizardModel?.status != 1 && !viewOnly" [disabled]="!formGroup.valid"
class="saveAndFinalizeButton" (click)="saveFinalize();" type="button">{{
'DATASET-WIZARD.ACTIONS.SAVE-AND-FINALISE' | translate }}</button>
class="saveAndFinalizeButton" (click)="saveFinalize();" type="button">{{ 'DATASET-WIZARD.ACTIONS.SAVE-AND-FINALISE' | translate }}</button>
<button mat-raised-button color="primary" *ngIf="datasetWizardModel&&datasetWizardModel?.status == 1" class="downloadPDF"
(click)="downloadPDF();" type="button">{{ 'DATASET-WIZARD.ACTIONS.DOWNLOAD-PDF' | translate }}</button>
<button mat-raised-button color="primary" *ngIf="datasetWizardModel&&datasetWizardModel?.status == 1" class="downloadDOCX"
<button mat-raised-button color="primary" *ngIf="datasetWizardModel&&datasetWizardModel?.status == 1" class="downloadDOCX"
(click)="downloadDOCX();" type="button">{{ 'DATASET-WIZARD.ACTIONS.DOWNLOAD-DOCX' | translate }}</button>
<button mat-raised-button color="primary" *ngIf="datasetWizardModel&&datasetWizardModel?.status == 1" class="downloadXML"
(click)="downloadXML();" type="button">{{ 'DATASET-WIZARD.ACTIONS.DOWNLOAD-XML' | translate }}</button>
@ -58,8 +66,9 @@
<div class="col-12">
<div class="row">
<div class="col"></div>
<div class="col-auto"><button matStepperNext mat-raised-button color="primary" (click)="getDefinition()">{{'DATASET-WIZARD.ACTIONS.NEXT'
| translate}}</button></div>
<div class="col-auto">
<button matStepperNext mat-raised-button color="primary" (click)="getDefinition()">{{'DATASET-WIZARD.ACTIONS.NEXT' | translate}}</button>
</div>
</div>
</div>
</div>
@ -73,8 +82,9 @@
<div class="col-12">
<div class="row">
<div class="col"></div>
<div class="col-auto"><button matStepperNext mat-raised-button color="primary">{{'DATASET-WIZARD.ACTIONS.NEXT'
| translate}}</button></div>
<div class="col-auto">
<button matStepperNext mat-raised-button color="primary">{{'DATASET-WIZARD.ACTIONS.NEXT' | translate}}</button>
</div>
</div>
</div>
</div>
@ -88,8 +98,9 @@
[datasetProfileId]="formGroup.get('profile').value"></app-dataset-description-form>
<div class="col-12 description-action-row">
<div class="row">
<div class="col-auto"><button matStepperPrevious mat-raised-button color="primary">{{'DATASET-WIZARD.ACTIONS.BACK'
| translate}}</button></div>
<div class="col-auto">
<button matStepperPrevious mat-raised-button color="primary">{{'DATASET-WIZARD.ACTIONS.BACK' | translate}}</button>
</div>
</div>
</div>
</div>

View File

@ -27,6 +27,8 @@ import { DatasetWizardEditorModel } from './dataset-wizard-editor.model';
import { SnackBarNotificationLevel, UiNotificationService } from '../../../core/services/notification/ui-notification-service';
import { ConfirmationDialogComponent } from '../../../library/confirmation-dialog/confirmation-dialog.component';
import { DataTableRequest } from '../../../core/model/data-table/data-table-request';
import { DatasetCopyDialogueComponent } from './dataset-copy-dialogue/dataset-copy-dialogue.component';
import { FormControl } from '@angular/forms';
@Component({
selector: 'app-dataset-wizard-component',
@ -45,16 +47,13 @@ export class DatasetWizardComponent extends BaseComponent implements OnInit, IBr
datasetWizardModel: DatasetWizardEditorModel;
isNew = true;
isCopy = false;
formGroup: FormGroup;
datasetProfileDefinitionModel: DatasetDescriptionFormEditorModel;
availableProfiles: DatasetProfileModel[] = [];
itemId: string;
isLinear = false;
firstStepFormGroup: FormGroup;
secondFormGroup: FormGroup;
constructor(
private datasetWizardService: DatasetWizardService,
@ -114,9 +113,11 @@ export class DatasetWizardComponent extends BaseComponent implements OnInit, IBr
};
const params = this.route.snapshot.params;
const queryParams = this.route.snapshot.queryParams;
this.itemId = params['id'];
const dmpId = params['dmpId'];
if (this.itemId != null) {
const newDmpId = queryParams['newDmpId'];
if (this.itemId != null && newDmpId == null) {
this.isNew = false;
this.datasetWizardService.getSingle(this.itemId)
.pipe(takeUntil(this._destroyed))
@ -183,7 +184,52 @@ export class DatasetWizardComponent extends BaseComponent implements OnInit, IBr
}]);
});
});
} else {
} else if (newDmpId != null) {
this.isNew = false;
this.isCopy = true;
this.datasetWizardService.getSingle(this.itemId)
.pipe(takeUntil(this._destroyed))
.subscribe(data => {
this.datasetWizardModel = new DatasetWizardEditorModel().fromModel(data);
this.formGroup = this.datasetWizardModel.buildForm();
this.formGroup.get('id').setValue(null);
this.dmpService.getSingle(newDmpId).map(data => data as DmpModel)
.pipe(takeUntil(this._destroyed))
.subscribe(data => {
setTimeout(() => {
this.datasetWizardModel.dmp = data;
this.formGroup.get('dmp').setValue(this.datasetWizardModel.dmp);
this.loadDatasetProfiles();
this.breadCrumbs = Observable.of([
{
parentComponentName: null,
label: 'Datasets',
url: '/datasets',
notFoundResolver: [
{
parentComponentName: null,
label: this.datasetWizardModel.dmp.project.label,
url: '/projects/edit/' + this.datasetWizardModel.dmp.project.id
},
{
parentComponentName: null,
label: this.datasetWizardModel.dmp.label,
url: '/plans/edit/' + this.datasetWizardModel.dmp.id,
}]
}]);
});
});
this.editMode = this.datasetWizardModel.status === DatasetStatus.Draft;
if (this.datasetWizardModel.status === 1) {
this.formGroup.disable();
this.viewOnly = true;
}
// if (this.viewOnly) { this.formGroup.disable(); } // For future use, to make Dataset edit like DMP.
this.loadDatasetProfiles();
});
}
else {
this.datasetWizardModel = new DatasetWizardEditorModel();
this.formGroup = this.datasetWizardModel.buildForm();
this.editMode = this.datasetWizardModel.status === DatasetStatus.Draft;
@ -251,7 +297,6 @@ export class DatasetWizardComponent extends BaseComponent implements OnInit, IBr
}
}
formSubmit(): void {
if (!this.isFormValid()) { return; }
this.onSubmit();
@ -327,7 +372,7 @@ export class DatasetWizardComponent extends BaseComponent implements OnInit, IBr
downloadDOCX(): void {
this.datasetWizardService.downloadDOCX(this.itemId)
.pipe(takeUntil(this._destroyed))
.pipe(takeUntil(this._destroyed))
.subscribe(response => {
const blob = new Blob([response.body], { type: 'application/msword' });
const filename = this.getFilenameFromContentDispositionHeader(response.headers.get('Content-Disposition'));
@ -416,10 +461,34 @@ export class DatasetWizardComponent extends BaseComponent implements OnInit, IBr
this.datasetWizardService.delete(id)
.pipe(takeUntil(this._destroyed))
.subscribe(
complete => { this.onCallbackSuccess(); this.router.navigateByUrl('/datasets')},
complete => { this.onCallbackSuccess(); this.router.navigateByUrl('/datasets') },
error => this.onCallbackError(error)
);
}
});
}
openDmpSearchDialogue() {
const formControl = new FormControl();
const dialogRef = this.dialog.open(DatasetCopyDialogueComponent, {
data: {
formControl: formControl,
datasetId: this.formGroup.value.id,
datasetProfileId: this.formGroup.value.profile,
datasetProfileExist: false,
confirmButton: this.language.instant('GENERAL.CONFIRMATION-DIALOG.ACTIONS.CONFIRM'),
cancelButton: this.language.instant('GENERAL.CONFIRMATION-DIALOG.ACTIONS.CANCEL')
}
});
dialogRef.afterClosed().pipe(takeUntil(this._destroyed))
.subscribe(result => {
if (result && result.datasetProfileExist) {
console.log("I came out of the dialogue with result");
console.log(result.formControl);
const newDmpId = result.formControl.value.id
this.router.navigate(['/datasets/copy/' + result.datasetId], { queryParams: { newDmpId: newDmpId } });
}
});
}
}

View File

@ -16,6 +16,7 @@ import { DatasetExternalServiceDialogEditorComponent } from './dataset-wizard/ex
import { DatasetRoutingModule } from './dataset.routing';
import { DatasetCriteriaComponent } from './listing/criteria/dataset-criteria.component';
import { DatasetListingComponent } from './listing/dataset-listing.component';
import { DatasetCopyDialogueComponent } from './dataset-wizard/dataset-copy-dialogue/dataset-copy-dialogue.component';
@NgModule({
imports: [
@ -37,13 +38,15 @@ import { DatasetListingComponent } from './listing/dataset-listing.component';
DatasetExternalDataRepositoryDialogEditorComponent,
DatasetExternalDatasetDialogEditorComponent,
DatasetExternalRegistryDialogEditorComponent,
DatasetExternalServiceDialogEditorComponent
DatasetExternalServiceDialogEditorComponent,
DatasetCopyDialogueComponent
],
entryComponents: [
DatasetExternalDataRepositoryDialogEditorComponent,
DatasetExternalDatasetDialogEditorComponent,
DatasetExternalRegistryDialogEditorComponent,
DatasetExternalServiceDialogEditorComponent
DatasetExternalServiceDialogEditorComponent,
DatasetCopyDialogueComponent
]
})
export class DatasetModule { }

View File

@ -53,6 +53,11 @@ const routes: Routes = [
data: {
breadcrumb: true
},
},
{
path: 'copy/:id',
component: DatasetWizardComponent,
}
];
@ -60,4 +65,4 @@ const routes: Routes = [
imports: [RouterModule.forChild(routes)],
exports: [RouterModule]
})
export class DatasetRoutingModule { }
export class DatasetRoutingModule { }

View File

@ -256,7 +256,8 @@
"SAVE-AND-FINALISE": "Save and Finalise",
"DOWNLOAD-PDF": "Download PDF",
"DOWNLOAD-XML": "Download XML",
"DOWNLOAD-DOCX": "Download DOCX"
"DOWNLOAD-DOCX": "Download DOCX",
"COPY-DATASET": "Copy Dataset"
},
"UPLOAD": {
"UPLOAD-XML": "Import",
@ -264,6 +265,12 @@
"UPLOAD-XML-NAME": "Name Of Dataset Profile",
"UPLOAD-XML-IMPORT": "File",
"UPLOAD-XML-FILE-CANCEL": "Cancel"
},
"DIALOGUE": {
"DMP-SEARCH": {
"PLACEHOLDER": "Search DMP"
},
"ERROR-MESSAGE": "This DMP does not contain this Dataset Profile"
}
},
"DATASET-LISTING": {