summaryrefslogtreecommitdiff
path: root/app/assets/javascripts/pages
diff options
context:
space:
mode:
Diffstat (limited to 'app/assets/javascripts/pages')
-rw-r--r--app/assets/javascripts/pages/dashboard/projects/index/components/customize_homepage_banner.vue2
-rw-r--r--app/assets/javascripts/pages/groups/issues/index.js34
-rw-r--r--app/assets/javascripts/pages/groups/new/index.js3
-rw-r--r--app/assets/javascripts/pages/groups/new/toggle_invite_members.js14
-rw-r--r--app/assets/javascripts/pages/projects/blob/show/index.js2
-rw-r--r--app/assets/javascripts/pages/projects/commit/show/index.js8
-rw-r--r--app/assets/javascripts/pages/projects/compare/show/index.js4
-rw-r--r--app/assets/javascripts/pages/projects/issues/show.js2
-rw-r--r--app/assets/javascripts/pages/projects/issues/show/index.js3
-rw-r--r--app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab.vue (renamed from app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_a.vue)0
-rw-r--r--app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_b.vue116
-rw-r--r--app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_section_link.vue2
-rw-r--r--app/assets/javascripts/pages/projects/learn_gitlab/index/index.js10
-rw-r--r--app/assets/javascripts/pages/projects/merge_requests/init_merge_request_show.js13
-rw-r--r--app/assets/javascripts/pages/projects/merge_requests/show/index.js11
-rw-r--r--app/assets/javascripts/pages/projects/new/components/new_project_url_select.vue98
-rw-r--r--app/assets/javascripts/pages/projects/new/index.js40
-rw-r--r--app/assets/javascripts/pages/projects/new/queries/search_namespaces_where_user_can_create_projects.query.graphql14
-rw-r--r--app/assets/javascripts/pages/projects/packages/packages/show/index.js14
-rw-r--r--app/assets/javascripts/pages/projects/pipeline_schedules/shared/components/interval_pattern_input.vue4
-rw-r--r--app/assets/javascripts/pages/projects/pipeline_schedules/shared/components/pipeline_schedules_callout.vue2
-rw-r--r--app/assets/javascripts/pages/projects/project_members/index.js2
-rw-r--r--app/assets/javascripts/pages/projects/usage_quotas/index.js23
-rw-r--r--app/assets/javascripts/pages/projects/wikis/index.js2
-rw-r--r--app/assets/javascripts/pages/projects/work_items/index/index.js3
-rw-r--r--app/assets/javascripts/pages/sessions/new/signin_tabs_memoizer.js2
26 files changed, 244 insertions, 184 deletions
diff --git a/app/assets/javascripts/pages/dashboard/projects/index/components/customize_homepage_banner.vue b/app/assets/javascripts/pages/dashboard/projects/index/components/customize_homepage_banner.vue
index d17c37e9e1a..99461475af0 100644
--- a/app/assets/javascripts/pages/dashboard/projects/index/components/customize_homepage_banner.vue
+++ b/app/assets/javascripts/pages/dashboard/projects/index/components/customize_homepage_banner.vue
@@ -77,7 +77,7 @@ export default {
);
if (button) {
- button.setAttribute('data-track-event', 'click_go_to_preferences');
+ button.setAttribute('data-track-action', 'click_go_to_preferences');
button.setAttribute('data-track-label', this.trackLabel);
}
},
diff --git a/app/assets/javascripts/pages/groups/issues/index.js b/app/assets/javascripts/pages/groups/issues/index.js
index 342c054471d..8c9f23732aa 100644
--- a/app/assets/javascripts/pages/groups/issues/index.js
+++ b/app/assets/javascripts/pages/groups/issues/index.js
@@ -1,26 +1,30 @@
import IssuableFilteredSearchTokenKeys from 'ee_else_ce/filtered_search/issuable_filtered_search_token_keys';
import issuableInitBulkUpdateSidebar from '~/issuable_bulk_update_sidebar/issuable_init_bulk_update_sidebar';
-import { mountIssuablesListApp } from '~/issues_list';
+import { mountIssuablesListApp, mountIssuesListApp } from '~/issues_list';
import initManualOrdering from '~/manual_ordering';
import { FILTERED_SEARCH } from '~/pages/constants';
import initFilteredSearch from '~/pages/search/init_filtered_search';
import projectSelect from '~/project_select';
-const ISSUE_BULK_UPDATE_PREFIX = 'issue_';
+if (gon.features?.vueIssuesList) {
+ mountIssuesListApp();
+} else {
+ const ISSUE_BULK_UPDATE_PREFIX = 'issue_';
-IssuableFilteredSearchTokenKeys.addExtraTokensForIssues();
-IssuableFilteredSearchTokenKeys.removeTokensForKeys('release');
-issuableInitBulkUpdateSidebar.init(ISSUE_BULK_UPDATE_PREFIX);
+ IssuableFilteredSearchTokenKeys.addExtraTokensForIssues();
+ IssuableFilteredSearchTokenKeys.removeTokensForKeys('release');
+ issuableInitBulkUpdateSidebar.init(ISSUE_BULK_UPDATE_PREFIX);
-initFilteredSearch({
- page: FILTERED_SEARCH.ISSUES,
- isGroupDecendent: true,
- useDefaultState: true,
- filteredSearchTokenKeys: IssuableFilteredSearchTokenKeys,
-});
-projectSelect();
-initManualOrdering();
+ initFilteredSearch({
+ page: FILTERED_SEARCH.ISSUES,
+ isGroupDecendent: true,
+ useDefaultState: true,
+ filteredSearchTokenKeys: IssuableFilteredSearchTokenKeys,
+ });
+ projectSelect();
+ initManualOrdering();
-if (gon.features?.vueIssuablesList) {
- mountIssuablesListApp();
+ if (gon.features?.vueIssuablesList) {
+ mountIssuablesListApp();
+ }
}
diff --git a/app/assets/javascripts/pages/groups/new/index.js b/app/assets/javascripts/pages/groups/new/index.js
index 7557edb1b49..7b0418e1ad5 100644
--- a/app/assets/javascripts/pages/groups/new/index.js
+++ b/app/assets/javascripts/pages/groups/new/index.js
@@ -5,6 +5,7 @@ import Group from '~/group';
import { parseBoolean } from '~/lib/utils/common_utils';
import NewGroupCreationApp from './components/app.vue';
import GroupPathValidator from './group_path_validator';
+import initToggleInviteMembers from './toggle_invite_members';
new GroupPathValidator(); // eslint-disable-line no-new
@@ -31,3 +32,5 @@ function initNewGroupCreation(el) {
const el = document.querySelector('.js-new-group-creation');
initNewGroupCreation(el);
+
+initToggleInviteMembers();
diff --git a/app/assets/javascripts/pages/groups/new/toggle_invite_members.js b/app/assets/javascripts/pages/groups/new/toggle_invite_members.js
new file mode 100644
index 00000000000..ffb4964cf7d
--- /dev/null
+++ b/app/assets/javascripts/pages/groups/new/toggle_invite_members.js
@@ -0,0 +1,14 @@
+import { parseBoolean } from '~/lib/utils/common_utils';
+
+export default function initToggleInviteMembers() {
+ const inviteMembersSection = document.querySelector('.js-invite-members-section');
+ const setupForCompanyRadios = document.querySelectorAll('input[name="group[setup_for_company]"]');
+
+ if (inviteMembersSection && setupForCompanyRadios.length) {
+ setupForCompanyRadios.forEach((el) => {
+ el.addEventListener('change', (event) => {
+ inviteMembersSection.classList.toggle('hidden', !parseBoolean(event.target.value));
+ });
+ });
+ }
+}
diff --git a/app/assets/javascripts/pages/projects/blob/show/index.js b/app/assets/javascripts/pages/projects/blob/show/index.js
index b365e039191..80bcbefab46 100644
--- a/app/assets/javascripts/pages/projects/blob/show/index.js
+++ b/app/assets/javascripts/pages/projects/blob/show/index.js
@@ -14,7 +14,7 @@ import '~/sourcegraph/load';
Vue.use(VueApollo);
const apolloProvider = new VueApollo({
- defaultClient: createDefaultClient(),
+ defaultClient: createDefaultClient({}, { assumeImmutableResults: true }),
});
const viewBlobEl = document.querySelector('#js-view-blob-app');
diff --git a/app/assets/javascripts/pages/projects/commit/show/index.js b/app/assets/javascripts/pages/projects/commit/show/index.js
index e3b30560fef..c6a76df7bde 100644
--- a/app/assets/javascripts/pages/projects/commit/show/index.js
+++ b/app/assets/javascripts/pages/projects/commit/show/index.js
@@ -4,8 +4,8 @@ import loadAwardsHandler from '~/awards_handler';
import ShortcutsNavigation from '~/behaviors/shortcuts/shortcuts_navigation';
import Diff from '~/diff';
import createFlash from '~/flash';
-import initChangesDropdown from '~/init_changes_dropdown';
-import initNotes from '~/init_notes';
+import initDeprecatedNotes from '~/init_deprecated_notes';
+import { initDiffStatsDropdown } from '~/init_diff_stats_dropdown';
import axios from '~/lib/utils/axios_utils';
import { handleLocationHash } from '~/lib/utils/common_utils';
import { __ } from '~/locale';
@@ -17,13 +17,13 @@ import '~/sourcegraph/load';
const hasPerfBar = document.querySelector('.with-performance-bar');
const performanceHeight = hasPerfBar ? 35 : 0;
-initChangesDropdown(document.querySelector('.navbar-gitlab').offsetHeight + performanceHeight);
+initDiffStatsDropdown(document.querySelector('.navbar-gitlab').offsetHeight + performanceHeight);
new ZenMode();
new ShortcutsNavigation();
initCommitBoxInfo();
-initNotes();
+initDeprecatedNotes();
const filesContainer = $('.js-diffs-batch');
diff --git a/app/assets/javascripts/pages/projects/compare/show/index.js b/app/assets/javascripts/pages/projects/compare/show/index.js
index 5edaa7f7e51..b74f7d1cf57 100644
--- a/app/assets/javascripts/pages/projects/compare/show/index.js
+++ b/app/assets/javascripts/pages/projects/compare/show/index.js
@@ -1,11 +1,11 @@
import Diff from '~/diff';
import GpgBadges from '~/gpg_badges';
-import initChangesDropdown from '~/init_changes_dropdown';
+import { initDiffStatsDropdown } from '~/init_diff_stats_dropdown';
import initCompareSelector from '~/projects/compare';
initCompareSelector();
new Diff(); // eslint-disable-line no-new
const paddingTop = 16;
-initChangesDropdown(document.querySelector('.navbar-gitlab').offsetHeight - paddingTop);
+initDiffStatsDropdown(document.querySelector('.navbar-gitlab').offsetHeight - paddingTop);
GpgBadges.fetch();
diff --git a/app/assets/javascripts/pages/projects/issues/show.js b/app/assets/javascripts/pages/projects/issues/show.js
index e365f51567d..62aa5df888f 100644
--- a/app/assets/javascripts/pages/projects/issues/show.js
+++ b/app/assets/javascripts/pages/projects/issues/show.js
@@ -6,7 +6,7 @@ import Issue from '~/issue';
import initIncidentApp from '~/issue_show/incident';
import { initIssuableApp, initIssueHeaderActions } from '~/issue_show/issue';
import { parseIssuableData } from '~/issue_show/utils/parse_data';
-import initNotesApp from '~/notes/index';
+import initNotesApp from '~/notes';
import { store } from '~/notes/stores';
import initRelatedMergeRequestsApp from '~/related_merge_requests';
import initSentryErrorStackTraceApp from '~/sentry_error_stack_trace';
diff --git a/app/assets/javascripts/pages/projects/issues/show/index.js b/app/assets/javascripts/pages/projects/issues/show/index.js
index e4f99d1e7fd..1282d2aa303 100644
--- a/app/assets/javascripts/pages/projects/issues/show/index.js
+++ b/app/assets/javascripts/pages/projects/issues/show/index.js
@@ -1,7 +1,8 @@
+import { store } from '~/notes/stores';
import initRelatedIssues from '~/related_issues';
import initSidebarBundle from '~/sidebar/sidebar_bundle';
import initShow from '../show';
initShow();
-initSidebarBundle();
+initSidebarBundle(store);
initRelatedIssues();
diff --git a/app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_a.vue b/app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab.vue
index 51980b2d971..51980b2d971 100644
--- a/app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_a.vue
+++ b/app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab.vue
diff --git a/app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_b.vue b/app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_b.vue
deleted file mode 100644
index 8f92ce95dbf..00000000000
--- a/app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_b.vue
+++ /dev/null
@@ -1,116 +0,0 @@
-<script>
-import { GlProgressBar, GlSprintf } from '@gitlab/ui';
-import { pick } from 'lodash';
-import { s__ } from '~/locale';
-import { ACTION_LABELS } from '../constants';
-import LearnGitlabInfoCard from './learn_gitlab_info_card.vue';
-
-export default {
- components: { LearnGitlabInfoCard, GlProgressBar, GlSprintf },
- i18n: {
- title: s__('LearnGitLab|Learn GitLab'),
- description: s__(
- 'LearnGitLab|Ready to get started with GitLab? Follow these steps to set up your workspace, plan and commit changes, and deploy your project.',
- ),
- percentageCompleted: s__(`LearnGitLab|%{percentage}%{percentSymbol} completed`),
- workspace: {
- title: s__('LearnGitLab|Set up your workspace'),
- description: s__(
- "LearnGitLab|Complete these tasks first so you can enjoy GitLab's features to their fullest:",
- ),
- },
- plan: {
- title: s__('LearnGitLab|Plan and execute'),
- description: s__(
- 'LearnGitLab|Create a workflow for your new workspace, and learn how GitLab features work together:',
- ),
- },
- deploy: {
- title: s__('LearnGitLab|Deploy'),
- description: s__(
- 'LearnGitLab|Use your new GitLab workflow to deploy your application, monitor its health, and keep it secure:',
- ),
- },
- },
- props: {
- actions: {
- required: true,
- type: Object,
- },
- },
- maxValue: Object.keys(ACTION_LABELS).length,
- methods: {
- infoProps(action) {
- return {
- ...this.actions[action],
- ...pick(ACTION_LABELS[action], ['title', 'actionLabel', 'description', 'trialRequired']),
- };
- },
- progressValue() {
- return Object.values(this.actions).filter((a) => a.completed).length;
- },
- progressPercentage() {
- return Math.round((this.progressValue() / this.$options.maxValue) * 100);
- },
- },
-};
-</script>
-<template>
- <div>
- <div class="row">
- <div class="gl-mb-7 col-md-8 col-lg-7">
- <h1 class="gl-font-size-h1">{{ $options.i18n.title }}</h1>
- <p class="gl-text-gray-700 gl-mb-0">{{ $options.i18n.description }}</p>
- </div>
- </div>
-
- <div class="gl-mb-3">
- <p class="gl-text-gray-500 gl-mb-2" data-testid="completion-percentage">
- <gl-sprintf :message="$options.i18n.percentageCompleted">
- <template #percentage>{{ progressPercentage() }}</template>
- <template #percentSymbol>%</template>
- </gl-sprintf>
- </p>
- <gl-progress-bar :value="progressValue()" :max="$options.maxValue" />
- </div>
-
- <h2 class="gl-font-lg gl-mb-3">{{ $options.i18n.workspace.title }}</h2>
- <p class="gl-text-gray-700 gl-mb-6">{{ $options.i18n.workspace.description }}</p>
-
- <div class="row row-cols-2 row-cols-md-3 row-cols-lg-4">
- <div class="col gl-mb-6"><learn-gitlab-info-card v-bind="infoProps('userAdded')" /></div>
- <div class="col gl-mb-6"><learn-gitlab-info-card v-bind="infoProps('gitWrite')" /></div>
- <div class="col gl-mb-6">
- <learn-gitlab-info-card v-bind="infoProps('pipelineCreated')" />
- </div>
- <div class="col gl-mb-6"><learn-gitlab-info-card v-bind="infoProps('trialStarted')" /></div>
- <div class="col gl-mb-6">
- <learn-gitlab-info-card v-bind="infoProps('codeOwnersEnabled')" />
- </div>
- <div class="col gl-mb-6">
- <learn-gitlab-info-card v-bind="infoProps('requiredMrApprovalsEnabled')" />
- </div>
- </div>
-
- <h2 class="gl-font-lg gl-mb-3">{{ $options.i18n.plan.title }}</h2>
- <p class="gl-text-gray-700 gl-mb-6">{{ $options.i18n.plan.description }}</p>
-
- <div class="row row-cols-2 row-cols-md-3 row-cols-lg-4">
- <div class="col gl-mb-6">
- <learn-gitlab-info-card v-bind="infoProps('issueCreated')" />
- </div>
- <div class="col gl-mb-6">
- <learn-gitlab-info-card v-bind="infoProps('mergeRequestCreated')" />
- </div>
- </div>
-
- <h2 class="gl-font-lg gl-mb-3">{{ $options.i18n.deploy.title }}</h2>
- <p class="gl-text-gray-700 gl-mb-6">{{ $options.i18n.deploy.description }}</p>
-
- <div class="row row-cols-2 row-cols-lg-4 g-2 g-lg-3">
- <div class="col gl-mb-6">
- <learn-gitlab-info-card v-bind="infoProps('securityScanEnabled')" />
- </div>
- </div>
- </div>
-</template>
diff --git a/app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_section_link.vue b/app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_section_link.vue
index 3d31ac6c267..69fb5878f5c 100644
--- a/app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_section_link.vue
+++ b/app/assets/javascripts/pages/projects/learn_gitlab/components/learn_gitlab_section_link.vue
@@ -39,7 +39,7 @@ export default {
:href="value.url"
data-track-action="click_link"
:data-track-label="$options.i18n.ACTION_LABELS[action].title"
- data-track-property="Growth::Conversion::Experiment::LearnGitLabA"
+ data-track-property="Growth::Conversion::Experiment::LearnGitLab"
>
{{ $options.i18n.ACTION_LABELS[action].title }}
</gl-link>
diff --git a/app/assets/javascripts/pages/projects/learn_gitlab/index/index.js b/app/assets/javascripts/pages/projects/learn_gitlab/index/index.js
index ac7c94bdd9e..6da0a8fd212 100644
--- a/app/assets/javascripts/pages/projects/learn_gitlab/index/index.js
+++ b/app/assets/javascripts/pages/projects/learn_gitlab/index/index.js
@@ -1,8 +1,6 @@
import Vue from 'vue';
-import trackLearnGitlab from '~/learn_gitlab/track_learn_gitlab';
import { convertObjectPropsToCamelCase } from '~/lib/utils/common_utils';
-import LearnGitlabA from '../components/learn_gitlab_a.vue';
-import LearnGitlabB from '../components/learn_gitlab_b.vue';
+import LearnGitlab from '../components/learn_gitlab.vue';
function initLearnGitlab() {
const el = document.getElementById('js-learn-gitlab-app');
@@ -14,14 +12,10 @@ function initLearnGitlab() {
const actions = convertObjectPropsToCamelCase(JSON.parse(el.dataset.actions));
const sections = convertObjectPropsToCamelCase(JSON.parse(el.dataset.sections));
- const { learnGitlabA } = gon.experiments;
-
- trackLearnGitlab(learnGitlabA);
-
return new Vue({
el,
render(createElement) {
- return createElement(learnGitlabA ? LearnGitlabA : LearnGitlabB, {
+ return createElement(LearnGitlab, {
props: { actions, sections },
});
},
diff --git a/app/assets/javascripts/pages/projects/merge_requests/init_merge_request_show.js b/app/assets/javascripts/pages/projects/merge_requests/init_merge_request_show.js
index d6b6c9fe06a..dadf0988582 100644
--- a/app/assets/javascripts/pages/projects/merge_requests/init_merge_request_show.js
+++ b/app/assets/javascripts/pages/projects/merge_requests/init_merge_request_show.js
@@ -2,11 +2,10 @@ import Vue from 'vue';
import VueApollo from 'vue-apollo';
import loadAwardsHandler from '~/awards_handler';
import ShortcutsIssuable from '~/behaviors/shortcuts/shortcuts_issuable';
-import initPipelines from '~/commit/pipelines/pipelines_bundle';
+import { initPipelineCountListener } from '~/commit/pipelines/utils';
import initIssuableSidebar from '~/init_issuable_sidebar';
import StatusBox from '~/issuable/components/status_box.vue';
import createDefaultClient from '~/lib/graphql';
-import { handleLocationHash } from '~/lib/utils/common_utils';
import initSourcegraph from '~/sourcegraph';
import ZenMode from '~/zen_mode';
import getStateQuery from './queries/get_state.query.graphql';
@@ -15,11 +14,10 @@ export default function initMergeRequestShow() {
const awardEmojiEl = document.getElementById('js-vue-awards-block');
new ZenMode(); // eslint-disable-line no-new
- initIssuableSidebar();
- initPipelines();
+ initPipelineCountListener(document.querySelector('#commit-pipeline-table-view'));
new ShortcutsIssuable(true); // eslint-disable-line no-new
- handleLocationHash();
initSourcegraph();
+ initIssuableSidebar();
if (awardEmojiEl) {
import('~/emoji/awards_app')
.then((m) => m.default(awardEmojiEl))
@@ -29,7 +27,10 @@ export default function initMergeRequestShow() {
}
const el = document.querySelector('.js-mr-status-box');
- const apolloProvider = new VueApollo({ defaultClient: createDefaultClient() });
+ const apolloProvider = new VueApollo({
+ assumeImmutableResults: true,
+ defaultClient: createDefaultClient(),
+ });
// eslint-disable-next-line no-new
new Vue({
el,
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 546fa66eda6..25dede33880 100644
--- a/app/assets/javascripts/pages/projects/merge_requests/show/index.js
+++ b/app/assets/javascripts/pages/projects/merge_requests/show/index.js
@@ -5,8 +5,11 @@ import initSidebarBundle from '~/sidebar/sidebar_bundle';
import initIssuableHeaderWarning from '~/vue_shared/components/issuable/init_issuable_header_warning';
import initShow from '../init_merge_request_show';
-initShow();
-initSidebarBundle();
initMrNotes();
-initReviewBar();
-initIssuableHeaderWarning(store);
+initShow();
+
+requestIdleCallback(() => {
+ initSidebarBundle(store);
+ initReviewBar();
+ initIssuableHeaderWarning(store);
+});
diff --git a/app/assets/javascripts/pages/projects/new/components/new_project_url_select.vue b/app/assets/javascripts/pages/projects/new/components/new_project_url_select.vue
new file mode 100644
index 00000000000..ba8858c985a
--- /dev/null
+++ b/app/assets/javascripts/pages/projects/new/components/new_project_url_select.vue
@@ -0,0 +1,98 @@
+<script>
+import {
+ GlButton,
+ GlButtonGroup,
+ GlDropdown,
+ GlDropdownItem,
+ GlDropdownSectionHeader,
+ GlLoadingIcon,
+ GlSearchBoxByType,
+} from '@gitlab/ui';
+import { MINIMUM_SEARCH_LENGTH } from '~/graphql_shared/constants';
+import { getIdFromGraphQLId } from '~/graphql_shared/utils';
+import Tracking from '~/tracking';
+import { DEBOUNCE_DELAY } from '~/vue_shared/components/filtered_search_bar/constants';
+import searchNamespacesWhereUserCanCreateProjectsQuery from '../queries/search_namespaces_where_user_can_create_projects.query.graphql';
+
+export default {
+ components: {
+ GlButton,
+ GlButtonGroup,
+ GlDropdown,
+ GlDropdownItem,
+ GlDropdownSectionHeader,
+ GlLoadingIcon,
+ GlSearchBoxByType,
+ },
+ mixins: [Tracking.mixin()],
+ apollo: {
+ currentUser: {
+ query: searchNamespacesWhereUserCanCreateProjectsQuery,
+ variables() {
+ return {
+ search: this.search,
+ };
+ },
+ skip() {
+ return this.search.length > 0 && this.search.length < MINIMUM_SEARCH_LENGTH;
+ },
+ debounce: DEBOUNCE_DELAY,
+ },
+ },
+ inject: ['namespaceFullPath', 'namespaceId', 'rootUrl', 'trackLabel'],
+ data() {
+ return {
+ currentUser: {},
+ search: '',
+ selectedNamespace: {
+ id: this.namespaceId,
+ fullPath: this.namespaceFullPath,
+ },
+ };
+ },
+ computed: {
+ userGroups() {
+ return this.currentUser.groups?.nodes || [];
+ },
+ userNamespace() {
+ return this.currentUser.namespace || {};
+ },
+ },
+ methods: {
+ handleClick({ id, fullPath }) {
+ this.selectedNamespace = {
+ id: getIdFromGraphQLId(id),
+ fullPath,
+ };
+ },
+ },
+};
+</script>
+
+<template>
+ <gl-button-group class="gl-w-full">
+ <gl-button label>{{ rootUrl }}</gl-button>
+ <gl-dropdown
+ class="gl-w-full"
+ :text="selectedNamespace.fullPath"
+ toggle-class="gl-rounded-top-right-base! gl-rounded-bottom-right-base!"
+ data-qa-selector="select_namespace_dropdown"
+ @show="track('activate_form_input', { label: trackLabel, property: 'project_path' })"
+ >
+ <gl-search-box-by-type v-model.trim="search" />
+ <gl-loading-icon v-if="$apollo.queries.currentUser.loading" />
+ <template v-else>
+ <gl-dropdown-section-header>{{ __('Groups') }}</gl-dropdown-section-header>
+ <gl-dropdown-item v-for="group of userGroups" :key="group.id" @click="handleClick(group)">
+ {{ group.fullPath }}
+ </gl-dropdown-item>
+ <gl-dropdown-section-header>{{ __('Users') }}</gl-dropdown-section-header>
+ <gl-dropdown-item @click="handleClick(userNamespace)">
+ {{ userNamespace.fullPath }}
+ </gl-dropdown-item>
+ </template>
+ </gl-dropdown>
+
+ <input type="hidden" name="project[namespace_id]" :value="selectedNamespace.id" />
+ </gl-button-group>
+</template>
diff --git a/app/assets/javascripts/pages/projects/new/index.js b/app/assets/javascripts/pages/projects/new/index.js
index f469c56e808..ed816e3be95 100644
--- a/app/assets/javascripts/pages/projects/new/index.js
+++ b/app/assets/javascripts/pages/projects/new/index.js
@@ -1,13 +1,15 @@
import Vue from 'vue';
+import VueApollo from 'vue-apollo';
+import createDefaultClient from '~/lib/graphql';
import { parseBoolean } from '~/lib/utils/common_utils';
import initProjectVisibilitySelector from '../../../project_visibility';
import initProjectNew from '../../../projects/project_new';
import NewProjectCreationApp from './components/app.vue';
+import NewProjectUrlSelect from './components/new_project_url_select.vue';
-initProjectVisibilitySelector();
-initProjectNew.bindEvents();
+function initNewProjectCreation() {
+ const el = document.querySelector('.js-new-project-creation');
-function initNewProjectCreation(el) {
const {
pushToCreateProjectCommand,
workingWithProjectsHelpPath,
@@ -29,9 +31,6 @@ function initNewProjectCreation(el) {
return new Vue({
el,
- components: {
- NewProjectCreationApp,
- },
provide,
render(h) {
return h(NewProjectCreationApp, { props });
@@ -39,6 +38,31 @@ function initNewProjectCreation(el) {
});
}
-const el = document.querySelector('.js-new-project-creation');
+function initNewProjectUrlSelect() {
+ const el = document.querySelector('.js-vue-new-project-url-select');
+
+ if (!el) {
+ return undefined;
+ }
-initNewProjectCreation(el);
+ Vue.use(VueApollo);
+
+ return new Vue({
+ el,
+ apolloProvider: new VueApollo({
+ defaultClient: createDefaultClient({}, { assumeImmutableResults: true }),
+ }),
+ provide: {
+ namespaceFullPath: el.dataset.namespaceFullPath,
+ namespaceId: el.dataset.namespaceId,
+ rootUrl: el.dataset.rootUrl,
+ trackLabel: el.dataset.trackLabel,
+ },
+ render: (createElement) => createElement(NewProjectUrlSelect),
+ });
+}
+
+initProjectVisibilitySelector();
+initProjectNew.bindEvents();
+initNewProjectCreation();
+initNewProjectUrlSelect();
diff --git a/app/assets/javascripts/pages/projects/new/queries/search_namespaces_where_user_can_create_projects.query.graphql b/app/assets/javascripts/pages/projects/new/queries/search_namespaces_where_user_can_create_projects.query.graphql
new file mode 100644
index 00000000000..e16fe5dde49
--- /dev/null
+++ b/app/assets/javascripts/pages/projects/new/queries/search_namespaces_where_user_can_create_projects.query.graphql
@@ -0,0 +1,14 @@
+query searchNamespacesWhereUserCanCreateProjects($search: String) {
+ currentUser {
+ groups(permissionScope: CREATE_PROJECTS, search: $search) {
+ nodes {
+ id
+ fullPath
+ }
+ }
+ namespace {
+ id
+ fullPath
+ }
+ }
+}
diff --git a/app/assets/javascripts/pages/projects/packages/packages/show/index.js b/app/assets/javascripts/pages/projects/packages/packages/show/index.js
index ee06f247ddc..2dee87985cb 100644
--- a/app/assets/javascripts/pages/projects/packages/packages/show/index.js
+++ b/app/assets/javascripts/pages/projects/packages/packages/show/index.js
@@ -1,11 +1,3 @@
-(async function initPackage() {
- let app;
- if (document.getElementById('js-vue-packages-detail-new')) {
- app = await import(
- /* webpackChunkName: 'new_package_app' */ `~/packages_and_registries/package_registry/pages/details.js`
- );
- } else {
- app = await import('~/packages/details/');
- }
- app.default();
-})();
+import initPackageDetails from '~/packages_and_registries/package_registry/pages/details';
+
+initPackageDetails();
diff --git a/app/assets/javascripts/pages/projects/pipeline_schedules/shared/components/interval_pattern_input.vue b/app/assets/javascripts/pages/projects/pipeline_schedules/shared/components/interval_pattern_input.vue
index d0ec5668d21..0e646e8c505 100644
--- a/app/assets/javascripts/pages/projects/pipeline_schedules/shared/components/interval_pattern_input.vue
+++ b/app/assets/javascripts/pages/projects/pipeline_schedules/shared/components/interval_pattern_input.vue
@@ -141,9 +141,7 @@ export default {
return Math.floor(Math.random() * 28);
},
showDailyLimitMessage({ value }) {
- return (
- value === KEY_CUSTOM && this.glFeatures.ciDailyLimitForPipelineSchedules && this.dailyLimit
- );
+ return value === KEY_CUSTOM && this.dailyLimit;
},
},
};
diff --git a/app/assets/javascripts/pages/projects/pipeline_schedules/shared/components/pipeline_schedules_callout.vue b/app/assets/javascripts/pages/projects/pipeline_schedules/shared/components/pipeline_schedules_callout.vue
index 92b2bc9644b..42b08bcaa7b 100644
--- a/app/assets/javascripts/pages/projects/pipeline_schedules/shared/components/pipeline_schedules_callout.vue
+++ b/app/assets/javascripts/pages/projects/pipeline_schedules/shared/components/pipeline_schedules_callout.vue
@@ -53,7 +53,7 @@ Those scheduled pipelines will inherit limited project access based on their ass
<p>
{{ __('Learn more in the') }}
<a :href="docsUrl" target="_blank" rel="nofollow">
- {{ s__('Learn more in the|pipeline schedules documentation') }}</a
+ {{ __('pipeline schedules documentation') }}</a
>.
<!-- oneline to prevent extra space before period -->
</p>
diff --git a/app/assets/javascripts/pages/projects/project_members/index.js b/app/assets/javascripts/pages/projects/project_members/index.js
index fb0be31834d..0b662c945c6 100644
--- a/app/assets/javascripts/pages/projects/project_members/index.js
+++ b/app/assets/javascripts/pages/projects/project_members/index.js
@@ -1,4 +1,5 @@
import groupsSelect from '~/groups_select';
+import initImportAProjectModal from '~/invite_members/init_import_a_project_modal';
import initInviteGroupTrigger from '~/invite_members/init_invite_group_trigger';
import initInviteMembersForm from '~/invite_members/init_invite_members_form';
import initInviteMembersModal from '~/invite_members/init_invite_members_modal';
@@ -14,6 +15,7 @@ import UsersSelect from '~/users_select';
groupsSelect();
memberExpirationDate();
memberExpirationDate('.js-access-expiration-date-groups');
+initImportAProjectModal();
initInviteMembersModal();
initInviteMembersTrigger();
initInviteGroupTrigger();
diff --git a/app/assets/javascripts/pages/projects/usage_quotas/index.js b/app/assets/javascripts/pages/projects/usage_quotas/index.js
new file mode 100644
index 00000000000..9cd80b85c8a
--- /dev/null
+++ b/app/assets/javascripts/pages/projects/usage_quotas/index.js
@@ -0,0 +1,23 @@
+import LinkedTabs from '~/lib/utils/bootstrap_linked_tabs';
+import storageCounter from '~/projects/storage_counter';
+import initSearchSettings from '~/search_settings';
+
+const initLinkedTabs = () => {
+ if (!document.querySelector('.js-usage-quota-tabs')) {
+ return false;
+ }
+
+ return new LinkedTabs({
+ defaultAction: '#storage-quota-tab',
+ parentEl: '.js-usage-quota-tabs',
+ hashedTabs: true,
+ });
+};
+
+const initVueApp = () => {
+ storageCounter('js-project-storage-count-app');
+};
+
+initVueApp();
+initLinkedTabs();
+initSearchSettings();
diff --git a/app/assets/javascripts/pages/projects/wikis/index.js b/app/assets/javascripts/pages/projects/wikis/index.js
index dead61cf358..2c1f9e634ab 100644
--- a/app/assets/javascripts/pages/projects/wikis/index.js
+++ b/app/assets/javascripts/pages/projects/wikis/index.js
@@ -1,3 +1,5 @@
+import { initDiffStatsDropdown } from '~/init_diff_stats_dropdown';
import initWikis from '~/pages/shared/wikis';
initWikis();
+initDiffStatsDropdown();
diff --git a/app/assets/javascripts/pages/projects/work_items/index/index.js b/app/assets/javascripts/pages/projects/work_items/index/index.js
new file mode 100644
index 00000000000..11c257611f0
--- /dev/null
+++ b/app/assets/javascripts/pages/projects/work_items/index/index.js
@@ -0,0 +1,3 @@
+import { initWorkItemsRoot } from '~/work_items/index';
+
+initWorkItemsRoot();
diff --git a/app/assets/javascripts/pages/sessions/new/signin_tabs_memoizer.js b/app/assets/javascripts/pages/sessions/new/signin_tabs_memoizer.js
index 1e7c29aefaa..7e646125331 100644
--- a/app/assets/javascripts/pages/sessions/new/signin_tabs_memoizer.js
+++ b/app/assets/javascripts/pages/sessions/new/signin_tabs_memoizer.js
@@ -8,7 +8,7 @@ export default class SigninTabsMemoizer {
constructor({ currentTabKey = 'current_signin_tab', tabSelector = 'ul.new-session-tabs' } = {}) {
this.currentTabKey = currentTabKey;
this.tabSelector = tabSelector;
- this.isLocalStorageAvailable = AccessorUtilities.isLocalStorageAccessSafe();
+ this.isLocalStorageAvailable = AccessorUtilities.canUseLocalStorage();
// sets selected tab if given as hash tag
if (window.location.hash) {
this.saveData(window.location.hash);