diff options
author | Clement Ho <408677-ClemMakesApps@users.noreply.gitlab.com> | 2019-08-14 22:57:34 +0000 |
---|---|---|
committer | Clement Ho <408677-ClemMakesApps@users.noreply.gitlab.com> | 2019-08-14 22:57:34 +0000 |
commit | c8dfb11b28e0292f2b89f65da12e7fc31aea5b48 (patch) | |
tree | 25cc9fbfd266f54c529da25d6c966932bee898d9 | |
parent | 0b43c1027f712567d654c3e61c6557db1f4e2faa (diff) | |
parent | 9e75711aead6c5991ea116a9326762d58b91b18b (diff) | |
download | gitlab-ce-c8dfb11b28e0292f2b89f65da12e7fc31aea5b48.tar.gz |
Merge branch '64950-move-download-csv-button-functionality-in-metrics-dashboard-cards-into-the-dropdown' into 'master'
Move download CSV functionality to dropdown in metrics
Closes #64950
See merge request gitlab-org/gitlab-ce!31679
12 files changed, 83 insertions, 73 deletions
diff --git a/app/assets/javascripts/monitoring/components/charts/area.vue b/app/assets/javascripts/monitoring/components/charts/area.vue index 5b950f8c966..838447e6c75 100644 --- a/app/assets/javascripts/monitoring/components/charts/area.vue +++ b/app/assets/javascripts/monitoring/components/charts/area.vue @@ -1,7 +1,6 @@ <script> import { __ } from '~/locale'; -import { mapState } from 'vuex'; -import { GlLink, GlButton } from '@gitlab/ui'; +import { GlLink } from '@gitlab/ui'; import { GlAreaChart, GlChartSeriesLabel } from '@gitlab/ui/dist/charts'; import dateFormat from 'dateformat'; import { debounceByAnimationFrame, roundOffFloat } from '~/lib/utils/common_utils'; @@ -16,7 +15,6 @@ let debouncedResize; export default { components: { GlAreaChart, - GlButton, GlChartSeriesLabel, GlLink, Icon, @@ -69,7 +67,6 @@ export default { }; }, computed: { - ...mapState('monitoringDashboard', ['exportMetricsToCsvEnabled']), chartData() { // Transforms & supplements query data to render appropriate labels & styles // Input: [{ queryAttributes1 }, { queryAttributes2 }] @@ -179,18 +176,6 @@ export default { yAxisLabel() { return `${this.graphData.y_label}`; }, - csvText() { - const chartData = this.chartData[0].data; - const header = `timestamp,${this.graphData.y_label}\r\n`; // eslint-disable-line @gitlab/i18n/no-non-i18n-strings - return chartData.reduce((csv, data) => { - const row = data.join(','); - return `${csv}${row}\r\n`; - }, header); - }, - downloadLink() { - const data = new Blob([this.csvText], { type: 'text/plain' }); - return window.URL.createObjectURL(data); - }, }, watch: { containerWidth: 'onResize', @@ -259,16 +244,6 @@ export default { <div :class="{ 'prometheus-graph-embed w-100 p-3': showBorder }"> <div class="prometheus-graph-header"> <h5 ref="graphTitle" class="prometheus-graph-title">{{ graphData.title }}</h5> - <gl-button - v-if="exportMetricsToCsvEnabled" - :href="downloadLink" - :title="__('Download CSV')" - :aria-label="__('Download CSV')" - style="margin-left: 200px;" - download="chart_metrics.csv" - > - {{ __('Download CSV') }} - </gl-button> <div ref="graphWidgets" class="prometheus-graph-widgets"><slot></slot></div> </div> <gl-area-chart diff --git a/app/assets/javascripts/monitoring/components/dashboard.vue b/app/assets/javascripts/monitoring/components/dashboard.vue index 782e4310f3e..587392adbc3 100644 --- a/app/assets/javascripts/monitoring/components/dashboard.vue +++ b/app/assets/javascripts/monitoring/components/dashboard.vue @@ -235,6 +235,19 @@ export default { chart.metrics.some(metric => this.metricsWithData.includes(metric.metric_id)), ); }, + csvText(graphData) { + const chartData = graphData.queries[0].result[0].values; + const yLabel = graphData.y_label; + const header = `timestamp,${yLabel}\r\n`; // eslint-disable-line @gitlab/i18n/no-non-i18n-strings + return chartData.reduce((csv, data) => { + const row = data.join(','); + return `${csv}${row}\r\n`; + }, header); + }, + downloadCsv(graphData) { + const data = new Blob([this.csvText(graphData)], { type: 'text/plain' }); + return window.URL.createObjectURL(data); + }, // TODO: BEGIN, Duplicated code with panel_type until feature flag is removed // Issue number: https://gitlab.com/gitlab-org/gitlab-ce/issues/63845 getGraphAlerts(queries) { @@ -448,7 +461,6 @@ export default { @setAlerts="setAlerts" /> <gl-dropdown - v-if="alertWidgetAvailable" v-gl-tooltip class="mx-2" toggle-class="btn btn-transparent border-0" @@ -459,6 +471,9 @@ export default { <template slot="button-content"> <icon name="ellipsis_v" class="text-secondary" /> </template> + <gl-dropdown-item :href="downloadCsv(graphData)" download="chart_metrics.csv"> + {{ __('Download CSV') }} + </gl-dropdown-item> <gl-dropdown-item v-if="alertWidgetAvailable" v-gl-modal="`alert-modal-${index}-${graphIndex}`" diff --git a/app/assets/javascripts/monitoring/components/panel_type.vue b/app/assets/javascripts/monitoring/components/panel_type.vue index 295c0851f12..3fbac71f3d7 100644 --- a/app/assets/javascripts/monitoring/components/panel_type.vue +++ b/app/assets/javascripts/monitoring/components/panel_type.vue @@ -1,7 +1,14 @@ <script> import { mapState } from 'vuex'; import _ from 'underscore'; -import { GlDropdown, GlDropdownItem, GlModal, GlModalDirective } from '@gitlab/ui'; +import { + GlDropdown, + GlDropdownItem, + GlModal, + GlModalDirective, + GlTooltipDirective, +} from '@gitlab/ui'; +import Icon from '~/vue_shared/components/icon.vue'; import MonitorAreaChart from './charts/area.vue'; import MonitorSingleStatChart from './charts/single_stat.vue'; import MonitorEmptyChart from './charts/empty_chart.vue'; @@ -11,12 +18,14 @@ export default { MonitorAreaChart, MonitorSingleStatChart, MonitorEmptyChart, + Icon, GlDropdown, GlDropdownItem, GlModal, }, directives: { GlModal: GlModalDirective, + GlTooltip: GlTooltipDirective, }, props: { graphData: { @@ -41,6 +50,19 @@ export default { graphDataHasMetrics() { return this.graphData.queries[0].result.length > 0; }, + csvText() { + const chartData = this.graphData.queries[0].result[0].values; + const yLabel = this.graphData.y_label; + const header = `timestamp,${yLabel}\r\n`; // eslint-disable-line @gitlab/i18n/no-non-i18n-strings + return chartData.reduce((csv, data) => { + const row = data.join(','); + return `${csv}${row}\r\n`; + }, header); + }, + downloadCsv() { + const data = new Blob([this.csvText], { type: 'text/plain' }); + return window.URL.createObjectURL(data); + }, }, methods: { getGraphAlerts(queries) { @@ -81,7 +103,6 @@ export default { @setAlerts="setAlerts" /> <gl-dropdown - v-if="alertWidgetAvailable" v-gl-tooltip class="mx-2" toggle-class="btn btn-transparent border-0" @@ -92,6 +113,9 @@ export default { <template slot="button-content"> <icon name="ellipsis_v" class="text-secondary" /> </template> + <gl-dropdown-item :href="downloadCsv" download="chart_metrics.csv"> + {{ __('Download CSV') }} + </gl-dropdown-item> <gl-dropdown-item v-if="alertWidgetAvailable" v-gl-modal="`alert-modal-${index}`"> {{ __('Alerts') }} </gl-dropdown-item> diff --git a/app/assets/javascripts/monitoring/monitoring_bundle.js b/app/assets/javascripts/monitoring/monitoring_bundle.js index 366034becd0..c0fee1ebb99 100644 --- a/app/assets/javascripts/monitoring/monitoring_bundle.js +++ b/app/assets/javascripts/monitoring/monitoring_bundle.js @@ -13,7 +13,6 @@ export default (props = {}) => { prometheusEndpointEnabled: gon.features.environmentMetricsUsePrometheusEndpoint, multipleDashboardsEnabled: gon.features.environmentMetricsShowMultipleDashboards, additionalPanelTypesEnabled: gon.features.environmentMetricsAdditionalPanelTypes, - exportMetricsToCsvEnabled: gon.features.exportMetricsToCsvEnabled, }); } diff --git a/app/assets/javascripts/monitoring/stores/actions.js b/app/assets/javascripts/monitoring/stores/actions.js index a9c491c7c6c..0cbad179f17 100644 --- a/app/assets/javascripts/monitoring/stores/actions.js +++ b/app/assets/javascripts/monitoring/stores/actions.js @@ -37,17 +37,11 @@ export const setEndpoints = ({ commit }, endpoints) => { export const setFeatureFlags = ( { commit }, - { - prometheusEndpointEnabled, - multipleDashboardsEnabled, - additionalPanelTypesEnabled, - exportMetricsToCsvEnabled, - }, + { prometheusEndpointEnabled, multipleDashboardsEnabled, additionalPanelTypesEnabled }, ) => { commit(types.SET_DASHBOARD_ENABLED, prometheusEndpointEnabled); commit(types.SET_MULTIPLE_DASHBOARDS_ENABLED, multipleDashboardsEnabled); commit(types.SET_ADDITIONAL_PANEL_TYPES_ENABLED, additionalPanelTypesEnabled); - commit(types.SET_EXPORT_METRICS_TO_CSV_ENABLED, exportMetricsToCsvEnabled); }; export const setShowErrorBanner = ({ commit }, enabled) => { diff --git a/app/assets/javascripts/monitoring/stores/mutation_types.js b/app/assets/javascripts/monitoring/stores/mutation_types.js index 9ec8214b167..4b1aadbcf05 100644 --- a/app/assets/javascripts/monitoring/stores/mutation_types.js +++ b/app/assets/javascripts/monitoring/stores/mutation_types.js @@ -17,4 +17,3 @@ export const SET_ENDPOINTS = 'SET_ENDPOINTS'; export const SET_GETTING_STARTED_EMPTY_STATE = 'SET_GETTING_STARTED_EMPTY_STATE'; export const SET_NO_DATA_EMPTY_STATE = 'SET_NO_DATA_EMPTY_STATE'; export const SET_SHOW_ERROR_BANNER = 'SET_SHOW_ERROR_BANNER'; -export const SET_EXPORT_METRICS_TO_CSV_ENABLED = 'SET_EXPORT_METRICS_TO_CSV_ENABLED'; diff --git a/app/assets/javascripts/monitoring/stores/mutations.js b/app/assets/javascripts/monitoring/stores/mutations.js index a2dceb21fc0..b19520d6638 100644 --- a/app/assets/javascripts/monitoring/stores/mutations.js +++ b/app/assets/javascripts/monitoring/stores/mutations.js @@ -99,7 +99,4 @@ export default { [types.SET_SHOW_ERROR_BANNER](state, enabled) { state.showErrorBanner = enabled; }, - [types.SET_EXPORT_METRICS_TO_CSV_ENABLED](state, enabled) { - state.exportMetricsToCsvEnabled = enabled; - }, }; diff --git a/app/assets/javascripts/monitoring/stores/state.js b/app/assets/javascripts/monitoring/stores/state.js index a14a25e3a20..440bdc951e0 100644 --- a/app/assets/javascripts/monitoring/stores/state.js +++ b/app/assets/javascripts/monitoring/stores/state.js @@ -10,7 +10,6 @@ export default () => ({ useDashboardEndpoint: false, multipleDashboardsEnabled: false, additionalPanelTypesEnabled: false, - exportMetricsToCsvEnabled: false, emptyState: 'gettingStarted', showEmptyState: true, showErrorBanner: true, diff --git a/app/controllers/projects/environments_controller.rb b/app/controllers/projects/environments_controller.rb index df9e55fda2a..5a1f93dc609 100644 --- a/app/controllers/projects/environments_controller.rb +++ b/app/controllers/projects/environments_controller.rb @@ -15,7 +15,6 @@ class Projects::EnvironmentsController < Projects::ApplicationController push_frontend_feature_flag(:environment_metrics_show_multiple_dashboards) push_frontend_feature_flag(:environment_metrics_additional_panel_types) push_frontend_feature_flag(:prometheus_computed_alerts) - push_frontend_feature_flag(:export_metrics_to_csv_enabled) end def index diff --git a/changelogs/unreleased/64950-move-download-csv-button-functionality-in-metrics-dashboard-cards-i.yml b/changelogs/unreleased/64950-move-download-csv-button-functionality-in-metrics-dashboard-cards-i.yml new file mode 100644 index 00000000000..21771c76873 --- /dev/null +++ b/changelogs/unreleased/64950-move-download-csv-button-functionality-in-metrics-dashboard-cards-i.yml @@ -0,0 +1,5 @@ +--- +title: 'feat: adds a download to csv functionality to the dropdown in prometheus metrics' +merge_request: 31679 +author: +type: changed diff --git a/spec/javascripts/monitoring/charts/area_spec.js b/spec/javascripts/monitoring/charts/area_spec.js index 4541119dd2e..57f99a09002 100644 --- a/spec/javascripts/monitoring/charts/area_spec.js +++ b/spec/javascripts/monitoring/charts/area_spec.js @@ -24,7 +24,6 @@ describe('Area component', () => { store.commit(`monitoringDashboard/${types.RECEIVE_METRICS_DATA_SUCCESS}`, MonitoringMock.data); store.commit(`monitoringDashboard/${types.RECEIVE_DEPLOYMENTS_DATA_SUCCESS}`, deploymentData); - store.dispatch('monitoringDashboard/setFeatureFlags', { exportMetricsToCsvEnabled: true }); [mockGraphData] = store.state.monitoringDashboard.groups[0].metrics; areaChart = shallowMount(Area, { @@ -109,16 +108,6 @@ describe('Area component', () => { }); }); - describe('when exportMetricsToCsvEnabled is disabled', () => { - beforeEach(() => { - store.dispatch('monitoringDashboard/setFeatureFlags', { exportMetricsToCsvEnabled: false }); - }); - - it('does not render the Download CSV button', () => { - expect(areaChart.contains('glbutton-stub')).toBe(false); - }); - }); - describe('methods', () => { describe('formatTooltipText', () => { const mockDate = deploymentData[0].created_at; @@ -264,23 +253,5 @@ describe('Area component', () => { expect(areaChart.vm.yAxisLabel).toBe('CPU'); }); }); - - describe('csvText', () => { - it('converts data from json to csv', () => { - const header = `timestamp,${mockGraphData.y_label}`; - const data = mockGraphData.queries[0].result[0].values; - const firstRow = `${data[0][0]},${data[0][1]}`; - - expect(areaChart.vm.csvText).toMatch(`^${header}\r\n${firstRow}`); - }); - }); - - describe('downloadLink', () => { - it('produces a link to download metrics as csv', () => { - const link = areaChart.vm.downloadLink; - - expect(link).toContain('blob:'); - }); - }); }); }); diff --git a/spec/javascripts/monitoring/dashboard_spec.js b/spec/javascripts/monitoring/dashboard_spec.js index 36f650d5933..b78896c45fc 100644 --- a/spec/javascripts/monitoring/dashboard_spec.js +++ b/spec/javascripts/monitoring/dashboard_spec.js @@ -5,7 +5,7 @@ import { timeWindows, timeWindowsKeyNames } from '~/monitoring/constants'; import * as types from '~/monitoring/stores/mutation_types'; import { createStore } from '~/monitoring/stores'; import axios from '~/lib/utils/axios_utils'; -import { +import MonitoringMock, { metricsGroupsAPIResponse, mockApiEndpoint, environmentData, @@ -40,6 +40,7 @@ describe('Dashboard', () => { let mock; let store; let component; + let mockGraphData; beforeEach(() => { setFixtures(` @@ -482,4 +483,36 @@ describe('Dashboard', () => { }); }); }); + + describe('when downloading metrics data as CSV', () => { + beforeEach(() => { + component = new DashboardComponent({ + propsData: { + ...propsData, + }, + store, + }); + store.commit( + `monitoringDashboard/${types.RECEIVE_METRICS_DATA_SUCCESS}`, + MonitoringMock.data, + ); + [mockGraphData] = component.$store.state.monitoringDashboard.groups[0].metrics; + }); + + describe('csvText', () => { + it('converts metrics data from json to csv', () => { + const header = `timestamp,${mockGraphData.y_label}`; + const data = mockGraphData.queries[0].result[0].values; + const firstRow = `${data[0][0]},${data[0][1]}`; + + expect(component.csvText(mockGraphData)).toMatch(`^${header}\r\n${firstRow}`); + }); + }); + + describe('downloadCsv', () => { + it('produces a link with a Blob', () => { + expect(component.downloadCsv(mockGraphData)).toContain(`blob:`); + }); + }); + }); }); |