openaire-library/claims/linking/bulkClaim/bulkClaim.component.ts

258 lines
11 KiB
TypeScript

import {Component, Input, Output, EventEmitter,ViewChild} from '@angular/core';
import {Observable} from 'rxjs/Observable';
import {SearchCrossrefService} from '../../claim-utils/service/searchCrossref.service';
import {SearchDataciteService} from '../../claim-utils/service/searchDatacite.service';
import {ModalLoading} from '../../../utils/modal/loading.component';
import {Dates, DOI} from '../../../utils/string-utils.class';
import {ClaimResult} from '../../claim-utils/claimEntities.class';
import{EnvProperties} from '../../../utils/properties/env-properties';
@Component({
selector: 'bulk-claim',
template: `
<div class="uk-animation " style=" ">
<form class=" uk-padding ">
<div class="uk-clearfix">
<a class="uk-float-right" uk-toggle="target: #uploadInfo; animation: uk-animation-fade"><span class="uk-icon">
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 20 20" icon="info" ratio="1"><path d="M12.13,11.59 C11.97,12.84 10.35,14.12 9.1,14.16 C6.17,14.2 9.89,9.46 8.74,8.37 C9.3,8.16 10.62,7.83 10.62,8.81 C10.62,9.63 10.12,10.55 9.88,11.32 C8.66,15.16 12.13,11.15 12.14,11.18 C12.16,11.21 12.16,11.35 12.13,11.59 C12.08,11.95 12.16,11.35 12.13,11.59 L12.13,11.59 Z M11.56,5.67 C11.56,6.67 9.36,7.15 9.36,6.03 C9.36,5 11.56,4.54 11.56,5.67 L11.56,5.67 Z"></path><circle fill="none" stroke="#000" stroke-width="1.1" cx="10" cy="10" r="9"></circle></svg>
</span> What is upload mode? </a>
</div>
<div id="uploadInfo" class="uk-card uk-card-default uk-card-body uk-margin-small" hidden>
<a uk-toggle="target: #uploadInfo; animation: uk-animation-fade" class="uk-float-right"><span class="uk-icon">
<svg width="20" height="20" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg" icon="close" ratio="1"><path fill="none" stroke="#000" stroke-width="1.06" d="M16,16 L4,4"></path><path fill="none" stroke="#000" stroke-width="1.06" d="M16,4 L4,16"></path></svg>
</span></a>
<div class="uk-text-bold"><span class="uk-icon">
<svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 20 20" icon="info" ratio="1"><path d="M12.13,11.59 C11.97,12.84 10.35,14.12 9.1,14.16 C6.17,14.2 9.89,9.46 8.74,8.37 C9.3,8.16 10.62,7.83 10.62,8.81 C10.62,9.63 10.12,10.55 9.88,11.32 C8.66,15.16 12.13,11.15 12.14,11.18 C12.16,11.21 12.16,11.35 12.13,11.59 C12.08,11.95 12.16,11.35 12.13,11.59 L12.13,11.59 Z M11.56,5.67 C11.56,6.67 9.36,7.15 9.36,6.03 C9.36,5 11.56,4.54 11.56,5.67 L11.56,5.67 Z"></path><circle fill="none" stroke="#000" stroke-width="1.1" cx="10" cy="10" r="9"></circle></svg>
</span> Upload information:</div>
Upload a csv file containing a list of DOIs. For each DOI found in the file, metadata will be fetched from CrossRef or Datacite.
Available results will be added to your selected resarch results list in order to be linked with the selected Projects and Contexts.
<div class="uk-article-meta">
CSV format:
<ul class="uk-list">
<li>The format of CSV file should be "DOI","ACCESS_MODE","DATE".</li>
<li>The value "DOI" is required </li>
<li>Access mode column should have values: "OPEN","CLOSED" or "EMBARGO".</li>
<li>Date column valid format is YYYY-MM-DD and is required when access mode has value EMBARGO.</li>
<li>In case access mode is not available default value is "OPEN".</li>
</ul>
</div>
</div>
<div for="exampleInputFile">Upload a DOI csv file:</div>
<label for="exampleInputFile">Select a file</label>
<input id="exampleInputFile" class="uk-width-1-2" type="file" (change)="fileChangeEvent($event)" placeholder="Upload file..." />
<button class="uk-button uk-button-success" [class.disabled]="!enableUpload" type="button" (click)="upload()">Upload</button>
<div *ngIf="showReport" uk-alert class="uk-alert uk-alert-primary" role="alert" >
<a class="uk-alert-close" uk-close></a>
<div>Uploaded file contains {{allIds.length}} rows. {{foundIds.length}} results were sucefully fetched from CrossRef and Datacite.</div>
<div *ngIf ="duplicateIds.length > 0" >{{duplicateIds.length}} duplicate DOIs.</div>
<div *ngIf = "notFoundIds.length > 0" >Couldn't be found:
<ul class="">
<li *ngFor="let id of notFoundIds">"{{id}}"</li>
</ul>
</div>
<div *ngIf = "noValidIds.length > 0" >No valid DOIs:
<ul class="">
<li *ngFor="let id of noValidIds">"{{id}}"</li>
</ul>
</div>
<div *ngIf = "allIds.length == 0 || foundIds.length == 0" > Please make sure you are using the right format for the csv file... </div>
</div>
<div *ngIf="errorMessage.length > 0 " class="uk-alert uk-alert-danger" role="alert">{{errorMessage}}</div>
<modal-loading [message]= "'Uploading, reading and fetching results from your document. Please give us a moment..'"></modal-loading>
</form>
</div>
`
})
//[(ngModel)]="date"
export class BulkClaimComponent {
filesToUpload: Array<File>;
navigateTo: string = "Search";
source: string = "crossref";
type : string = "publication";
resultsFromSearch:number;
@Input() public select:boolean = true ;
@Input() public results;
@Input() public properties:EnvProperties;
allIds:string[] = [];
foundIds:string[] = [];
duplicateIds:string[] = [];
notFoundIds:string[] = [];
noValidIds:string[] = [];
showReport:boolean = false;
showInfo :boolean = false;
@ViewChild (ModalLoading) loading : ModalLoading ;
errorMessage = "";
infoMEssage = "";
enableUpload:boolean = true;
constructor(private _searchCrossrefService: SearchCrossrefService, private _searchDataciteService: SearchDataciteService) {
this.filesToUpload = [];
}
ngOnInit() {}
upload() {
this.enableUpload = false;
this.showReport = false;
this.errorMessage = "";
if(this.filesToUpload.length == 0){
this.errorMessage = "There is no selected file to upload.";
return ;
}
this.loading.open();
this.makeFileRequest(this.properties.uploadService, [], this.filesToUpload).then((result) => {
var rows = (result as any).split('\n'); // I have used space, you can use any thing.
var i = 0;
this.duplicateIds = [];
this.allIds = [];
this.foundIds = [];
this.noValidIds = [];
this.results.slice(0,this.results.length);
this.notFoundIds = [];
for(i=0;i<rows.length;i++){
if(rows[i] && rows[i] != null ){
console.log("Row is:" + rows[i]);
var values = rows[i].split(',');
var id=this.removeDoubleQuotes(values[0]);
if(DOI.isValidDOI(id)){
var accessMode = (values[1] != undefined) ? this.removeDoubleQuotes(values[1]):"OPEN";
accessMode = (this.validateAccessMode(accessMode)?accessMode:"OPEN");
var embargoDate =(values[2] != undefined) ? this.removeDoubleQuotes(values[2]):Dates.getDateToday();
embargoDate = (Dates.isValidDate(embargoDate)?embargoDate:Dates.getDateToday());
if(this.allIds.indexOf(id)>-1){
this.duplicateIds.push(id);
}else{
this.allIds.push(id);
this.fetchResult(id,accessMode,embargoDate);
}
}else{
this.noValidIds.push(id);
}
}
}
}, (error) => {
this.enableUpload = true;
console.log(error);
this.loading.close();
this.errorMessage = "An error occured while uploading...";
});
}
private removeDoubleQuotes(value){
if(value.indexOf('"')== 0){
value = value.substring(1,value.length);
}
var index =+value.indexOf('"');
if(index == (value.length - 1) || index == (value.length - 2) ){
value = value.substring(0,index);
}
return value;
}
private validateAccessMode(value){
var accessModes = ["OPEN", "CLOSED", "EMBARGO"];
if(accessModes.indexOf(value) > -1){
return true;
}
return false;
}
fileChangeEvent(fileInput: any){
this.filesToUpload = <Array<File>> fileInput.target.files;
}
makeFileRequest(url: string, params: Array<string>, files: Array<File>) {
return new Promise((resolve, reject) => {
var formData: any = new FormData();
var xhr = new XMLHttpRequest();
for(var i = 0; i < files.length; i++) {
formData.append("uploads[]", files[i], files[i].name);
}
xhr.onreadystatechange = function () {
if (xhr.readyState == 4) {
if (xhr.status == 200) {
resolve(xhr.response);
} else {
reject(xhr.response);
}
}
}
xhr.open("POST", url, true);
xhr.send(formData);
});
}
fetchResult(id:string,accessMode:string,date:string){
this._searchCrossrefService.searchCrossrefByDOIs([id], this.properties.searchCrossrefAPIURL).subscribe(
data => {
var crossrefResult = data.items[0];
if(data.items.length > 0){
this.foundIds.push(id);
var result: ClaimResult = ClaimResult.generateResult(crossrefResult, id,"crossref","publication", crossrefResult.URL, crossrefResult.title, crossrefResult.created['date-time'], accessMode);
result.embargoEndDate = date;
this.results.push(result);
this.endOfFetching();
}else{
this.searchInDatacite(id,accessMode,date);
// this.notFoundIds.push(id);
}
},
err => {
console.log(err);
this.notFoundIds.push(id);
this.endOfFetching();
}
);
}
searchInDatacite(id:string,accessMode:string,date:string){
this._searchDataciteService.getDataciteResultByDOI(id,this.properties).subscribe(
item => {
var dataciteResult = item.data;
if(dataciteResult != null && dataciteResult.attributes!= null ){
this.foundIds.push(id);
var result: ClaimResult = ClaimResult.generateResult(dataciteResult, id,"datacite","dataset", 'http://dx.doi.org/'+dataciteResult.attributes.doi, dataciteResult.attributes.title, dataciteResult.attributes.published, accessMode);
result.embargoEndDate = date;
this.results.push(result);
}else{
this.notFoundIds.push(id);
}
this.endOfFetching();
},
err => {
console.log(err);
this.notFoundIds.push(id);
this.endOfFetching();
}
);
}
endOfFetching(){
if(this.allIds.length == this.foundIds.length+this.notFoundIds.length+ this.duplicateIds.length ){
this.showReport = true;
this.enableUpload = true;
this.loading.close();
}
}
}