diff --git a/.rubocop_manual_todo.yml b/.rubocop_manual_todo.yml index 7f18912b34c..d32db0336e5 100644 --- a/.rubocop_manual_todo.yml +++ b/.rubocop_manual_todo.yml @@ -198,7 +198,6 @@ Rails/SaveBang: - 'ee/spec/services/start_pull_mirroring_service_spec.rb' - 'ee/spec/services/status_page/trigger_publish_service_spec.rb' - 'ee/spec/services/todo_service_spec.rb' - - 'ee/spec/services/update_build_minutes_service_spec.rb' - 'ee/spec/services/vulnerability_feedback/create_service_spec.rb' - 'ee/spec/support/protected_tags/access_control_shared_examples.rb' - 'ee/spec/support/shared_examples/features/protected_branches_access_control_shared_examples.rb' @@ -2530,7 +2529,6 @@ Gitlab/NamespacedClass: - 'ee/app/services/ldap_group_reset_service.rb' - 'ee/app/services/start_pull_mirroring_service.rb' - 'ee/app/services/timebox_report_service.rb' - - 'ee/app/services/update_build_minutes_service.rb' - 'ee/app/uploaders/issuable_metric_image_uploader.rb' - 'ee/app/validators/host_validator.rb' - 'ee/app/validators/ldap_filter_validator.rb' diff --git a/app/services/boards/create_service.rb b/app/services/boards/create_service.rb index 2ccaea64d14..54dab581686 100644 --- a/app/services/boards/create_service.rb +++ b/app/services/boards/create_service.rb @@ -13,11 +13,11 @@ module Boards private def can_create_board? - parent.boards.empty? || parent.multiple_issue_boards_available? + parent_board_collection.empty? || parent.multiple_issue_boards_available? end def create_board! - board = parent.boards.create(params) + board = parent_board_collection.create(params) unless board.persisted? return ServiceResponse.error(message: "There was an error when creating a board.", payload: board) @@ -30,6 +30,10 @@ module Boards ServiceResponse.success(payload: board) end + + def parent_board_collection + parent.boards + end end end diff --git a/changelogs/unreleased/52756-pipeline_schedule_worker_cron.yml b/changelogs/unreleased/52756-pipeline_schedule_worker_cron.yml new file mode 100644 index 00000000000..ddcecb52d99 --- /dev/null +++ b/changelogs/unreleased/52756-pipeline_schedule_worker_cron.yml @@ -0,0 +1,5 @@ +--- +title: Run pipeline_schedule_worker at every 10th minute from 3 through 59 +merge_request: 52756 +author: Ben Bodenmiller (@bbodenmiller) +type: changed diff --git a/config/gitlab.yml.example b/config/gitlab.yml.example index 9997772674d..29b60aa91c5 100644 --- a/config/gitlab.yml.example +++ b/config/gitlab.yml.example @@ -435,7 +435,7 @@ production: &base cron: "0 * * * *" # Execute scheduled triggers pipeline_schedule_worker: - cron: "19 * * * *" + cron: "3-59/10 * * * *" # Remove expired build artifacts expire_build_artifacts_worker: cron: "*/7 * * * *" diff --git a/config/initializers/1_settings.rb b/config/initializers/1_settings.rb index 2f00d6dd099..e3c614b720b 100644 --- a/config/initializers/1_settings.rb +++ b/config/initializers/1_settings.rb @@ -416,7 +416,7 @@ Settings.cron_jobs['stuck_ci_jobs_worker'] ||= Settingslogic.new({}) Settings.cron_jobs['stuck_ci_jobs_worker']['cron'] ||= '0 * * * *' Settings.cron_jobs['stuck_ci_jobs_worker']['job_class'] = 'StuckCiJobsWorker' Settings.cron_jobs['pipeline_schedule_worker'] ||= Settingslogic.new({}) -Settings.cron_jobs['pipeline_schedule_worker']['cron'] ||= '19 * * * *' +Settings.cron_jobs['pipeline_schedule_worker']['cron'] ||= '3-59/10 * * * *' Settings.cron_jobs['pipeline_schedule_worker']['job_class'] = 'PipelineScheduleWorker' Settings.cron_jobs['expire_build_artifacts_worker'] ||= Settingslogic.new({}) Settings.cron_jobs['expire_build_artifacts_worker']['cron'] ||= '*/7 * * * *' diff --git a/doc/api/graphql/reference/gitlab_schema.graphql b/doc/api/graphql/reference/gitlab_schema.graphql index 437a31ec426..bf7966d2a67 100644 --- a/doc/api/graphql/reference/gitlab_schema.graphql +++ b/doc/api/graphql/reference/gitlab_schema.graphql @@ -8967,6 +8967,56 @@ type EpicBoardConnection { pageInfo: PageInfo! } +""" +Autogenerated input type of EpicBoardCreate +""" +input EpicBoardCreateInput { + """ + A unique identifier for the client performing the mutation. + """ + clientMutationId: String + + """ + Full path of the group with which the resource is associated. + """ + groupPath: ID + + """ + Whether or not backlog list is hidden. + """ + hideBacklogList: Boolean + + """ + Whether or not closed list is hidden. + """ + hideClosedList: Boolean + + """ + The board name. + """ + name: String +} + +""" +Autogenerated return type of EpicBoardCreate +""" +type EpicBoardCreatePayload { + """ + A unique identifier for the client performing the mutation. + """ + clientMutationId: String + + """ + The created epic board. + """ + epicBoard: EpicBoard + + """ + Errors encountered during execution of the mutation. + """ + errors: [String!]! +} + """ An edge in a connection. """ @@ -16051,6 +16101,7 @@ type Mutation { dismissVulnerability(input: DismissVulnerabilityInput!): DismissVulnerabilityPayload @deprecated(reason: "Use vulnerabilityDismiss. Deprecated in 13.5.") environmentsCanaryIngressUpdate(input: EnvironmentsCanaryIngressUpdateInput!): EnvironmentsCanaryIngressUpdatePayload epicAddIssue(input: EpicAddIssueInput!): EpicAddIssuePayload + epicBoardCreate(input: EpicBoardCreateInput!): EpicBoardCreatePayload epicSetSubscription(input: EpicSetSubscriptionInput!): EpicSetSubscriptionPayload epicTreeReorder(input: EpicTreeReorderInput!): EpicTreeReorderPayload exportRequirements(input: ExportRequirementsInput!): ExportRequirementsPayload @@ -28014,6 +28065,11 @@ type VulnerabilityLocationContainerScanning { Represents the location of a vulnerability found by a Coverage Fuzzing scan """ type VulnerabilityLocationCoverageFuzzing { + """ + Blob path to the vulnerable file + """ + blobPath: String + """ Number of the last relevant line in the vulnerable file """ @@ -28069,6 +28125,11 @@ type VulnerabilityLocationDast { Represents the location of a vulnerability found by a dependency security scan """ type VulnerabilityLocationDependencyScanning { + """ + Blob path to the vulnerable file + """ + blobPath: String + """ Dependency containing the vulnerability """ @@ -28084,6 +28145,11 @@ type VulnerabilityLocationDependencyScanning { Represents the location of a vulnerability found by a SAST scan """ type VulnerabilityLocationSast { + """ + Blob path to the vulnerable file + """ + blobPath: String + """ Number of the last relevant line in the vulnerable file """ @@ -28114,6 +28180,11 @@ type VulnerabilityLocationSast { Represents the location of a vulnerability found by a secret detection scan """ type VulnerabilityLocationSecretDetection { + """ + Blob path to the vulnerable file + """ + blobPath: String + """ Number of the last relevant line in the vulnerable file """ diff --git a/doc/api/graphql/reference/gitlab_schema.json b/doc/api/graphql/reference/gitlab_schema.json index 5519afd51b9..aa4dd9d1133 100644 --- a/doc/api/graphql/reference/gitlab_schema.json +++ b/doc/api/graphql/reference/gitlab_schema.json @@ -24811,6 +24811,134 @@ "enumValues": null, "possibleTypes": null }, + { + "kind": "INPUT_OBJECT", + "name": "EpicBoardCreateInput", + "description": "Autogenerated input type of EpicBoardCreate", + "fields": null, + "inputFields": [ + { + "name": "name", + "description": "The board name.", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "hideBacklogList", + "description": "Whether or not backlog list is hidden.", + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "hideClosedList", + "description": "Whether or not closed list is hidden.", + "type": { + "kind": "SCALAR", + "name": "Boolean", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "groupPath", + "description": "Full path of the group with which the resource is associated.", + "type": { + "kind": "SCALAR", + "name": "ID", + "ofType": null + }, + "defaultValue": null + }, + { + "name": "clientMutationId", + "description": "A unique identifier for the client performing the mutation.", + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "defaultValue": null + } + ], + "interfaces": null, + "enumValues": null, + "possibleTypes": null + }, + { + "kind": "OBJECT", + "name": "EpicBoardCreatePayload", + "description": "Autogenerated return type of EpicBoardCreate", + "fields": [ + { + "name": "clientMutationId", + "description": "A unique identifier for the client performing the mutation.", + "args": [ + + ], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "epicBoard", + "description": "The created epic board.", + "args": [ + + ], + "type": { + "kind": "OBJECT", + "name": "EpicBoard", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, + { + "name": "errors", + "description": "Errors encountered during execution of the mutation.", + "args": [ + + ], + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "LIST", + "name": null, + "ofType": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "SCALAR", + "name": "String", + "ofType": null + } + } + } + }, + "isDeprecated": false, + "deprecationReason": null + } + ], + "inputFields": null, + "interfaces": [ + + ], + "enumValues": null, + "possibleTypes": null + }, { "kind": "OBJECT", "name": "EpicBoardEdge", @@ -45574,6 +45702,33 @@ "isDeprecated": false, "deprecationReason": null }, + { + "name": "epicBoardCreate", + "description": null, + "args": [ + { + "name": "input", + "description": null, + "type": { + "kind": "NON_NULL", + "name": null, + "ofType": { + "kind": "INPUT_OBJECT", + "name": "EpicBoardCreateInput", + "ofType": null + } + }, + "defaultValue": null + } + ], + "type": { + "kind": "OBJECT", + "name": "EpicBoardCreatePayload", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "epicSetSubscription", "description": null, @@ -81316,6 +81471,20 @@ "name": "VulnerabilityLocationCoverageFuzzing", "description": "Represents the location of a vulnerability found by a Coverage Fuzzing scan", "fields": [ + { + "name": "blobPath", + "description": "Blob path to the vulnerable file", + "args": [ + + ], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "endLine", "description": "Number of the last relevant line in the vulnerable file", @@ -81468,6 +81637,20 @@ "name": "VulnerabilityLocationDependencyScanning", "description": "Represents the location of a vulnerability found by a dependency security scan", "fields": [ + { + "name": "blobPath", + "description": "Blob path to the vulnerable file", + "args": [ + + ], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "dependency", "description": "Dependency containing the vulnerability", @@ -81509,6 +81692,20 @@ "name": "VulnerabilityLocationSast", "description": "Represents the location of a vulnerability found by a SAST scan", "fields": [ + { + "name": "blobPath", + "description": "Blob path to the vulnerable file", + "args": [ + + ], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "endLine", "description": "Number of the last relevant line in the vulnerable file", @@ -81592,6 +81789,20 @@ "name": "VulnerabilityLocationSecretDetection", "description": "Represents the location of a vulnerability found by a secret detection scan", "fields": [ + { + "name": "blobPath", + "description": "Blob path to the vulnerable file", + "args": [ + + ], + "type": { + "kind": "SCALAR", + "name": "String", + "ofType": null + }, + "isDeprecated": false, + "deprecationReason": null + }, { "name": "endLine", "description": "Number of the last relevant line in the vulnerable file", diff --git a/doc/api/graphql/reference/index.md b/doc/api/graphql/reference/index.md index 43005747da7..1b6be923792 100644 --- a/doc/api/graphql/reference/index.md +++ b/doc/api/graphql/reference/index.md @@ -1448,6 +1448,16 @@ Represents an epic board. | `lists` | EpicListConnection | Epic board lists. | | `name` | String | Name of the board. | +### EpicBoardCreatePayload + +Autogenerated return type of EpicBoardCreate. + +| Field | Type | Description | +| ----- | ---- | ----------- | +| `clientMutationId` | String | A unique identifier for the client performing the mutation. | +| `epicBoard` | EpicBoard | The created epic board. | +| `errors` | String! => Array | Errors encountered during execution of the mutation. | + ### EpicDescendantCount Counts of descendent epics. @@ -4266,6 +4276,7 @@ Represents the location of a vulnerability found by a Coverage Fuzzing scan. | Field | Type | Description | | ----- | ---- | ----------- | +| `blobPath` | String | Blob path to the vulnerable file | | `endLine` | String | Number of the last relevant line in the vulnerable file | | `file` | String | Path to the vulnerable file | | `startLine` | String | Number of the first relevant line in the vulnerable file | @@ -4289,6 +4300,7 @@ Represents the location of a vulnerability found by a dependency security scan. | Field | Type | Description | | ----- | ---- | ----------- | +| `blobPath` | String | Blob path to the vulnerable file | | `dependency` | VulnerableDependency | Dependency containing the vulnerability | | `file` | String | Path to the vulnerable file | @@ -4298,6 +4310,7 @@ Represents the location of a vulnerability found by a SAST scan. | Field | Type | Description | | ----- | ---- | ----------- | +| `blobPath` | String | Blob path to the vulnerable file | | `endLine` | String | Number of the last relevant line in the vulnerable file | | `file` | String | Path to the vulnerable file | | `startLine` | String | Number of the first relevant line in the vulnerable file | @@ -4310,6 +4323,7 @@ Represents the location of a vulnerability found by a secret detection scan. | Field | Type | Description | | ----- | ---- | ----------- | +| `blobPath` | String | Blob path to the vulnerable file | | `endLine` | String | Number of the last relevant line in the vulnerable file | | `file` | String | Path to the vulnerable file | | `startLine` | String | Number of the first relevant line in the vulnerable file | diff --git a/doc/user/gitlab_com/index.md b/doc/user/gitlab_com/index.md index 9bae089b9d6..d474392b52a 100644 --- a/doc/user/gitlab_com/index.md +++ b/doc/user/gitlab_com/index.md @@ -97,7 +97,7 @@ Any settings or feature limits not listed here are using the defaults listed in | ----------- | ----------------- | ------------- | | Artifacts maximum size (compressed) | 1G | 100M | | Artifacts [expiry time](../../ci/yaml/README.md#artifactsexpire_in) | From June 22, 2020, deleted after 30 days unless otherwise specified (artifacts created before that date have no expiry). | deleted after 30 days unless otherwise specified | -| Scheduled Pipeline Cron | `*/5 * * * *` | `19 * * * *` | +| Scheduled Pipeline Cron | `*/5 * * * *` | `3-59/10 * * * *` | | [Max jobs in active pipelines](../../administration/instance_limits.md#number-of-jobs-in-active-pipelines) | `500` for Free tier, unlimited otherwise | Unlimited | [Max CI/CD subscriptions to a project](../../administration/instance_limits.md#number-of-cicd-subscriptions-to-a-project) | `2` | Unlimited | | [Max pipeline schedules in projects](../../administration/instance_limits.md#number-of-pipeline-schedules) | `10` for Free tier, `50` for all paid tiers | Unlimited | diff --git a/doc/user/project/repository/reducing_the_repo_size_using_git.md b/doc/user/project/repository/reducing_the_repo_size_using_git.md index ccb1b4f11b8..c371da0586e 100644 --- a/doc/user/project/repository/reducing_the_repo_size_using_git.md +++ b/doc/user/project/repository/reducing_the_repo_size_using_git.md @@ -23,9 +23,9 @@ Rewriting repository history is a destructive operation. Make sure to back up yo you begin. The best way back up a repository is to [export the project](../settings/import_export.md#exporting-a-project-and-its-data). -## Purge files from repository history and storage +## Purge files from repository history -To reduce the size of your repository in GitLab, you must remove references to large files from branches, tags, *and* +To reduce the size of your repository in GitLab, you must first remove references to large files from branches, tags, *and* other internal references (refs) that are automatically created by GitLab. These refs include: - `refs/merge-requests/*` for merge requests. diff --git a/qa/qa.rb b/qa/qa.rb index 1d1ac2e2749..1cf6d7b79f7 100644 --- a/qa/qa.rb +++ b/qa/qa.rb @@ -156,6 +156,7 @@ module QA autoload :Mattermost, 'qa/scenario/test/integration/mattermost' autoload :ObjectStorage, 'qa/scenario/test/integration/object_storage' autoload :SMTP, 'qa/scenario/test/integration/smtp' + autoload :SSHTunnel, 'qa/scenario/test/integration/ssh_tunnel' end module Sanity diff --git a/qa/qa/specs/features/browser_ui/2_plan/issue/create_issue_spec.rb b/qa/qa/specs/features/browser_ui/2_plan/issue/create_issue_spec.rb index 42c53c275df..de6b24e8477 100644 --- a/qa/qa/specs/features/browser_ui/2_plan/issue/create_issue_spec.rb +++ b/qa/qa/specs/features/browser_ui/2_plan/issue/create_issue_spec.rb @@ -1,7 +1,7 @@ # frozen_string_literal: true module QA - RSpec.describe 'Plan' do + RSpec.describe 'Plan', :smoke do describe 'Issue creation' do let(:closed_issue) { Resource::Issue.fabricate_via_api! } @@ -9,7 +9,7 @@ module QA Flow::Login.sign_in end - it 'creates an issue', :smoke, :reliable, testcase: 'https://gitlab.com/gitlab-org/quality/testcases/-/issues/1167' do + it 'creates an issue', testcase: 'https://gitlab.com/gitlab-org/quality/testcases/-/issues/1167' do issue = Resource::Issue.fabricate_via_browser_ui! Page::Project::Menu.perform(&:click_issues) @@ -19,7 +19,7 @@ module QA end end - it 'closes an issue', :smoke, testcase: 'https://gitlab.com/gitlab-org/quality/testcases/-/issues/1085' do + it 'closes an issue', testcase: 'https://gitlab.com/gitlab-org/quality/testcases/-/issues/1085' do closed_issue.visit! Page::Project::Issue::Show.perform do |issue_page| @@ -38,7 +38,7 @@ module QA end end - context 'when using attachments in comments', :smoke, :object_storage do + context 'when using attachments in comments', :object_storage do let(:gif_file_name) { 'banana_sample.gif' } let(:file_to_attach) do File.absolute_path(File.join('qa', 'fixtures', 'designs', gif_file_name)) @@ -56,42 +56,6 @@ module QA end end end - - context 'when using custom issue templates' do - let(:template_name) { 'custom_issue_template'} - let(:template_content) { 'This is a custom issue template test' } - - let(:template_project) do - Resource::Project.fabricate_via_api! do |project| - project.name = "custom-issue-template-project-#{SecureRandom.hex(8)}" - project.initialize_with_readme = true - end - end - - before do - Resource::Repository::Commit.fabricate_via_api! do |commit| - commit.project = template_project - commit.commit_message = 'Add custom issue template' - commit.add_files([ - { - file_path: ".gitlab/issue_templates/#{template_name}.md", - content: template_content - } - ]) - end - end - - it 'creates an issue via custom template', testcase: 'https://gitlab.com/gitlab-org/quality/testcases/-/issues/1229' do - Resource::Issue.fabricate_via_browser_ui! do |issue| - issue.project = template_project - issue.template = template_name - end - - Page::Project::Issue::Show.perform do |issue_page| - expect(issue_page).to have_content(template_content) - end - end - end end end end diff --git a/qa/qa/specs/features/browser_ui/2_plan/issue/custom_issue_template_spec.rb b/qa/qa/specs/features/browser_ui/2_plan/issue/custom_issue_template_spec.rb new file mode 100644 index 00000000000..5f5fe161e71 --- /dev/null +++ b/qa/qa/specs/features/browser_ui/2_plan/issue/custom_issue_template_spec.rb @@ -0,0 +1,43 @@ +# frozen_string_literal: true + +module QA + RSpec.describe 'Plan' do + describe 'Custom issue templates' do + let(:template_name) { 'custom_issue_template'} + let(:template_content) { 'This is a custom issue template test' } + + let(:template_project) do + Resource::Project.fabricate_via_api! do |project| + project.name = "custom-issue-template-project" + project.initialize_with_readme = true + end + end + + before do + Flow::Login.sign_in + + Resource::Repository::Commit.fabricate_via_api! do |commit| + commit.project = template_project + commit.commit_message = 'Add custom issue template' + commit.add_files([ + { + file_path: ".gitlab/issue_templates/#{template_name}.md", + content: template_content + } + ]) + end + end + + it 'creates an issue via custom template', testcase: 'https://gitlab.com/gitlab-org/quality/testcases/-/issues/1229' do + Resource::Issue.fabricate_via_browser_ui! do |issue| + issue.project = template_project + issue.template = template_name + end + + Page::Project::Issue::Show.perform do |issue_page| + expect(issue_page).to have_content(template_content) + end + end + end + end +end diff --git a/spec/deprecation_toolkit_env.rb b/spec/deprecation_toolkit_env.rb index a3f1bd0a269..531b15b5592 100644 --- a/spec/deprecation_toolkit_env.rb +++ b/spec/deprecation_toolkit_env.rb @@ -55,8 +55,6 @@ module DeprecationToolkitEnv # one by one def self.allowed_kwarg_warning_paths %w[ - ee/lib/ee/gitlab/usage_data.rb - spec/lib/gitlab/utils/usage_data_spec.rb spec/support/gitlab_experiment.rb spec/support/helpers/next_instance_of.rb rspec-mocks-3.10.0/lib/rspec/mocks/message_expectation.rb @@ -70,8 +68,6 @@ module DeprecationToolkitEnv grape_logging-1.8.3/lib/grape_logging/middleware/request_logger.rb activesupport-6.0.3.4/lib/active_support/cache.rb factory_bot-6.1.0/lib/factory_bot/decorator.rb - doorkeeper-5.4.0/lib/doorkeeper/models/access_token_mixin.rb - rouge-3.26.0/lib/rouge/formatter.rb batch-loader-1.4.0/lib/batch_loader/graphql.rb carrierwave-1.3.1/lib/carrierwave/sanitized_file.rb activerecord-6.0.3.4/lib/active_record/relation.rb diff --git a/spec/lib/gitlab/ci/cron_parser_spec.rb b/spec/lib/gitlab/ci/cron_parser_spec.rb index dd27b4045c9..15293429354 100644 --- a/spec/lib/gitlab/ci/cron_parser_spec.rb +++ b/spec/lib/gitlab/ci/cron_parser_spec.rb @@ -63,6 +63,17 @@ RSpec.describe Gitlab::Ci::CronParser do end end + context 'when range and slash used' do + let(:cron) { '3-59/10 * * * *' } + let(:cron_timezone) { 'UTC' } + + it_behaves_like returns_time_for_epoch + + it 'returns specific time' do + expect(subject.min).to be_in([3, 13, 23, 33, 43, 53]) + end + end + context 'when cron_timezone is TZInfo format' do before do allow(Time).to receive(:zone) diff --git a/spec/lib/gitlab/utils/usage_data_spec.rb b/spec/lib/gitlab/utils/usage_data_spec.rb index 12a73f4f4aa..27248d1d95a 100644 --- a/spec/lib/gitlab/utils/usage_data_spec.rb +++ b/spec/lib/gitlab/utils/usage_data_spec.rb @@ -397,7 +397,7 @@ RSpec.describe Gitlab::Utils::UsageData do expect(redis).to receive(:set).with("#{metric_name}_#{time_period_name}-#{timestamp}", '{"141":1,"56":1}', ex: 80.hours) end - described_class.save_aggregated_metrics(method_params) + described_class.save_aggregated_metrics(**method_params) end context 'error handling' do @@ -406,7 +406,7 @@ RSpec.describe Gitlab::Utils::UsageData do end it 'rescues and reraise ::Redis::CommandError for development and test environments' do - expect { described_class.save_aggregated_metrics(method_params) }.to raise_error ::Redis::CommandError + expect { described_class.save_aggregated_metrics(**method_params) }.to raise_error ::Redis::CommandError end context 'for environment different than development' do @@ -415,7 +415,7 @@ RSpec.describe Gitlab::Utils::UsageData do end it 'rescues ::Redis::CommandError' do - expect { described_class.save_aggregated_metrics(method_params) }.not_to raise_error + expect { described_class.save_aggregated_metrics(**method_params) }.not_to raise_error end end end @@ -434,12 +434,12 @@ RSpec.describe Gitlab::Utils::UsageData do expect(redis).not_to receive(:set) end - described_class.save_aggregated_metrics(method_params) + described_class.save_aggregated_metrics(**method_params) end end it 'raises error for development environment' do - expect { described_class.save_aggregated_metrics(method_params) }.to raise_error /Unsupported data type/ + expect { described_class.save_aggregated_metrics(**method_params) }.to raise_error /Unsupported data type/ end end end