Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.com/gitlab-org/gitlab-foss.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'app/assets/javascripts/pipelines/components/pipelines_list/failure_widget/pipeline_failed_jobs_widget.vue')
-rw-r--r--app/assets/javascripts/pipelines/components/pipelines_list/failure_widget/pipeline_failed_jobs_widget.vue143
1 files changed, 143 insertions, 0 deletions
diff --git a/app/assets/javascripts/pipelines/components/pipelines_list/failure_widget/pipeline_failed_jobs_widget.vue b/app/assets/javascripts/pipelines/components/pipelines_list/failure_widget/pipeline_failed_jobs_widget.vue
new file mode 100644
index 00000000000..fce0b5f525e
--- /dev/null
+++ b/app/assets/javascripts/pipelines/components/pipelines_list/failure_widget/pipeline_failed_jobs_widget.vue
@@ -0,0 +1,143 @@
+<script>
+import {
+ GlButton,
+ GlCollapse,
+ GlIcon,
+ GlLink,
+ GlLoadingIcon,
+ GlPopover,
+ GlSprintf,
+} from '@gitlab/ui';
+import { createAlert } from '~/alert';
+import { __, s__ } from '~/locale';
+import getPipelineFailedJobs from '../../../graphql/queries/get_pipeline_failed_jobs.query.graphql';
+import WidgetFailedJobRow from './widget_failed_job_row.vue';
+import { sortJobsByStatus } from './utils';
+
+const JOB_ID_HEADER = __('Job ID');
+const JOB_NAME_HEADER = __('Job name');
+const STAGE_HEADER = __('Stage');
+
+export default {
+ components: {
+ GlButton,
+ GlCollapse,
+ GlIcon,
+ GlLink,
+ GlLoadingIcon,
+ GlPopover,
+ GlSprintf,
+ WidgetFailedJobRow,
+ },
+ inject: ['fullPath'],
+ props: {
+ pipelineIid: {
+ required: true,
+ type: Number,
+ },
+ pipelinePath: {
+ required: true,
+ type: String,
+ },
+ },
+ data() {
+ return {
+ failedJobs: [],
+ isExpanded: false,
+ };
+ },
+ apollo: {
+ failedJobs: {
+ query: getPipelineFailedJobs,
+ skip() {
+ return !this.isExpanded;
+ },
+ variables() {
+ return {
+ fullPath: this.fullPath,
+ pipelineIid: this.pipelineIid,
+ };
+ },
+ update(data) {
+ const jobs = data?.project?.pipeline?.jobs?.nodes || [];
+ return sortJobsByStatus(jobs);
+ },
+ error(e) {
+ createAlert({ message: e?.message || this.$options.i18n.fetchError, variant: 'danger' });
+ },
+ },
+ },
+ computed: {
+ bodyClasses() {
+ return this.isExpanded ? '' : 'gl-display-none';
+ },
+ failedJobsCount() {
+ return this.failedJobs.length;
+ },
+ iconName() {
+ return this.isExpanded ? 'chevron-down' : 'chevron-right';
+ },
+ isLoading() {
+ return this.$apollo.queries.failedJobs.loading;
+ },
+ },
+ methods: {
+ toggleWidget() {
+ this.isExpanded = !this.isExpanded;
+ },
+ },
+ columns: [
+ { text: JOB_NAME_HEADER, class: 'col-6' },
+ { text: STAGE_HEADER, class: 'col-2' },
+ { text: JOB_ID_HEADER, class: 'col-2' },
+ ],
+ i18n: {
+ additionalInfoPopover: s__(
+ 'Pipelines|You will see a maximum of 100 jobs in this list. To view all failed jobs, %{linkStart}go to the details page%{linkEnd} of this pipeline.',
+ ),
+ additionalInfoTitle: __('Limitation on this view'),
+ fetchError: __('There was a problem fetching failed jobs'),
+ showFailedJobs: __('Show failed jobs'),
+ },
+};
+</script>
+<template>
+ <div class="gl-border-none!">
+ <gl-button variant="link" @click="toggleWidget">
+ <gl-icon :name="iconName" />
+ {{ $options.i18n.showFailedJobs }}
+ <gl-icon id="target" name="information-o" />
+ <gl-popover target="target" placement="top">
+ <template #title> {{ $options.i18n.additionalInfoTitle }} </template>
+ <slot>
+ <gl-sprintf :message="$options.i18n.additionalInfoPopover">
+ <template #link="{ content }">
+ <gl-link class="gl-font-sm" :href="pipelinePath"> {{ content }}</gl-link>
+ </template>
+ </gl-sprintf>
+ </slot>
+ </gl-popover>
+ </gl-button>
+ <gl-loading-icon v-if="isLoading" />
+ <gl-collapse
+ v-else
+ v-model="isExpanded"
+ class="gl-bg-gray-10 gl-border-1 gl-border-t gl-border-color-gray-100 gl-mt-4 gl-pt-3"
+ >
+ <div class="container-fluid gl-grid-tpl-rows-auto">
+ <div class="row gl-mb-6 gl-text-gray-900">
+ <div
+ v-for="col in $options.columns"
+ :key="col.text"
+ class="gl-font-weight-bold gl-text-left"
+ :class="col.class"
+ data-testid="header"
+ >
+ {{ col.text }}
+ </div>
+ </div>
+ </div>
+ <widget-failed-job-row v-for="job in failedJobs" :key="job.id" :job="job" />
+ </gl-collapse>
+ </div>
+</template>