Commit e763104a by Daniel Lee

csv: add toggle for export to Excel

Adds back feature that adds 'sep=;' text that excel needs in a csv file.
Also adds toggle to make this optional if exporting to other spreadsheet
programs. Fixes #9083.
parent a31d0df8
...@@ -7,8 +7,8 @@ declare var window: any; ...@@ -7,8 +7,8 @@ declare var window: any;
const DEFAULT_DATETIME_FORMAT: String = 'YYYY-MM-DDTHH:mm:ssZ'; const DEFAULT_DATETIME_FORMAT: String = 'YYYY-MM-DDTHH:mm:ssZ';
export function exportSeriesListToCsv(seriesList, dateTimeFormat = DEFAULT_DATETIME_FORMAT) { export function exportSeriesListToCsv(seriesList, dateTimeFormat = DEFAULT_DATETIME_FORMAT, excel = false) {
var text = 'Series;Time;Value\n'; var text = excel ? 'sep=;\n' : '' + 'Series;Time;Value\n';
_.each(seriesList, function(series) { _.each(seriesList, function(series) {
_.each(series.datapoints, function(dp) { _.each(series.datapoints, function(dp) {
text += series.alias + ';' + moment(dp[1]).format(dateTimeFormat) + ';' + dp[0] + '\n'; text += series.alias + ';' + moment(dp[1]).format(dateTimeFormat) + ';' + dp[0] + '\n';
...@@ -17,8 +17,8 @@ export function exportSeriesListToCsv(seriesList, dateTimeFormat = DEFAULT_DATET ...@@ -17,8 +17,8 @@ export function exportSeriesListToCsv(seriesList, dateTimeFormat = DEFAULT_DATET
saveSaveBlob(text, 'grafana_data_export.csv'); saveSaveBlob(text, 'grafana_data_export.csv');
} }
export function exportSeriesListToCsvColumns(seriesList, dateTimeFormat = DEFAULT_DATETIME_FORMAT) { export function exportSeriesListToCsvColumns(seriesList, dateTimeFormat = DEFAULT_DATETIME_FORMAT, excel = false) {
var text = 'Time;'; var text = excel ? 'sep=;\n' : '' + 'Time;';
// add header // add header
_.each(seriesList, function(series) { _.each(seriesList, function(series) {
text += series.alias + ';'; text += series.alias + ';';
...@@ -52,8 +52,8 @@ export function exportSeriesListToCsvColumns(seriesList, dateTimeFormat = DEFAUL ...@@ -52,8 +52,8 @@ export function exportSeriesListToCsvColumns(seriesList, dateTimeFormat = DEFAUL
saveSaveBlob(text, 'grafana_data_export.csv'); saveSaveBlob(text, 'grafana_data_export.csv');
} }
export function exportTableDataToCsv(table) { export function exportTableDataToCsv(table, excel = false) {
var text = ''; var text = excel ? 'sep=;\n' : '';
// add header // add header
_.each(table.columns, function(column) { _.each(table.columns, function(column) {
text += (column.title || column.text) + ';'; text += (column.title || column.text) + ';';
......
...@@ -11,17 +11,21 @@ ...@@ -11,17 +11,21 @@
<div class="modal-content"> <div class="modal-content">
<div class="p-t-2"> <div class="p-t-2">
<div class="gf-form"> <div class="gf-form" ng-hide="ctrl.panel === 'table'">
<label class="gf-form-label width-10">Mode</label> <label class="gf-form-label width-10">Mode</label>
<div class="gf-form-select-wrapper"> <div class="gf-form-select-wrapper">
<select class="gf-form-input" ng-model="ctrl.asRows" ng-options="f.value as f.text for f in [{text: 'Series as rows', value: true}, {text: 'Series as columns', value: false}]"> <select class="gf-form-input" ng-model="ctrl.asRows" ng-options="f.value as f.text for f in [{text: 'Series as rows', value: true}, {text: 'Series as columns', value: false}]">
</select> </select>
</div> </div>
</div> </div>
<div class="gf-form"> <div class="gf-form" ng-hide="ctrl.panel === 'table'">
<label class="gf-form-label width-10">Date Time Format</label> <label class="gf-form-label width-10">Date Time Format</label>
<input type="text" class="gf-form-input" ng-model="ctrl.dateTimeFormat"> <input type="text" class="gf-form-input" ng-model="ctrl.dateTimeFormat">
</div> </div>
<gf-form-switch class="gf-form"
label="Export To Excel" label-class="width-12" switch-class="max-width-6"
checked="ctrl.excel">
</gf-form-switch>
</div> </div>
<div class="gf-form-button-row text-center"> <div class="gf-form-button-row text-center">
......
...@@ -6,17 +6,24 @@ import appEvents from 'app/core/app_events'; ...@@ -6,17 +6,24 @@ import appEvents from 'app/core/app_events';
export class ExportDataModalCtrl { export class ExportDataModalCtrl {
private data: any[]; private data: any[];
private panel: string;
asRows: Boolean = true; asRows: Boolean = true;
dateTimeFormat: String = 'YYYY-MM-DDTHH:mm:ssZ'; dateTimeFormat: String = 'YYYY-MM-DDTHH:mm:ssZ';
excel: false;
/** @ngInject */ /** @ngInject */
constructor(private $scope) { } constructor(private $scope) { }
export() { export() {
if (this.panel === 'table') {
fileExport.exportTableDataToCsv(this.data, this.excel);
} else {
if (this.asRows) { if (this.asRows) {
fileExport.exportSeriesListToCsv(this.data, this.dateTimeFormat); fileExport.exportSeriesListToCsv(this.data, this.dateTimeFormat, this.excel);
} else { } else {
fileExport.exportSeriesListToCsvColumns(this.data, this.dateTimeFormat); fileExport.exportSeriesListToCsvColumns(this.data, this.dateTimeFormat, this.excel);
}
} }
this.dismiss(); this.dismiss();
} }
...@@ -32,6 +39,7 @@ export function exportDataModal() { ...@@ -32,6 +39,7 @@ export function exportDataModal() {
controller: ExportDataModalCtrl, controller: ExportDataModalCtrl,
controllerAs: 'ctrl', controllerAs: 'ctrl',
scope: { scope: {
panel: '<',
data: '<' // The difference to '=' is that the bound properties are not watched data: '<' // The difference to '=' is that the bound properties are not watched
}, },
bindToController: true bindToController: true
......
...@@ -148,7 +148,14 @@ class TablePanelCtrl extends MetricsPanelCtrl { ...@@ -148,7 +148,14 @@ class TablePanelCtrl extends MetricsPanelCtrl {
} }
exportCsv() { exportCsv() {
FileExport.exportTableDataToCsv(this.renderer.render_values()); var scope = this.$scope.$new(true);
scope.tableData = this.renderer.render_values();
scope.panel = 'table';
this.publishAppEvent('show-modal', {
templateHtml: '<export-data-modal panel="panel" data="tableData"></export-data-modal>',
scope,
modalClass: 'modal--narrow'
});
} }
link(scope, elem, attrs, ctrl) { link(scope, elem, attrs, ctrl) {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment