diff options
author | GitLab Bot <gitlab-bot@gitlab.com> | 2020-01-14 15:07:55 +0000 |
---|---|---|
committer | GitLab Bot <gitlab-bot@gitlab.com> | 2020-01-14 15:07:55 +0000 |
commit | 85e494935a8726dc98bb19ffa584488420e5011e (patch) | |
tree | 5acf279dab81a2363e4504a9679c32c16510542b /app | |
parent | 4ce0bee95df15c05cdb0d777eba31fe753bc443b (diff) | |
download | gitlab-ce-85e494935a8726dc98bb19ffa584488420e5011e.tar.gz |
Add latest changes from gitlab-org/gitlab@master
Diffstat (limited to 'app')
20 files changed, 132 insertions, 26 deletions
diff --git a/app/assets/javascripts/repository/components/last_commit.vue b/app/assets/javascripts/repository/components/last_commit.vue index 70678b0db37..8e7529899c0 100644 --- a/app/assets/javascripts/repository/components/last_commit.vue +++ b/app/assets/javascripts/repository/components/last_commit.vue @@ -90,7 +90,7 @@ export default { <template> <div class="info-well d-none d-sm-flex project-last-commit commit p-3"> - <gl-loading-icon v-if="isLoading" size="md" class="m-auto" /> + <gl-loading-icon v-if="isLoading" size="md" color="dark" class="m-auto" /> <template v-else> <user-avatar-link v-if="commit.author" diff --git a/app/assets/javascripts/repository/components/preview/index.vue b/app/assets/javascripts/repository/components/preview/index.vue index 6b3822151ff..2bc93c3f1c1 100644 --- a/app/assets/javascripts/repository/components/preview/index.vue +++ b/app/assets/javascripts/repository/components/preview/index.vue @@ -44,7 +44,7 @@ export default { </div> </div> <div class="blob-viewer"> - <gl-loading-icon v-if="loading > 0" size="md" class="my-4 mx-auto" /> + <gl-loading-icon v-if="loading > 0" size="md" color="dark" class="my-4 mx-auto" /> <div v-else-if="readme" v-html="readme.html"></div> </div> </article> diff --git a/app/assets/javascripts/repository/components/table/index.vue b/app/assets/javascripts/repository/components/table/index.vue index 8f2e9264bca..29a3340b83d 100644 --- a/app/assets/javascripts/repository/components/table/index.vue +++ b/app/assets/javascripts/repository/components/table/index.vue @@ -34,6 +34,11 @@ export default { type: Boolean, required: true, }, + loadingPath: { + type: String, + required: false, + default: '', + }, }, data() { return { @@ -69,7 +74,12 @@ export default { <table :aria-label="tableCaption" class="table tree-table qa-file-tree" aria-live="polite"> <table-header v-once /> <tbody> - <parent-row v-show="showParentRow" :commit-ref="ref" :path="path" /> + <parent-row + v-show="showParentRow" + :commit-ref="ref" + :path="path" + :loading-path="loadingPath" + /> <template v-for="val in entries"> <table-row v-for="entry in val" @@ -84,6 +94,7 @@ export default { :url="entry.webUrl" :submodule-tree-url="entry.treeUrl" :lfs-oid="entry.lfsOid" + :loading-path="loadingPath" /> </template> <template v-if="isLoading"> diff --git a/app/assets/javascripts/repository/components/table/parent_row.vue b/app/assets/javascripts/repository/components/table/parent_row.vue index 3c39f404226..70a188f98cc 100644 --- a/app/assets/javascripts/repository/components/table/parent_row.vue +++ b/app/assets/javascripts/repository/components/table/parent_row.vue @@ -1,5 +1,10 @@ <script> +import { GlLoadingIcon } from '@gitlab/ui'; + export default { + components: { + GlLoadingIcon, + }, props: { commitRef: { type: String, @@ -9,13 +14,21 @@ export default { type: String, required: true, }, + loadingPath: { + type: String, + required: false, + default: null, + }, }, computed: { - parentRoute() { + parentPath() { const splitArray = this.path.split('/'); splitArray.pop(); - return { path: `/tree/${this.commitRef}/${splitArray.join('/')}` }; + return splitArray.join('/'); + }, + parentRoute() { + return { path: `/tree/${this.commitRef}/${this.parentPath}` }; }, }, methods: { @@ -29,7 +42,13 @@ export default { <template> <tr class="tree-item"> <td colspan="3" class="tree-item-file-name" @click.self="clickRow"> - <router-link :to="parentRoute" :aria-label="__('Go to parent')"> + <gl-loading-icon + v-if="parentPath === loadingPath" + size="sm" + inline + class="d-inline-block align-text-bottom" + /> + <router-link v-else :to="parentRoute" :aria-label="__('Go to parent')"> .. </router-link> </td> diff --git a/app/assets/javascripts/repository/components/table/row.vue b/app/assets/javascripts/repository/components/table/row.vue index cf0457a2abf..a8e13241c37 100644 --- a/app/assets/javascripts/repository/components/table/row.vue +++ b/app/assets/javascripts/repository/components/table/row.vue @@ -1,5 +1,5 @@ <script> -import { GlBadge, GlLink, GlSkeletonLoading, GlTooltipDirective } from '@gitlab/ui'; +import { GlBadge, GlLink, GlSkeletonLoading, GlTooltipDirective, GlLoadingIcon } from '@gitlab/ui'; import { visitUrl } from '~/lib/utils/url_utility'; import TimeagoTooltip from '~/vue_shared/components/time_ago_tooltip.vue'; import Icon from '~/vue_shared/components/icon.vue'; @@ -12,6 +12,7 @@ export default { GlBadge, GlLink, GlSkeletonLoading, + GlLoadingIcon, TimeagoTooltip, Icon, }, @@ -76,6 +77,11 @@ export default { required: false, default: null, }, + loadingPath: { + type: String, + required: false, + default: '', + }, }, data() { return { @@ -125,7 +131,13 @@ export default { <template> <tr :class="`file_${id}`" class="tree-item" @click="openRow"> <td class="tree-item-file-name"> - <i :aria-label="type" role="img" :class="iconName" class="fa fa-fw"></i> + <gl-loading-icon + v-if="path === loadingPath" + size="sm" + inline + class="d-inline-block align-text-bottom fa-fw" + /> + <i v-else :aria-label="type" role="img" :class="iconName" class="fa fa-fw"></i> <component :is="linkComponent" :to="routerLinkTo" :href="url" class="str-truncated"> {{ fullPath }} </component> diff --git a/app/assets/javascripts/repository/components/tree_content.vue b/app/assets/javascripts/repository/components/tree_content.vue index 949e653fc8f..c30d6f05c6a 100644 --- a/app/assets/javascripts/repository/components/tree_content.vue +++ b/app/assets/javascripts/repository/components/tree_content.vue @@ -27,6 +27,11 @@ export default { required: false, default: '/', }, + loadingPath: { + type: String, + required: false, + default: '', + }, }, data() { return { @@ -109,7 +114,12 @@ export default { <template> <div> - <file-table :path="path" :entries="entries" :is-loading="isLoadingFiles" /> + <file-table + :path="path" + :entries="entries" + :is-loading="isLoadingFiles" + :loading-path="loadingPath" + /> <file-preview v-if="readme" :blob="readme" /> </div> </template> diff --git a/app/assets/javascripts/repository/mixins/preload.js b/app/assets/javascripts/repository/mixins/preload.js new file mode 100644 index 00000000000..e68996245a8 --- /dev/null +++ b/app/assets/javascripts/repository/mixins/preload.js @@ -0,0 +1,36 @@ +import getFiles from '../queries/getFiles.query.graphql'; +import getRefMixin from './get_ref'; +import getProjectPath from '../queries/getProjectPath.query.graphql'; + +export default { + mixins: [getRefMixin], + apollo: { + projectPath: { + query: getProjectPath, + }, + }, + data() { + return { projectPath: '', loadingPath: null }; + }, + beforeRouteUpdate(to, from, next) { + this.preload(to.params.pathMatch, next); + }, + methods: { + preload(path, next) { + this.loadingPath = path.replace(/^\//, ''); + + return this.$apollo + .query({ + query: getFiles, + variables: { + projectPath: this.projectPath, + ref: this.ref, + path: this.loadingPath, + nextPageCursor: '', + pageSize: 100, + }, + }) + .then(() => next()); + }, + }, +}; diff --git a/app/assets/javascripts/repository/pages/tree.vue b/app/assets/javascripts/repository/pages/tree.vue index dd4d437f4dd..adc332fa370 100644 --- a/app/assets/javascripts/repository/pages/tree.vue +++ b/app/assets/javascripts/repository/pages/tree.vue @@ -1,11 +1,13 @@ <script> import TreeContent from '../components/tree_content.vue'; import { updateElementsVisibility } from '../utils/dom'; +import preloadMixin from '../mixins/preload'; export default { components: { TreeContent, }, + mixins: [preloadMixin], props: { path: { type: String, @@ -34,5 +36,5 @@ export default { </script> <template> - <tree-content :path="path" /> + <tree-content :path="path" :loading-path="loadingPath" /> </template> diff --git a/app/controllers/projects/wikis_controller.rb b/app/controllers/projects/wikis_controller.rb index fb06299676c..cfc0925d9e1 100644 --- a/app/controllers/projects/wikis_controller.rb +++ b/app/controllers/projects/wikis_controller.rb @@ -39,6 +39,10 @@ class Projects::WikisController < Projects::ApplicationController if @page set_encoding_error unless valid_encoding? + # Assign vars expected by MarkupHelper + @ref = params[:version_id] + @path = @page.path + render 'show' elsif file_blob send_blob(@project_wiki.repository, file_blob) diff --git a/app/helpers/markup_helper.rb b/app/helpers/markup_helper.rb index e1e756c2f4c..657e5accdab 100644 --- a/app/helpers/markup_helper.rb +++ b/app/helpers/markup_helper.rb @@ -132,6 +132,7 @@ module MarkupHelper pipeline: :wiki, project: @project, project_wiki: @project_wiki, + repository: @project_wiki.repository, page_slug: wiki_page.slug, issuable_state_filter_enabled: true ) diff --git a/app/models/ci/pipeline.rb b/app/models/ci/pipeline.rb index 5ad3a9b4431..663389050d1 100644 --- a/app/models/ci/pipeline.rb +++ b/app/models/ci/pipeline.rb @@ -26,7 +26,7 @@ module Ci belongs_to :merge_request, class_name: 'MergeRequest' belongs_to :external_pull_request - has_internal_id :iid, scope: :project, presence: false, ensure_if: -> { !importing? }, init: ->(s) do + has_internal_id :iid, scope: :project, presence: false, track_if: -> { !importing? }, ensure_if: -> { !importing? }, init: ->(s) do s&.project&.all_pipelines&.maximum(:iid) || s&.project&.all_pipelines&.count end diff --git a/app/models/concerns/atomic_internal_id.rb b/app/models/concerns/atomic_internal_id.rb index 64df265dc25..3e9b084e784 100644 --- a/app/models/concerns/atomic_internal_id.rb +++ b/app/models/concerns/atomic_internal_id.rb @@ -27,13 +27,13 @@ module AtomicInternalId extend ActiveSupport::Concern class_methods do - def has_internal_id(column, scope:, init:, ensure_if: nil, presence: true) # rubocop:disable Naming/PredicateName + def has_internal_id(column, scope:, init:, ensure_if: nil, track_if: nil, presence: true) # rubocop:disable Naming/PredicateName # We require init here to retain the ability to recalculate in the absence of a - # InternaLId record (we may delete records in `internal_ids` for example). + # InternalId record (we may delete records in `internal_ids` for example). raise "has_internal_id requires a init block, none given." unless init raise "has_internal_id needs to be defined on association." unless self.reflect_on_association(scope) - before_validation :"track_#{scope}_#{column}!", on: :create + before_validation :"track_#{scope}_#{column}!", on: :create, if: track_if before_validation :"ensure_#{scope}_#{column}!", on: :create, if: ensure_if validates column, presence: presence diff --git a/app/models/deployment.rb b/app/models/deployment.rb index 5a22a6ada9d..74cc7f93580 100644 --- a/app/models/deployment.rb +++ b/app/models/deployment.rb @@ -5,6 +5,7 @@ class Deployment < ApplicationRecord include IidRoutes include AfterCommitQueue include UpdatedAtFilterable + include Importable include Gitlab::Utils::StrongMemoize belongs_to :project, required: true @@ -17,7 +18,7 @@ class Deployment < ApplicationRecord has_many :merge_requests, through: :deployment_merge_requests - has_internal_id :iid, scope: :project, init: ->(s) do + has_internal_id :iid, scope: :project, track_if: -> { !importing? }, init: ->(s) do Deployment.where(project: s.project).maximum(:iid) if s&.project end diff --git a/app/models/issue.rb b/app/models/issue.rb index da6450c6092..bf600278162 100644 --- a/app/models/issue.rb +++ b/app/models/issue.rb @@ -31,7 +31,7 @@ class Issue < ApplicationRecord belongs_to :duplicated_to, class_name: 'Issue' belongs_to :closed_by, class_name: 'User' - has_internal_id :iid, scope: :project, init: ->(s) { s&.project&.issues&.maximum(:iid) } + has_internal_id :iid, scope: :project, track_if: -> { !importing? }, init: ->(s) { s&.project&.issues&.maximum(:iid) } has_many :issue_milestones has_many :milestones, through: :issue_milestones @@ -78,8 +78,8 @@ class Issue < ApplicationRecord ignore_column :state, remove_with: '12.7', remove_after: '2019-12-22' - after_commit :expire_etag_cache - after_save :ensure_metrics, unless: :imported? + after_commit :expire_etag_cache, unless: :importing? + after_save :ensure_metrics, unless: :importing? attr_spammable :title, spam_title: true attr_spammable :description, spam_description: true diff --git a/app/models/merge_request.rb b/app/models/merge_request.rb index 61f10620e39..6be14abe744 100644 --- a/app/models/merge_request.rb +++ b/app/models/merge_request.rb @@ -31,7 +31,7 @@ class MergeRequest < ApplicationRecord belongs_to :source_project, class_name: "Project" belongs_to :merge_user, class_name: "User" - has_internal_id :iid, scope: :target_project, init: ->(s) { s&.target_project&.merge_requests&.maximum(:iid) } + has_internal_id :iid, scope: :target_project, track_if: -> { !importing? }, init: ->(s) { s&.target_project&.merge_requests&.maximum(:iid) } has_many :merge_request_diffs @@ -97,8 +97,8 @@ class MergeRequest < ApplicationRecord after_create :ensure_merge_request_diff after_update :clear_memoized_shas after_update :reload_diff_if_branch_changed - after_save :ensure_metrics - after_commit :expire_etag_cache + after_save :ensure_metrics, unless: :importing? + after_commit :expire_etag_cache, unless: :importing? # When this attribute is true some MR validation is ignored # It allows us to close or modify broken merge requests diff --git a/app/models/merge_request_diff.rb b/app/models/merge_request_diff.rb index 71a344e69e3..fa633a1a725 100644 --- a/app/models/merge_request_diff.rb +++ b/app/models/merge_request_diff.rb @@ -138,7 +138,7 @@ class MergeRequestDiff < ApplicationRecord # All diff information is collected from repository after object is created. # It allows you to override variables like head_commit_sha before getting diff. after_create :save_git_content, unless: :importing? - after_create_commit :set_as_latest_diff + after_create_commit :set_as_latest_diff, unless: :importing? after_save :update_external_diff_store, if: -> { !importing? && saved_change_to_external_diff? } diff --git a/app/models/milestone.rb b/app/models/milestone.rb index 920c28aeceb..5da92fc4bc5 100644 --- a/app/models/milestone.rb +++ b/app/models/milestone.rb @@ -17,6 +17,7 @@ class Milestone < ApplicationRecord include StripAttribute include Milestoneish include FromUnion + include Importable include Gitlab::SQL::Pattern prepend_if_ee('::EE::Milestone') # rubocop: disable Cop/InjectEnterpriseEditionModule @@ -30,8 +31,8 @@ class Milestone < ApplicationRecord has_many :milestone_releases has_many :releases, through: :milestone_releases - has_internal_id :iid, scope: :project, init: ->(s) { s&.project&.milestones&.maximum(:iid) } - has_internal_id :iid, scope: :group, init: ->(s) { s&.group&.milestones&.maximum(:iid) } + has_internal_id :iid, scope: :project, track_if: -> { !importing? }, init: ->(s) { s&.project&.milestones&.maximum(:iid) } + has_internal_id :iid, scope: :group, track_if: -> { !importing? }, init: ->(s) { s&.group&.milestones&.maximum(:iid) } has_many :issues has_many :labels, -> { distinct.reorder('labels.title') }, through: :issues diff --git a/app/models/release.rb b/app/models/release.rb index 823fd61eebd..ecfae554fe0 100644 --- a/app/models/release.rb +++ b/app/models/release.rb @@ -3,6 +3,7 @@ class Release < ApplicationRecord include Presentable include CacheMarkdownField + include Importable include Gitlab::Utils::StrongMemoize cache_markdown_field :description @@ -33,8 +34,8 @@ class Release < ApplicationRecord delegate :repository, to: :project - after_commit :create_evidence!, on: :create - after_commit :notify_new_release, on: :create + after_commit :create_evidence!, on: :create, unless: :importing? + after_commit :notify_new_release, on: :create, unless: :importing? MAX_NUMBER_TO_DISPLAY = 3 diff --git a/app/models/user.rb b/app/models/user.rb index b9efbcdf502..6442e74bbe3 100644 --- a/app/models/user.rb +++ b/app/models/user.rb @@ -20,6 +20,7 @@ class User < ApplicationRecord include WithUploads include OptionallySearch include FromUnion + include BatchDestroyDependentAssociations DEFAULT_NOTIFICATION_LEVEL = :participating diff --git a/app/services/users/destroy_service.rb b/app/services/users/destroy_service.rb index e341c7f0537..643ebdc6839 100644 --- a/app/services/users/destroy_service.rb +++ b/app/services/users/destroy_service.rb @@ -56,6 +56,13 @@ module Users MigrateToGhostUserService.new(user).execute unless options[:hard_delete] + if Feature.enabled?(:destroy_user_associations_in_batches) + # Rails attempts to load all related records into memory before + # destroying: https://github.com/rails/rails/issues/22510 + # This ensures we delete records in batches. + user.destroy_dependent_associations_in_batches + end + # Destroy the namespace after destroying the user since certain methods may depend on the namespace existing user_data = user.destroy namespace.destroy |