diff options
author | GitLab Bot <gitlab-bot@gitlab.com> | 2020-06-18 11:18:50 +0000 |
---|---|---|
committer | GitLab Bot <gitlab-bot@gitlab.com> | 2020-06-18 11:18:50 +0000 |
commit | 8c7f4e9d5f36cff46365a7f8c4b9c21578c1e781 (patch) | |
tree | a77e7fe7a93de11213032ed4ab1f33a3db51b738 /app/assets/javascripts/pages/projects | |
parent | 00b35af3db1abfe813a778f643dad221aad51fca (diff) | |
download | gitlab-ce-8c7f4e9d5f36cff46365a7f8c4b9c21578c1e781.tar.gz |
Add latest changes from gitlab-org/gitlab@13-1-stable-ee
Diffstat (limited to 'app/assets/javascripts/pages/projects')
17 files changed, 321 insertions, 255 deletions
diff --git a/app/assets/javascripts/pages/projects/clusters/index.js b/app/assets/javascripts/pages/projects/clusters/index.js new file mode 100644 index 00000000000..4d04c37caa7 --- /dev/null +++ b/app/assets/javascripts/pages/projects/clusters/index.js @@ -0,0 +1,5 @@ +import initCreateCluster from '~/create_cluster/init_create_cluster'; + +document.addEventListener('DOMContentLoaded', () => { + initCreateCluster(document, gon); +}); diff --git a/app/assets/javascripts/pages/projects/edit/index.js b/app/assets/javascripts/pages/projects/edit/index.js index c9dbe576c4b..9fb07917f9b 100644 --- a/app/assets/javascripts/pages/projects/edit/index.js +++ b/app/assets/javascripts/pages/projects/edit/index.js @@ -4,12 +4,12 @@ import setupTransferEdit from '~/transfer_edit'; import initConfirmDangerModal from '~/confirm_danger_modal'; import mountBadgeSettings from '~/pages/shared/mount_badge_settings'; import dirtySubmitFactory from '~/dirty_submit/dirty_submit_factory'; -import initAvatarPicker from '~/avatar_picker'; +import initFilePickers from '~/file_pickers'; import initProjectLoadingSpinner from '../shared/save_project_loader'; import initProjectPermissionsSettings from '../shared/permissions'; document.addEventListener('DOMContentLoaded', () => { - initAvatarPicker(); + initFilePickers(); initConfirmDangerModal(); initSettingsPanels(); mountBadgeSettings(PROJECT_BADGE); diff --git a/app/assets/javascripts/pages/projects/environments/metrics/index.js b/app/assets/javascripts/pages/projects/environments/metrics/index.js index 31ec4e29ad2..d3028aec313 100644 --- a/app/assets/javascripts/pages/projects/environments/metrics/index.js +++ b/app/assets/javascripts/pages/projects/environments/metrics/index.js @@ -1,3 +1,3 @@ -import monitoringBundle from '~/monitoring/monitoring_bundle_with_alerts'; +import monitoringApp from '~/monitoring/monitoring_app'; -document.addEventListener('DOMContentLoaded', monitoringBundle); +document.addEventListener('DOMContentLoaded', monitoringApp); diff --git a/app/assets/javascripts/pages/projects/graphs/charts/index.js b/app/assets/javascripts/pages/projects/graphs/charts/index.js index 803f4e37705..03504fba1ae 100644 --- a/app/assets/javascripts/pages/projects/graphs/charts/index.js +++ b/app/assets/javascripts/pages/projects/graphs/charts/index.js @@ -1,10 +1,12 @@ import Vue from 'vue'; import { __ } from '~/locale'; import { GlColumnChart } from '@gitlab/ui/dist/charts'; +import CodeCoverage from '../components/code_coverage.vue'; import SeriesDataMixin from './series_data_mixin'; document.addEventListener('DOMContentLoaded', () => { const languagesContainer = document.getElementById('js-languages-chart'); + const codeCoverageContainer = document.getElementById('js-code-coverage-chart'); const monthContainer = document.getElementById('js-month-chart'); const weekdayContainer = document.getElementById('js-weekday-chart'); const hourContainer = document.getElementById('js-hour-chart'); @@ -59,6 +61,18 @@ document.addEventListener('DOMContentLoaded', () => { // eslint-disable-next-line no-new new Vue({ + el: codeCoverageContainer, + render(h) { + return h(CodeCoverage, { + props: { + graphEndpoint: codeCoverageContainer.dataset?.graphEndpoint, + }, + }); + }, + }); + + // eslint-disable-next-line no-new + new Vue({ el: monthContainer, components: { GlColumnChart, diff --git a/app/assets/javascripts/pages/projects/graphs/components/code_coverage.vue b/app/assets/javascripts/pages/projects/graphs/components/code_coverage.vue new file mode 100644 index 00000000000..af8fb032c22 --- /dev/null +++ b/app/assets/javascripts/pages/projects/graphs/components/code_coverage.vue @@ -0,0 +1,177 @@ +<script> +import { GlAlert, GlDropdown, GlDropdownItem, GlIcon, GlSprintf } from '@gitlab/ui'; +import { GlAreaChart } from '@gitlab/ui/dist/charts'; +import dateFormat from 'dateformat'; +import axios from '~/lib/utils/axios_utils'; +import { get } from 'lodash'; + +import { __ } from '~/locale'; + +export default { + components: { + GlAlert, + GlAreaChart, + GlDropdown, + GlDropdownItem, + GlIcon, + GlSprintf, + }, + props: { + graphEndpoint: { + type: String, + required: true, + }, + }, + data() { + return { + dailyCoverageData: [], + hasFetchError: false, + isLoading: true, + selectedCoverageIndex: 0, + tooltipTitle: '', + coveragePercentage: '', + chartOptions: { + yAxis: { + name: __('Bi-weekly code coverage'), + type: 'value', + min: 0, + max: 100, + }, + xAxis: { + name: '', + type: 'category', + }, + }, + }; + }, + computed: { + hasData() { + return this.dailyCoverageData.length > 0; + }, + isReady() { + return !this.isLoading && !this.hasFetchError; + }, + canShowData() { + return this.isReady && this.hasData; + }, + noDataAvailable() { + return this.isReady && !this.hasData; + }, + selectedDailyCoverage() { + return this.hasData && this.dailyCoverageData[this.selectedCoverageIndex]; + }, + selectedDailyCoverageName() { + return this.selectedDailyCoverage?.group_name; + }, + formattedData() { + if (this.selectedDailyCoverage?.data) { + return this.selectedDailyCoverage.data.map(value => [ + dateFormat(value.date, 'mmm dd'), + value.coverage, + ]); + } + + // If the fetching failed, we return an empty array which + // allow the graph to render while empty + return []; + }, + chartData() { + return [ + { + // The default string 'data' will get shown in the legend if we fail to fetch the data + name: this.canShowData ? this.selectedDailyCoverageName : __('data'), + data: this.formattedData, + type: 'line', + smooth: true, + }, + ]; + }, + }, + created() { + axios + .get(this.graphEndpoint) + .then(({ data }) => { + this.dailyCoverageData = data; + }) + .catch(() => { + this.hasFetchError = true; + }) + .finally(() => { + this.isLoading = false; + }); + }, + methods: { + setSelectedCoverage(index) { + this.selectedCoverageIndex = index; + }, + formatTooltipText(params) { + this.tooltipTitle = params.value; + this.coveragePercentage = get(params, 'seriesData[0].data[1]', ''); + }, + }, + height: 200, +}; +</script> + +<template> + <div> + <div class="gl-mt-3 gl-mb-3"> + <gl-alert + v-if="hasFetchError" + variant="danger" + :title="s__('Code Coverage|Couldn\'t fetch the code coverage data')" + :dismissible="false" + /> + <gl-alert + v-if="noDataAvailable" + variant="info" + :title="s__('Code Coverage| Empty code coverage data')" + :dismissible="false" + > + <span> + {{ __('It seems that there is currently no available data for code coverage') }} + </span> + </gl-alert> + <gl-dropdown v-if="canShowData" :text="selectedDailyCoverageName"> + <gl-dropdown-item + v-for="({ group_name }, index) in dailyCoverageData" + :key="index" + :value="group_name" + @click="setSelectedCoverage(index)" + > + <div class="gl-display-flex"> + <gl-icon + v-if="index === selectedCoverageIndex" + name="mobile-issue-close" + class="gl-absolute" + /> + <span class="gl-display-flex align-items-center ml-4"> + {{ group_name }} + </span> + </div> + </gl-dropdown-item> + </gl-dropdown> + </div> + <gl-area-chart + v-if="!isLoading" + :height="$options.height" + :data="chartData" + :option="chartOptions" + :format-tooltip-text="formatTooltipText" + > + <template v-if="canShowData" #tooltipTitle> + {{ tooltipTitle }} + </template> + <template v-if="canShowData" #tooltipContent> + <gl-sprintf :message="__('Code Coverage: %{coveragePercentage}%{percentSymbol}')"> + <template #coveragePercentage> + {{ coveragePercentage }} + </template> + <template #percentSymbol> + % + </template> + </gl-sprintf> + </template> + </gl-area-chart> + </div> +</template> diff --git a/app/assets/javascripts/pages/projects/index.js b/app/assets/javascripts/pages/projects/index.js index 190d0806c28..8e0af018b61 100644 --- a/app/assets/javascripts/pages/projects/index.js +++ b/app/assets/javascripts/pages/projects/index.js @@ -1,10 +1,7 @@ import Project from './project'; import ShortcutsNavigation from '../../behaviors/shortcuts/shortcuts_navigation'; -import initCreateCluster from '~/create_cluster/init_create_cluster'; document.addEventListener('DOMContentLoaded', () => { - initCreateCluster(document, gon); - new Project(); // eslint-disable-line no-new new ShortcutsNavigation(); // eslint-disable-line no-new }); diff --git a/app/assets/javascripts/pages/projects/issues/index/index.js b/app/assets/javascripts/pages/projects/issues/index/index.js index e8e0cda2139..a66b665d152 100644 --- a/app/assets/javascripts/pages/projects/issues/index/index.js +++ b/app/assets/javascripts/pages/projects/issues/index/index.js @@ -9,6 +9,7 @@ import { FILTERED_SEARCH } from '~/pages/constants'; import { ISSUABLE_INDEX } from '~/pages/projects/constants'; import initIssuablesList from '~/issuables_list'; import initManualOrdering from '~/manual_ordering'; +import { showLearnGitLabIssuesPopover } from '~/onboarding_issues'; document.addEventListener('DOMContentLoaded', () => { IssuableFilteredSearchTokenKeys.addExtraTokensForIssues(); @@ -24,4 +25,5 @@ document.addEventListener('DOMContentLoaded', () => { initManualOrdering(); initIssuablesList(); + showLearnGitLabIssuesPopover(); }); diff --git a/app/assets/javascripts/pages/projects/labels/components/promote_label_modal.vue b/app/assets/javascripts/pages/projects/labels/components/promote_label_modal.vue index 3b26047455d..08078fa6b62 100644 --- a/app/assets/javascripts/pages/projects/labels/components/promote_label_modal.vue +++ b/app/assets/javascripts/pages/projects/labels/components/promote_label_modal.vue @@ -90,7 +90,7 @@ export default { footer-primary-button-variant="warning" @submit="onSubmit" > - <div slot="title" class="modal-title-with-label" v-html="title">{{ title }}</div> + <div slot="title" class="modal-title-with-label" v-html="title"></div> {{ text }} </gl-modal> diff --git a/app/assets/javascripts/pages/projects/merge_requests/show/index.js b/app/assets/javascripts/pages/projects/merge_requests/show/index.js index ddc648702f1..4708970efef 100644 --- a/app/assets/javascripts/pages/projects/merge_requests/show/index.js +++ b/app/assets/javascripts/pages/projects/merge_requests/show/index.js @@ -1,4 +1,5 @@ import initMrNotes from '~/mr_notes'; +import { initReviewBar } from '~/batch_comments'; import initSidebarBundle from '~/sidebar/sidebar_bundle'; import initShow from '../init_merge_request_show'; @@ -8,4 +9,5 @@ document.addEventListener('DOMContentLoaded', () => { initSidebarBundle(); } initMrNotes(); + initReviewBar(); }); diff --git a/app/assets/javascripts/pages/projects/new/index.js b/app/assets/javascripts/pages/projects/new/index.js index 097403ba9e2..e17059dd55a 100644 --- a/app/assets/javascripts/pages/projects/new/index.js +++ b/app/assets/javascripts/pages/projects/new/index.js @@ -1,7 +1,46 @@ import initProjectVisibilitySelector from '../../../project_visibility'; import initProjectNew from '../../../projects/project_new'; +import { __ } from '~/locale'; +import createFlash from '~/flash'; +import Tracking from '~/tracking'; document.addEventListener('DOMContentLoaded', () => { initProjectVisibilitySelector(); initProjectNew.bindEvents(); + + const { category, property } = gon.tracking_data ?? { category: 'projects:new' }; + const hasNewCreateProjectUi = 'newCreateProjectUi' in gon?.features; + + if (!hasNewCreateProjectUi) { + // Setting additional tracking for HAML template + + Array.from( + document.querySelectorAll('.project-edit-container [data-experiment-track-label]'), + ).forEach(node => + node.addEventListener('click', event => { + const { experimentTrackLabel: label } = event.currentTarget.dataset; + Tracking.event(category, 'click_tab', { property, label }); + }), + ); + } else { + import( + /* webpackChunkName: 'experiment_new_project_creation' */ '../../../projects/experiment_new_project_creation' + ) + .then(m => { + const el = document.querySelector('.js-experiment-new-project-creation'); + + if (!el) { + return; + } + + const config = { + hasErrors: 'hasErrors' in el.dataset, + isCiCdAvailable: 'isCiCdAvailable' in el.dataset, + }; + m.default(el, config); + }) + .catch(() => { + createFlash(__('An error occurred while loading project creation UI')); + }); + } }); diff --git a/app/assets/javascripts/pages/projects/pipelines/index/index.js b/app/assets/javascripts/pages/projects/pipelines/index/index.js index bbad3238ec4..2c37d7da4a7 100644 --- a/app/assets/javascripts/pages/projects/pipelines/index/index.js +++ b/app/assets/javascripts/pages/projects/pipelines/index/index.js @@ -51,6 +51,7 @@ document.addEventListener( ciLintPath: this.dataset.ciLintPath, resetCachePath: this.dataset.resetCachePath, projectId: this.dataset.projectId, + params: JSON.parse(this.dataset.params), }, }); }, diff --git a/app/assets/javascripts/pages/projects/shared/permissions/components/settings_panel.vue b/app/assets/javascripts/pages/projects/shared/permissions/components/settings_panel.vue index ab32fe18972..7181332a1d6 100644 --- a/app/assets/javascripts/pages/projects/shared/permissions/components/settings_panel.vue +++ b/app/assets/javascripts/pages/projects/shared/permissions/components/settings_panel.vue @@ -46,7 +46,11 @@ export default { allowedVisibilityOptions: { type: Array, required: false, - default: () => [0, 10, 20], + default: () => [ + visibilityOptions.PRIVATE, + visibilityOptions.INTERNAL, + visibilityOptions.PUBLIC, + ], }, lfsAvailable: { type: Boolean, @@ -118,16 +122,14 @@ export default { const defaults = { visibilityOptions, visibilityLevel: visibilityOptions.PUBLIC, - // TODO: Change all of these to use the visibilityOptions constants - // https://gitlab.com/gitlab-org/gitlab/-/issues/214667 - issuesAccessLevel: 20, - repositoryAccessLevel: 20, - forkingAccessLevel: 20, - mergeRequestsAccessLevel: 20, - buildsAccessLevel: 20, - wikiAccessLevel: 20, - snippetsAccessLevel: 20, - pagesAccessLevel: 20, + issuesAccessLevel: featureAccessLevel.EVERYONE, + repositoryAccessLevel: featureAccessLevel.EVERYONE, + forkingAccessLevel: featureAccessLevel.EVERYONE, + mergeRequestsAccessLevel: featureAccessLevel.EVERYONE, + buildsAccessLevel: featureAccessLevel.EVERYONE, + wikiAccessLevel: featureAccessLevel.EVERYONE, + snippetsAccessLevel: featureAccessLevel.EVERYONE, + pagesAccessLevel: featureAccessLevel.EVERYONE, metricsDashboardAccessLevel: featureAccessLevel.PROJECT_MEMBERS, containerRegistryEnabled: true, lfsEnabled: true, @@ -180,7 +182,7 @@ export default { }, repositoryEnabled() { - return this.repositoryAccessLevel > 0; + return this.repositoryAccessLevel > featureAccessLevel.NOT_ENABLED; }, visibilityLevelDescription() { @@ -206,40 +208,70 @@ export default { visibilityLevel(value, oldValue) { if (value === visibilityOptions.PRIVATE) { // when private, features are restricted to "only team members" - this.issuesAccessLevel = Math.min(10, this.issuesAccessLevel); - this.repositoryAccessLevel = Math.min(10, this.repositoryAccessLevel); - this.mergeRequestsAccessLevel = Math.min(10, this.mergeRequestsAccessLevel); - this.buildsAccessLevel = Math.min(10, this.buildsAccessLevel); - this.wikiAccessLevel = Math.min(10, this.wikiAccessLevel); - this.snippetsAccessLevel = Math.min(10, this.snippetsAccessLevel); - this.metricsDashboardAccessLevel = Math.min(10, this.metricsDashboardAccessLevel); - if (this.pagesAccessLevel === 20) { + this.issuesAccessLevel = Math.min( + featureAccessLevel.PROJECT_MEMBERS, + this.issuesAccessLevel, + ); + this.repositoryAccessLevel = Math.min( + featureAccessLevel.PROJECT_MEMBERS, + this.repositoryAccessLevel, + ); + this.mergeRequestsAccessLevel = Math.min( + featureAccessLevel.PROJECT_MEMBERS, + this.mergeRequestsAccessLevel, + ); + this.buildsAccessLevel = Math.min( + featureAccessLevel.PROJECT_MEMBERS, + this.buildsAccessLevel, + ); + this.wikiAccessLevel = Math.min(featureAccessLevel.PROJECT_MEMBERS, this.wikiAccessLevel); + this.snippetsAccessLevel = Math.min( + featureAccessLevel.PROJECT_MEMBERS, + this.snippetsAccessLevel, + ); + this.metricsDashboardAccessLevel = Math.min( + featureAccessLevel.PROJECT_MEMBERS, + this.metricsDashboardAccessLevel, + ); + if (this.pagesAccessLevel === featureAccessLevel.EVERYONE) { // When from Internal->Private narrow access for only members - this.pagesAccessLevel = 10; + this.pagesAccessLevel = featureAccessLevel.PROJECT_MEMBERS; } this.highlightChanges(); } else if (oldValue === visibilityOptions.PRIVATE) { // if changing away from private, make enabled features more permissive - if (this.issuesAccessLevel > 0) this.issuesAccessLevel = 20; - if (this.repositoryAccessLevel > 0) this.repositoryAccessLevel = 20; - if (this.mergeRequestsAccessLevel > 0) this.mergeRequestsAccessLevel = 20; - if (this.buildsAccessLevel > 0) this.buildsAccessLevel = 20; - if (this.wikiAccessLevel > 0) this.wikiAccessLevel = 20; - if (this.snippetsAccessLevel > 0) this.snippetsAccessLevel = 20; - if (this.pagesAccessLevel === 10) this.pagesAccessLevel = 20; - if (this.metricsDashboardAccessLevel === 10) this.metricsDashboardAccessLevel = 20; + if (this.issuesAccessLevel > featureAccessLevel.NOT_ENABLED) + this.issuesAccessLevel = featureAccessLevel.EVERYONE; + if (this.repositoryAccessLevel > featureAccessLevel.NOT_ENABLED) + this.repositoryAccessLevel = featureAccessLevel.EVERYONE; + if (this.mergeRequestsAccessLevel > featureAccessLevel.NOT_ENABLED) + this.mergeRequestsAccessLevel = featureAccessLevel.EVERYONE; + if (this.buildsAccessLevel > featureAccessLevel.NOT_ENABLED) + this.buildsAccessLevel = featureAccessLevel.EVERYONE; + if (this.wikiAccessLevel > featureAccessLevel.NOT_ENABLED) + this.wikiAccessLevel = featureAccessLevel.EVERYONE; + if (this.snippetsAccessLevel > featureAccessLevel.NOT_ENABLED) + this.snippetsAccessLevel = featureAccessLevel.EVERYONE; + if (this.pagesAccessLevel === featureAccessLevel.PROJECT_MEMBERS) + this.pagesAccessLevel = featureAccessLevel.EVERYONE; + if (this.metricsDashboardAccessLevel === featureAccessLevel.PROJECT_MEMBERS) + this.metricsDashboardAccessLevel = featureAccessLevel.EVERYONE; this.highlightChanges(); } }, issuesAccessLevel(value, oldValue) { - if (value === 0) toggleHiddenClassBySelector('.issues-feature', true); - else if (oldValue === 0) toggleHiddenClassBySelector('.issues-feature', false); + if (value === featureAccessLevel.NOT_ENABLED) + toggleHiddenClassBySelector('.issues-feature', true); + else if (oldValue === featureAccessLevel.NOT_ENABLED) + toggleHiddenClassBySelector('.issues-feature', false); }, mergeRequestsAccessLevel(value, oldValue) { - if (value === 0) toggleHiddenClassBySelector('.merge-requests-feature', true); - else if (oldValue === 0) toggleHiddenClassBySelector('.merge-requests-feature', false); + if (value === featureAccessLevel.NOT_ENABLED) + toggleHiddenClassBySelector('.merge-requests-feature', true); + else if (oldValue === featureAccessLevel.NOT_ENABLED) + toggleHiddenClassBySelector('.merge-requests-feature', false); }, }, diff --git a/app/assets/javascripts/pages/projects/show/index.js b/app/assets/javascripts/pages/projects/show/index.js index 6ae10c98058..3c44053e2b2 100644 --- a/app/assets/javascripts/pages/projects/show/index.js +++ b/app/assets/javascripts/pages/projects/show/index.js @@ -1,4 +1,6 @@ import $ from 'jquery'; +import 'jquery.waitforimages'; + import initBlob from '~/blob_edit/blob_bundle'; import ShortcutsNavigation from '~/behaviors/shortcuts/shortcuts_navigation'; import NotificationsForm from '~/notifications_form'; @@ -12,9 +14,12 @@ import initReadMore from '~/read_more'; import leaveByUrl from '~/namespaces/leave_by_url'; import Star from '../../../star'; import notificationsDropdown from '../../../notifications_dropdown'; +import initNamespaceStorageLimitAlert from '~/namespace_storage_limit_alert'; +import { showLearnGitLabProjectPopover } from '~/onboarding_issues'; document.addEventListener('DOMContentLoaded', () => { initReadMore(); + initNamespaceStorageLimitAlert(); new Star(); // eslint-disable-line no-new notificationsDropdown(); new ShortcutsNavigation(); // eslint-disable-line no-new @@ -55,4 +60,6 @@ document.addEventListener('DOMContentLoaded', () => { throw e; }); } + + showLearnGitLabProjectPopover(); }); diff --git a/app/assets/javascripts/pages/projects/tree/show/index.js b/app/assets/javascripts/pages/projects/tree/show/index.js index 16d71379e31..0d1d32317fe 100644 --- a/app/assets/javascripts/pages/projects/tree/show/index.js +++ b/app/assets/javascripts/pages/projects/tree/show/index.js @@ -1,4 +1,6 @@ import $ from 'jquery'; +import 'jquery.waitforimages'; + import Vue from 'vue'; import initBlob from '~/blob_edit/blob_bundle'; import commitPipelineStatus from '~/projects/tree/components/commit_pipeline_status_component.vue'; diff --git a/app/assets/javascripts/pages/projects/wikis/components/delete_wiki_modal.vue b/app/assets/javascripts/pages/projects/wikis/components/delete_wiki_modal.vue deleted file mode 100644 index 580cca49b5e..00000000000 --- a/app/assets/javascripts/pages/projects/wikis/components/delete_wiki_modal.vue +++ /dev/null @@ -1,74 +0,0 @@ -<script> -import { escape } from 'lodash'; -import { GlModal, GlModalDirective } from '@gitlab/ui'; -import { s__, sprintf } from '~/locale'; - -export default { - components: { - GlModal, - }, - directives: { - 'gl-modal': GlModalDirective, - }, - props: { - deleteWikiUrl: { - type: String, - required: true, - default: '', - }, - pageTitle: { - type: String, - required: true, - default: '', - }, - csrfToken: { - type: String, - required: true, - default: '', - }, - }, - computed: { - modalId() { - return 'delete-wiki-modal'; - }, - message() { - return s__('WikiPageConfirmDelete|Are you sure you want to delete this page?'); - }, - title() { - return sprintf( - s__('WikiPageConfirmDelete|Delete page %{pageTitle}?'), - { - pageTitle: escape(this.pageTitle), - }, - false, - ); - }, - }, - methods: { - onSubmit() { - window.onbeforeunload = null; - this.$refs.form.submit(); - }, - }, -}; -</script> - -<template> - <div class="d-inline-block"> - <button v-gl-modal="modalId" type="button" class="btn btn-danger">{{ __('Delete') }}</button> - <gl-modal - :title="title" - :ok-title="s__('WikiPageConfirmDelete|Delete page')" - :modal-id="modalId" - title-tag="h4" - ok-variant="danger" - @ok="onSubmit" - > - {{ message }} - <form ref="form" :action="deleteWikiUrl" method="post" class="js-requires-input"> - <input ref="method" type="hidden" name="_method" value="delete" /> - <input :value="csrfToken" type="hidden" name="authenticity_token" /> - </form> - </gl-modal> - </div> -</template> diff --git a/app/assets/javascripts/pages/projects/wikis/index.js b/app/assets/javascripts/pages/projects/wikis/index.js index f5fd84d69ac..9c75531ca40 100644 --- a/app/assets/javascripts/pages/projects/wikis/index.js +++ b/app/assets/javascripts/pages/projects/wikis/index.js @@ -1,41 +1,3 @@ -import $ from 'jquery'; -import Vue from 'vue'; -import Translate from '~/vue_shared/translate'; -import csrf from '~/lib/utils/csrf'; -import ShortcutsWiki from '~/behaviors/shortcuts/shortcuts_wiki'; -import Wikis from './wikis'; -import ZenMode from '../../../zen_mode'; -import GLForm from '../../../gl_form'; -import deleteWikiModal from './components/delete_wiki_modal.vue'; +import initWikis from '~/pages/shared/wikis'; -document.addEventListener('DOMContentLoaded', () => { - new Wikis(); // eslint-disable-line no-new - new ShortcutsWiki(); // eslint-disable-line no-new - new ZenMode(); // eslint-disable-line no-new - new GLForm($('.wiki-form')); // eslint-disable-line no-new - - const deleteWikiModalWrapperEl = document.getElementById('delete-wiki-modal-wrapper'); - - if (deleteWikiModalWrapperEl) { - Vue.use(Translate); - - const { deleteWikiUrl, pageTitle } = deleteWikiModalWrapperEl.dataset; - - // eslint-disable-next-line no-new - new Vue({ - el: deleteWikiModalWrapperEl, - data: { - deleteWikiUrl: '', - }, - render(createElement) { - return createElement(deleteWikiModal, { - props: { - pageTitle, - deleteWikiUrl, - csrfToken: csrf.token, - }, - }); - }, - }); - } -}); +document.addEventListener('DOMContentLoaded', initWikis); diff --git a/app/assets/javascripts/pages/projects/wikis/wikis.js b/app/assets/javascripts/pages/projects/wikis/wikis.js deleted file mode 100644 index ed67219383b..00000000000 --- a/app/assets/javascripts/pages/projects/wikis/wikis.js +++ /dev/null @@ -1,100 +0,0 @@ -import { GlBreakpointInstance as bp } from '@gitlab/ui/dist/utils'; -import { s__, sprintf } from '~/locale'; - -const MARKDOWN_LINK_TEXT = { - markdown: '[Link Title](page-slug)', - rdoc: '{Link title}[link:page-slug]', - asciidoc: 'link:page-slug[Link title]', - org: '[[page-slug]]', -}; - -export default class Wikis { - constructor() { - this.sidebarEl = document.querySelector('.js-wiki-sidebar'); - this.sidebarExpanded = false; - - const sidebarToggles = document.querySelectorAll('.js-sidebar-wiki-toggle'); - for (let i = 0; i < sidebarToggles.length; i += 1) { - sidebarToggles[i].addEventListener('click', e => this.handleToggleSidebar(e)); - } - - this.isNewWikiPage = Boolean(document.querySelector('.js-new-wiki-page')); - this.editTitleInput = document.querySelector('form.wiki-form #wiki_title'); - this.commitMessageInput = document.querySelector('form.wiki-form #wiki_message'); - this.commitMessageI18n = this.isNewWikiPage - ? s__('WikiPageCreate|Create %{pageTitle}') - : s__('WikiPageEdit|Update %{pageTitle}'); - - if (this.editTitleInput) { - // Initialize the commit message on load - if (this.editTitleInput.value) this.setWikiCommitMessage(this.editTitleInput.value); - - // Set the commit message as the page title is changed - this.editTitleInput.addEventListener('keyup', e => this.handleWikiTitleChange(e)); - } - - window.addEventListener('resize', () => this.renderSidebar()); - this.renderSidebar(); - - const changeFormatSelect = document.querySelector('#wiki_format'); - const linkExample = document.querySelector('.js-markup-link-example'); - - if (changeFormatSelect) { - changeFormatSelect.addEventListener('change', e => { - linkExample.innerHTML = MARKDOWN_LINK_TEXT[e.target.value]; - }); - } - - const wikiTextarea = document.querySelector('form.wiki-form #wiki_content'); - const wikiForm = document.querySelector('form.wiki-form'); - - if (wikiTextarea) { - wikiTextarea.addEventListener('input', () => { - window.onbeforeunload = () => ''; - }); - - wikiForm.addEventListener('submit', () => { - window.onbeforeunload = null; - }); - } - } - - handleWikiTitleChange(e) { - this.setWikiCommitMessage(e.target.value); - } - - setWikiCommitMessage(rawTitle) { - let title = rawTitle; - - // Replace hyphens with spaces - if (title) title = title.replace(/-+/g, ' '); - - const newCommitMessage = sprintf(this.commitMessageI18n, { pageTitle: title }, false); - this.commitMessageInput.value = newCommitMessage; - } - - handleToggleSidebar(e) { - e.preventDefault(); - this.sidebarExpanded = !this.sidebarExpanded; - this.renderSidebar(); - } - - static sidebarCanCollapse() { - const bootstrapBreakpoint = bp.getBreakpointSize(); - return bootstrapBreakpoint === 'xs' || bootstrapBreakpoint === 'sm'; - } - - renderSidebar() { - if (!this.sidebarEl) return; - const { classList } = this.sidebarEl; - if (this.sidebarExpanded || !Wikis.sidebarCanCollapse()) { - if (!classList.contains('right-sidebar-expanded')) { - classList.remove('right-sidebar-collapsed'); - classList.add('right-sidebar-expanded'); - } - } else if (classList.contains('right-sidebar-expanded')) { - classList.add('right-sidebar-collapsed'); - classList.remove('right-sidebar-expanded'); - } - } -} |