diff options
author | GitLab Bot <gitlab-bot@gitlab.com> | 2022-02-21 12:15:42 +0300 |
---|---|---|
committer | GitLab Bot <gitlab-bot@gitlab.com> | 2022-02-21 12:15:42 +0300 |
commit | 0976c2c3d9b722acce50120ea4a09d0e83f50d6e (patch) | |
tree | ee47e57f2cbf58dd8ab21461d2255baa932f1c08 /app/assets/javascripts/runner | |
parent | 803fa8d1c797a089c4350988e89180340577a601 (diff) |
Add latest changes from gitlab-org/gitlab@master
Diffstat (limited to 'app/assets/javascripts/runner')
3 files changed, 152 insertions, 100 deletions
diff --git a/app/assets/javascripts/runner/components/cells/runner_actions_cell.vue b/app/assets/javascripts/runner/components/cells/runner_actions_cell.vue index ae9c774f2a2..eb50899ddb7 100644 --- a/app/assets/javascripts/runner/components/cells/runner_actions_cell.vue +++ b/app/assets/javascripts/runner/components/cells/runner_actions_cell.vue @@ -1,29 +1,16 @@ <script> -import { GlButton, GlButtonGroup, GlModalDirective, GlTooltipDirective } from '@gitlab/ui'; -import { createAlert } from '~/flash'; -import { s__, sprintf } from '~/locale'; -import runnerDeleteMutation from '~/runner/graphql/runner_delete.mutation.graphql'; -import { captureException } from '~/runner/sentry_utils'; -import { getIdFromGraphQLId } from '~/graphql_shared/utils'; +import { GlButtonGroup } from '@gitlab/ui'; import RunnerEditButton from '../runner_edit_button.vue'; import RunnerPauseButton from '../runner_pause_button.vue'; -import RunnerDeleteModal from '../runner_delete_modal.vue'; - -const I18N_DELETE = s__('Runners|Delete runner'); -const I18N_DELETED_TOAST = s__('Runners|Runner %{name} was deleted'); +import RunnerDeleteButton from '../runner_delete_button.vue'; export default { name: 'RunnerActionsCell', components: { - GlButton, GlButtonGroup, RunnerEditButton, RunnerPauseButton, - RunnerDeleteModal, - }, - directives: { - GlTooltip: GlTooltipDirective, - GlModal: GlModalDirective, + RunnerDeleteButton, }, props: { runner: { @@ -31,30 +18,7 @@ export default { required: true, }, }, - data() { - return { - updating: false, - deleting: false, - }; - }, computed: { - deleteTitle() { - if (this.deleting) { - // Prevent a "sticky" tooltip: If this button is disabled, - // mouseout listeners don't run leaving the tooltip stuck - return ''; - } - return I18N_DELETE; - }, - runnerId() { - return getIdFromGraphQLId(this.runner.id); - }, - runnerName() { - return `#${this.runnerId} (${this.runner.shortSha})`; - }, - runnerDeleteModalId() { - return `delete-runner-modal-${this.runnerId}`; - }, canUpdate() { return this.runner.userPermissions?.updateRunner; }, @@ -62,49 +26,6 @@ export default { return this.runner.userPermissions?.deleteRunner; }, }, - methods: { - async onDelete() { - // Deleting stays "true" until this row is removed, - // should only change back if the operation fails. - this.deleting = true; - try { - const { - data: { - runnerDelete: { errors }, - }, - } = await this.$apollo.mutate({ - mutation: runnerDeleteMutation, - variables: { - input: { - id: this.runner.id, - }, - }, - awaitRefetchQueries: true, - refetchQueries: ['getRunners', 'getGroupRunners'], - }); - if (errors && errors.length) { - throw new Error(errors.join(' ')); - } else { - // Use $root to have the toast message stay after this element is removed - this.$root.$toast?.show(sprintf(I18N_DELETED_TOAST, { name: this.runnerName })); - } - } catch (e) { - this.deleting = false; - this.onError(e); - } - }, - - onError(error) { - const { message } = error; - createAlert({ message }); - - this.reportToSentry(error); - }, - reportToSentry(error) { - captureException({ error, component: this.$options.name }); - }, - }, - I18N_DELETE, }; </script> @@ -119,23 +40,6 @@ export default { --> <runner-edit-button v-if="canUpdate && runner.editAdminUrl" :href="runner.editAdminUrl" /> <runner-pause-button v-if="canUpdate" :runner="runner" :compact="true" /> - <gl-button - v-if="canDelete" - v-gl-tooltip.hover.viewport="deleteTitle" - v-gl-modal="runnerDeleteModalId" - :aria-label="deleteTitle" - icon="close" - :loading="deleting" - variant="danger" - data-testid="delete-runner" - /> - - <runner-delete-modal - v-if="canDelete" - :ref="runnerDeleteModalId" - :modal-id="runnerDeleteModalId" - :runner-name="runnerName" - @primary="onDelete" - /> + <runner-delete-button v-if="canDelete" :runner="runner" :compact="true" /> </gl-button-group> </template> diff --git a/app/assets/javascripts/runner/components/runner_delete_button.vue b/app/assets/javascripts/runner/components/runner_delete_button.vue new file mode 100644 index 00000000000..0ff1f93b1df --- /dev/null +++ b/app/assets/javascripts/runner/components/runner_delete_button.vue @@ -0,0 +1,147 @@ +<script> +import { GlButton, GlModalDirective, GlTooltipDirective } from '@gitlab/ui'; +import runnerDeleteMutation from '~/runner/graphql/runner_delete.mutation.graphql'; +import { createAlert } from '~/flash'; +import { s__, sprintf } from '~/locale'; +import { captureException } from '~/runner/sentry_utils'; +import { getIdFromGraphQLId } from '~/graphql_shared/utils'; +import { I18N_DELETE_RUNNER } from '../constants'; +import RunnerDeleteModal from './runner_delete_modal.vue'; + +const I18N_DELETED_TOAST = s__('Runners|Runner %{name} was deleted'); + +export default { + name: 'RunnerDeleteButton', + components: { + GlButton, + RunnerDeleteModal, + }, + directives: { + GlTooltip: GlTooltipDirective, + GlModal: GlModalDirective, + }, + props: { + runner: { + type: Object, + required: true, + validator: (runner) => { + return runner?.id && runner?.shortSha; + }, + }, + compact: { + type: Boolean, + required: false, + default: false, + }, + }, + data() { + return { + deleting: false, + }; + }, + computed: { + runnerId() { + return getIdFromGraphQLId(this.runner.id); + }, + runnerName() { + return `#${this.runnerId} (${this.runner.shortSha})`; + }, + runnerDeleteModalId() { + return `delete-runner-modal-${this.runnerId}`; + }, + icon() { + if (this.compact) { + return 'close'; + } + return ''; + }, + buttonContent() { + if (this.compact) { + return null; + } + return I18N_DELETE_RUNNER; + }, + buttonClass() { + // Ensure a square button is shown when compact: true. + // Without this class we will have distorted/rectangular button. + if (this.compact) { + return 'btn-icon'; + } + return null; + }, + ariaLabel() { + if (this.compact) { + return I18N_DELETE_RUNNER; + } + return null; + }, + tooltip() { + // Only show tooltip when compact. + // Also prevent a "sticky" tooltip: If this button is + // disabled, mouseout listeners don't run leaving the tooltip stuck + if (this.compact && !this.deleting) { + return I18N_DELETE_RUNNER; + } + return ''; + }, + }, + methods: { + async onDelete() { + // Deleting stays "true" until this row is removed, + // should only change back if the operation fails. + this.deleting = true; + try { + const { + data: { + runnerDelete: { errors }, + }, + } = await this.$apollo.mutate({ + mutation: runnerDeleteMutation, + variables: { + input: { + id: this.runner.id, + }, + }, + refetchQueries: ['getRunners', 'getGroupRunners'], + }); + if (errors && errors.length) { + throw new Error(errors.join(' ')); + } else { + this.$root.$toast?.show(sprintf(I18N_DELETED_TOAST, { name: this.runnerName })); + } + } catch (e) { + this.deleting = false; + this.onError(e); + } + }, + onError(error) { + const { message } = error; + createAlert({ message }); + + this.reportToSentry(error); + }, + reportToSentry(error) { + captureException({ error, component: this.$options.name }); + }, + }, +}; +</script> + +<template> + <gl-button + v-gl-tooltip.hover.viewport="tooltip" + v-gl-modal="runnerDeleteModalId" + :aria-label="ariaLabel" + :icon="icon" + :class="buttonClass" + :loading="deleting" + variant="danger" + > + {{ buttonContent }} + <runner-delete-modal + :modal-id="runnerDeleteModalId" + :runner-name="runnerName" + @primary="onDelete" + /> + </gl-button> +</template> diff --git a/app/assets/javascripts/runner/constants.js b/app/assets/javascripts/runner/constants.js index d88c2c0f919..4120753dc95 100644 --- a/app/assets/javascripts/runner/constants.js +++ b/app/assets/javascripts/runner/constants.js @@ -38,6 +38,7 @@ export const I18N_STALE_RUNNER_DESCRIPTION = s__( // Active flag export const I18N_PAUSE = __('Pause'); export const I18N_RESUME = __('Resume'); +export const I18N_DELETE_RUNNER = s__('Runners|Delete runner'); export const I18N_LOCKED_RUNNER_DESCRIPTION = s__('Runners|You cannot assign to other projects'); export const I18N_PAUSED_RUNNER_DESCRIPTION = s__('Runners|Not available to run jobs'); |