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
path: root/app
diff options
context:
space:
mode:
Diffstat (limited to 'app')
-rw-r--r--app/assets/javascripts/design_management/components/design_notes/design_discussion.vue85
-rw-r--r--app/assets/javascripts/design_management/components/design_notes/design_note_signed_out.vue50
-rw-r--r--app/assets/javascripts/design_management/components/design_presentation.vue4
-rw-r--r--app/assets/javascripts/design_management/components/design_sidebar.vue24
-rw-r--r--app/assets/javascripts/design_management/index.js4
-rw-r--r--app/assets/javascripts/gitlab_version_check.js20
-rw-r--r--app/assets/javascripts/issues/show/components/app.vue8
-rw-r--r--app/assets/javascripts/issues/show/components/fields/type.vue10
-rw-r--r--app/assets/javascripts/issues/show/components/header_actions.vue4
-rw-r--r--app/assets/javascripts/issues/show/constants.js26
-rw-r--r--app/assets/javascripts/issues/show/index.js6
-rw-r--r--app/assets/javascripts/lib/utils/constants.js1
-rw-r--r--app/assets/javascripts/pages/help/index/index.js5
-rw-r--r--app/assets/javascripts/pages/shared/wikis/components/wiki_form.vue4
-rw-r--r--app/assets/javascripts/version_check_image.js6
-rw-r--r--app/assets/javascripts/vue_shared/components/gitlab_version_check.vue67
-rw-r--r--app/graphql/types/packages/package_details_type.rb43
-rw-r--r--app/helpers/packages_helper.rb2
-rw-r--r--app/helpers/version_check_helper.rb9
-rw-r--r--app/views/admin/dashboard/index.html.haml4
-rw-r--r--app/views/admin/labels/_form.html.haml31
-rw-r--r--app/views/admin/labels/edit.html.haml2
-rw-r--r--app/views/admin/labels/new.html.haml2
-rw-r--r--app/views/help/index.html.haml15
-rw-r--r--app/views/projects/issues/_design_management.html.haml6
-rw-r--r--app/views/shared/issuable/_form.html.haml4
-rw-r--r--app/views/shared/labels/_form.html.haml14
-rw-r--r--app/views/shared/web_hooks/_form.html.haml32
-rw-r--r--app/views/shared/web_hooks/_index.html.haml2
29 files changed, 343 insertions, 147 deletions
diff --git a/app/assets/javascripts/design_management/components/design_notes/design_discussion.vue b/app/assets/javascripts/design_management/components/design_notes/design_discussion.vue
index 10976202d06..7fefbab977d 100644
--- a/app/assets/javascripts/design_management/components/design_notes/design_discussion.vue
+++ b/app/assets/javascripts/design_management/components/design_notes/design_discussion.vue
@@ -7,6 +7,7 @@ import ReplyPlaceholder from '~/notes/components/discussion_reply_placeholder.vu
import { updateGlobalTodoCount } from '~/vue_shared/components/sidebar/todo_toggle/utils';
import TimeAgoTooltip from '~/vue_shared/components/time_ago_tooltip.vue';
import DesignNotePin from '~/vue_shared/components/design_management/design_note_pin.vue';
+import { isLoggedIn } from '~/lib/utils/common_utils';
import { ACTIVE_DISCUSSION_SOURCE_TYPES } from '../../constants';
import createNoteMutation from '../../graphql/mutations/create_note.mutation.graphql';
import toggleResolveDiscussionMutation from '../../graphql/mutations/toggle_resolve_discussion.mutation.graphql';
@@ -17,6 +18,7 @@ import { hasErrors } from '../../utils/cache_update';
import { extractDesign } from '../../utils/design_management_utils';
import { ADD_DISCUSSION_COMMENT_ERROR } from '../../utils/error_messages';
import DesignNote from './design_note.vue';
+import DesignNoteSignedOut from './design_note_signed_out.vue';
import DesignReplyForm from './design_reply_form.vue';
import ToggleRepliesWidget from './toggle_replies_widget.vue';
@@ -24,6 +26,7 @@ export default {
components: {
ApolloMutation,
DesignNote,
+ DesignNoteSignedOut,
ReplyPlaceholder,
DesignReplyForm,
GlIcon,
@@ -55,6 +58,14 @@ export default {
required: false,
default: '',
},
+ registerPath: {
+ type: String,
+ required: true,
+ },
+ signInPath: {
+ type: String,
+ required: true,
+ },
resolvedDiscussionsExpanded: {
type: Boolean,
required: true,
@@ -93,6 +104,7 @@ export default {
isResolving: false,
shouldChangeResolvedStatus: false,
areRepliesCollapsed: this.discussion.resolved,
+ isLoggedIn: isLoggedIn(),
};
},
computed: {
@@ -226,7 +238,7 @@ export default {
:class="{ 'gl-bg-blue-50': isDiscussionActive }"
@error="$emit('update-note-error', $event)"
>
- <template v-if="discussion.resolvable" #resolve-discussion>
+ <template v-if="isLoggedIn && discussion.resolvable" #resolve-discussion>
<button
v-gl-tooltip
:class="{ 'is-active': discussion.resolved }"
@@ -269,38 +281,47 @@ export default {
:class="{ 'gl-bg-blue-50': isDiscussionActive }"
@error="$emit('update-note-error', $event)"
/>
- <li v-show="isReplyPlaceholderVisible" class="reply-wrapper discussion-reply-holder">
- <reply-placeholder
- v-if="!isFormVisible"
- class="qa-discussion-reply"
- :placeholder-text="__('Reply…')"
- @focus="showForm"
- />
- <apollo-mutation
- v-else
- #default="{ mutate, loading }"
- :mutation="$options.createNoteMutation"
- :variables="{
- input: mutationPayload,
- }"
- @done="onDone"
- @error="onCreateNoteError"
- >
- <design-reply-form
- v-model="discussionComment"
- :is-saving="loading"
- :markdown-preview-path="markdownPreviewPath"
- @submit-form="mutate"
- @cancel-form="hideForm"
+ <li
+ v-show="isReplyPlaceholderVisible"
+ class="reply-wrapper discussion-reply-holder"
+ :class="{ 'gl-bg-gray-10': !isLoggedIn }"
+ >
+ <template v-if="!isLoggedIn">
+ <design-note-signed-out :register-path="registerPath" :sign-in-path="signInPath" />
+ </template>
+ <template v-else>
+ <reply-placeholder
+ v-if="!isFormVisible"
+ class="qa-discussion-reply"
+ :placeholder-text="__('Reply…')"
+ @focus="showForm"
+ />
+ <apollo-mutation
+ v-else
+ #default="{ mutate, loading }"
+ :mutation="$options.createNoteMutation"
+ :variables="{
+ input: mutationPayload,
+ }"
+ @done="onDone"
+ @error="onCreateNoteError"
>
- <template v-if="discussion.resolvable" #resolve-checkbox>
- <label data-testid="resolve-checkbox">
- <input v-model="shouldChangeResolvedStatus" type="checkbox" />
- {{ resolveCheckboxText }}
- </label>
- </template>
- </design-reply-form>
- </apollo-mutation>
+ <design-reply-form
+ v-model="discussionComment"
+ :is-saving="loading"
+ :markdown-preview-path="markdownPreviewPath"
+ @submit-form="mutate"
+ @cancel-form="hideForm"
+ >
+ <template v-if="discussion.resolvable" #resolve-checkbox>
+ <label data-testid="resolve-checkbox">
+ <input v-model="shouldChangeResolvedStatus" type="checkbox" />
+ {{ resolveCheckboxText }}
+ </label>
+ </template>
+ </design-reply-form>
+ </apollo-mutation>
+ </template>
</li>
</ul>
</div>
diff --git a/app/assets/javascripts/design_management/components/design_notes/design_note_signed_out.vue b/app/assets/javascripts/design_management/components/design_notes/design_note_signed_out.vue
new file mode 100644
index 00000000000..f0812e62bba
--- /dev/null
+++ b/app/assets/javascripts/design_management/components/design_notes/design_note_signed_out.vue
@@ -0,0 +1,50 @@
+<script>
+import { GlSprintf, GlLink } from '@gitlab/ui';
+import { __ } from '~/locale';
+
+export default {
+ components: {
+ GlSprintf,
+ GlLink,
+ },
+ props: {
+ registerPath: {
+ type: String,
+ required: true,
+ },
+ signInPath: {
+ type: String,
+ required: true,
+ },
+ isAddDiscussion: {
+ type: Boolean,
+ required: false,
+ default: false,
+ },
+ },
+ computed: {
+ signedOutText() {
+ return this.isAddDiscussion
+ ? __(
+ 'Please %{registerLinkStart}register%{registerLinkEnd} or %{signInLinkStart}sign in%{signInLinkEnd} to start a new discussion.',
+ )
+ : __(
+ 'Please %{registerLinkStart}register%{registerLinkEnd} or %{signInLinkStart}sign in%{signInLinkEnd} to reply.',
+ );
+ },
+ },
+};
+</script>
+
+<template>
+ <div class="disabled-comment text-center">
+ <gl-sprintf :message="signedOutText">
+ <template #registerLink="{ content }">
+ <gl-link :href="registerPath">{{ content }}</gl-link>
+ </template>
+ <template #signInLink="{ content }">
+ <gl-link :href="signInPath">{{ content }}</gl-link>
+ </template>
+ </gl-sprintf>
+ </div>
+</template>
diff --git a/app/assets/javascripts/design_management/components/design_presentation.vue b/app/assets/javascripts/design_management/components/design_presentation.vue
index 11d2f3b2e37..5116bacefa5 100644
--- a/app/assets/javascripts/design_management/components/design_presentation.vue
+++ b/app/assets/javascripts/design_management/components/design_presentation.vue
@@ -1,5 +1,6 @@
<script>
import { throttle } from 'lodash';
+import { isLoggedIn } from '~/lib/utils/common_utils';
import DesignOverlay from './design_overlay.vue';
import DesignImage from './image.vue';
@@ -54,6 +55,7 @@ export default {
initialLoad: true,
lastDragPosition: null,
isDraggingDesign: false,
+ isLoggedIn: isLoggedIn(),
};
},
computed: {
@@ -311,7 +313,7 @@ export default {
:position="overlayPosition"
:notes="discussionStartingNotes"
:current-comment-form="currentCommentForm"
- :disable-commenting="isDraggingDesign"
+ :disable-commenting="!isLoggedIn || isDraggingDesign"
:resolved-discussions-expanded="resolvedDiscussionsExpanded"
@openCommentForm="openCommentForm"
@closeCommentForm="closeCommentForm"
diff --git a/app/assets/javascripts/design_management/components/design_sidebar.vue b/app/assets/javascripts/design_management/components/design_sidebar.vue
index ced76eb4843..6d0ed3b08a3 100644
--- a/app/assets/javascripts/design_management/components/design_sidebar.vue
+++ b/app/assets/javascripts/design_management/components/design_sidebar.vue
@@ -1,7 +1,7 @@
<script>
import { GlCollapse, GlButton, GlPopover } from '@gitlab/ui';
import Cookies from 'js-cookie';
-import { parseBoolean } from '~/lib/utils/common_utils';
+import { parseBoolean, isLoggedIn } from '~/lib/utils/common_utils';
import { s__ } from '~/locale';
import Participants from '~/sidebar/components/participants/participants.vue';
import glFeatureFlagsMixin from '~/vue_shared/mixins/gl_feature_flags_mixin';
@@ -9,11 +9,13 @@ import { ACTIVE_DISCUSSION_SOURCE_TYPES } from '../constants';
import updateActiveDiscussionMutation from '../graphql/mutations/update_active_discussion.mutation.graphql';
import { extractDiscussions, extractParticipants } from '../utils/design_management_utils';
import DesignDiscussion from './design_notes/design_discussion.vue';
+import DesignNoteSignedOut from './design_notes/design_note_signed_out.vue';
import DesignTodoButton from './design_todo_button.vue';
export default {
components: {
DesignDiscussion,
+ DesignNoteSignedOut,
Participants,
GlCollapse,
GlButton,
@@ -28,6 +30,12 @@ export default {
issueIid: {
default: '',
},
+ registerPath: {
+ default: '',
+ },
+ signInPath: {
+ default: '',
+ },
},
props: {
design: {
@@ -47,6 +55,7 @@ export default {
return {
isResolvedCommentsPopoverHidden: parseBoolean(Cookies.get(this.$options.cookieKey)),
discussionWithOpenForm: '',
+ isLoggedIn: isLoggedIn(),
};
},
computed: {
@@ -134,12 +143,19 @@ export default {
class="gl-mb-4"
/>
<h2
- v-if="unresolvedDiscussions.length === 0"
+ v-if="isLoggedIn && unresolvedDiscussions.length === 0"
class="new-discussion-disclaimer gl-font-base gl-m-0 gl-mb-4"
data-testid="new-discussion-disclaimer"
>
{{ s__("DesignManagement|Click the image where you'd like to start a new discussion") }}
</h2>
+ <design-note-signed-out
+ v-if="!isLoggedIn"
+ class="gl-mb-4"
+ :register-path="registerPath"
+ :sign-in-path="signInPath"
+ :is-add-discussion="true"
+ />
<design-discussion
v-for="discussion in unresolvedDiscussions"
:key="discussion.id"
@@ -147,6 +163,8 @@ export default {
:design-id="$route.params.id"
:noteable-id="design.id"
:markdown-preview-path="markdownPreviewPath"
+ :register-path="registerPath"
+ :sign-in-path="signInPath"
:resolved-discussions-expanded="resolvedDiscussionsExpanded"
:discussion-with-open-form="discussionWithOpenForm"
data-testid="unresolved-discussion"
@@ -197,6 +215,8 @@ export default {
:design-id="$route.params.id"
:noteable-id="design.id"
:markdown-preview-path="markdownPreviewPath"
+ :register-path="registerPath"
+ :sign-in-path="signInPath"
:resolved-discussions-expanded="resolvedDiscussionsExpanded"
:discussion-with-open-form="discussionWithOpenForm"
data-testid="resolved-discussion"
diff --git a/app/assets/javascripts/design_management/index.js b/app/assets/javascripts/design_management/index.js
index 11666587265..4ae76050aa5 100644
--- a/app/assets/javascripts/design_management/index.js
+++ b/app/assets/javascripts/design_management/index.js
@@ -8,7 +8,7 @@ import createRouter from './router';
export default () => {
const el = document.querySelector('.js-design-management');
- const { issueIid, projectPath, issuePath } = el.dataset;
+ const { issueIid, projectPath, issuePath, registerPath, signInPath } = el.dataset;
const router = createRouter(issuePath);
apolloProvider.clients.defaultClient.cache.writeQuery({
@@ -29,6 +29,8 @@ export default () => {
provide: {
projectPath,
issueIid,
+ registerPath,
+ signInPath,
},
mounted() {
performanceMarkAndMeasure({
diff --git a/app/assets/javascripts/gitlab_version_check.js b/app/assets/javascripts/gitlab_version_check.js
new file mode 100644
index 00000000000..2892aded7c5
--- /dev/null
+++ b/app/assets/javascripts/gitlab_version_check.js
@@ -0,0 +1,20 @@
+import Vue from 'vue';
+import GitlabVersionCheck from '~/vue_shared/components/gitlab_version_check.vue';
+
+const mountGitlabVersionCheck = (el) => {
+ const { size } = el.dataset;
+
+ return new Vue({
+ el,
+ render(createElement) {
+ return createElement(GitlabVersionCheck, {
+ props: {
+ size,
+ },
+ });
+ },
+ });
+};
+
+export default () =>
+ [...document.querySelectorAll('.js-gitlab-version-check')].map(mountGitlabVersionCheck);
diff --git a/app/assets/javascripts/issues/show/components/app.vue b/app/assets/javascripts/issues/show/components/app.vue
index eeaf865a35f..0490728c6bc 100644
--- a/app/assets/javascripts/issues/show/components/app.vue
+++ b/app/assets/javascripts/issues/show/components/app.vue
@@ -6,7 +6,7 @@ import { IssuableStatus, IssuableStatusText, IssuableType } from '~/issues/const
import Poll from '~/lib/utils/poll';
import { visitUrl } from '~/lib/utils/url_utility';
import { __, sprintf } from '~/locale';
-import { IssueTypePath, IncidentTypePath, IncidentType, POLLING_DELAY } from '../constants';
+import { ISSUE_TYPE_PATH, INCIDENT_TYPE_PATH, INCIDENT_TYPE, POLLING_DELAY } from '../constants';
import eventHub from '../event_hub';
import getIssueStateQuery from '../queries/get_issue_state.query.graphql';
import Service from '../services/index';
@@ -378,15 +378,15 @@ export default {
.then((data) => {
if (
!window.location.pathname.includes(data.web_url) &&
- issueState.issueType !== IncidentType
+ issueState.issueType !== INCIDENT_TYPE
) {
visitUrl(data.web_url);
}
if (issueState.isDirty) {
const URI =
- issueState.issueType === IncidentType
- ? data.web_url.replace(IssueTypePath, IncidentTypePath)
+ issueState.issueType === INCIDENT_TYPE
+ ? data.web_url.replace(ISSUE_TYPE_PATH, INCIDENT_TYPE_PATH)
: data.web_url;
visitUrl(URI);
}
diff --git a/app/assets/javascripts/issues/show/components/fields/type.vue b/app/assets/javascripts/issues/show/components/fields/type.vue
index 9110a6924b4..75d0b9e5e76 100644
--- a/app/assets/javascripts/issues/show/components/fields/type.vue
+++ b/app/assets/javascripts/issues/show/components/fields/type.vue
@@ -2,7 +2,7 @@
import { GlFormGroup, GlDropdown, GlDropdownItem, GlIcon } from '@gitlab/ui';
import { capitalize } from 'lodash';
import { __ } from '~/locale';
-import { IssuableTypes, IncidentType } from '../../constants';
+import { issuableTypes, INCIDENT_TYPE } from '../../constants';
import getIssueStateQuery from '../../queries/get_issue_state.query.graphql';
import updateIssueStateMutation from '../../queries/update_issue_state.mutation.graphql';
@@ -12,7 +12,7 @@ export const i18n = {
export default {
i18n,
- IssuableTypes,
+ issuableTypes,
components: {
GlFormGroup,
GlIcon,
@@ -45,7 +45,7 @@ export default {
return capitalize(issueType);
},
shouldShowIncident() {
- return this.issueType === IncidentType || this.canCreateIncident;
+ return this.issueType === INCIDENT_TYPE || this.canCreateIncident;
},
},
methods: {
@@ -59,7 +59,7 @@ export default {
});
},
isShown(type) {
- return type.value !== IncidentType || this.shouldShowIncident;
+ return type.value !== INCIDENT_TYPE || this.shouldShowIncident;
},
},
};
@@ -81,7 +81,7 @@ export default {
toggle-class="dropdown-menu-toggle"
>
<gl-dropdown-item
- v-for="type in $options.IssuableTypes"
+ v-for="type in $options.issuableTypes"
v-show="isShown(type)"
:key="type.value"
:is-checked="issueState.issueType === type.value"
diff --git a/app/assets/javascripts/issues/show/components/header_actions.vue b/app/assets/javascripts/issues/show/components/header_actions.vue
index 700ef92a0f3..52c95d48a23 100644
--- a/app/assets/javascripts/issues/show/components/header_actions.vue
+++ b/app/assets/javascripts/issues/show/components/header_actions.vue
@@ -13,7 +13,7 @@ import createFlash, { FLASH_TYPES } from '~/flash';
import { EVENT_ISSUABLE_VUE_APP_CHANGE } from '~/issuable/constants';
import { IssuableType } from '~/vue_shared/issuable/show/constants';
import { IssuableStatus } from '~/issues/constants';
-import { IssueStateEvent } from '~/issues/show/constants';
+import { ISSUE_STATE_EVENT_CLOSE, ISSUE_STATE_EVENT_REOPEN } from '~/issues/show/constants';
import { capitalizeFirstCharacter } from '~/lib/utils/text_utility';
import { visitUrl } from '~/lib/utils/url_utility';
import { s__, __, sprintf } from '~/locale';
@@ -163,7 +163,7 @@ export default {
input: {
iid: this.iid.toString(),
projectPath: this.projectPath,
- stateEvent: this.isClosed ? IssueStateEvent.Reopen : IssueStateEvent.Close,
+ stateEvent: this.isClosed ? ISSUE_STATE_EVENT_REOPEN : ISSUE_STATE_EVENT_CLOSE,
},
},
})
diff --git a/app/assets/javascripts/issues/show/constants.js b/app/assets/javascripts/issues/show/constants.js
index 35f3bcdad70..a100aaf88ad 100644
--- a/app/assets/javascripts/issues/show/constants.js
+++ b/app/assets/javascripts/issues/show/constants.js
@@ -1,22 +1,20 @@
import { __ } from '~/locale';
-export const IssueStateEvent = {
- Close: 'CLOSE',
- Reopen: 'REOPEN',
-};
-
-export const STATUS_PAGE_PUBLISHED = __('Published on status page');
+export const INCIDENT_TYPE = 'incident';
+export const INCIDENT_TYPE_PATH = 'issues/incident';
+export const ISSUE_STATE_EVENT_CLOSE = 'CLOSE';
+export const ISSUE_STATE_EVENT_REOPEN = 'REOPEN';
+export const ISSUE_TYPE_PATH = 'issues';
export const JOIN_ZOOM_MEETING = __('Join Zoom meeting');
+export const POLLING_DELAY = 2000;
+export const STATUS_PAGE_PUBLISHED = __('Published on status page');
-export const IssuableTypes = [
+export const issuableTypes = [
{ value: 'issue', text: __('Issue'), icon: 'issue-type-issue' },
{ value: 'incident', text: __('Incident'), icon: 'issue-type-incident' },
];
-export const IssueTypePath = 'issues';
-export const IncidentTypePath = 'issues/incident';
-export const IncidentType = 'incident';
-
-export const issueState = { issueType: undefined, isDirty: false };
-
-export const POLLING_DELAY = 2000;
+export const issueState = {
+ issueType: undefined,
+ isDirty: false,
+};
diff --git a/app/assets/javascripts/issues/show/index.js b/app/assets/javascripts/issues/show/index.js
index 3ac781089ba..3e6736d14bf 100644
--- a/app/assets/javascripts/issues/show/index.js
+++ b/app/assets/javascripts/issues/show/index.js
@@ -6,7 +6,7 @@ import IssueApp from './components/app.vue';
import HeaderActions from './components/header_actions.vue';
import IncidentTabs from './components/incidents/incident_tabs.vue';
import SentryErrorStackTrace from './components/sentry_error_stack_trace.vue';
-import { IncidentType, issueState } from './constants';
+import { INCIDENT_TYPE, issueState } from './constants';
import apolloProvider from './graphql';
import getIssueStateQuery from './queries/get_issue_state.query.graphql';
@@ -45,7 +45,7 @@ export function initIncidentApp(issueData = {}) {
el,
apolloProvider,
provide: {
- issueType: IncidentType,
+ issueType: INCIDENT_TYPE,
canCreateIncident,
canUpdate,
fullPath,
@@ -111,7 +111,7 @@ export function initHeaderActions(store, type = '') {
bootstrapApollo({ ...issueState, issueType: el.dataset.issueType });
const canCreate =
- type === IncidentType ? el.dataset.canCreateIncident : el.dataset.canCreateIssue;
+ type === INCIDENT_TYPE ? el.dataset.canCreateIncident : el.dataset.canCreateIssue;
return new Vue({
el,
diff --git a/app/assets/javascripts/lib/utils/constants.js b/app/assets/javascripts/lib/utils/constants.js
index a108b02bcbf..36c6545164e 100644
--- a/app/assets/javascripts/lib/utils/constants.js
+++ b/app/assets/javascripts/lib/utils/constants.js
@@ -17,7 +17,6 @@ export const BV_HIDE_MODAL = 'bv::hide::modal';
export const BV_HIDE_TOOLTIP = 'bv::hide::tooltip';
export const BV_DROPDOWN_SHOW = 'bv::dropdown::show';
export const BV_DROPDOWN_HIDE = 'bv::dropdown::hide';
-export const BV_COLLAPSE_STATE = 'bv::collapse::state';
export const DEFAULT_TH_CLASSES =
'gl-bg-transparent! gl-border-b-solid! gl-border-b-gray-100! gl-p-5! gl-border-b-1!';
diff --git a/app/assets/javascripts/pages/help/index/index.js b/app/assets/javascripts/pages/help/index/index.js
index 736add8dca3..a8e67c57307 100644
--- a/app/assets/javascripts/pages/help/index/index.js
+++ b/app/assets/javascripts/pages/help/index/index.js
@@ -1,6 +1,5 @@
-import $ from 'jquery';
import docs from '~/docs/docs_bundle';
-import VersionCheckImage from '~/version_check_image';
+import initGitlabVersionCheck from '~/gitlab_version_check';
docs();
-VersionCheckImage.bindErrorEvent($('img.js-version-status-badge'));
+initGitlabVersionCheck();
diff --git a/app/assets/javascripts/pages/shared/wikis/components/wiki_form.vue b/app/assets/javascripts/pages/shared/wikis/components/wiki_form.vue
index b29e9455755..c28de88554a 100644
--- a/app/assets/javascripts/pages/shared/wikis/components/wiki_form.vue
+++ b/app/assets/javascripts/pages/shared/wikis/components/wiki_form.vue
@@ -596,7 +596,9 @@ export default {
:disabled="disableSubmitButton"
>{{ submitButtonText }}</gl-button
>
- <gl-button :href="cancelFormPath" class="float-right">{{ $options.i18n.cancel }}</gl-button>
+ <gl-button data-testid="wiki-cancel-button" :href="cancelFormPath" class="float-right">{{
+ $options.i18n.cancel
+ }}</gl-button>
</div>
</gl-form>
</template>
diff --git a/app/assets/javascripts/version_check_image.js b/app/assets/javascripts/version_check_image.js
deleted file mode 100644
index 4e00e0f11f7..00000000000
--- a/app/assets/javascripts/version_check_image.js
+++ /dev/null
@@ -1,6 +0,0 @@
-export default class VersionCheckImage {
- static bindErrorEvent(imageElement) {
- // eslint-disable-next-line @gitlab/no-global-event-off
- imageElement.off('error').on('error', () => imageElement.hide());
- }
-}
diff --git a/app/assets/javascripts/vue_shared/components/gitlab_version_check.vue b/app/assets/javascripts/vue_shared/components/gitlab_version_check.vue
new file mode 100644
index 00000000000..acddf16bd27
--- /dev/null
+++ b/app/assets/javascripts/vue_shared/components/gitlab_version_check.vue
@@ -0,0 +1,67 @@
+<script>
+import { GlBadge } from '@gitlab/ui';
+import { s__ } from '~/locale';
+import axios from '~/lib/utils/axios_utils';
+
+const STATUS_TYPES = {
+ SUCCESS: 'success',
+ WARNING: 'warning',
+ DANGER: 'danger',
+};
+
+export default {
+ name: 'GitlabVersionCheck',
+ components: {
+ GlBadge,
+ },
+ props: {
+ size: {
+ type: String,
+ required: false,
+ default: 'md',
+ },
+ },
+ data() {
+ return {
+ status: null,
+ };
+ },
+ computed: {
+ title() {
+ if (this.status === STATUS_TYPES.SUCCESS) {
+ return s__('VersionCheck|Up to date');
+ } else if (this.status === STATUS_TYPES.WARNING) {
+ return s__('VersionCheck|Update available');
+ } else if (this.status === STATUS_TYPES.DANGER) {
+ return s__('VersionCheck|Update ASAP');
+ }
+
+ return null;
+ },
+ },
+ created() {
+ this.checkGitlabVersion();
+ },
+ methods: {
+ checkGitlabVersion() {
+ axios
+ .get('/admin/version_check.json')
+ .then((res) => {
+ if (res.data) {
+ this.status = res.data.severity;
+ }
+ })
+ .catch(() => {
+ // Silently fail
+ this.status = null;
+ });
+ },
+ },
+};
+</script>
+
+<template>
+ <gl-badge v-if="status" class="version-check-badge" :variant="status" :size="size">{{
+ title
+ }}</gl-badge>
+</template>
diff --git a/app/graphql/types/packages/package_details_type.rb b/app/graphql/types/packages/package_details_type.rb
index 043cb7eff2b..07d8cf93b4e 100644
--- a/app/graphql/types/packages/package_details_type.rb
+++ b/app/graphql/types/packages/package_details_type.rb
@@ -3,6 +3,8 @@
module Types
module Packages
class PackageDetailsType < PackageType
+ include ::PackagesHelper
+
graphql_name 'PackageDetailsType'
description 'Represents a package details in the Package Registry. Note that this type is in beta and susceptible to changes'
authorize :read_package
@@ -21,6 +23,15 @@ module Types
description: 'Pipelines that built the package.',
deprecated: { reason: 'Due to scalability concerns, this field is going to be removed', milestone: '14.6' }
+ field :composer_config_repository_url, GraphQL::Types::String, null: true, description: 'Url of the Composer setup endpoint.'
+ field :composer_url, GraphQL::Types::String, null: true, description: 'Url of the Composer endpoint.'
+ field :conan_url, GraphQL::Types::String, null: true, description: 'Url of the Conan project endpoint.'
+ field :maven_url, GraphQL::Types::String, null: true, description: 'Url of the Maven project endpoint.'
+ field :npm_url, GraphQL::Types::String, null: true, description: 'Url of the NPM project endpoint.'
+ field :nuget_url, GraphQL::Types::String, null: true, description: 'Url of the Nuget project endpoint.'
+ field :pypi_setup_url, GraphQL::Types::String, null: true, description: 'Url of the PyPi project setup endpoint.'
+ field :pypi_url, GraphQL::Types::String, null: true, description: 'Url of the PyPi project endpoint.'
+
def versions
object.versions
end
@@ -32,6 +43,38 @@ module Types
object.package_files
end
end
+
+ def composer_config_repository_url
+ composer_config_repository_name(object.project.group&.id)
+ end
+
+ def composer_url
+ composer_registry_url(object.project.group&.id)
+ end
+
+ def conan_url
+ package_registry_project_url(object.project.id, :conan)
+ end
+
+ def maven_url
+ package_registry_project_url(object.project.id, :maven)
+ end
+
+ def npm_url
+ package_registry_project_url(object.project.id, :npm)
+ end
+
+ def nuget_url
+ nuget_package_registry_url(object.project.id)
+ end
+
+ def pypi_setup_url
+ package_registry_project_url(object.project.id, :pypi)
+ end
+
+ def pypi_url
+ pypi_registry_url(object.project.id)
+ end
end
end
end
diff --git a/app/helpers/packages_helper.rb b/app/helpers/packages_helper.rb
index 9e2b27de5b3..cf97fdf73e3 100644
--- a/app/helpers/packages_helper.rb
+++ b/app/helpers/packages_helper.rb
@@ -1,6 +1,8 @@
# frozen_string_literal: true
module PackagesHelper
+ include ::API::Helpers::RelatedResourcesHelpers
+
def package_sort_path(options = {})
"#{request.path}?#{options.to_param}"
end
diff --git a/app/helpers/version_check_helper.rb b/app/helpers/version_check_helper.rb
index 7875b9e4a28..48548ae9e6a 100644
--- a/app/helpers/version_check_helper.rb
+++ b/app/helpers/version_check_helper.rb
@@ -1,12 +1,11 @@
# frozen_string_literal: true
module VersionCheckHelper
- def version_status_badge
- return unless Rails.env.production?
- return unless Gitlab::CurrentSettings.version_check_enabled
- return if User.single_user&.requires_usage_stats_consent?
+ def show_version_check?
+ return false unless Gitlab::CurrentSettings.version_check_enabled
+ return false if User.single_user&.requires_usage_stats_consent?
- image_tag VersionCheck.image_url, class: 'js-version-status-badge'
+ current_user&.can_read_all_resources?
end
def link_to_version
diff --git a/app/views/admin/dashboard/index.html.haml b/app/views/admin/dashboard/index.html.haml
index 801b903395a..85b6ebfc63a 100644
--- a/app/views/admin/dashboard/index.html.haml
+++ b/app/views/admin/dashboard/index.html.haml
@@ -118,9 +118,9 @@
.gl-card-body
%h4
= s_('AdminArea|Components')
- - if Gitlab::CurrentSettings.version_check_enabled
+ - if show_version_check?
.float-right
- = version_status_badge
+ .js-gitlab-version-check{ data: { "size": "lg" } }
= link_to(sprite_icon('question'), "https://gitlab.com/gitlab-org/gitlab/-/blob/master/CHANGELOG.md", class: 'gl-ml-2', target: '_blank', rel: 'noopener noreferrer')
%p
= link_to _('GitLab'), general_admin_application_settings_path
diff --git a/app/views/admin/labels/_form.html.haml b/app/views/admin/labels/_form.html.haml
deleted file mode 100644
index abf380474e4..00000000000
--- a/app/views/admin/labels/_form.html.haml
+++ /dev/null
@@ -1,31 +0,0 @@
-= form_for [:admin, @label], html: { class: 'label-form js-requires-input' } do |f|
- = form_errors(@label)
-
- .form-group.row
- .col-sm-2.col-form-label
- = f.label :title
- .col-sm-10
- = f.text_field :title, class: "form-control gl-form-input", required: true
- .form-group.row
- .col-sm-2.col-form-label
- = f.label :description
- .col-sm-10
- = f.text_field :description, class: "form-control gl-form-input js-quick-submit"
- .form-group.row
- .col-sm-2.col-form-label
- = f.label :color, _("Background color")
- .col-sm-10
- .input-group
- .input-group-prepend
- .input-group-text.label-color-preview &nbsp;
- = f.text_field :color, class: "form-control gl-form-input"
- .form-text.text-muted
- = _('Choose any color.')
- %br
- = _("Or you can choose one of the suggested colors below")
-
- = render_suggested_colors
-
- .form-actions
- = f.submit _('Save'), class: 'btn gl-button btn-confirm js-save-button'
- = link_to _("Cancel"), admin_labels_path, class: 'btn gl-button btn-default btn-cancel'
diff --git a/app/views/admin/labels/edit.html.haml b/app/views/admin/labels/edit.html.haml
index 652ed095d00..44dd2b6a646 100644
--- a/app/views/admin/labels/edit.html.haml
+++ b/app/views/admin/labels/edit.html.haml
@@ -4,4 +4,4 @@
%h3.page-title
= _('Edit Label')
%hr
-= render 'form'
+= render 'shared/labels/form', url: admin_label_path(@label), back_path: admin_labels_path
diff --git a/app/views/admin/labels/new.html.haml b/app/views/admin/labels/new.html.haml
index 20103fb8a29..5166bdb4d20 100644
--- a/app/views/admin/labels/new.html.haml
+++ b/app/views/admin/labels/new.html.haml
@@ -2,4 +2,4 @@
%h3.page-title
= _('New Label')
%hr
-= render 'form'
+= render 'shared/labels/form', url: admin_labels_path, back_path: admin_labels_path
diff --git a/app/views/help/index.html.haml b/app/views/help/index.html.haml
index f81afd0a82e..3992cb527ed 100644
--- a/app/views/help/index.html.haml
+++ b/app/views/help/index.html.haml
@@ -4,12 +4,15 @@
= markdown_field(Gitlab::CurrentSettings.current_application_settings, :help_page_text)
%hr
-%h1
- = default_brand_title
- - if user_signed_in?
- %span= link_to_version
- = version_status_badge
- %hr
+.gl-display-flex.gl-align-items-flex-end
+ %h1.gl-mt-5.gl-mb-3
+ = default_brand_title
+ - if user_signed_in?
+ %span= link_to_version
+ - if show_version_check?
+ %span.gl-mt-5.gl-mb-3.gl-ml-3
+ .js-gitlab-version-check{ data: { "size": "lg" } }
+%hr
- unless Gitlab::CurrentSettings.help_page_hide_commercial_content?
%p.slead
diff --git a/app/views/projects/issues/_design_management.html.haml b/app/views/projects/issues/_design_management.html.haml
index a2ff9620c0c..c5ce0549816 100644
--- a/app/views/projects/issues/_design_management.html.haml
+++ b/app/views/projects/issues/_design_management.html.haml
@@ -8,7 +8,11 @@
- if @project.design_management_enabled?
- add_page_startup_graphql_call('design_management/get_design_list', { fullPath: @project.full_path, iid: @issue.iid.to_s, atVersion: nil })
- add_page_startup_graphql_call('design_management/design_permissions', { fullPath: @project.full_path, iid: @issue.iid.to_s })
- .js-design-management{ data: { project_path: @project.full_path, issue_iid: @issue.iid, issue_path: project_issue_path(@project, @issue) } }
+ .js-design-management{ data: { project_path: @project.full_path,
+ issue_iid: @issue.iid,
+ issue_path: project_issue_path(@project, @issue),
+ register_path: new_user_registration_path(redirect_to_referer: 'yes'),
+ sign_in_path: new_session_path(:user, redirect_to_referer: 'yes') } }
- else
.gl-border-solid.gl-border-1.gl-border-gray-100.gl-rounded-base.gl-mt-5.gl-p-3.gl-text-center
= enable_lfs_message
diff --git a/app/views/shared/issuable/_form.html.haml b/app/views/shared/issuable/_form.html.haml
index 4024c5b77f6..16301789b65 100644
--- a/app/views/shared/issuable/_form.html.haml
+++ b/app/views/shared/issuable/_form.html.haml
@@ -64,9 +64,9 @@
for this project.
- if issuable.new_record?
- = form.submit "#{_('Create')} #{issuable.class.model_name.human.downcase}", class: 'gl-button btn btn-confirm gl-mr-2', data: { qa_selector: 'issuable_create_button' }
+ = form.submit "#{_('Create')} #{issuable.class.model_name.human.downcase}", class: 'gl-button btn btn-confirm gl-mr-2', data: { qa_selector: 'issuable_create_button', track_experiment: 'promote_mr_approvals_in_free', track_action: 'click_button', track_label: 'submit_mr', track_value: 0 }
- else
- = form.submit _('Save changes'), class: 'gl-button btn btn-confirm gl-mr-2'
+ = form.submit _('Save changes'), class: 'gl-button btn btn-confirm gl-mr-2', data: { track_experiment: 'promote_mr_approvals_in_free', track_action: 'click_button', track_label: 'submit_mr', track_value: 0 }
- if issuable.new_record?
= link_to _('Cancel'), polymorphic_path([@project, issuable.class]), class: 'btn gl-button btn-default'
diff --git a/app/views/shared/labels/_form.html.haml b/app/views/shared/labels/_form.html.haml
index 6f65dbe4811..9c17735cd14 100644
--- a/app/views/shared/labels/_form.html.haml
+++ b/app/views/shared/labels/_form.html.haml
@@ -5,30 +5,30 @@
.col-sm-2.col-form-label
= f.label :title
.col-sm-10
- = f.text_field :title, class: "form-control js-label-title qa-label-title", required: true, autofocus: true
+ = f.text_field :title, class: "gl-form-input form-control js-label-title qa-label-title", required: true, autofocus: true
= render_if_exists 'shared/labels/create_label_help_text'
.form-group.row
.col-sm-2.col-form-label
= f.label :description
.col-sm-10
- = f.text_field :description, class: "form-control js-quick-submit qa-label-description"
+ = f.text_field :description, class: "gl-form-input form-control js-quick-submit qa-label-description"
.form-group.row
.col-sm-2.col-form-label
- = f.label :color, "Background color"
+ = f.label :color, _("Background color")
.col-sm-10
.input-group
.input-group-prepend
.input-group-text.label-color-preview &nbsp;
- = f.text_field :color, class: "form-control qa-label-color"
+ = f.text_field :color, class: "gl-form-input form-control qa-label-color"
.form-text.text-muted
- Choose any color.
+ = _('Choose any color.')
%br
- Or you can choose one of the suggested colors below
+ = _("Or you can choose one of the suggested colors below")
= render_suggested_colors
.form-actions
- if @label.persisted?
= f.submit _('Save changes'), class: 'btn gl-button btn-confirm js-save-button'
- else
- = f.submit 'Create label', class: 'btn gl-button btn-confirm js-save-button qa-label-create-button'
+ = f.submit _('Create label'), class: 'btn gl-button btn-confirm js-save-button qa-label-create-button'
= link_to _('Cancel'), back_path, class: 'btn gl-button btn-default btn-cancel'
diff --git a/app/views/shared/web_hooks/_form.html.haml b/app/views/shared/web_hooks/_form.html.haml
index 18912bf149f..5650f08b2a9 100644
--- a/app/views/shared/web_hooks/_form.html.haml
+++ b/app/views/shared/web_hooks/_form.html.haml
@@ -4,12 +4,14 @@
= form.label :url, s_('Webhooks|URL'), class: 'label-bold'
= form.text_field :url, class: 'form-control gl-form-input', placeholder: 'http://example.com/trigger-ci.json'
%p.form-text.text-muted
- = s_('Webhooks|URL must be percent-encoded if neccessary.')
+ = s_('Webhooks|URL must be percent-encoded if it contains one or more special characters.')
.form-group
= form.label :token, s_('Webhooks|Secret token'), class: 'label-bold'
= form.text_field :token, class: 'form-control gl-form-input', placeholder: ''
%p.form-text.text-muted
- = s_('Webhooks|Use this token to validate received payloads. It is sent with the request in the X-Gitlab-Token HTTP header.')
+ - code_start = '<code>'.html_safe
+ - code_end = '</code>'.html_safe
+ = s_('Webhooks|Used to validate received payloads. Sent with the request in the %{code_start}X-Gitlab-Token HTTP%{code_end} header.').html_safe % { code_start: code_start, code_end: code_end }
.form-group
= form.label :url, s_('Webhooks|Trigger'), class: 'label-bold'
%ul.list-unstyled.gl-ml-6
@@ -19,37 +21,37 @@
%strong= s_('Webhooks|Push events')
= form.text_field :push_events_branch_filter, class: 'form-control gl-form-input', placeholder: 'Branch name or wildcard pattern to trigger on (leave blank for all)'
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered by a push to the repository')
+ = s_('Webhooks|Push to the repository.')
%li
= form.check_box :tag_push_events, class: 'form-check-input'
= form.label :tag_push_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Tag push events')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when a new tag is pushed to the repository')
+ = s_('Webhooks|A new tag is pushed to the repository.')
%li
= form.check_box :note_events, class: 'form-check-input'
= form.label :note_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Comments')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when someone adds a comment')
+ = s_('Webhooks|A comment is added to an issue.')
%li
= form.check_box :confidential_note_events, class: 'form-check-input'
= form.label :confidential_note_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Confidential comments')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when someone adds a comment on a confidential issue')
+ = s_('Webhooks|A comment is added to a confidential issue.')
%li
= form.check_box :issues_events, class: 'form-check-input'
= form.label :issues_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Issues events')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when an issue is created, updated, closed, or reopened')
+ = s_('Webhooks|An issue is created, updated, closed, or reopened.')
%li
= form.check_box :confidential_issues_events, class: 'form-check-input'
= form.label :confidential_issues_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Confidential issues events')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when a confidential issue is created, updated, closed, or reopened')
+ = s_('Webhooks|A confidential issue is created, updated, closed, or reopened.')
- if @group
= render_if_exists 'groups/hooks/member_events', form: form
= render_if_exists 'groups/hooks/subgroup_events', form: form
@@ -58,43 +60,43 @@
= form.label :merge_requests_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Merge request events')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when a merge request is created, updated, or merged')
+ = s_('Webhooks|A merge request is created, updated, or merged.')
%li
= form.check_box :job_events, class: 'form-check-input'
= form.label :job_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Job events')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when the job status changes')
+ = s_("Webhooks|A job's status changes.")
%li
= form.check_box :pipeline_events, class: 'form-check-input'
= form.label :pipeline_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Pipeline events')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when the pipeline status changes')
+ = s_("Webhooks|A pipeline's status changes.")
%li
= form.check_box :wiki_page_events, class: 'form-check-input'
= form.label :wiki_page_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Wiki page events')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when a wiki page is created or updated')
+ = s_('Webhooks|A wiki page is created or updated.')
%li
= form.check_box :deployment_events, class: 'form-check-input'
= form.label :deployment_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Deployment events')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when a deployment starts, finishes, fails, or is canceled')
+ = s_('Webhooks|A deployment starts, finishes, fails, or is canceled.')
%li
= form.check_box :feature_flag_events, class: 'form-check-input'
= form.label :feature_flag_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Feature flag events')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when a feature flag is turned on or off')
+ = s_('Webhooks|A feature flag is turned on or off.')
%li
= form.check_box :releases_events, class: 'form-check-input'
= form.label :releases_events, class: 'list-label form-check-label gl-ml-1' do
%strong= s_('Webhooks|Releases events')
%p.text-muted.gl-ml-1
- = s_('Webhooks|URL is triggered when a release is created or updated')
+ = s_('Webhooks|A release is created or updated.')
.form-group
= form.label :enable_ssl_verification, s_('Webhooks|SSL verification'), class: 'label-bold checkbox'
.form-check
diff --git a/app/views/shared/web_hooks/_index.html.haml b/app/views/shared/web_hooks/_index.html.haml
index f1eef5d7f0f..5d07b0f95ab 100644
--- a/app/views/shared/web_hooks/_index.html.haml
+++ b/app/views/shared/web_hooks/_index.html.haml
@@ -11,4 +11,4 @@
= render 'shared/web_hooks/hook', hook: hook
- else
%p.text-center.gl-mt-3.gl-mb-3
- = _('No webhooks found, add one in the form above.')
+ = _('No webhooks enabled. Select trigger events above.')