Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

download buttons #1

Open
wants to merge 10 commits into
base: frink
Choose a base branch
from
6 changes: 4 additions & 2 deletions index.html
Original file line number Diff line number Diff line change
Expand Up @@ -89,13 +89,15 @@ <h1><a href="#">Query the Web of Linked Data</a></h1>
</li>

<li>
<label>Query results</label>
<label class="padded-top">Query results</label>
<div class="results"></div>
<div><button id="download_csv" class="download">Download CSV</button></div>
</li>

<li>
<label>Execution log</label>
<label class="padded-top">Execution log</label>
<pre class="log"></pre>
<div><button id="download_log" class="download">Download Log</button></div>
</li>
</ul>
</fieldset>
Expand Down
47 changes: 45 additions & 2 deletions src/ldf-client-ui.js
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,8 @@ if (typeof global.process === 'undefined')
$element = this.element,
$stop = this.$stop = $('.stop', $element),
$start = this.$start = $('.start', $element),
$downloadCsv = this.$downloadCsv = $('#download_csv', $element),
$downloadLogs = this.$downloadCsv = $('#download_log', $element),
$queryTexts = $('.querytext'),
$queryContexts = $('.querycontext'),
$queryResultsToTrees = $('.results-to-tree'),
Expand All @@ -111,7 +113,8 @@ if (typeof global.process === 'undefined')
$showDetails = this.$showDetails = $('.details-toggle', $element),
$proxyDefault = $('.proxy-default', $element);
this.$details = $('.details', $element);

this.bindingResults = [];
this.logs = '';
// Replace non-existing elements by an empty text box
if (!$datasources.length) $datasources = this.$datasources = $('<select>');
if (!$results.length) $results = $('<div>');
Expand Down Expand Up @@ -236,6 +239,10 @@ if (typeof global.process === 'undefined')
$start.click(this._startExecution.bind(this));
$stop.click(this._stopExecutionForcefully.bind(this));

// Download csv data
$downloadCsv.click(this._downloadCSV.bind(this));
$downloadLogs.click(this._downloadLog.bind(this));

// Set up details toggling
$showDetails.click(function () {
self.$details.is(':visible') ? self._hideDetails() : self._showDetails();
Expand Down Expand Up @@ -680,6 +687,37 @@ if (typeof global.process === 'undefined')
}
},

_downloadCSV: function () {
if (!this._resultCount) return alert('Please execute a query to download');
else {
let csvContent = 'data:text/csv;charset=utf-8,';
let header = Object.keys(this.bindingResults[0]);
csvContent += [header].map(e => e.join(',')) + '\n';
this.bindingResults.forEach(function (v, i, a) {
let line = [];
header.forEach(function (h, i) {
line.push(v[h]);
});
csvContent += [line].map(e => e.join(',')) + '\n';
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@YaphetKG how hard would it be to make this a bit more robust? How should CSV handle comments within values, or newlines?

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@YaphetKG Comunica has built-in support, somewhere, for various output formats including text/csv (this is an option in the comunica-sparql CLI tool. Can this be reused?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi Jim, added the csv streaming changes (https://github.com/frink-okn/jQuery-Widget.js/pull/3/files) this are the changes this uses the text/csv format , but i have found that the query needs to be re-executed, to use this. It seems like once another consumer such as for displaying the results on the page, goes over the result set, the result set stream becomes empty to do the csv. Due to this, i have it setup so that the same query is executed again, and a new stream is consumed to generate the csv results.

And i can confirm the file properly quotes comma containing labels

<http://purl.obolibrary.org/obo/CL_4030038>,"CD24-positive, CD-133-positive, vimentin-positive proximal tubular cell",<http://purl.obolibrary.org/obo/UBERON_0002113>,kidney```
This is one result from the ubergraph (Cell types abdominal organs) query. 

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@YaphetKG I think we need to find another way to download the results. People will be surprised to have to execute the query twice.

});
let encodedUri = encodeURI(csvContent);
window.open(encodedUri);
}
},
_downloadLog: function () {
let filename = 'execution.log';

let blob = new Blob([this.logs], { type: 'text/json' });
let e = document.createEvent('MouseEvents');
let a = document.createElement('a');

a.download = filename;
a.href = window.URL.createObjectURL(blob);
a.dataset.downloadurl = ['text/json', a.download, a.href].join(':');
e.initMouseEvent('click', true, false, window, 0, 0, 0, 0, 0, false, false, false, false, 0, null);
a.dispatchEvent(e);
},

// Starts query execution
_startExecution: function () {
var datasources = this.$datasources.val() || [];
Expand All @@ -694,6 +732,8 @@ if (typeof global.process === 'undefined')
}

// Clear results and log
this.bindingResults = [];
this.logs = [];
this.$stop.show();
this.$start.hide();
this._resultsScroller.removeAll();
Expand Down Expand Up @@ -799,6 +839,7 @@ if (typeof global.process === 'undefined')
// For SELECT queries, add the rows to the result
case 'bindings':
this._writeResult = function (row) {
this.bindingResults.push(row);
this._resultsScroller.addContent([row]);
};
this._writeEnd = function () {
Expand Down Expand Up @@ -971,7 +1012,9 @@ if (typeof global.process === 'undefined')
case 'queryInfo': return self._initResults(data.queryType);
case 'result': return self._addResult(data.result);
case 'end': return self._endResults();
case 'log': return self._logAppender(data.log);
case 'log':
self.logs += data.log;
return self._logAppender(data.log);
case 'error': return this.onerror(data.error);
case 'webIdName': return self._setWebIdName(data.name);
}
Expand Down
11 changes: 11 additions & 0 deletions styles/ldf-client.css
Original file line number Diff line number Diff line change
Expand Up @@ -706,3 +706,14 @@ li.search-choice-focus .search-choice-close {
.extra-information.highlighted {
background-color: grey;
}

button.download{
float: right;
display: block;
margin-right: 0;
margin-left: auto;
}

.padded-top {
padding-top: 10px;
}