diff options
author | GitLab Bot <gitlab-bot@gitlab.com> | 2021-02-23 12:14:52 +0300 |
---|---|---|
committer | GitLab Bot <gitlab-bot@gitlab.com> | 2021-02-23 12:14:52 +0300 |
commit | 347bf09d6ecf4871da234c06ca8ee541e27b5105 (patch) | |
tree | 2ad6943e0c681c22acc8850d1debc6a983b0e006 /lib | |
parent | 0a51be0866d33273070f535257626a9eb2e10700 (diff) |
Add latest changes from gitlab-org/gitlab@13-10-stable-eev13.10.0-rc20210223090520
Diffstat (limited to 'lib')
64 files changed, 533 insertions, 212 deletions
diff --git a/lib/api/api.rb b/lib/api/api.rb index 0598f03c7ab..bf4b031cb9f 100644 --- a/lib/api/api.rb +++ b/lib/api/api.rb @@ -147,7 +147,7 @@ module API # Only overwrite `text/plain+deprecated` if content_types[api_format] == 'text/plain+deprecated' - if Feature.enabled?(:api_always_use_application_json) + if Feature.enabled?(:api_always_use_application_json, default_enabled: :yaml) content_type 'application/json' else content_type 'text/plain' diff --git a/lib/api/concerns/packages/npm_endpoints.rb b/lib/api/concerns/packages/npm_endpoints.rb index 833288c6013..d6e006df976 100644 --- a/lib/api/concerns/packages/npm_endpoints.rb +++ b/lib/api/concerns/packages/npm_endpoints.rb @@ -41,8 +41,8 @@ module API authorize_read_package!(project) - packages = ::Packages::Npm::PackageFinder.new(project, package_name) - .execute + packages = ::Packages::Npm::PackageFinder.new(package_name, project: project) + .execute not_found! if packages.empty? @@ -68,9 +68,8 @@ module API authorize_create_package!(project) - package = ::Packages::Npm::PackageFinder - .new(project, package_name) - .find_by_version(version) + package = ::Packages::Npm::PackageFinder.new(package_name, project: project) + .find_by_version(version) not_found!('Package') unless package ::Packages::Npm::CreateTagService.new(package, tag).execute @@ -112,9 +111,8 @@ module API route_setting :authentication, job_token_allowed: true, deploy_token_allowed: true get '*package_name', format: false, requirements: ::API::Helpers::Packages::Npm::NPM_ENDPOINT_REQUIREMENTS do package_name = params[:package_name] - - packages = ::Packages::Npm::PackageFinder.new(project_or_nil, package_name) - .execute + packages = ::Packages::Npm::PackageFinder.new(package_name, project: project_or_nil) + .execute redirect_request = project_or_nil.blank? || packages.empty? diff --git a/lib/api/helpers/packages/npm.rb b/lib/api/helpers/packages/npm.rb index c1f6a001201..2d556f889bf 100644 --- a/lib/api/helpers/packages/npm.rb +++ b/lib/api/helpers/packages/npm.rb @@ -49,13 +49,28 @@ module API when :project params[:id] when :instance - ::Packages::Package.npm - .with_name(params[:package_name]) - .first - &.project_id + namespace_path = namespace_path_from_package_name + next unless namespace_path + + namespace = Namespace.top_most + .by_path(namespace_path) + next unless namespace + + finder = ::Packages::Npm::PackageFinder.new(params[:package_name], namespace: namespace) + + finder.last&.project_id end end end + + # from "@scope/package-name" return "scope" or nil + def namespace_path_from_package_name + package_name = params[:package_name] + return unless package_name.starts_with?('@') + return unless package_name.include?('/') + + package_name.match(Gitlab::Regex.npm_package_name_regex)&.captures&.first + end end end end diff --git a/lib/api/lint.rb b/lib/api/lint.rb index 2d30754a36d..e0806674c6a 100644 --- a/lib/api/lint.rb +++ b/lib/api/lint.rb @@ -11,7 +11,7 @@ module API optional :include_merged_yaml, type: Boolean, desc: 'Whether or not to include merged CI config yaml in the response' end post '/lint' do - unauthorized! unless Gitlab::CurrentSettings.signup_enabled? && current_user + unauthorized! if Gitlab::CurrentSettings.signup_disabled? && current_user.nil? result = Gitlab::Ci::YamlProcessor.new(params[:content], user: current_user).execute diff --git a/lib/api/nuget_project_packages.rb b/lib/api/nuget_project_packages.rb index e071b6bd68f..73ecc140959 100644 --- a/lib/api/nuget_project_packages.rb +++ b/lib/api/nuget_project_packages.rb @@ -62,8 +62,9 @@ module API file_name: PACKAGE_FILENAME ) - package = ::Packages::Nuget::CreatePackageService.new(project_or_group, current_user, declared_params.merge(build: current_authenticated_job)) - .execute + package = ::Packages::CreateTemporaryPackageService.new( + project_or_group, current_user, declared_params.merge(build: current_authenticated_job) + ).execute(:nuget, name: ::Packages::Nuget::TEMPORARY_PACKAGE_NAME) package_file = ::Packages::CreatePackageFileService.new(package, file_params.merge(build: current_authenticated_job)) .execute diff --git a/lib/api/rubygem_packages.rb b/lib/api/rubygem_packages.rb index 7819aab879c..5bacf9b122d 100644 --- a/lib/api/rubygem_packages.rb +++ b/lib/api/rubygem_packages.rb @@ -12,7 +12,7 @@ module API # The Marshal version can be found by "#{Marshal::MAJOR_VERSION}.#{Marshal::MINOR_VERSION}" # Updating the version should require a GitLab API version change. MARSHAL_VERSION = '4.8' - + PACKAGE_FILENAME = 'package.gem' FILE_NAME_REQUIREMENTS = { file_name: API::NO_SLASH_URL_PART_REGEX }.freeze @@ -73,16 +73,45 @@ module API detail 'This feature was introduced in GitLab 13.9' end post 'gems/authorize' do - # To be implemented in https://gitlab.com/gitlab-org/gitlab/-/issues/299263 - not_found! + authorize_workhorse!( + subject: user_project, + has_length: false, + maximum_size: user_project.actual_limits.rubygems_max_file_size + ) end desc 'Upload a gem' do detail 'This feature was introduced in GitLab 13.9' end + params do + requires :file, type: ::API::Validations::Types::WorkhorseFile, desc: 'The package file to be published (generated by Multipart middleware)' + end post 'gems' do - # To be implemented in https://gitlab.com/gitlab-org/gitlab/-/issues/299263 - not_found! + authorize_upload!(user_project) + bad_request!('File is too large') if user_project.actual_limits.exceeded?(:rubygems_max_file_size, params[:file].size) + + track_package_event('push_package', :rubygems) + + ActiveRecord::Base.transaction do + package = ::Packages::CreateTemporaryPackageService.new( + user_project, current_user, declared_params.merge(build: current_authenticated_job) + ).execute(:rubygems, name: ::Packages::Rubygems::TEMPORARY_PACKAGE_NAME) + + file_params = { + file: params[:file], + file_name: PACKAGE_FILENAME + } + + ::Packages::CreatePackageFileService.new( + package, file_params.merge(build: current_authenticated_job) + ).execute + end + + created! + rescue ObjectStorage::RemoteStoreError => e + Gitlab::ErrorTracking.track_exception(e, extra: { file_name: params[:file_name], project_id: user_project.id }) + + forbidden! end desc 'Fetch a list of dependencies' do diff --git a/lib/backup/repositories.rb b/lib/backup/repositories.rb index d15114a72a3..79b7b2c61f2 100644 --- a/lib/backup/repositories.rb +++ b/lib/backup/repositories.rb @@ -201,7 +201,12 @@ module Backup PoolRepository.includes(:source_project).find_each do |pool| progress.puts " - Object pool #{pool.disk_path}..." - pool.source_project ||= pool.member_projects.first.root_of_fork_network + pool.source_project ||= pool.member_projects.first&.root_of_fork_network + unless pool.source_project + progress.puts " - Object pool #{pool.disk_path}... " + "[SKIPPED]".color(:cyan) + next + end + pool.state = 'none' pool.save diff --git a/lib/banzai/filter/video_link_filter.rb b/lib/banzai/filter/video_link_filter.rb index 98987ee2019..3789a215dd8 100644 --- a/lib/banzai/filter/video_link_filter.rb +++ b/lib/banzai/filter/video_link_filter.rb @@ -15,7 +15,7 @@ module Banzai end def extra_element_attrs - { width: "400" } + { width: "400", preload: "metadata" } end end end diff --git a/lib/bulk_imports/common/loaders/entity_loader.rb b/lib/bulk_imports/common/loaders/entity_loader.rb deleted file mode 100644 index 8644f3c9dcb..00000000000 --- a/lib/bulk_imports/common/loaders/entity_loader.rb +++ /dev/null @@ -1,15 +0,0 @@ -# frozen_string_literal: true - -module BulkImports - module Common - module Loaders - class EntityLoader - def initialize(*args); end - - def load(context, entity) - context.bulk_import.entities.create!(entity) - end - end - end - end -end diff --git a/lib/bulk_imports/common/transformers/award_emoji_transformer.rb b/lib/bulk_imports/common/transformers/award_emoji_transformer.rb index 260b47ab917..676c71f1316 100644 --- a/lib/bulk_imports/common/transformers/award_emoji_transformer.rb +++ b/lib/bulk_imports/common/transformers/award_emoji_transformer.rb @@ -4,8 +4,6 @@ module BulkImports module Common module Transformers class AwardEmojiTransformer - def initialize(*args); end - def transform(context, data) user = find_user(context, data&.dig('user', 'public_email')) || context.current_user diff --git a/lib/bulk_imports/common/transformers/prohibited_attributes_transformer.rb b/lib/bulk_imports/common/transformers/prohibited_attributes_transformer.rb index 858c4c8976b..37b64923d56 100644 --- a/lib/bulk_imports/common/transformers/prohibited_attributes_transformer.rb +++ b/lib/bulk_imports/common/transformers/prohibited_attributes_transformer.rb @@ -14,10 +14,6 @@ module BulkImports /\Aremote_\w+_(url|urls|request_header)\Z/ # carrierwave automatically creates these attribute methods for uploads ).freeze - def initialize(options = {}) - @options = options - end - def transform(context, data) data.each_with_object({}) do |(key, value), result| prohibited = prohibited_key?(key) diff --git a/lib/bulk_imports/groups/extractors/subgroups_extractor.rb b/lib/bulk_imports/groups/extractors/subgroups_extractor.rb index b01fb6f68ac..e5e2b9fdbd4 100644 --- a/lib/bulk_imports/groups/extractors/subgroups_extractor.rb +++ b/lib/bulk_imports/groups/extractors/subgroups_extractor.rb @@ -4,8 +4,6 @@ module BulkImports module Groups module Extractors class SubgroupsExtractor - def initialize(*args); end - def extract(context) encoded_parent_path = ERB::Util.url_encode(context.entity.source_full_path) diff --git a/lib/bulk_imports/groups/graphql/get_labels_query.rb b/lib/bulk_imports/groups/graphql/get_labels_query.rb index d1fe791c2ce..23efbc33581 100644 --- a/lib/bulk_imports/groups/graphql/get_labels_query.rb +++ b/lib/bulk_imports/groups/graphql/get_labels_query.rb @@ -10,7 +10,7 @@ module BulkImports <<-'GRAPHQL' query ($full_path: ID!, $cursor: String) { group(fullPath: $full_path) { - labels(first: 100, after: $cursor) { + labels(first: 100, after: $cursor, onlyGroupLabels: true) { page_info: pageInfo { end_cursor: endCursor has_next_page: hasNextPage @@ -19,6 +19,8 @@ module BulkImports title description color + created_at: createdAt + updated_at: updatedAt } } } diff --git a/lib/bulk_imports/groups/loaders/group_loader.rb b/lib/bulk_imports/groups/loaders/group_loader.rb index 386fc695182..a631685c2ad 100644 --- a/lib/bulk_imports/groups/loaders/group_loader.rb +++ b/lib/bulk_imports/groups/loaders/group_loader.rb @@ -4,10 +4,6 @@ module BulkImports module Groups module Loaders class GroupLoader - def initialize(options = {}) - @options = options - end - def load(context, data) return unless user_can_create_group?(context.current_user, data) diff --git a/lib/bulk_imports/groups/loaders/labels_loader.rb b/lib/bulk_imports/groups/loaders/labels_loader.rb deleted file mode 100644 index b8c9ba9609c..00000000000 --- a/lib/bulk_imports/groups/loaders/labels_loader.rb +++ /dev/null @@ -1,15 +0,0 @@ -# frozen_string_literal: true - -module BulkImports - module Groups - module Loaders - class LabelsLoader - def initialize(*); end - - def load(context, data) - Labels::CreateService.new(data).execute(group: context.group) - end - end - end - end -end diff --git a/lib/bulk_imports/groups/loaders/members_loader.rb b/lib/bulk_imports/groups/loaders/members_loader.rb deleted file mode 100644 index ccf44b31aee..00000000000 --- a/lib/bulk_imports/groups/loaders/members_loader.rb +++ /dev/null @@ -1,17 +0,0 @@ -# frozen_string_literal: true - -module BulkImports - module Groups - module Loaders - class MembersLoader - def initialize(*); end - - def load(context, data) - return unless data - - context.group.members.create!(data) - end - end - end - end -end diff --git a/lib/bulk_imports/groups/pipelines/labels_pipeline.rb b/lib/bulk_imports/groups/pipelines/labels_pipeline.rb index 40dab9b444c..9f8b8682751 100644 --- a/lib/bulk_imports/groups/pipelines/labels_pipeline.rb +++ b/lib/bulk_imports/groups/pipelines/labels_pipeline.rb @@ -11,7 +11,9 @@ module BulkImports transformer Common::Transformers::ProhibitedAttributesTransformer - loader BulkImports::Groups::Loaders::LabelsLoader + def load(context, data) + Labels::CreateService.new(data).execute(group: context.group) + end def after_run(extracted_data) context.entity.update_tracker_for( diff --git a/lib/bulk_imports/groups/pipelines/members_pipeline.rb b/lib/bulk_imports/groups/pipelines/members_pipeline.rb index b00c4c1a659..32fc931e8c3 100644 --- a/lib/bulk_imports/groups/pipelines/members_pipeline.rb +++ b/lib/bulk_imports/groups/pipelines/members_pipeline.rb @@ -12,7 +12,11 @@ module BulkImports transformer Common::Transformers::ProhibitedAttributesTransformer transformer BulkImports::Groups::Transformers::MemberAttributesTransformer - loader BulkImports::Groups::Loaders::MembersLoader + def load(context, data) + return unless data + + context.group.members.create!(data) + end def after_run(extracted_data) context.entity.update_tracker_for( diff --git a/lib/bulk_imports/groups/pipelines/subgroup_entities_pipeline.rb b/lib/bulk_imports/groups/pipelines/subgroup_entities_pipeline.rb index d7e1a118d0b..c47a8bd1daa 100644 --- a/lib/bulk_imports/groups/pipelines/subgroup_entities_pipeline.rb +++ b/lib/bulk_imports/groups/pipelines/subgroup_entities_pipeline.rb @@ -9,7 +9,10 @@ module BulkImports extractor BulkImports::Groups::Extractors::SubgroupsExtractor transformer Common::Transformers::ProhibitedAttributesTransformer transformer BulkImports::Groups::Transformers::SubgroupToEntityTransformer - loader BulkImports::Common::Loaders::EntityLoader + + def load(context, data) + context.bulk_import.entities.create!(data) + end end end end diff --git a/lib/bulk_imports/groups/transformers/group_attributes_transformer.rb b/lib/bulk_imports/groups/transformers/group_attributes_transformer.rb index 7de9a430421..23e898a7bb2 100644 --- a/lib/bulk_imports/groups/transformers/group_attributes_transformer.rb +++ b/lib/bulk_imports/groups/transformers/group_attributes_transformer.rb @@ -4,10 +4,6 @@ module BulkImports module Groups module Transformers class GroupAttributesTransformer - def initialize(options = {}) - @options = options - end - def transform(context, data) import_entity = context.entity @@ -39,12 +35,11 @@ module BulkImports end def transform_parent(context, import_entity, data) - current_user = context.current_user - namespace = Namespace.find_by_full_path(import_entity.destination_namespace) - - return data if namespace == current_user.namespace + unless import_entity.destination_namespace.blank? + namespace = Namespace.find_by_full_path(import_entity.destination_namespace) + data['parent_id'] = namespace.id + end - data['parent_id'] = namespace.id data end diff --git a/lib/bulk_imports/groups/transformers/member_attributes_transformer.rb b/lib/bulk_imports/groups/transformers/member_attributes_transformer.rb index 622f5b60ffe..e92c898171a 100644 --- a/lib/bulk_imports/groups/transformers/member_attributes_transformer.rb +++ b/lib/bulk_imports/groups/transformers/member_attributes_transformer.rb @@ -4,8 +4,6 @@ module BulkImports module Groups module Transformers class MemberAttributesTransformer - def initialize(*); end - def transform(context, data) data .then { |data| add_user(data) } diff --git a/lib/bulk_imports/groups/transformers/subgroup_to_entity_transformer.rb b/lib/bulk_imports/groups/transformers/subgroup_to_entity_transformer.rb index 6c3c299c2d2..676a6ca8d2a 100644 --- a/lib/bulk_imports/groups/transformers/subgroup_to_entity_transformer.rb +++ b/lib/bulk_imports/groups/transformers/subgroup_to_entity_transformer.rb @@ -4,8 +4,6 @@ module BulkImports module Groups module Transformers class SubgroupToEntityTransformer - def initialize(*args); end - def transform(context, entry) { source_type: :group_entity, diff --git a/lib/bulk_imports/pipeline.rb b/lib/bulk_imports/pipeline.rb index 1d55ad95887..254ae0e792e 100644 --- a/lib/bulk_imports/pipeline.rb +++ b/lib/bulk_imports/pipeline.rb @@ -15,16 +15,78 @@ module BulkImports attr_reader :context + # Fetch pipeline extractor. + # An extractor is defined either by instance `#extract(context)` method + # or by using `extractor` DSL. + # + # @example + # class MyPipeline + # extractor MyExtractor, foo: :bar + # end + # + # class MyPipeline + # def extract(context) + # puts 'Fetch some data' + # end + # end + # + # If pipeline implements instance method `extract` - use it + # and ignore class `extractor` method implementation. def extractor - @extractor ||= instantiate(self.class.get_extractor) + @extractor ||= self.respond_to?(:extract) ? self : instantiate(self.class.get_extractor) end + # Fetch pipeline transformers. + # + # A transformer can be defined using: + # - `transformer` class method + # - `transform` instance method + # + # Multiple transformers can be defined within a single + # pipeline and run sequentially for each record in the + # following order: + # - Transformers defined using `transformer` class method + # - Instance method `transform` + # + # Instance method `transform` is always the last to run. + # + # @example + # class MyPipeline + # transformer MyTransformerOne, foo: :bar + # transformer MyTransformerTwo, foo: :bar + # + # def transform(context, data) + # # perform transformation here + # end + # end + # + # In the example above `MyTransformerOne` is the first to run and + # the instance `#transform` method is the last. def transformers @transformers ||= self.class.transformers.map(&method(:instantiate)) + @transformers << self if respond_to?(:transform) && @transformers.exclude?(self) + @transformers end + # Fetch pipeline loader. + # A loader is defined either by instance method `#load(context, data)` + # or by using `loader` DSL. + # + # @example + # class MyPipeline + # loader MyLoader, foo: :bar + # end + # + # class MyPipeline + # def load(context, data) + # puts 'Load some data' + # end + # end + # + # If pipeline implements instance method `load` - use it + # and ignore class `loader` method implementation. def loader - @loaders ||= instantiate(self.class.get_loader) + @loader ||= self.respond_to?(:load) ? self : instantiate(self.class.get_loader) end def pipeline @@ -32,7 +94,13 @@ module BulkImports end def instantiate(class_config) - class_config[:klass].new(class_config[:options]) + options = class_config[:options] + + if options + class_config[:klass].new(class_config[:options]) + else + class_config[:klass].new + end end def abort_on_failure? diff --git a/lib/csv_builder.rb b/lib/csv_builder.rb index a9ef5a83ae8..6116009f171 100644 --- a/lib/csv_builder.rb +++ b/lib/csv_builder.rb @@ -16,6 +16,7 @@ class CsvBuilder DEFAULT_ORDER_BY = 'id'.freeze DEFAULT_BATCH_SIZE = 1000 + PREFIX_REGEX = /^[=\+\-@;]/.freeze attr_reader :rows_written @@ -114,8 +115,8 @@ class CsvBuilder def excel_sanitize(line) return if line.nil? + return line unless line.is_a?(String) && line.match?(PREFIX_REGEX) - line = ["'", line].join if line =~ /^[=\+\-@;]/ - line + ["'", line].join end end diff --git a/lib/gitlab/analytics/cycle_analytics/average.rb b/lib/gitlab/analytics/cycle_analytics/average.rb new file mode 100644 index 00000000000..a449b71b165 --- /dev/null +++ b/lib/gitlab/analytics/cycle_analytics/average.rb @@ -0,0 +1,48 @@ +# frozen_string_literal: true + +module Gitlab + module Analytics + module CycleAnalytics + class Average + include Gitlab::Utils::StrongMemoize + include StageQueryHelpers + + def initialize(stage:, query:) + @stage = stage + @query = query + end + + def seconds + select_average ? select_average['average'] : nil + end + + def days + seconds ? seconds.fdiv(1.day) : nil + end + + private + + attr_reader :stage + + # rubocop: disable CodeReuse/ActiveRecord + def select_average + strong_memoize(:select_average) do + execute_query(@query.select(average_in_seconds.as('average')).reorder(nil)).first + end + end + # rubocop: enable CodeReuse/ActiveRecord + + def average + Arel::Nodes::NamedFunction.new( + 'AVG', + [duration] + ) + end + + def average_in_seconds + Arel::Nodes::Extract.new(average, :epoch) + end + end + end + end +end diff --git a/lib/gitlab/analytics/cycle_analytics/data_collector.rb b/lib/gitlab/analytics/cycle_analytics/data_collector.rb index 5eca364a697..10a008a76d5 100644 --- a/lib/gitlab/analytics/cycle_analytics/data_collector.rb +++ b/lib/gitlab/analytics/cycle_analytics/data_collector.rb @@ -31,6 +31,12 @@ module Gitlab end end + def average + strong_memoize(:average) do + Average.new(stage: stage, query: query) + end + end + private attr_reader :stage, :params diff --git a/lib/gitlab/analytics/instance_statistics/workers_argument_builder.rb b/lib/gitlab/analytics/usage_trends/workers_argument_builder.rb index 54b3bbb3ce6..a502f46287d 100644 --- a/lib/gitlab/analytics/instance_statistics/workers_argument_builder.rb +++ b/lib/gitlab/analytics/usage_trends/workers_argument_builder.rb @@ -2,7 +2,7 @@ module Gitlab module Analytics - module InstanceStatistics + module UsageTrends class WorkersArgumentBuilder def initialize(measurement_identifiers: [], recorded_at: Time.zone.now) @measurement_identifiers = measurement_identifiers @@ -35,11 +35,11 @@ module Gitlab end def custom_min_max_queries - ::Analytics::InstanceStatistics::Measurement.identifier_min_max_queries + ::Analytics::UsageTrends::Measurement.identifier_min_max_queries end def query_mappings - ::Analytics::InstanceStatistics::Measurement.identifier_query_mapping + ::Analytics::UsageTrends::Measurement.identifier_query_mapping end end end diff --git a/lib/gitlab/application_rate_limiter.rb b/lib/gitlab/application_rate_limiter.rb index 0a69a9c503d..f74edf2b767 100644 --- a/lib/gitlab/application_rate_limiter.rb +++ b/lib/gitlab/application_rate_limiter.rb @@ -47,7 +47,7 @@ module Gitlab # @option scope [Array<ActiveRecord>] Array of ActiveRecord models to scope throttling to a specific request (e.g. per user per project) # @option threshold [Integer] Optional threshold value to override default one registered in `.rate_limits` # @option interval [Integer] Optional interval value to override default one registered in `.rate_limits` - # @option users_allowlist [Array<String>] Optional list of usernames to excepted from the limit. This param will only be functional if Scope includes a current user. + # @option users_allowlist [Array<String>] Optional list of usernames to exclude from the limit. This param will only be functional if Scope includes a current user. # # @return [Boolean] Whether or not a request should be throttled def throttled?(key, **options) diff --git a/lib/gitlab/auth/o_auth/provider.rb b/lib/gitlab/auth/o_auth/provider.rb index 57ff3fcd1f0..ab6ac815601 100644 --- a/lib/gitlab/auth/o_auth/provider.rb +++ b/lib/gitlab/auth/o_auth/provider.rb @@ -5,11 +5,12 @@ module Gitlab module OAuth class Provider LABELS = { - "github" => "GitHub", - "gitlab" => "GitLab.com", - "google_oauth2" => "Google", - "azure_oauth2" => "Azure AD", - 'atlassian_oauth2' => 'Atlassian' + "github" => "GitHub", + "gitlab" => "GitLab.com", + "google_oauth2" => "Google", + "azure_oauth2" => "Azure AD", + "azure_activedirectory_v2" => "Azure AD v2", + 'atlassian_oauth2' => 'Atlassian' }.freeze def self.authentication(user, provider) diff --git a/lib/gitlab/background_migration/set_default_iteration_cadences.rb b/lib/gitlab/background_migration/set_default_iteration_cadences.rb new file mode 100644 index 00000000000..530608144aa --- /dev/null +++ b/lib/gitlab/background_migration/set_default_iteration_cadences.rb @@ -0,0 +1,57 @@ +# frozen_string_literal: true + +module Gitlab + module BackgroundMigration + # rubocop:disable Style/Documentation + class SetDefaultIterationCadences + class Iteration < ApplicationRecord + self.table_name = 'sprints' + end + + class IterationCadence < ApplicationRecord + self.table_name = 'iterations_cadences' + + include BulkInsertSafe + end + + class Group < ApplicationRecord + self.table_name = 'namespaces' + end + + def perform(*group_ids) + create_iterations_cadences(group_ids) + assign_iterations_cadences(group_ids) + end + + private + + def create_iterations_cadences(group_ids) + groups_with_cadence = IterationCadence.select(:group_id) + new_cadences = Group.where(id: group_ids).where.not(id: groups_with_cadence).map do |group| + last_iteration = Iteration.where(group_id: group.id).order(:start_date)&.last + + next unless last_iteration + + time = Time.now + IterationCadence.new( + group_id: group.id, + title: "#{group.name} Iterations", + start_date: last_iteration.start_date, + last_run_date: last_iteration.start_date, + automatic: false, + created_at: time, + updated_at: time + ) + end + + IterationCadence.bulk_insert!(new_cadences.compact) + end + + def assign_iterations_cadences(group_ids) + IterationCadence.where(group_id: group_ids).each do |cadence| + Iteration.where(iterations_cadence_id: nil).where(group_id: cadence.group_id).update_all(iterations_cadence_id: cadence.id) + end + end + end + end +end diff --git a/lib/gitlab/ci/jwt.rb b/lib/gitlab/ci/jwt.rb index 0870c74053a..af06e124736 100644 --- a/lib/gitlab/ci/jwt.rb +++ b/lib/gitlab/ci/jwt.rb @@ -60,7 +60,7 @@ module Gitlab ref_protected: build.protected.to_s } - if include_environment_claims? + if environment.present? fields.merge!( environment: environment.name, environment_protected: environment_protected?.to_s @@ -119,10 +119,6 @@ module Gitlab def environment_protected? false # Overridden in EE end - - def include_environment_claims? - Feature.enabled?(:ci_jwt_include_environment) && environment.present? - end end end end diff --git a/lib/gitlab/ci/templates/LaTeX.gitlab-ci.yml b/lib/gitlab/ci/templates/LaTeX.gitlab-ci.yml index a4aed36889e..e4ed7fadfaa 100644 --- a/lib/gitlab/ci/templates/LaTeX.gitlab-ci.yml +++ b/lib/gitlab/ci/templates/LaTeX.gitlab-ci.yml @@ -1,11 +1,20 @@ -# use docker image with latex preinstalled -# since there is no official latex image, use https://github.com/blang/latex-docker -# possible alternative: https://github.com/natlownes/docker-latex -image: blang/latex +--- +variables: + # Feel free to choose the image that suits you best. + # blang/latex:latest ... Former image used in this template. No longer maintained by author. + # listx/texlive:2020 ... The default, referring to TexLive 2020. Current at least to 2021-02-02. + + # Additional alternatives with high Docker pull counts: + # thomasweise/docker-texlive-full + # thomasweise/texlive + # adnrv/texlive + LATEX_IMAGE: listx/texlive:2020 build: + image: $LATEX_IMAGE script: - latexmk -pdf + artifacts: paths: - "*.pdf" diff --git a/lib/gitlab/ci/templates/Security/API-Fuzzing.gitlab-ci.yml b/lib/gitlab/ci/templates/Security/API-Fuzzing.gitlab-ci.yml index 135f0df99fe..460cb84460a 100644 --- a/lib/gitlab/ci/templates/Security/API-Fuzzing.gitlab-ci.yml +++ b/lib/gitlab/ci/templates/Security/API-Fuzzing.gitlab-ci.yml @@ -172,6 +172,7 @@ apifuzzer_fuzz_dnd: -e FUZZAPI_HAR \ -e FUZZAPI_OPENAPI \ -e FUZZAPI_POSTMAN_COLLECTION \ + -e FUZZAPI_POSTMAN_COLLECTION_VARIABLES \ -e FUZZAPI_TARGET_URL \ -e FUZZAPI_OVERRIDES_FILE \ -e FUZZAPI_OVERRIDES_ENV \ @@ -214,6 +215,7 @@ apifuzzer_fuzz_dnd: -e FUZZAPI_HAR \ -e FUZZAPI_OPENAPI \ -e FUZZAPI_POSTMAN_COLLECTION \ + -e FUZZAPI_POSTMAN_COLLECTION_VARIABLES \ -e FUZZAPI_TARGET_URL \ -e FUZZAPI_OVERRIDES_FILE \ -e FUZZAPI_OVERRIDES_ENV \ diff --git a/lib/gitlab/ci/templates/Security/SAST.gitlab-ci.yml b/lib/gitlab/ci/templates/Security/SAST.gitlab-ci.yml index 828352743b4..3b166505e0a 100644 --- a/lib/gitlab/ci/templates/Security/SAST.gitlab-ci.yml +++ b/lib/gitlab/ci/templates/Security/SAST.gitlab-ci.yml @@ -140,7 +140,9 @@ gosec-sast: mobsf-android-sast: extends: .sast-analyzer services: - - name: opensecurity/mobile-security-framework-mobsf:latest + # this version must match with analyzer version mentioned in: https://gitlab.com/gitlab-org/security-products/analyzers/mobsf/-/blob/master/Dockerfile + # Unfortunately, we need to keep track of mobsf version in 2 different places for now. + - name: opensecurity/mobile-security-framework-mobsf:v3.2.9 alias: mobsf image: name: "$SAST_ANALYZER_IMAGE" @@ -161,7 +163,9 @@ mobsf-android-sast: mobsf-ios-sast: extends: .sast-analyzer services: - - name: opensecurity/mobile-security-framework-mobsf:latest + # this version must match with analyzer version mentioned in: https://gitlab.com/gitlab-org/security-products/analyzers/mobsf/-/blob/master/Dockerfile + # Unfortunately, we need to keep track of mobsf version in 2 different places for now. + - name: opensecurity/mobile-security-framework-mobsf:v3.2.9 alias: mobsf image: name: "$SAST_ANALYZER_IMAGE" diff --git a/lib/gitlab/current_settings.rb b/lib/gitlab/current_settings.rb index 0bf41f9dc0d..55f381fcb64 100644 --- a/lib/gitlab/current_settings.rb +++ b/lib/gitlab/current_settings.rb @@ -3,6 +3,10 @@ module Gitlab module CurrentSettings class << self + def signup_disabled? + !signup_enabled? + end + def current_application_settings Gitlab::SafeRequestStore.fetch(:current_application_settings) { ensure_application_settings! } end diff --git a/lib/gitlab/database/migrations/observation.rb b/lib/gitlab/database/migrations/observation.rb index 518c2c560d2..046843824a4 100644 --- a/lib/gitlab/database/migrations/observation.rb +++ b/lib/gitlab/database/migrations/observation.rb @@ -7,7 +7,8 @@ module Gitlab :migration, :walltime, :success, - :total_database_size_change + :total_database_size_change, + :query_statistics ) end end diff --git a/lib/gitlab/database/migrations/observers.rb b/lib/gitlab/database/migrations/observers.rb index 4b931d3c19c..592993aeac5 100644 --- a/lib/gitlab/database/migrations/observers.rb +++ b/lib/gitlab/database/migrations/observers.rb @@ -6,7 +6,8 @@ module Gitlab module Observers def self.all_observers [ - TotalDatabaseSizeChange.new + TotalDatabaseSizeChange.new, + QueryStatistics.new ] end end diff --git a/lib/gitlab/database/migrations/observers/query_statistics.rb b/lib/gitlab/database/migrations/observers/query_statistics.rb new file mode 100644 index 00000000000..466f4724256 --- /dev/null +++ b/lib/gitlab/database/migrations/observers/query_statistics.rb @@ -0,0 +1,38 @@ +# frozen_string_literal: true + +module Gitlab + module Database + module Migrations + module Observers + # This observer gathers statistics from the pg_stat_statements extension. + # Notice that this extension is not installed by default. In case it cannot + # be found, the observer does nothing and doesn't throw an error. + class QueryStatistics < MigrationObserver + include Gitlab::Database::SchemaHelpers + + def before + return unless enabled? + + connection.execute('select pg_stat_statements_reset()') + end + + def record(observation) + return unless enabled? + + observation.query_statistics = connection.execute(<<~SQL) + SELECT query, calls, total_time, max_time, mean_time, rows + FROM pg_stat_statements + ORDER BY total_time DESC + SQL + end + + private + + def enabled? + function_exists?(:pg_stat_statements_reset) && connection.view_exists?(:pg_stat_statements) + end + end + end + end + end +end diff --git a/lib/gitlab/email/handler/service_desk_handler.rb b/lib/gitlab/email/handler/service_desk_handler.rb index d1dd616385d..80e8b726099 100644 --- a/lib/gitlab/email/handler/service_desk_handler.rb +++ b/lib/gitlab/email/handler/service_desk_handler.rb @@ -79,7 +79,7 @@ module Gitlab @issue = Issues::CreateService.new( project, User.support_bot, - title: issue_title, + title: mail.subject, description: message_including_template, confidential: true, external_author: from_address @@ -137,12 +137,6 @@ module Gitlab (mail.reply_to || []).first || mail.from.first || mail.sender end - def issue_title - from = "(from #{from_address})" if from_address - - "Service Desk #{from}: #{mail.subject}" - end - def can_handle_legacy_format? project_path && project_path.include?('/') && !mail_key.include?('+') end diff --git a/lib/gitlab/experimentation.rb b/lib/gitlab/experimentation.rb index 423f238a0a2..337c28f3179 100644 --- a/lib/gitlab/experimentation.rb +++ b/lib/gitlab/experimentation.rb @@ -58,10 +58,6 @@ module Gitlab tracking_category: 'Growth::Conversion::Experiment::ContactSalesInApp', use_backwards_compatible_subject_index: true }, - customize_homepage: { - tracking_category: 'Growth::Expansion::Experiment::CustomizeHomepage', - use_backwards_compatible_subject_index: true - }, group_only_trials: { tracking_category: 'Growth::Conversion::Experiment::GroupOnlyTrials', use_backwards_compatible_subject_index: true @@ -81,7 +77,7 @@ module Gitlab trial_during_signup: { tracking_category: 'Growth::Conversion::Experiment::TrialDuringSignup' }, - ci_syntax_templates: { + ci_syntax_templates_b: { tracking_category: 'Growth::Activation::Experiment::CiSyntaxTemplates', rollout_strategy: :user }, diff --git a/lib/gitlab/gitaly_client.rb b/lib/gitlab/gitaly_client.rb index 3c7fa88977e..e3788814dd5 100644 --- a/lib/gitlab/gitaly_client.rb +++ b/lib/gitlab/gitaly_client.rb @@ -246,9 +246,7 @@ module Gitlab def self.route_to_primary return {} unless Gitlab::SafeRequestStore.active? - return {} unless Gitlab::SafeRequestStore[:gitlab_git_env] - - return {} if Gitlab::SafeRequestStore[:gitlab_git_env].empty? + return {} if Gitlab::SafeRequestStore[:gitlab_git_env].blank? { 'gitaly-route-repository-accessor-policy' => 'primary-only' } end diff --git a/lib/gitlab/gitaly_client/storage_settings.rb b/lib/gitlab/gitaly_client/storage_settings.rb index 5e50ac72965..7edd42f9ef7 100644 --- a/lib/gitlab/gitaly_client/storage_settings.rb +++ b/lib/gitlab/gitaly_client/storage_settings.rb @@ -60,7 +60,8 @@ module Gitlab end def legacy_disk_path - if self.class.disk_access_denied? + # Do not use self.class due to Spring reloading issues + if Gitlab::GitalyClient::StorageSettings.disk_access_denied? raise DirectPathAccessError, "git disk access denied" end diff --git a/lib/gitlab/graphql/docs/helper.rb b/lib/gitlab/graphql/docs/helper.rb index ad9e08e189c..155602740c4 100644 --- a/lib/gitlab/graphql/docs/helper.rb +++ b/lib/gitlab/graphql/docs/helper.rb @@ -28,16 +28,20 @@ module Gitlab end def render_name_and_description(object) - content = "### #{object[:name]}\n" + content = "### #{object[:name].camelcase}\n" if object[:description].present? - content += "\n#{object[:description]}.\n" + content += "\n#{object[:description]}" + content += '.' unless object[:description].ends_with?('.') + content += "\n" end content end def sorted_by_name(objects) + return [] unless objects.present? + objects.sort_by { |o| o[:name] } end @@ -49,6 +53,14 @@ module Gitlab ] end + def render_argument(argument) + '| %s | %s | %s |' % [ + render_name(argument), + render_description(argument), + render_field_type(argument[:type][:info]) + ] + end + def render_enum_value(value) '| %s | %s |' % [ render_name(value), @@ -98,6 +110,10 @@ module Gitlab end end + def queries + graphql_operation_types.find { |type| type[:name] == 'Query' }.to_h[:fields] + end + # We ignore the built-in enum types. def enums graphql_enum_types.select do |enum_type| diff --git a/lib/gitlab/graphql/docs/templates/default.md.haml b/lib/gitlab/graphql/docs/templates/default.md.haml index 9dfb9b090a8..1df1c3a3e58 100644 --- a/lib/gitlab/graphql/docs/templates/default.md.haml +++ b/lib/gitlab/graphql/docs/templates/default.md.haml @@ -21,6 +21,24 @@ \ :plain + ## Queries + + Queries are used to get the resources, filter or query them. + + For more information, visit [Queries and Mutations](https://graphql.org/learn/queries/). +\ + +- sorted_by_name(queries).each do |query| + + = render_name_and_description(query) + - unless query[:arguments].empty? + ~ "| Name | Description | Type |" + ~ "| ----- | ---- | ----------- |" + - sorted_by_name(query[:arguments]).each do |argument| + = render_argument(argument) + \ + +:plain ## Object types Object types represent the resources that the GitLab GraphQL API can return. diff --git a/lib/gitlab/import_export/repo_restorer.rb b/lib/gitlab/import_export/repo_restorer.rb index 8af7b68d78e..998da3e4afb 100644 --- a/lib/gitlab/import_export/repo_restorer.rb +++ b/lib/gitlab/import_export/repo_restorer.rb @@ -42,7 +42,7 @@ module Gitlab def ensure_repository_does_not_exist! if repository.exists? shared.logger.info( - message: %Q{Deleting existing "#{repository.path}" to re-import it.} + message: %Q{Deleting existing "#{repository.disk_path}" to re-import it.} ) Repositories::DestroyService.new(repository).execute diff --git a/lib/gitlab/marginalia.rb b/lib/gitlab/marginalia.rb index 325a8c5c325..c99cf113638 100644 --- a/lib/gitlab/marginalia.rb +++ b/lib/gitlab/marginalia.rb @@ -2,8 +2,6 @@ module Gitlab module Marginalia - cattr_accessor :enabled, default: false - def self.set_application_name ::Marginalia.application_name = Gitlab.process_name end @@ -13,12 +11,5 @@ module Gitlab ::Marginalia::SidekiqInstrumentation.enable! end end - - def self.set_enabled_from_feature_flag - # During db:create and db:bootstrap skip feature query as DB is not available yet. - return false unless Gitlab::Database.cached_table_exists?('features') - - self.enabled = Feature.enabled?(:marginalia, type: :ops) - end end end diff --git a/lib/gitlab/marginalia/active_record_instrumentation.rb b/lib/gitlab/marginalia/active_record_instrumentation.rb deleted file mode 100644 index 452f472bf6a..00000000000 --- a/lib/gitlab/marginalia/active_record_instrumentation.rb +++ /dev/null @@ -1,12 +0,0 @@ -# frozen_string_literal: true - -# Patch to annotate sql only when the feature is enabled. -module Gitlab - module Marginalia - module ActiveRecordInstrumentation - def annotate_sql(sql) - Gitlab::Marginalia.enabled ? super(sql) : sql - end - end - end -end diff --git a/lib/gitlab/metrics/samplers/ruby_sampler.rb b/lib/gitlab/metrics/samplers/ruby_sampler.rb index 76175b465e4..3d29d38fa1f 100644 --- a/lib/gitlab/metrics/samplers/ruby_sampler.rb +++ b/lib/gitlab/metrics/samplers/ruby_sampler.rb @@ -7,7 +7,7 @@ module Gitlab module Samplers class RubySampler < BaseSampler DEFAULT_SAMPLING_INTERVAL_SECONDS = 60 - GC_REPORT_BUCKETS = [0.005, 0.01, 0.02, 0.04, 0.07, 0.1, 0.5].freeze + GC_REPORT_BUCKETS = [0.01, 0.05, 0.1, 0.2, 0.3, 0.5, 1].freeze def initialize(*) GC::Profiler.clear diff --git a/lib/gitlab/metrics/subscribers/active_record.rb b/lib/gitlab/metrics/subscribers/active_record.rb index d725d8d7b29..111aa2cab48 100644 --- a/lib/gitlab/metrics/subscribers/active_record.rb +++ b/lib/gitlab/metrics/subscribers/active_record.rb @@ -9,6 +9,7 @@ module Gitlab IGNORABLE_SQL = %w{BEGIN COMMIT}.freeze DB_COUNTERS = %i{db_count db_write_count db_cached_count}.freeze + SQL_COMMANDS_WITH_COMMENTS_REGEX = /\A(\/\*.*\*\/\s)?((?!(.*[^\w'"](DELETE|UPDATE|INSERT INTO)[^\w'"])))(WITH.*)?(SELECT)((?!(FOR UPDATE|FOR SHARE)).)*$/i.freeze def sql(event) # Mark this thread as requiring a database connection. This is used @@ -37,7 +38,7 @@ module Gitlab private def select_sql_command?(payload) - payload[:sql].match(/\A((?!(.*[^\w'"](DELETE|UPDATE|INSERT INTO)[^\w'"])))(WITH.*)?(SELECT)((?!(FOR UPDATE|FOR SHARE)).)*$/i) + payload[:sql].match(SQL_COMMANDS_WITH_COMMENTS_REGEX) end def increment_db_counters(payload) diff --git a/lib/gitlab/performance_bar/redis_adapter_when_peek_enabled.rb b/lib/gitlab/performance_bar/redis_adapter_when_peek_enabled.rb index 133d777fc32..ac5c907465e 100644 --- a/lib/gitlab/performance_bar/redis_adapter_when_peek_enabled.rb +++ b/lib/gitlab/performance_bar/redis_adapter_when_peek_enabled.rb @@ -17,7 +17,7 @@ module Gitlab # to a structured log # rubocop:disable Gitlab/ModuleWithInstanceVariables def enqueue_stats_job(request_id) - return unless gather_stats? + return unless Feature.enabled?(:performance_bar_stats) @client.sadd(GitlabPerformanceBarStatsWorker::STATS_KEY, request_id) @@ -43,12 +43,6 @@ module Gitlab ) end # rubocop:enable Gitlab/ModuleWithInstanceVariables - - def gather_stats? - return unless Feature.enabled?(:performance_bar_stats) - - Gitlab.com? || Gitlab.staging? || !Rails.env.production? - end end end end diff --git a/lib/gitlab/regex.rb b/lib/gitlab/regex.rb index 96f2b7570b3..00739c05386 100644 --- a/lib/gitlab/regex.rb +++ b/lib/gitlab/regex.rb @@ -61,6 +61,10 @@ module Gitlab maven_app_name_regex end + def npm_package_name_regex + @npm_package_name_regex ||= %r{\A(?:@(#{Gitlab::PathRegex::NAMESPACE_FORMAT_REGEX})/)?[-+\.\_a-zA-Z0-9]+\z} + end + def nuget_package_name_regex @nuget_package_name_regex ||= %r{\A[-+\.\_a-zA-Z0-9]+\z}.freeze end diff --git a/lib/gitlab/template/base_template.rb b/lib/gitlab/template/base_template.rb index 0f933a61598..dc006877129 100644 --- a/lib/gitlab/template/base_template.rb +++ b/lib/gitlab/template/base_template.rb @@ -87,11 +87,11 @@ module Gitlab raise NotImplementedError end - def by_category(category, project = nil) + def by_category(category, project = nil, empty_category_title: nil) directory = category_directory(category) files = finder(project).list_files_for(directory) - files.map { |f| new(f, project, category: category) }.sort + files.map { |f| new(f, project, category: category.presence || empty_category_title) }.sort end def category_directory(category) @@ -108,7 +108,7 @@ module Gitlab # Gitaly the actual template names within a given project's repository for all file templates # other than `issue` and `merge request` description templates, which would instead # overwrite the `template_names` method to return a redis cached version, by reading cached values - # from `repository.issue_template_names_by_category` and `repository.merge_request_template_names_by_category` + # from `repository.issue_template_names_hash` and `repository.merge_request_template_names_hash` # methods. def repository_template_names(project) template_names_by_category(self.all(project)) diff --git a/lib/gitlab/template/issue_template.rb b/lib/gitlab/template/issue_template.rb index 3049f43b322..6e579018e45 100644 --- a/lib/gitlab/template/issue_template.rb +++ b/lib/gitlab/template/issue_template.rb @@ -23,7 +23,11 @@ module Gitlab # own caching mechanism to avoid the back and forth call jumps between finder and model. # # follow-up issue: https://gitlab.com/gitlab-org/gitlab/-/issues/300279 - project.repository.issue_template_names_by_category + project.repository.issue_template_names_hash + end + + def by_category(category, project = nil, empty_category_title: nil) + super(category, project, empty_category_title: _('Project Templates')) end end end diff --git a/lib/gitlab/template/merge_request_template.rb b/lib/gitlab/template/merge_request_template.rb index 9442f3b13fb..241a823d870 100644 --- a/lib/gitlab/template/merge_request_template.rb +++ b/lib/gitlab/template/merge_request_template.rb @@ -23,7 +23,11 @@ module Gitlab # own caching mechanism to avoid the back and forth call jumps between finder and model. # # follow-up issue: https://gitlab.com/gitlab-org/gitlab/-/issues/300279 - project.repository.merge_request_template_names_by_category + project.repository.merge_request_template_names_hash + end + + def by_category(category, project = nil, empty_category_title: nil) + super(category, project, empty_category_title: _('Project Templates')) end end end diff --git a/lib/gitlab/tracking/standard_context.rb b/lib/gitlab/tracking/standard_context.rb index 92fdd008249..8ce16c11267 100644 --- a/lib/gitlab/tracking/standard_context.rb +++ b/lib/gitlab/tracking/standard_context.rb @@ -15,10 +15,14 @@ module Gitlab end def environment - return 'production' if Gitlab.com_and_canary? - return 'staging' if Gitlab.staging? + return 'production' if Gitlab.com? + + return 'org' if Gitlab.org? + + return 'self-managed' if Rails.env.production? + 'development' end diff --git a/lib/gitlab/usage/docs/helper.rb b/lib/gitlab/usage/docs/helper.rb index 8483334800b..e090eb65b4b 100644 --- a/lib/gitlab/usage/docs/helper.rb +++ b/lib/gitlab/usage/docs/helper.rb @@ -31,7 +31,9 @@ module Gitlab end def render_description(object) - object.description + return 'Missing description' unless object.attributes[:description].present? + + object.attributes[:description] end def render_attribute_row(key, value) diff --git a/lib/gitlab/usage/docs/value_formatter.rb b/lib/gitlab/usage/docs/value_formatter.rb index a2dc9b081f8..22c5c13fc0f 100644 --- a/lib/gitlab/usage/docs/value_formatter.rb +++ b/lib/gitlab/usage/docs/value_formatter.rb @@ -5,12 +5,14 @@ module Gitlab module Docs class ValueFormatter def self.format(key, value) + return '' unless value.present? + case key when :key_path "**`#{value}`**" when :data_source value.to_s.capitalize - when :product_group + when :product_group, :product_category "`#{value}`" when :introduced_by_url "[Introduced by](#{value})" diff --git a/lib/gitlab/usage_data_counters/aggregated_metrics/code_review.yml b/lib/gitlab/usage_data_counters/aggregated_metrics/code_review.yml new file mode 100644 index 00000000000..4f86d500164 --- /dev/null +++ b/lib/gitlab/usage_data_counters/aggregated_metrics/code_review.yml @@ -0,0 +1,89 @@ +# code_review_extension_category_monthly_active_users +# This is only metrics related to the VS Code Extension for now. +# +# code_review_category_monthly_active_users +# This is the user based metrics. These should only be user based metrics and only be related to the Code Review things inside of GitLab. +# +# code_review_group_monthly_active_users +# This is an aggregation of both of the above aggregations. It's intended to represent all users who interact with our group across all of our categories. +--- +- name: code_review_group_monthly_active_users + operator: OR + feature_flag: usage_data_code_review_aggregation + source: redis + events: [ + 'i_code_review_user_single_file_diffs', + 'i_code_review_user_create_mr', + 'i_code_review_user_close_mr', + 'i_code_review_user_reopen_mr', + 'i_code_review_user_resolve_thread', + 'i_code_review_user_unresolve_thread', + 'i_code_review_edit_mr_title', + 'i_code_review_edit_mr_desc', + 'i_code_review_user_merge_mr', + 'i_code_review_user_create_mr_comment', + 'i_code_review_user_edit_mr_comment', + 'i_code_review_user_remove_mr_comment', + 'i_code_review_user_create_review_note', + 'i_code_review_user_publish_review', + 'i_code_review_user_create_multiline_mr_comment', + 'i_code_review_user_edit_multiline_mr_comment', + 'i_code_review_user_remove_multiline_mr_comment', + 'i_code_review_user_add_suggestion', + 'i_code_review_user_apply_suggestion', + 'i_code_review_user_assigned', + 'i_code_review_user_review_requested', + 'i_code_review_user_approve_mr', + 'i_code_review_user_unapprove_mr', + 'i_code_review_user_marked_as_draft', + 'i_code_review_user_unmarked_as_draft', + 'i_code_review_user_approval_rule_added', + 'i_code_review_user_approval_rule_deleted', + 'i_code_review_user_approval_rule_edited', + 'i_code_review_user_vs_code_api_request', + 'i_code_review_user_toggled_task_item_status', + 'i_code_review_user_create_mr_from_issue' + ] +- name: code_review_category_monthly_active_users + operator: OR + feature_flag: usage_data_code_review_aggregation + source: redis + events: [ + 'i_code_review_user_single_file_diffs', + 'i_code_review_user_create_mr', + 'i_code_review_user_close_mr', + 'i_code_review_user_reopen_mr', + 'i_code_review_user_resolve_thread', + 'i_code_review_user_unresolve_thread', + 'i_code_review_edit_mr_title', + 'i_code_review_edit_mr_desc', + 'i_code_review_user_merge_mr', + 'i_code_review_user_create_mr_comment', + 'i_code_review_user_edit_mr_comment', + 'i_code_review_user_remove_mr_comment', + 'i_code_review_user_create_review_note', + 'i_code_review_user_publish_review', + 'i_code_review_user_create_multiline_mr_comment', + 'i_code_review_user_edit_multiline_mr_comment', + 'i_code_review_user_remove_multiline_mr_comment', + 'i_code_review_user_add_suggestion', + 'i_code_review_user_apply_suggestion', + 'i_code_review_user_assigned', + 'i_code_review_user_review_requested', + 'i_code_review_user_approve_mr', + 'i_code_review_user_unapprove_mr', + 'i_code_review_user_marked_as_draft', + 'i_code_review_user_unmarked_as_draft', + 'i_code_review_user_approval_rule_added', + 'i_code_review_user_approval_rule_deleted', + 'i_code_review_user_approval_rule_edited', + 'i_code_review_user_toggled_task_item_status', + 'i_code_review_user_create_mr_from_issue' + ] +- name: code_review_extension_category_monthly_active_users + operator: OR + feature_flag: usage_data_code_review_aggregation + source: redis + events: [ + 'i_code_review_user_vs_code_api_request' + ] diff --git a/lib/gitlab/usage_data_counters/counter_events/package_events.yml b/lib/gitlab/usage_data_counters/counter_events/package_events.yml index f6bddabdd44..e1648245f3f 100644 --- a/lib/gitlab/usage_data_counters/counter_events/package_events.yml +++ b/lib/gitlab/usage_data_counters/counter_events/package_events.yml @@ -41,6 +41,9 @@ - i_package_pypi_delete_package - i_package_pypi_pull_package - i_package_pypi_push_package +- i_package_rubygems_delete_package +- i_package_rubygems_pull_package +- i_package_rubygems_push_package - i_package_tag_delete_package - i_package_tag_pull_package - i_package_tag_push_package diff --git a/lib/gitlab/usage_data_counters/known_events/package_events.yml b/lib/gitlab/usage_data_counters/known_events/package_events.yml index 78a2a587b34..6cf31ba4db7 100644 --- a/lib/gitlab/usage_data_counters/known_events/package_events.yml +++ b/lib/gitlab/usage_data_counters/known_events/package_events.yml @@ -99,6 +99,16 @@ aggregation: weekly redis_slot: package feature_flag: collect_package_events_redis +- name: i_package_rubygems_deploy_token + category: deploy_token_packages + aggregation: weekly + redis_slot: package + feature_flag: collect_package_events_redis +- name: i_package_rubygems_user + category: user_packages + aggregation: weekly + redis_slot: package + feature_flag: collect_package_events_redis - name: i_package_tag_deploy_token category: deploy_token_packages aggregation: weekly diff --git a/lib/tasks/eslint.rake b/lib/tasks/eslint.rake index ad63de66c81..35c3e834258 100644 --- a/lib/tasks/eslint.rake +++ b/lib/tasks/eslint.rake @@ -3,7 +3,7 @@ unless Rails.env.production? desc "GitLab | Run ESLint" task eslint: ['yarn:check'] do - unless system('yarn run eslint') + unless system('yarn run lint:eslint') abort('rake eslint failed') end end diff --git a/lib/tasks/gitlab/graphql.rake b/lib/tasks/gitlab/graphql.rake index e4eb4604138..caf5879a154 100644 --- a/lib/tasks/gitlab/graphql.rake +++ b/lib/tasks/gitlab/graphql.rake @@ -6,6 +6,7 @@ require 'graphql/rake_task' namespace :gitlab do OUTPUT_DIR = Rails.root.join("doc/api/graphql/reference") + TEMP_SCHEMA_DIR = Rails.root.join('tmp/tests/graphql') TEMPLATES_DIR = 'lib/gitlab/graphql/docs/templates/' # Make all feature flags enabled so that all feature flag @@ -27,7 +28,7 @@ namespace :gitlab do GraphQL::RakeTask.new( schema_name: 'GitlabSchema', dependencies: [:environment, :enable_feature_flags], - directory: OUTPUT_DIR, + directory: TEMP_SCHEMA_DIR, idl_outfile: "gitlab_schema.graphql", json_outfile: "gitlab_schema.json" ) @@ -129,19 +130,6 @@ namespace :gitlab do abort end end - - desc 'GitLab | GraphQL | Check if GraphQL schemas are up to date' - task check_schema: [:environment, :enable_feature_flags] do - idl_doc = File.read(Rails.root.join(OUTPUT_DIR, 'gitlab_schema.graphql')) - json_doc = File.read(Rails.root.join(OUTPUT_DIR, 'gitlab_schema.json')) - - if idl_doc == GitlabSchema.to_definition && json_doc == GitlabSchema.to_json - puts "GraphQL schema is up to date" - else - format_output('GraphQL schema is outdated! Please update it by running `bundle exec rake gitlab:graphql:schema:dump`.') - abort - end - end end end diff --git a/lib/tasks/lint.rake b/lib/tasks/lint.rake index 5d60bc41f21..976ec089011 100644 --- a/lib/tasks/lint.rake +++ b/lib/tasks/lint.rake @@ -33,7 +33,6 @@ unless Rails.env.production? tasks = %w[ config_lint lint:haml - scss_lint gettext:lint lint:static_verification gitlab:sidekiq:all_queues_yml:check diff --git a/lib/tasks/scss-lint.rake b/lib/tasks/scss-lint.rake deleted file mode 100644 index 8a4809f80fd..00000000000 --- a/lib/tasks/scss-lint.rake +++ /dev/null @@ -1,12 +0,0 @@ -# frozen_string_literal: true - -unless Rails.env.production? - require 'scss_lint/rake_task' - - SCSSLint::RakeTask.new do |t| - t.config = '.scss-lint.yml' - # See https://github.com/brigade/scss-lint/issues/726 - # Hack, otherwise linter won't respect scss_files option in config file. - t.files = [] - end -end |