gitlab-qa 6.8.0 → 6.12.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: daf050b7d871f8eefdc1fa68b052608c11ee186b927fe89accfceca15291ed45
4
- data.tar.gz: 4510e98db8e41c11a1585070a39cd19769384917cff551195942955974dcd78d
3
+ metadata.gz: a7db5ca406c7143f6b4b8ac2d5061080f52157dbe77f23459fdf15919cc24209
4
+ data.tar.gz: b0dca304397f7c373ca94b41936f8d04db818b797dc9a09e05e31accfd8a9cfd
5
5
  SHA512:
6
- metadata.gz: 3a3a6dc22aac1a77fe46f1379a43b489d08cc771b38ea629f9ff3a8f24fd9886f767ed3b3ca8aa18bfeabadc9019aefe2933261c969167e6c8e95f7f75e2c6a1
7
- data.tar.gz: c612e3b42691a28864bcf703fdf89cbbf57f75817341f867d1e8486a25adcbfcf262f3506157841d734813e699e628620dd524af22b4f8da17c689a96c6116cf
6
+ metadata.gz: 25678e888d7a338ef9f54269927e16ab6d5f60bc4b37175185bda64174689d9aecf40ac35c7d31be15e6fb1305527604f4667f09aa6c89f42ba4e02c7187a68d
7
+ data.tar.gz: ff1c2808b0030677ba8420444e4cb303b0d58d6751511bef90a8bcbea98df6a98e1efea83945d7b6488f076eb8f978519198b4938dc9b99503bd97c0d2b9ea57
@@ -49,9 +49,9 @@ variables:
49
49
  QA_CAN_TEST_GIT_PROTOCOL_V2: "true"
50
50
  QA_CAN_TEST_PRAEFECT: "false"
51
51
  QA_TESTCASES_REPORTING_PROJECT: "gitlab-org/quality/testcases"
52
- QA_FAILURES_REPORTING_PROJECT: "gitlab-org/gitlab"
52
+ QA_FAILURES_REPORTING_PROJECT: "rymai/gitlab-qa-issues"
53
53
  # The --dry-run or --max-diff-ratio option can be set to modify the behavior of `exe/gitlab-qa-report --relate-failure-issue` without releasing a new gem version.
54
- QA_FAILURES_REPORTER_OPTIONS: "--dry-run"
54
+ QA_FAILURES_REPORTER_OPTIONS: ""
55
55
  QA_TESTCASE_SESSIONS_PROJECT: "gitlab-org/quality/testcase-sessions"
56
56
 
57
57
  .check-base:
@@ -95,8 +95,8 @@ release:
95
95
  reports:
96
96
  junit: gitlab-qa-run-*/**/rspec-*.xml
97
97
  script:
98
- - 'echo "Running: exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS"'
99
- - exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS || test_run_exit_code=$?
98
+ - 'echo "Running: exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} $GITLAB_QA_OPTS -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS"'
99
+ - exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} $GITLAB_QA_OPTS -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS || test_run_exit_code=$?
100
100
  - exe/gitlab-qa-report --update-screenshot-path "gitlab-qa-run-*/**/rspec-*.xml"
101
101
  - export GITLAB_QA_ACCESS_TOKEN="$GITLAB_QA_PRODUCTION_ACCESS_TOKEN"
102
102
  - if [ "$TOP_UPSTREAM_SOURCE_REF" == "master" ] || [[ "$TOP_UPSTREAM_SOURCE_JOB" == https://ops.gitlab.net* ]]; then exe/gitlab-qa-report --report-in-issues "gitlab-qa-run-*/**/rspec-*.json" --project "$QA_TESTCASES_REPORTING_PROJECT" || true; fi
@@ -175,8 +175,8 @@ ee:sanity-framework:
175
175
  # The custom jobs are for manually running specific/alternative tests in MRs, so we don't report them in issues
176
176
  ce:custom-parallel:
177
177
  script:
178
- - 'echo "Running: exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS"'
179
- - exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS
178
+ - 'echo "Running: exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} $GITLAB_QA_OPTS -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS"'
179
+ - exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} $GITLAB_QA_OPTS -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS
180
180
  extends:
181
181
  - .test
182
182
  - .high-capacity
@@ -187,8 +187,8 @@ ce:custom-parallel:
187
187
 
188
188
  ee:custom-parallel:
189
189
  script:
190
- - 'echo "Running: exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS"'
191
- - exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS
190
+ - 'echo "Running: exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} $GITLAB_QA_OPTS -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS"'
191
+ - exe/gitlab-qa ${QA_SCENARIO:=Test::Instance::Image} ${RELEASE:=$DEFAULT_RELEASE} $GITLAB_QA_OPTS -- $QA_TESTS $QA_RSPEC_TAGS $RSPEC_REPORT_OPTS
192
192
  extends:
193
193
  - .test
194
194
  - .high-capacity
@@ -4,7 +4,7 @@
4
4
 
5
5
  The [maven repository spec](https://gitlab.com/gitlab-org/gitlab/-/blob/master/qa/qa/specs/features/ee/browser_ui/5_package/maven_repository_spec.rb) creates a Maven artifact and links it to a GitLab project. The artifact is created within a [Maven docker image](https://gitlab.com/gitlab-org/gitlab/-/blob/master/qa/qa/service/docker_run/maven.rb#L8).
6
6
 
7
- Using `gitlab-qa` to run these tests reduces the liklihood of network errors between the maven container and GitLab instance.
7
+ Using `gitlab-qa` to run these tests reduces the likelihood of network errors between the maven container and GitLab instance.
8
8
 
9
9
  To run this with `gitlab-qa` you can use the `Test::Instance::Image` that is needed for your test. For example:
10
10
 
@@ -84,6 +84,7 @@ All environment variables used by GitLab QA should be defined in [`lib/gitlab/qa
84
84
  | `JIRA_ADMIN_PASSWORD` |- | Password for authenticating with Jira server as admin. | No|
85
85
  | `CACHE_NAMESPACE_NAME` | `true` | Cache namespace name for groups. | No|
86
86
  | `DEPLOY_VERSION` |- | The version of GitLab being tested against. | No|
87
+ | `GITLAB_QA_USER_AGENT` |- | The browser user-agent to use instead of the default Chrome user-agent. | No|
87
88
 
88
89
  ## [Supported Remote Grid environment variables](./running_against_remote_grid.md)
89
90
 
@@ -27,8 +27,8 @@ Gem::Specification.new do |spec|
27
27
  spec.add_development_dependency 'rubocop', '~> 0.82.0'
28
28
  spec.add_development_dependency 'rubocop-rspec', '~> 1.36'
29
29
  spec.add_development_dependency 'webmock', '3.7.0'
30
- spec.add_runtime_dependency 'activesupport', '~> 6.0.2'
31
- spec.add_runtime_dependency 'gitlab', '~> 4.11.0'
30
+ spec.add_runtime_dependency 'activesupport', '~> 6.0.2'
31
+ spec.add_runtime_dependency 'gitlab', '~> 4.16.1'
32
32
  spec.add_runtime_dependency 'http', '4.3.0'
33
33
  spec.add_runtime_dependency 'nokogiri', '~> 1.10'
34
34
  spec.add_runtime_dependency 'table_print', '1.5.6'
@@ -53,6 +53,7 @@ module Gitlab
53
53
 
54
54
  def prepare
55
55
  prepare_docker_image
56
+ prepare_docker_container
56
57
  prepare_network
57
58
  end
58
59
 
@@ -70,6 +71,12 @@ module Gitlab
70
71
  docker.network_create(network)
71
72
  end
72
73
 
74
+ def prepare_docker_container
75
+ return unless docker.container_exists?(name)
76
+
77
+ docker.remove(name)
78
+ end
79
+
73
80
  def start # rubocop:disable Metrics/AbcSize
74
81
  docker.run(image, tag) do |command|
75
82
  command << "-d"
@@ -63,6 +63,14 @@ module Gitlab
63
63
  Docker::Command.execute("rm -f #{name}")
64
64
  end
65
65
 
66
+ def container_exists?(name)
67
+ Docker::Command.execute("container inspect #{name}")
68
+ rescue Docker::Shellout::StatusError
69
+ false
70
+ else
71
+ true
72
+ end
73
+
66
74
  def network_exists?(name)
67
75
  Docker::Command.execute("network inspect #{name}")
68
76
  rescue Docker::Shellout::StatusError
@@ -161,11 +161,11 @@ module Gitlab
161
161
  end
162
162
 
163
163
  def generate_test_job(tests_with_same_testcase)
164
- tests_with_same_testcase.map(&:ci_job_url).uniq.map do |ci_job_url|
165
- ci_job_id = ci_job_url[/\d+\z/]
164
+ tests_with_same_testcase.map do |test|
165
+ ci_job_id = test.ci_job_url[/\d+\z/]
166
166
 
167
- "[#{ci_job_id}](#{ci_job_url})"
168
- end.join(', ')
167
+ "[#{ci_job_id}](#{test.ci_job_url})#{' ~"quarantine"' if test.quarantine?}"
168
+ end.uniq.join(', ')
169
169
  end
170
170
 
171
171
  def generate_test_status(tests_with_same_testcase)
@@ -59,7 +59,7 @@ module Gitlab
59
59
 
60
60
  def find_issue_discussions(iid:)
61
61
  handle_gitlab_client_exceptions do
62
- Gitlab.issue_discussions(project, iid, order_by: 'created_at', sort: 'asc')
62
+ Gitlab.issue_discussions(project, iid, order_by: 'created_at', sort: 'asc').auto_paginate
63
63
  end
64
64
  end
65
65
 
@@ -109,6 +109,9 @@ module Gitlab
109
109
  pipeline = QA::Runtime::Env.pipeline_from_project_name
110
110
  channel = pipeline == "canary" ? "qa-production" : "qa-#{pipeline}"
111
111
  error_msg = warn_exception(e)
112
+
113
+ return unless QA::Runtime::Env.ci_commit_ref_name == 'master'
114
+
112
115
  slack_options = {
113
116
  channel: channel,
114
117
  icon_emoji: ':ci_failing:',
@@ -10,7 +10,7 @@ module Gitlab
10
10
  # Uses the API to create or update GitLab issues with the results of tests from RSpec report files.
11
11
  class RelateFailureIssue < ReportAsIssue
12
12
  DEFAULT_MAX_DIFF_RATIO_FOR_DETECTION = 0.05
13
- STACKTRACE_REGEX = %r{### Stack trace\s*(```)\s*.*(Failure/Error: .+)(\1)}m.freeze
13
+ STACKTRACE_REGEX = %r{### Stack trace\s*(```)\s*.*(Failure/Error:.+)(\1)}m.freeze
14
14
  NEW_ISSUE_LABELS = Set.new(%w[QA Quality test failure::investigating priority::2]).freeze
15
15
 
16
16
  MultipleIssuesFound = Class.new(StandardError)
@@ -47,6 +47,7 @@ module Gitlab
47
47
  issue = find_or_create_issue(test)
48
48
  return unless issue
49
49
 
50
+ update_labels(issue, test)
50
51
  post_failed_job_note(issue, test)
51
52
  puts " => Marked #{issue.web_url} as related to #{test.testcase}."
52
53
  rescue MultipleIssuesFound => e
@@ -81,17 +82,15 @@ module Gitlab
81
82
  # Search with the `search` param returns 500 errors, so we filter by ~QA and then filter further in Ruby
82
83
  failure_issues(test).each_with_object({}) do |issue, memo|
83
84
  relevant_issue_stacktrace = find_issue_stacktrace(issue)
84
- unless relevant_issue_stacktrace
85
- puts " => [DEBUG] Found issue #{issue.web_url} but stacktrace doesn't match."
86
- next
87
- end
85
+ next unless relevant_issue_stacktrace
88
86
 
89
87
  distance = ld.call(first_test_failure_stacktrace, relevant_issue_stacktrace)
90
88
  diff_ratio = (distance.to_f / first_test_failure_stacktrace.size).round(3)
91
89
  if diff_ratio <= max_diff_ratio
90
+ puts " => [DEBUG] Issue #{issue} has an acceptable diff ratio of #{(diff_ratio * 100).round(2)}%."
92
91
  memo[issue] = diff_ratio
93
92
  else
94
- puts " => [DEBUG] Found issue #{issue.web_url} but stacktrace is too different (#{(diff_ratio * 100).round(2)}%)."
93
+ puts " => [DEBUG] Found issue #{issue.web_url} but stacktraces are too different (#{(diff_ratio * 100).round(2)}%)."
95
94
  end
96
95
  end
97
96
  end
@@ -102,7 +101,7 @@ module Gitlab
102
101
  if issue_stacktrace_match
103
102
  issue_stacktrace_match[2].gsub(/^#.*$/, '').strip
104
103
  else
105
- puts "\n => Stacktrace couldn't be found for #{issue.web_url}:\n\n#{issue.description}\n\n----------------------------------\n"
104
+ puts " => [DEBUG] Stacktrace couldn't be found for #{issue.web_url}:\n\n#{issue.description}\n\n----------------------------------\n"
106
105
  end
107
106
  end
108
107
 
@@ -123,16 +122,45 @@ module Gitlab
123
122
  end
124
123
 
125
124
  def new_issue_description(test)
126
- super + "\n\n### Stack trace\n\n```\n#{test.failures.first['message_lines'].join("\n")}\n```"
125
+ super + [
126
+ "\n\n### Stack trace",
127
+ "```\n#{test.failures.first['message_lines'].join("\n")}\n```",
128
+ "First happened in #{test.ci_job_url}."
129
+ ].join("\n\n")
130
+ end
131
+
132
+ def deploy_environment_label
133
+ environment = Runtime::Env.deploy_environment
134
+
135
+ case environment
136
+ when 'production'
137
+ 'found:gitlab.com'
138
+ when 'canary', 'staging'
139
+ "found:#{environment}.gitlab.com"
140
+ when 'preprod'
141
+ 'found:pre.gitlab.com'
142
+ when 'staging-orchestrated', 'nightly', 'master'
143
+ "found:#{environment}"
144
+ else
145
+ raise "No `found:*` label for the `#{environment}` environment!"
146
+ end
127
147
  end
128
148
 
129
149
  def new_issue_labels(test)
130
150
  NEW_ISSUE_LABELS + up_to_date_labels(test: test)
131
151
  end
132
152
 
153
+ def up_to_date_labels(test:, issue: nil)
154
+ super << deploy_environment_label
155
+ end
156
+
133
157
  def post_failed_job_note(issue, test)
134
158
  gitlab.create_issue_note(iid: issue.iid, note: "/relate #{test.testcase}")
135
159
  end
160
+
161
+ def new_issue_title(test)
162
+ "Failure in #{super}"
163
+ end
136
164
  end
137
165
  end
138
166
  end
@@ -28,6 +28,10 @@ module Gitlab
28
28
  raise NotImplementedError
29
29
  end
30
30
 
31
+ def new_issue_title(test)
32
+ "#{partial_file_path(test.file)} | #{search_safe(test.name)}".strip
33
+ end
34
+
31
35
  def new_issue_description(test)
32
36
  "### Full description\n\n#{search_safe(test.name)}\n\n### File path\n\n#{test.file}"
33
37
  end
@@ -76,7 +80,7 @@ module Gitlab
76
80
  gitlab.create_issue(
77
81
  title: title_from_test(test),
78
82
  description: new_issue_description(test),
79
- labels: new_issue_labels(test)
83
+ labels: new_issue_labels(test).to_a
80
84
  )
81
85
  end
82
86
 
@@ -113,7 +117,7 @@ module Gitlab
113
117
  end
114
118
 
115
119
  def title_from_test(test)
116
- title = "#{partial_file_path(test.file)} | #{search_safe(test.name)}".strip
120
+ title = new_issue_title(test)
117
121
 
118
122
  return title unless title.length > MAX_TITLE_LENGTH
119
123
 
@@ -25,8 +25,6 @@ module Gitlab
25
25
  end
26
26
 
27
27
  def report_test(test)
28
- return if test.skipped
29
-
30
28
  puts "Reporting test: #{test.file} | #{test.name}"
31
29
 
32
30
  issue = find_issue(test)
@@ -34,16 +32,23 @@ module Gitlab
34
32
  if issue
35
33
  puts "Found existing issue: #{issue.web_url}"
36
34
  else
35
+ # Don't create new issues for skipped tests
36
+ return if test.skipped
37
+
37
38
  issue = create_issue(test)
38
39
  puts "Created new issue: #{issue.web_url}"
39
40
  end
40
41
 
41
42
  test.testcase ||= issue.web_url
42
43
 
43
- update_labels(issue, test)
44
- note_status(issue, test)
44
+ labels_updated = update_labels(issue, test)
45
+ note_posted = note_status(issue, test)
45
46
 
46
- puts "Issue updated"
47
+ if labels_updated || note_posted
48
+ puts "Issue updated."
49
+ else
50
+ puts "Test passed, no update needed."
51
+ end
47
52
  end
48
53
 
49
54
  def find_issue(test)
@@ -79,7 +84,8 @@ module Gitlab
79
84
  end
80
85
 
81
86
  def note_status(issue, test)
82
- return if test.failures.empty?
87
+ return false if test.skipped
88
+ return false if test.failures.empty?
83
89
 
84
90
  note = note_content(test)
85
91
 
@@ -88,6 +94,8 @@ module Gitlab
88
94
  end
89
95
 
90
96
  gitlab.create_issue_note(iid: issue.iid, note: note)
97
+
98
+ true
91
99
  end
92
100
 
93
101
  def note_content(test)
@@ -125,11 +133,7 @@ module Gitlab
125
133
  end
126
134
 
127
135
  def error_and_stack_trace(text)
128
- result = text.strip[/Error:(.*)/m, 1].to_s
129
-
130
- warn "Could not find `Error:` in text: #{text}" if result.empty?
131
-
132
- result
136
+ text.strip[/Error:(.*)/m, 1].to_s
133
137
  end
134
138
  end
135
139
  end
@@ -1,5 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require 'active_support/core_ext/object/blank'
4
+
3
5
  module Gitlab
4
6
  module QA
5
7
  module Report
@@ -78,6 +80,13 @@ module Gitlab
78
80
  report['failure_issue'] = new_failure_issue
79
81
  end
80
82
 
83
+ def quarantine?
84
+ # The value for 'quarantine' could be nil, a hash, a string,
85
+ # or true (if the test just has the :quarantine tag)
86
+ # But any non-nil or false value should means the test is in quarantine
87
+ report['quarantine'].present?
88
+ end
89
+
81
90
  private
82
91
 
83
92
  # rubocop:disable Metrics/AbcSize
@@ -8,6 +8,7 @@ module Gitlab
8
8
 
9
9
  # Variables that are used in tests and are passed through to the docker container that executes the tests.
10
10
  # These variables should be listed in /docs/what_tests_can_be_run.md#supported-gitlab-environment-variables
11
+ # unless they're defined elsewhere (e.g.: https://docs.gitlab.com/ee/ci/variables/predefined_variables.html)
11
12
  ENV_VARIABLES = {
12
13
  'QA_REMOTE_GRID' => :remote_grid,
13
14
  'QA_REMOTE_GRID_USERNAME' => :remote_grid_username,
@@ -68,6 +69,7 @@ module Gitlab
68
69
  'CI_SERVER_PERSONAL_ACCESS_TOKEN' => :ci_server_personal_access_token,
69
70
  'CI_NODE_INDEX' => :ci_node_index,
70
71
  'CI_NODE_TOTAL' => :ci_node_total,
72
+ 'CI_PROJECT_NAME' => :ci_project_name,
71
73
  'GITLAB_CI' => :gitlab_ci,
72
74
  'QA_SKIP_PULL' => :qa_skip_pull,
73
75
  'ELASTIC_URL' => :elastic_url,
@@ -83,7 +85,8 @@ module Gitlab
83
85
  'JIRA_ADMIN_USERNAME' => :jira_admin_username,
84
86
  'JIRA_ADMIN_PASSWORD' => :jira_admin_password,
85
87
  'CACHE_NAMESPACE_NAME' => :cache_namespace_name,
86
- 'DEPLOY_VERSION' => :deploy_version
88
+ 'DEPLOY_VERSION' => :deploy_version,
89
+ 'GITLAB_QA_USER_AGENT' => :gitlab_qa_user_agent
87
90
  }.freeze
88
91
 
89
92
  ENV_VARIABLES.each do |env_name, method_name|
@@ -137,6 +140,10 @@ module Gitlab
137
140
  ENV['CI_PROJECT_NAME']
138
141
  end
139
142
 
143
+ def ci_commit_ref_name
144
+ ENV['CI_COMMIT_REF_NAME']
145
+ end
146
+
140
147
  def pipeline_from_project_name
141
148
  if ci_project_name.to_s.start_with?('gitlab-qa')
142
149
  if ENV['TOP_UPSTREAM_SOURCE_JOB'].to_s.start_with?('https://ops.gitlab.net')
@@ -1,5 +1,5 @@
1
1
  module Gitlab
2
2
  module QA
3
- VERSION = '6.8.0'.freeze
3
+ VERSION = '6.12.0'.freeze
4
4
  end
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: gitlab-qa
3
3
  version: !ruby/object:Gem::Version
4
- version: 6.8.0
4
+ version: 6.12.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Grzegorz Bizon
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2020-11-10 00:00:00.000000000 Z
11
+ date: 2020-11-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: climate_control
@@ -142,14 +142,14 @@ dependencies:
142
142
  requirements:
143
143
  - - "~>"
144
144
  - !ruby/object:Gem::Version
145
- version: 4.11.0
145
+ version: 4.16.1
146
146
  type: :runtime
147
147
  prerelease: false
148
148
  version_requirements: !ruby/object:Gem::Requirement
149
149
  requirements:
150
150
  - - "~>"
151
151
  - !ruby/object:Gem::Version
152
- version: 4.11.0
152
+ version: 4.16.1
153
153
  - !ruby/object:Gem::Dependency
154
154
  name: http
155
155
  requirement: !ruby/object:Gem::Requirement