diff options
author | GitLab Bot <gitlab-bot@gitlab.com> | 2020-08-20 21:42:06 +0300 |
---|---|---|
committer | GitLab Bot <gitlab-bot@gitlab.com> | 2020-08-20 21:42:06 +0300 |
commit | 6e4e1050d9dba2b7b2523fdd1768823ab85feef4 (patch) | |
tree | 78be5963ec075d80116a932011d695dd33910b4e /app/assets/javascripts/monitoring/stores/actions.js | |
parent | 1ce776de4ae122aba3f349c02c17cebeaa8ecf07 (diff) |
Add latest changes from gitlab-org/gitlab@13-3-stable-ee
Diffstat (limited to 'app/assets/javascripts/monitoring/stores/actions.js')
-rw-r--r-- | app/assets/javascripts/monitoring/stores/actions.js | 130 |
1 files changed, 84 insertions, 46 deletions
diff --git a/app/assets/javascripts/monitoring/stores/actions.js b/app/assets/javascripts/monitoring/stores/actions.js index a441882a47d..16a685305dc 100644 --- a/app/assets/javascripts/monitoring/stores/actions.js +++ b/app/assets/javascripts/monitoring/stores/actions.js @@ -1,7 +1,7 @@ import * as Sentry from '@sentry/browser'; import * as types from './mutation_types'; import axios from '~/lib/utils/axios_utils'; -import createFlash from '~/flash'; +import { deprecatedCreateFlash as createFlash } from '~/flash'; import { convertToFixedRange } from '~/lib/utils/datetime_range'; import { gqClient, @@ -13,16 +13,14 @@ import trackDashboardLoad from '../monitoring_tracking_helper'; import getEnvironments from '../queries/getEnvironments.query.graphql'; import getAnnotations from '../queries/getAnnotations.query.graphql'; import getDashboardValidationWarnings from '../queries/getDashboardValidationWarnings.query.graphql'; -import statusCodes from '../../lib/utils/http_status'; -import { backOff, convertObjectPropsToCamelCase } from '../../lib/utils/common_utils'; +import { convertObjectPropsToCamelCase } from '../../lib/utils/common_utils'; import { s__, sprintf } from '../../locale'; +import { getDashboard, getPrometheusQueryData } from '../requests'; -import { - PROMETHEUS_TIMEOUT, - ENVIRONMENT_AVAILABLE_STATE, - DEFAULT_DASHBOARD_PATH, - VARIABLE_TYPES, -} from '../constants'; +import { ENVIRONMENT_AVAILABLE_STATE, OVERVIEW_DASHBOARD_PATH, VARIABLE_TYPES } from '../constants'; + +const axiosCancelToken = axios.CancelToken; +let cancelTokenSource; function prometheusMetricQueryParams(timeRange) { const { start, end } = convertToFixedRange(timeRange); @@ -38,29 +36,18 @@ function prometheusMetricQueryParams(timeRange) { }; } -function backOffRequest(makeRequestCallback) { - return backOff((next, stop) => { - makeRequestCallback() - .then(resp => { - if (resp.status === statusCodes.NO_CONTENT) { - next(); - } else { - stop(resp); - } - }) - .catch(stop); - }, PROMETHEUS_TIMEOUT); -} - -function getPrometheusQueryData(prometheusEndpoint, params) { - return backOffRequest(() => axios.get(prometheusEndpoint, { params })) - .then(res => res.data) - .then(response => { - if (response.status === 'error') { - throw new Error(response.error); - } - return response.data; - }); +/** + * Extract error messages from API or HTTP request errors. + * + * - API errors are in `error.response.data.message` + * - HTTP (axios) errors are in `error.messsage` + * + * @param {Object} error + * @returns {String} User friendly error message + */ +function extractErrorMessage(error) { + const message = error?.response?.data?.message; + return message ?? error.message; } // Setup @@ -126,8 +113,7 @@ export const fetchDashboard = ({ state, commit, dispatch, getters }) => { params.dashboard = getters.fullDashboardPath; } - return backOffRequest(() => axios.get(state.dashboardEndpoint, { params })) - .then(resp => resp.data) + return getDashboard(state.dashboardEndpoint, params) .then(response => { dispatch('receiveMetricsDashboardSuccess', { response }); /** @@ -329,7 +315,7 @@ export const receiveEnvironmentsDataFailure = ({ commit }) => { export const fetchAnnotations = ({ state, dispatch, getters }) => { const { start } = convertToFixedRange(state.timeRange); - const dashboardPath = getters.fullDashboardPath || DEFAULT_DASHBOARD_PATH; + const dashboardPath = getters.fullDashboardPath || OVERVIEW_DASHBOARD_PATH; return gqClient .mutate({ mutation: getAnnotations, @@ -362,12 +348,12 @@ export const receiveAnnotationsFailure = ({ commit }) => commit(types.RECEIVE_AN export const fetchDashboardValidationWarnings = ({ state, dispatch, getters }) => { /** - * Normally, the default dashboard won't throw any validation warnings. + * Normally, the overview dashboard won't throw any validation warnings. * - * However, if a bug sneaks into the default dashboard making it invalid, + * However, if a bug sneaks into the overview dashboard making it invalid, * this might come handy for our clients */ - const dashboardPath = getters.fullDashboardPath || DEFAULT_DASHBOARD_PATH; + const dashboardPath = getters.fullDashboardPath || OVERVIEW_DASHBOARD_PATH; return gqClient .mutate({ mutation: getDashboardValidationWarnings, @@ -484,12 +470,10 @@ export const fetchVariableMetricLabelValues = ({ state, commit }, { defaultQuery if (variable.type === VARIABLE_TYPES.metric_label_values) { const { prometheusEndpointPath, label } = variable.options; - const optionsRequest = backOffRequest(() => - axios.get(prometheusEndpointPath, { - params: { start_time, end_time }, - }), - ) - .then(({ data }) => data.data) + const optionsRequest = getPrometheusQueryData(prometheusEndpointPath, { + start_time, + end_time, + }) .then(data => { commit(types.UPDATE_VARIABLE_METRIC_LABEL_VALUES, { variable, label, data }); }) @@ -507,5 +491,59 @@ export const fetchVariableMetricLabelValues = ({ state, commit }, { defaultQuery return Promise.all(optionsRequests); }; -// prevent babel-plugin-rewire from generating an invalid default during karma tests -export default () => {}; +// Panel Builder + +export const setPanelPreviewTimeRange = ({ commit }, timeRange) => { + commit(types.SET_PANEL_PREVIEW_TIME_RANGE, timeRange); +}; + +export const fetchPanelPreview = ({ state, commit, dispatch }, panelPreviewYml) => { + if (!panelPreviewYml) { + return null; + } + + commit(types.SET_PANEL_PREVIEW_IS_SHOWN, true); + commit(types.REQUEST_PANEL_PREVIEW, panelPreviewYml); + + return axios + .post(state.panelPreviewEndpoint, { panel_yaml: panelPreviewYml }) + .then(({ data }) => { + commit(types.RECEIVE_PANEL_PREVIEW_SUCCESS, data); + + dispatch('fetchPanelPreviewMetrics'); + }) + .catch(error => { + commit(types.RECEIVE_PANEL_PREVIEW_FAILURE, extractErrorMessage(error)); + }); +}; + +export const fetchPanelPreviewMetrics = ({ state, commit }) => { + if (cancelTokenSource) { + cancelTokenSource.cancel(); + } + cancelTokenSource = axiosCancelToken.source(); + + const defaultQueryParams = prometheusMetricQueryParams(state.panelPreviewTimeRange); + + state.panelPreviewGraphData.metrics.forEach((metric, index) => { + commit(types.REQUEST_PANEL_PREVIEW_METRIC_RESULT, { index }); + + const params = { ...defaultQueryParams }; + if (metric.step) { + params.step = metric.step; + } + return getPrometheusQueryData(metric.prometheusEndpointPath, params, { + cancelToken: cancelTokenSource.token, + }) + .then(data => { + commit(types.RECEIVE_PANEL_PREVIEW_METRIC_RESULT_SUCCESS, { index, data }); + }) + .catch(error => { + Sentry.captureException(error); + + commit(types.RECEIVE_PANEL_PREVIEW_METRIC_RESULT_FAILURE, { index, error }); + // Continue to throw error so the panel builder can notify using createFlash + throw error; + }); + }); +}; |