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
diff options
context:
space:
mode:
authorGitLab Bot <gitlab-bot@gitlab.com>2022-05-19 10:33:21 +0300
committerGitLab Bot <gitlab-bot@gitlab.com>2022-05-19 10:33:21 +0300
commit36a59d088eca61b834191dacea009677a96c052f (patch)
treee4f33972dab5d8ef79e3944a9f403035fceea43f /app/services/projects
parenta1761f15ec2cae7c7f7bbda39a75494add0dfd6f (diff)
Add latest changes from gitlab-org/gitlab@15-0-stable-eev15.0.0-rc42
Diffstat (limited to 'app/services/projects')
-rw-r--r--app/services/projects/after_import_service.rb43
-rw-r--r--app/services/projects/android_target_platform_detector_service.rb35
-rw-r--r--app/services/projects/blame_service.rb65
-rw-r--r--app/services/projects/branches_by_mode_service.rb2
-rw-r--r--app/services/projects/container_repository/cleanup_tags_service.rb5
-rw-r--r--app/services/projects/container_repository/delete_tags_service.rb18
-rw-r--r--app/services/projects/container_repository/gitlab/delete_tags_service.rb7
-rw-r--r--app/services/projects/create_service.rb33
-rw-r--r--app/services/projects/group_links/create_service.rb35
-rw-r--r--app/services/projects/in_product_marketing_campaign_emails_service.rb57
-rw-r--r--app/services/projects/lfs_pointers/lfs_download_service.rb2
-rw-r--r--app/services/projects/open_issues_count_service.rb93
-rw-r--r--app/services/projects/overwrite_project_service.rb2
-rw-r--r--app/services/projects/participants_service.rb10
-rw-r--r--app/services/projects/prometheus/alerts/alert_params.rb17
-rw-r--r--app/services/projects/prometheus/alerts/create_service.rb15
-rw-r--r--app/services/projects/prometheus/alerts/destroy_service.rb13
-rw-r--r--app/services/projects/prometheus/alerts/update_service.rb15
-rw-r--r--app/services/projects/prometheus/metrics/base_service.rb30
-rw-r--r--app/services/projects/prometheus/metrics/destroy_service.rb1
-rw-r--r--app/services/projects/prometheus/metrics/update_service.rb29
-rw-r--r--app/services/projects/record_target_platforms_service.rb34
-rw-r--r--app/services/projects/update_pages_service.rb5
-rw-r--r--app/services/projects/update_remote_mirror_service.rb2
24 files changed, 286 insertions, 282 deletions
diff --git a/app/services/projects/after_import_service.rb b/app/services/projects/after_import_service.rb
deleted file mode 100644
index bb0d084d191..00000000000
--- a/app/services/projects/after_import_service.rb
+++ /dev/null
@@ -1,43 +0,0 @@
-# frozen_string_literal: true
-
-module Projects
- class AfterImportService
- RESERVED_REF_PREFIXES = Repository::RESERVED_REFS_NAMES.map { |n| File.join('refs', n, '/') }
-
- def initialize(project)
- @project = project
- end
-
- def execute
- service = Repositories::HousekeepingService.new(@project)
-
- service.execute do
- import_failure_service.with_retry(action: 'delete_all_refs') do
- repository.delete_all_refs_except(RESERVED_REF_PREFIXES)
- end
- end
-
- # Right now we don't actually have a way to know if a project
- # import actually changed, so we increment the counter to avoid
- # causing GC to run every time.
- service.increment!
- rescue Repositories::HousekeepingService::LeaseTaken => e
- Gitlab::Import::Logger.info(
- message: 'Project housekeeping failed',
- project_full_path: @project.full_path,
- project_id: @project.id,
- 'error.message' => e.message
- )
- end
-
- private
-
- def import_failure_service
- Gitlab::ImportExport::ImportFailureService.new(@project)
- end
-
- def repository
- @project.repository
- end
- end
-end
diff --git a/app/services/projects/android_target_platform_detector_service.rb b/app/services/projects/android_target_platform_detector_service.rb
new file mode 100644
index 00000000000..11635ad18d5
--- /dev/null
+++ b/app/services/projects/android_target_platform_detector_service.rb
@@ -0,0 +1,35 @@
+# frozen_string_literal: true
+
+module Projects
+ # Service class to detect if a project is made to run on the Android platform.
+ #
+ # This service searches for an AndroidManifest.xml file which all Android app
+ # project must have. It returns the symbol :android if the given project is an
+ # Android app project.
+ #
+ # Ref: https://developer.android.com/guide/topics/manifest/manifest-intro
+ #
+ # Example usage:
+ # > AndroidTargetPlatformDetectorService.new(a_project).execute
+ # => nil
+ # > AndroidTargetPlatformDetectorService.new(an_android_project).execute
+ # => :android
+ class AndroidTargetPlatformDetectorService < BaseService
+ # <manifest> element is required and must occur once inside AndroidManifest.xml
+ MANIFEST_FILE_SEARCH_QUERY = '<manifest filename:AndroidManifest.xml'
+
+ def execute
+ detect
+ end
+
+ private
+
+ def file_finder
+ @file_finder ||= ::Gitlab::FileFinder.new(project, project.default_branch)
+ end
+
+ def detect
+ return :android if file_finder.find(MANIFEST_FILE_SEARCH_QUERY).present?
+ end
+ end
+end
diff --git a/app/services/projects/blame_service.rb b/app/services/projects/blame_service.rb
new file mode 100644
index 00000000000..f7c1240a3ba
--- /dev/null
+++ b/app/services/projects/blame_service.rb
@@ -0,0 +1,65 @@
+# frozen_string_literal: true
+
+# Service class to correctly initialize Gitlab::Blame and Kaminari pagination
+# objects
+module Projects
+ class BlameService
+ PER_PAGE = 1000
+
+ def initialize(blob, commit, params)
+ @blob = blob
+ @commit = commit
+ @page = extract_page(params)
+ end
+
+ def blame
+ Gitlab::Blame.new(blob, commit, range: blame_range)
+ end
+
+ def pagination
+ return unless pagination_enabled?
+
+ Kaminari.paginate_array([], total_count: blob_lines_count)
+ .page(page)
+ .per(per_page)
+ .limit(per_page)
+ end
+
+ private
+
+ attr_reader :blob, :commit, :page
+
+ def blame_range
+ return unless pagination_enabled?
+
+ first_line = (page - 1) * per_page + 1
+ last_line = (first_line + per_page).to_i - 1
+
+ first_line..last_line
+ end
+
+ def extract_page(params)
+ page = params.fetch(:page, 1).to_i
+
+ return 1 if page < 1 || overlimit?(page)
+
+ page
+ end
+
+ def per_page
+ PER_PAGE
+ end
+
+ def overlimit?(page)
+ page * per_page >= blob_lines_count + per_page
+ end
+
+ def blob_lines_count
+ @blob_lines_count ||= blob.data.lines.count
+ end
+
+ def pagination_enabled?
+ Feature.enabled?(:blame_page_pagination, commit.project)
+ end
+ end
+end
diff --git a/app/services/projects/branches_by_mode_service.rb b/app/services/projects/branches_by_mode_service.rb
index 090671cc79a..0248f997a03 100644
--- a/app/services/projects/branches_by_mode_service.rb
+++ b/app/services/projects/branches_by_mode_service.rb
@@ -37,7 +37,7 @@ class Projects::BranchesByModeService
def use_gitaly_pagination?
return false if params[:page].present? || params[:search].present?
- Feature.enabled?(:branch_list_keyset_pagination, project, default_enabled: :yaml)
+ Feature.enabled?(:branch_list_keyset_pagination, project)
end
def fetch_branches_via_offset_pagination
diff --git a/app/services/projects/container_repository/cleanup_tags_service.rb b/app/services/projects/container_repository/cleanup_tags_service.rb
index 72f3fddb4c3..0a8e8e72766 100644
--- a/app/services/projects/container_repository/cleanup_tags_service.rb
+++ b/app/services/projects/container_repository/cleanup_tags_service.rb
@@ -117,7 +117,6 @@ module Projects
@counts[:before_truncate_size] = @tags.size
@counts[:after_truncate_size] = @tags.size
- return unless throttling_enabled?
return if max_list_size == 0
# truncate the list to make sure that after the #filter_keep_n
@@ -151,10 +150,6 @@ module Projects
!!result
end
- def throttling_enabled?
- Feature.enabled?(:container_registry_expiration_policies_throttling, default_enabled: :yaml)
- end
-
def max_list_size
::Gitlab::CurrentSettings.current_application_settings.container_registry_cleanup_tags_service_max_list_size.to_i
end
diff --git a/app/services/projects/container_repository/delete_tags_service.rb b/app/services/projects/container_repository/delete_tags_service.rb
index b4a57c70111..a3e533c670e 100644
--- a/app/services/projects/container_repository/delete_tags_service.rb
+++ b/app/services/projects/container_repository/delete_tags_service.rb
@@ -8,13 +8,13 @@ module Projects
def execute(container_repository)
@container_repository = container_repository
- unless params[:container_expiration_policy]
+ unless container_expiration_policy?
return error('access denied') unless can?(current_user, :destroy_container_image, project)
end
@tag_names = params[:tags]
return error('not tags specified') if @tag_names.blank?
- return error('repository importing') if @container_repository.migration_importing?
+ return error('repository importing') if cancel_while_importing?
delete_tags
end
@@ -49,6 +49,20 @@ module Projects
log_error(log_data)
end
end
+
+ def cancel_while_importing?
+ return true if @container_repository.importing?
+
+ if container_expiration_policy?
+ return @container_repository.pre_importing? || @container_repository.pre_import_done?
+ end
+
+ false
+ end
+
+ def container_expiration_policy?
+ params[:container_expiration_policy].present?
+ end
end
end
end
diff --git a/app/services/projects/container_repository/gitlab/delete_tags_service.rb b/app/services/projects/container_repository/gitlab/delete_tags_service.rb
index f109cb0ca20..81cef554dec 100644
--- a/app/services/projects/container_repository/gitlab/delete_tags_service.rb
+++ b/app/services/projects/container_repository/gitlab/delete_tags_service.rb
@@ -46,18 +46,11 @@ module Projects
end
def timeout?(start_time)
- return false unless throttling_enabled?
return false if service_timeout.in?(DISABLED_TIMEOUTS)
(Time.zone.now - start_time) > service_timeout
end
- def throttling_enabled?
- strong_memoize(:feature_flag) do
- Feature.enabled?(:container_registry_expiration_policies_throttling, default_enabled: :yaml)
- end
- end
-
def service_timeout
::Gitlab::CurrentSettings.current_application_settings.container_registry_delete_tags_service_timeout
end
diff --git a/app/services/projects/create_service.rb b/app/services/projects/create_service.rb
index 3e26c8c35b2..c7f284bec9b 100644
--- a/app/services/projects/create_service.rb
+++ b/app/services/projects/create_service.rb
@@ -4,6 +4,9 @@ module Projects
class CreateService < BaseService
include ValidatesClassificationLabel
+ ImportSourceDisabledError = Class.new(StandardError)
+ INTERNAL_IMPORT_SOURCES = %w[bare_repository gitlab_custom_project_template gitlab_project_migration].freeze
+
def initialize(user, params)
@current_user = user
@params = params.dup
@@ -25,6 +28,8 @@ module Projects
@project = Project.new(params)
+ validate_import_source_enabled!
+
@project.visibility_level = @project.group.visibility_level unless @project.visibility_level_allowed_by_group?
# If a project is newly created it should have shared runners settings
@@ -77,6 +82,9 @@ module Projects
rescue ActiveRecord::RecordInvalid => e
message = "Unable to save #{e.inspect}: #{e.record.errors.full_messages.join(", ")}"
fail(error: message)
+ rescue ImportSourceDisabledError => e
+ @project.errors.add(:import_source_disabled, e.message) if @project
+ fail(error: e.message)
rescue StandardError => e
@project.errors.add(:base, e.message) if @project
fail(error: e.message)
@@ -124,11 +132,7 @@ module Projects
end
def create_project_settings
- if Feature.enabled?(:create_project_settings, default_enabled: :yaml)
- @project.project_setting.save if @project.project_setting.changed?
- else
- @project.create_project_setting unless @project.project_setting
- end
+ @project.project_setting.save if @project.project_setting.changed?
end
# Add an authorization for the current user authorizations inline
@@ -157,6 +161,13 @@ module Projects
)
else
@project.add_owner(@project.namespace.owner, current_user: current_user)
+ # During the process of adding a project owner, a check on permissions is made on the user which caches
+ # the max member access for that user on this project.
+ # Since that is `0` before the member is created - and we are still inside the request
+ # cycle when we need to do other operations that might check those permissions (e.g. write a commit)
+ # we need to purge that cache so that the updated permissions is fetched instead of using the outdated cached value of 0
+ # from before member creation
+ @project.team.purge_member_access_cache_for_user_id(@project.namespace.owner.id)
end
end
@@ -242,6 +253,18 @@ module Projects
private
+ def validate_import_source_enabled!
+ return unless @params[:import_type]
+
+ import_type = @params[:import_type].to_s
+
+ return if INTERNAL_IMPORT_SOURCES.include?(import_type)
+
+ unless ::Gitlab::CurrentSettings.import_sources&.include?(import_type)
+ raise ImportSourceDisabledError, "#{import_type} import source is disabled"
+ end
+ end
+
def parent_namespace
@parent_namespace ||= Namespace.find_by_id(@params[:namespace_id]) || current_user.namespace
end
diff --git a/app/services/projects/group_links/create_service.rb b/app/services/projects/group_links/create_service.rb
index a0232779c97..72036aaff35 100644
--- a/app/services/projects/group_links/create_service.rb
+++ b/app/services/projects/group_links/create_service.rb
@@ -3,26 +3,31 @@
module Projects
module GroupLinks
class CreateService < BaseService
- def execute(group)
- return error('Not Found', 404) unless group && can?(current_user, :read_namespace, group)
+ include GroupLinkable
- link = project.project_group_links.new(
- group: group,
- group_access: params[:link_group_access],
- expires_at: params[:expires_at]
- )
+ def initialize(project, shared_with_group, user, params)
+ @shared_with_group = shared_with_group
- if link.save
- setup_authorizations(group)
- success(link: link)
- else
- error(link.errors.full_messages.to_sentence, 409)
- end
+ super(project, user, params)
end
private
- def setup_authorizations(group)
+ delegate :root_ancestor, to: :project
+
+ def valid_to_create?
+ can?(current_user, :read_namespace, shared_with_group) && sharing_allowed?
+ end
+
+ def build_link
+ @link = project.project_group_links.new(
+ group: shared_with_group,
+ group_access: params[:link_group_access],
+ expires_at: params[:expires_at]
+ )
+ end
+
+ def setup_authorizations
AuthorizedProjectUpdate::ProjectRecalculateWorker.perform_async(project.id)
# AuthorizedProjectsWorker uses an exclusive lease per user but
@@ -30,7 +35,7 @@ module Projects
# compare the inconsistency rates of both approaches, we still run
# AuthorizedProjectsWorker but with some delay and lower urgency as a
# safety net.
- group.refresh_members_authorized_projects(
+ shared_with_group.refresh_members_authorized_projects(
blocking: false,
priority: UserProjectAccessChangedService::LOW_PRIORITY
)
diff --git a/app/services/projects/in_product_marketing_campaign_emails_service.rb b/app/services/projects/in_product_marketing_campaign_emails_service.rb
new file mode 100644
index 00000000000..249a2d89fc1
--- /dev/null
+++ b/app/services/projects/in_product_marketing_campaign_emails_service.rb
@@ -0,0 +1,57 @@
+# frozen_string_literal: true
+
+module Projects
+ class InProductMarketingCampaignEmailsService
+ include Gitlab::Experiment::Dsl
+
+ def initialize(project, campaign)
+ @project = project
+ @campaign = campaign
+ @sent_email_records = ::Users::InProductMarketingEmailRecords.new
+ end
+
+ def execute
+ send_emails
+ end
+
+ private
+
+ attr_reader :project, :campaign, :sent_email_records
+
+ def send_emails
+ project_users.each do |user|
+ send_email(user)
+ end
+
+ sent_email_records.save!
+ end
+
+ # rubocop: disable CodeReuse/ActiveRecord
+ def project_users
+ @project_users ||= project.users
+ .where(email_opted_in: true)
+ .merge(Users::InProductMarketingEmail.without_campaign(campaign))
+ end
+ # rubocop: enable CodeReuse/ActiveRecord
+
+ def project_users_max_access_levels
+ ids = project_users.map(&:id)
+ @project_users_max_access_levels ||= project.team.max_member_access_for_user_ids(ids)
+ end
+
+ def send_email(user)
+ return unless user.can?(:receive_notifications)
+ return unless target_user?(user)
+
+ Notify.build_ios_app_guide_email(user.notification_email_or_default).deliver_later
+
+ sent_email_records.add(user, campaign: campaign)
+ experiment(:build_ios_app_guide_email, project: project).track(:email_sent)
+ end
+
+ def target_user?(user)
+ max_access_level = project_users_max_access_levels[user.id]
+ max_access_level >= Gitlab::Access::DEVELOPER
+ end
+ end
+end
diff --git a/app/services/projects/lfs_pointers/lfs_download_service.rb b/app/services/projects/lfs_pointers/lfs_download_service.rb
index 76005a1c96e..c032fbf1508 100644
--- a/app/services/projects/lfs_pointers/lfs_download_service.rb
+++ b/app/services/projects/lfs_pointers/lfs_download_service.rb
@@ -23,7 +23,7 @@ module Projects
def execute
return unless project&.lfs_enabled? && lfs_download_object
return error("LFS file with oid #{lfs_oid} has invalid attributes") unless lfs_download_object.valid?
- return link_existing_lfs_object! if Feature.enabled?(:lfs_link_existing_object, project, default_enabled: :yaml) && lfs_size > LARGE_FILE_SIZE && lfs_object
+ return link_existing_lfs_object! if Feature.enabled?(:lfs_link_existing_object, project) && lfs_size > LARGE_FILE_SIZE && lfs_object
wrap_download_errors do
download_lfs_file!
diff --git a/app/services/projects/open_issues_count_service.rb b/app/services/projects/open_issues_count_service.rb
index 8b7a418edf5..ee4d559e612 100644
--- a/app/services/projects/open_issues_count_service.rb
+++ b/app/services/projects/open_issues_count_service.rb
@@ -7,12 +7,8 @@ module Projects
include Gitlab::Utils::StrongMemoize
# Cache keys used to store issues count
- # TOTAL_COUNT_KEY includes confidential and hidden issues (admin)
- # TOTAL_COUNT_WITHOUT_HIDDEN_KEY includes confidential issues but not hidden issues (reporter and above)
- # PUBLIC_COUNT_WITHOUT_HIDDEN_KEY does not include confidential or hidden issues (guest)
- TOTAL_COUNT_KEY = 'project_open_issues_including_hidden_count'
- TOTAL_COUNT_WITHOUT_HIDDEN_KEY = 'project_open_issues_without_hidden_count'
- PUBLIC_COUNT_WITHOUT_HIDDEN_KEY = 'project_open_public_issues_without_hidden_count'
+ PUBLIC_COUNT_KEY = 'public_open_issues_count'
+ TOTAL_COUNT_KEY = 'total_open_issues_count'
def initialize(project, user = nil)
@user = user
@@ -20,98 +16,59 @@ module Projects
super(project)
end
- # rubocop: disable CodeReuse/ActiveRecord
- def refresh_cache(&block)
- if block_given?
- super(&block)
- else
- update_cache_for_key(total_count_cache_key) do
- issues_with_hidden
- end
-
- update_cache_for_key(public_count_without_hidden_cache_key) do
- issues_without_hidden_without_confidential
- end
-
- update_cache_for_key(total_count_without_hidden_cache_key) do
- issues_without_hidden_with_confidential
- end
- end
- end
-
- private
-
- def relation_for_count
- self.class.query(@project, public_only: public_only?, include_hidden: include_hidden?)
- end
-
def cache_key_name
- if include_hidden?
- TOTAL_COUNT_KEY
- elsif public_only?
- PUBLIC_COUNT_WITHOUT_HIDDEN_KEY
- else
- TOTAL_COUNT_WITHOUT_HIDDEN_KEY
- end
- end
-
- def include_hidden?
- user_is_admin?
+ public_only? ? PUBLIC_COUNT_KEY : TOTAL_COUNT_KEY
end
def public_only?
!user_is_at_least_reporter?
end
- def user_is_admin?
- strong_memoize(:user_is_admin) do
- @user&.can_admin_all_resources?
- end
- end
-
def user_is_at_least_reporter?
strong_memoize(:user_is_at_least_reporter) do
@user && @project.team.member?(@user, Gitlab::Access::REPORTER)
end
end
- def total_count_without_hidden_cache_key
- cache_key(TOTAL_COUNT_WITHOUT_HIDDEN_KEY)
+ def relation_for_count
+ self.class.query(@project, public_only: public_only?)
end
- def public_count_without_hidden_cache_key
- cache_key(PUBLIC_COUNT_WITHOUT_HIDDEN_KEY)
+ def public_count_cache_key
+ cache_key(PUBLIC_COUNT_KEY)
end
def total_count_cache_key
cache_key(TOTAL_COUNT_KEY)
end
- def issues_with_hidden
- self.class.query(@project, public_only: false, include_hidden: true).count
- end
+ # rubocop: disable CodeReuse/ActiveRecord
+ def refresh_cache(&block)
+ count_grouped_by_confidential = self.class.query(@project, public_only: false).group(:confidential).count
+ public_count = count_grouped_by_confidential[false] || 0
+ total_count = public_count + (count_grouped_by_confidential[true] || 0)
- def issues_without_hidden_without_confidential
- self.class.query(@project, public_only: true, include_hidden: false).count
- end
+ update_cache_for_key(public_count_cache_key) do
+ public_count
+ end
- def issues_without_hidden_with_confidential
- self.class.query(@project, public_only: false, include_hidden: false).count
+ update_cache_for_key(total_count_cache_key) do
+ total_count
+ end
end
- # We only show total issues count for admins, who are allowed to view hidden issues.
- # We also only show issues count including confidential for reporters, who are allowed to view confidential issues.
+ # We only show issues count including confidential for reporters, who are allowed to view confidential issues.
# This will still show a discrepancy on issues number but should be less than before.
# Check https://gitlab.com/gitlab-org/gitlab-foss/issues/38418 description.
+
# rubocop: disable CodeReuse/ActiveRecord
+ def self.query(projects, public_only: true)
+ issues_filtered_by_type = Issue.opened.with_issue_type(Issue::TYPES_FOR_LIST)
- def self.query(projects, public_only: true, include_hidden: false)
- if include_hidden
- Issue.opened.with_issue_type(Issue::TYPES_FOR_LIST).where(project: projects)
- elsif public_only
- Issue.public_only.opened.with_issue_type(Issue::TYPES_FOR_LIST).where(project: projects)
+ if public_only
+ issues_filtered_by_type.public_only.where(project: projects)
else
- Issue.without_hidden.opened.with_issue_type(Issue::TYPES_FOR_LIST).where(project: projects)
+ issues_filtered_by_type.where(project: projects)
end
end
# rubocop: enable CodeReuse/ActiveRecord
diff --git a/app/services/projects/overwrite_project_service.rb b/app/services/projects/overwrite_project_service.rb
index eea8f867b45..d3fed43363c 100644
--- a/app/services/projects/overwrite_project_service.rb
+++ b/app/services/projects/overwrite_project_service.rb
@@ -41,7 +41,7 @@ module Projects
private
def track_service(start_time, source_project, exception)
- return if ::Feature.disabled?(:project_overwrite_service_tracking, source_project, default_enabled: :yaml)
+ return if ::Feature.disabled?(:project_overwrite_service_tracking, source_project)
duration = ::Gitlab::Metrics::System.monotonic_time - start_time
diff --git a/app/services/projects/participants_service.rb b/app/services/projects/participants_service.rb
index c7a34afffb3..c29770d0c5f 100644
--- a/app/services/projects/participants_service.rb
+++ b/app/services/projects/participants_service.rb
@@ -45,7 +45,7 @@ module Projects
def visible_groups
visible_groups = project.invited_groups
- unless project_owner?
+ unless project.team.owner?(current_user)
visible_groups = visible_groups.public_or_visible_to_user(current_user)
end
@@ -60,13 +60,5 @@ module Projects
def individual_project_members
project.project_members.select(*GroupMember.cached_column_list)
end
-
- def project_owner?
- if project.group.present?
- project.group.owners.include?(current_user)
- else
- project.namespace.owner == current_user
- end
- end
end
end
diff --git a/app/services/projects/prometheus/alerts/alert_params.rb b/app/services/projects/prometheus/alerts/alert_params.rb
deleted file mode 100644
index 1c39ed36b12..00000000000
--- a/app/services/projects/prometheus/alerts/alert_params.rb
+++ /dev/null
@@ -1,17 +0,0 @@
-# frozen_string_literal: true
-
-module Projects
- module Prometheus
- module Alerts
- module AlertParams
- def alert_params
- return params if params[:operator].blank?
-
- params.merge(
- operator: PrometheusAlert.operator_to_enum(params[:operator])
- )
- end
- end
- end
- end
-end
diff --git a/app/services/projects/prometheus/alerts/create_service.rb b/app/services/projects/prometheus/alerts/create_service.rb
deleted file mode 100644
index 0d7d8ab1a62..00000000000
--- a/app/services/projects/prometheus/alerts/create_service.rb
+++ /dev/null
@@ -1,15 +0,0 @@
-# frozen_string_literal: true
-
-module Projects
- module Prometheus
- module Alerts
- class CreateService < BaseProjectService
- include AlertParams
-
- def execute
- project.prometheus_alerts.create(alert_params)
- end
- end
- end
- end
-end
diff --git a/app/services/projects/prometheus/alerts/destroy_service.rb b/app/services/projects/prometheus/alerts/destroy_service.rb
deleted file mode 100644
index 243b12eb654..00000000000
--- a/app/services/projects/prometheus/alerts/destroy_service.rb
+++ /dev/null
@@ -1,13 +0,0 @@
-# frozen_string_literal: true
-
-module Projects
- module Prometheus
- module Alerts
- class DestroyService < BaseProjectService
- def execute(alert)
- alert.destroy
- end
- end
- end
- end
-end
diff --git a/app/services/projects/prometheus/alerts/update_service.rb b/app/services/projects/prometheus/alerts/update_service.rb
deleted file mode 100644
index 1802f35dae9..00000000000
--- a/app/services/projects/prometheus/alerts/update_service.rb
+++ /dev/null
@@ -1,15 +0,0 @@
-# frozen_string_literal: true
-
-module Projects
- module Prometheus
- module Alerts
- class UpdateService < BaseProjectService
- include AlertParams
-
- def execute(alert)
- alert.update(alert_params)
- end
- end
- end
- end
-end
diff --git a/app/services/projects/prometheus/metrics/base_service.rb b/app/services/projects/prometheus/metrics/base_service.rb
index be1783dde70..15247d45776 100644
--- a/app/services/projects/prometheus/metrics/base_service.rb
+++ b/app/services/projects/prometheus/metrics/base_service.rb
@@ -8,40 +8,12 @@ module Projects
def initialize(metric, params = {})
@metric = metric
- @project = metric.project
@params = params.dup
end
protected
- attr_reader :metric, :project, :params
-
- def application
- alert.environment.cluster_prometheus_adapter
- end
-
- def schedule_alert_update
- return unless alert
- return unless alert.environment
-
- ::Clusters::Applications::ScheduleUpdateService.new(
- alert.environment.cluster_prometheus_adapter, project).execute
- end
-
- def alert
- strong_memoize(:alert) { find_alert(metric) }
- end
-
- def find_alert(metric)
- Projects::Prometheus::AlertsFinder
- .new(project: project, metric: metric)
- .execute
- .first
- end
-
- def has_alert?
- alert.present?
- end
+ attr_reader :metric, :params
end
end
end
diff --git a/app/services/projects/prometheus/metrics/destroy_service.rb b/app/services/projects/prometheus/metrics/destroy_service.rb
index 6a46eb5516c..d85499dc4ae 100644
--- a/app/services/projects/prometheus/metrics/destroy_service.rb
+++ b/app/services/projects/prometheus/metrics/destroy_service.rb
@@ -5,7 +5,6 @@ module Projects
module Metrics
class DestroyService < Metrics::BaseService
def execute
- schedule_alert_update if has_alert?
metric.destroy
end
end
diff --git a/app/services/projects/prometheus/metrics/update_service.rb b/app/services/projects/prometheus/metrics/update_service.rb
deleted file mode 100644
index 9b51f4ab47d..00000000000
--- a/app/services/projects/prometheus/metrics/update_service.rb
+++ /dev/null
@@ -1,29 +0,0 @@
-# frozen_string_literal: true
-
-module Projects
- module Prometheus
- module Metrics
- class UpdateService < Metrics::BaseService
- def execute
- metric.update!(params)
- schedule_alert_update if requires_alert_update?
- metric
- end
-
- private
-
- def requires_alert_update?
- has_alert? && (changing_title? || changing_query?)
- end
-
- def changing_title?
- metric.previous_changes.include?(:title)
- end
-
- def changing_query?
- metric.previous_changes.include?(:query)
- end
- end
- end
- end
-end
diff --git a/app/services/projects/record_target_platforms_service.rb b/app/services/projects/record_target_platforms_service.rb
index 224e16f53b3..664e72e9785 100644
--- a/app/services/projects/record_target_platforms_service.rb
+++ b/app/services/projects/record_target_platforms_service.rb
@@ -4,26 +4,50 @@ module Projects
class RecordTargetPlatformsService < BaseService
include Gitlab::Utils::StrongMemoize
+ def initialize(project, detector_service)
+ @project = project
+ @detector_service = detector_service
+ end
+
def execute
record_target_platforms
end
private
+ attr_reader :project, :detector_service
+
def target_platforms
strong_memoize(:target_platforms) do
- AppleTargetPlatformDetectorService.new(project).execute
+ Array(detector_service.new(project).execute)
end
end
def record_target_platforms
return unless target_platforms.present?
- setting = ::ProjectSetting.find_or_initialize_by(project: project) # rubocop:disable CodeReuse/ActiveRecord
- setting.target_platforms = target_platforms
- setting.save
+ project_setting.target_platforms = target_platforms
+ project_setting.save
+
+ send_build_ios_app_guide_email
+
+ project_setting.target_platforms
+ end
+
+ def project_setting
+ @project_setting ||= ::ProjectSetting.find_or_initialize_by(project: project) # rubocop:disable CodeReuse/ActiveRecord
+ end
+
+ def experiment_candidate?
+ experiment(:build_ios_app_guide_email, project: project).run
+ end
+
+ def send_build_ios_app_guide_email
+ return unless target_platforms.include? :ios
+ return unless experiment_candidate?
- setting.target_platforms
+ campaign = Users::InProductMarketingEmail::BUILD_IOS_APP_GUIDE
+ Projects::InProductMarketingCampaignEmailsService.new(project, campaign).execute
end
end
end
diff --git a/app/services/projects/update_pages_service.rb b/app/services/projects/update_pages_service.rb
index 2ec965fe2f4..c6ea364320f 100644
--- a/app/services/projects/update_pages_service.rb
+++ b/app/services/projects/update_pages_service.rb
@@ -30,6 +30,7 @@ module Projects
validate_state!
validate_max_size!
+ validate_public_folder!
validate_max_entries!
build.artifacts_file.use_file do |artifacts_path|
@@ -180,6 +181,10 @@ module Projects
end
end
+ def validate_public_folder!
+ raise InvalidStateError, 'Error: The `public/` folder is missing, or not declared in `.gitlab-ci.yml`.' unless total_size > 0
+ end
+
def entries_count
# we're using the full archive and pages daemon needs to read it
# so we want the total count from entries, not only "public/" directory
diff --git a/app/services/projects/update_remote_mirror_service.rb b/app/services/projects/update_remote_mirror_service.rb
index f3ea0967a99..705d23ec704 100644
--- a/app/services/projects/update_remote_mirror_service.rb
+++ b/app/services/projects/update_remote_mirror_service.rb
@@ -65,7 +65,7 @@ module Projects
message += "Error synchronizing LFS files:"
message += "\n\n#{lfs_status[:message]}\n\n"
- failed = Feature.enabled?(:remote_mirror_fail_on_lfs, project, default_enabled: :yaml)
+ failed = Feature.enabled?(:remote_mirror_fail_on_lfs, project)
end
if response.divergent_refs.any?