chelsea 0.0.23 → 0.0.28
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.circleci/config.yml +8 -3
- data/.github/ISSUE_TEMPLATE/bug_report.md +1 -1
- data/.rubocop.yml +6 -0
- data/Gemfile +7 -2
- data/Gemfile.lock +25 -5
- data/README.md +38 -2
- data/Rakefile +5 -3
- data/SECURITY.md +79 -0
- data/bin/chelsea +14 -7
- data/bin/console +5 -4
- data/chelsea.gemspec +30 -29
- data/lib/chelsea/bom.rb +3 -3
- data/lib/chelsea/cli.rb +36 -9
- data/lib/chelsea/config.rb +12 -11
- data/lib/chelsea/db.rb +4 -1
- data/lib/chelsea/dependency_exception.rb +4 -1
- data/lib/chelsea/deps.rb +5 -2
- data/lib/chelsea/formatters/factory.rb +4 -2
- data/lib/chelsea/formatters/formatter.rb +15 -11
- data/lib/chelsea/formatters/json.rb +5 -1
- data/lib/chelsea/formatters/text.rb +9 -4
- data/lib/chelsea/formatters/xml.rb +20 -16
- data/lib/chelsea/gems.rb +16 -17
- data/lib/chelsea/iq_client.rb +66 -38
- data/lib/chelsea/oss_index.rb +8 -9
- data/lib/chelsea/spinner.rb +4 -1
- data/lib/chelsea/version.rb +3 -1
- data/license-excludes.xml +1 -0
- metadata +50 -64
- data/bin/setup +0 -24
data/lib/chelsea/gems.rb
CHANGED
@@ -15,6 +15,7 @@
|
|
15
15
|
#
|
16
16
|
|
17
17
|
# frozen_string_literal: true
|
18
|
+
|
18
19
|
require 'pastel'
|
19
20
|
require 'bundler'
|
20
21
|
require 'bundler/lockfile_parser'
|
@@ -31,11 +32,10 @@ module Chelsea
|
|
31
32
|
# Class to collect and audit packages from a Gemfile.lock
|
32
33
|
class Gems
|
33
34
|
attr_accessor :deps
|
34
|
-
|
35
|
+
|
36
|
+
def initialize(file:, verbose:, options: { format: 'text' }) # rubocop:disable Metrics/MethodLength
|
35
37
|
@verbose = verbose
|
36
|
-
unless File.file?(file) || file.nil?
|
37
|
-
raise 'Gemfile.lock not found, check --file path'
|
38
|
-
end
|
38
|
+
raise 'Gemfile.lock not found, check --file path' unless File.file?(file) || file.nil?
|
39
39
|
|
40
40
|
_silence_stderr unless @verbose
|
41
41
|
|
@@ -52,7 +52,7 @@ module Chelsea
|
|
52
52
|
# Audits depenencies using deps library and prints results
|
53
53
|
# using formatter library
|
54
54
|
|
55
|
-
def execute
|
55
|
+
def execute # rubocop:disable Metrics/MethodLength
|
56
56
|
server_response, dependencies, reverse_dependencies = audit
|
57
57
|
if dependencies.nil?
|
58
58
|
_print_err 'No dependencies retrieved. Exiting.'
|
@@ -62,20 +62,19 @@ module Chelsea
|
|
62
62
|
_print_success 'No vulnerability data retrieved from server. Exiting.'
|
63
63
|
return
|
64
64
|
end
|
65
|
-
results = @formatter.
|
65
|
+
results = @formatter.fetch_results(server_response, reverse_dependencies)
|
66
66
|
@formatter.do_print(results)
|
67
67
|
|
68
68
|
server_response.map { |r| r['vulnerabilities'].length.positive? }.any?
|
69
69
|
end
|
70
70
|
|
71
71
|
def collect_iq
|
72
|
-
|
73
|
-
dependencies
|
72
|
+
@deps.dependencies
|
74
73
|
end
|
75
74
|
|
76
75
|
# Runs through auditing algorithm, raising exceptions
|
77
76
|
# on REST calls made by @deps.get_vulns
|
78
|
-
def audit
|
77
|
+
def audit # rubocop:disable Metrics/MethodLength, Metrics/AbcSize
|
79
78
|
# This spinner management is out of control
|
80
79
|
# we should wrap a block with start and stop messages,
|
81
80
|
# or use a stack to ensure all spinners stop.
|
@@ -84,7 +83,7 @@ module Chelsea
|
|
84
83
|
begin
|
85
84
|
dependencies = @deps.dependencies
|
86
85
|
spin.success('...done.')
|
87
|
-
rescue StandardError
|
86
|
+
rescue StandardError
|
88
87
|
spin.stop
|
89
88
|
_print_err "Parsing dependency line #{gem} failed."
|
90
89
|
end
|
@@ -100,16 +99,16 @@ module Chelsea
|
|
100
99
|
begin
|
101
100
|
server_response = @client.get_vulns(coordinates)
|
102
101
|
spin.success('...done.')
|
103
|
-
rescue SocketError
|
102
|
+
rescue SocketError
|
104
103
|
spin.stop('...request failed.')
|
105
104
|
_print_err 'Socket error getting data from OSS Index server.'
|
106
105
|
rescue RestClient::RequestFailed => e
|
107
106
|
spin.stop('...request failed.')
|
108
107
|
_print_err "Error getting data from OSS Index server:#{e.response}."
|
109
|
-
rescue RestClient::ResourceNotFound
|
108
|
+
rescue RestClient::ResourceNotFound
|
110
109
|
spin.stop('...request failed.')
|
111
110
|
_print_err 'Error getting data from OSS Index server. Resource not found.'
|
112
|
-
rescue Errno::ECONNREFUSED
|
111
|
+
rescue Errno::ECONNREFUSED
|
113
112
|
spin.stop('...request failed.')
|
114
113
|
_print_err 'Error getting data from OSS Index server. Connection refused.'
|
115
114
|
end
|
@@ -122,12 +121,12 @@ module Chelsea
|
|
122
121
|
$stderr.reopen('/dev/null', 'w')
|
123
122
|
end
|
124
123
|
|
125
|
-
def _print_err(
|
126
|
-
puts @pastel.red.bold(
|
124
|
+
def _print_err(msg)
|
125
|
+
puts @pastel.red.bold(msg)
|
127
126
|
end
|
128
127
|
|
129
|
-
def _print_success(
|
130
|
-
puts @pastel.green.bold(
|
128
|
+
def _print_success(msg)
|
129
|
+
puts @pastel.green.bold(msg)
|
131
130
|
end
|
132
131
|
end
|
133
132
|
end
|
data/lib/chelsea/iq_client.rb
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
#
|
2
4
|
# Copyright 2019-Present Sonatype Inc.
|
3
5
|
#
|
@@ -17,12 +19,13 @@
|
|
17
19
|
require 'rest-client'
|
18
20
|
require 'json'
|
19
21
|
require 'pastel'
|
22
|
+
require 'uri'
|
20
23
|
|
21
24
|
require_relative 'spinner'
|
22
25
|
|
23
26
|
module Chelsea
|
24
|
-
|
25
|
-
|
27
|
+
# IQ audit operations
|
28
|
+
class IQClient # rubocop:disable Metrics/ClassLength
|
26
29
|
DEFAULT_OPTIONS = {
|
27
30
|
public_application_id: 'testapp',
|
28
31
|
server_url: 'http://localhost:8070',
|
@@ -30,15 +33,16 @@ module Chelsea
|
|
30
33
|
auth_token: 'admin123',
|
31
34
|
internal_application_id: '',
|
32
35
|
stage: 'build'
|
33
|
-
}
|
36
|
+
}.freeze
|
37
|
+
|
34
38
|
def initialize(options: DEFAULT_OPTIONS)
|
35
39
|
@options = options
|
36
40
|
@pastel = Pastel.new
|
37
41
|
@spinner = Chelsea::Spinner.new
|
38
42
|
end
|
39
43
|
|
40
|
-
def post_sbom(sbom)
|
41
|
-
spin = @spinner.spin_msg
|
44
|
+
def post_sbom(sbom) # rubocop:disable Metrics/MethodLength
|
45
|
+
spin = @spinner.spin_msg 'Submitting sbom to Nexus IQ Server'
|
42
46
|
@internal_application_id = _get_internal_application_id
|
43
47
|
resource = RestClient::Resource.new(
|
44
48
|
_api_url,
|
@@ -46,8 +50,8 @@ module Chelsea
|
|
46
50
|
password: @options[:auth_token]
|
47
51
|
)
|
48
52
|
res = resource.post sbom.to_s, _headers.merge(content_type: 'application/xml')
|
49
|
-
|
50
|
-
spin.success(
|
53
|
+
if res.code == 202
|
54
|
+
spin.success('...done.')
|
51
55
|
status_url(res)
|
52
56
|
else
|
53
57
|
spin.stop('...request failed.')
|
@@ -61,33 +65,51 @@ module Chelsea
|
|
61
65
|
end
|
62
66
|
|
63
67
|
def poll_status(url)
|
64
|
-
spin = @spinner.spin_msg
|
68
|
+
spin = @spinner.spin_msg 'Polling Nexus IQ Server for results'
|
65
69
|
loop do
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
_handle_response(res)
|
71
|
-
break
|
72
|
-
end
|
73
|
-
rescue
|
74
|
-
sleep(1)
|
70
|
+
res = _poll_iq_server(url)
|
71
|
+
if res.code == 200
|
72
|
+
spin.success('...done.')
|
73
|
+
return _handle_response(res)
|
75
74
|
end
|
75
|
+
rescue StandardError
|
76
|
+
sleep(1)
|
76
77
|
end
|
77
78
|
end
|
78
79
|
|
80
|
+
# colors to use when printing message
|
81
|
+
COLOR_FAILURE = 31
|
82
|
+
COLOR_WARNING = 33 # want yellow, but doesn't appear to print
|
83
|
+
COLOR_NONE = 32
|
84
|
+
# Known policy actions
|
85
|
+
POLICY_ACTION_FAILURE = 'Failure'
|
86
|
+
POLICY_ACTION_WARNING = 'Warning'
|
87
|
+
POLICY_ACTION_NONE = 'None'
|
88
|
+
|
79
89
|
private
|
80
90
|
|
81
|
-
def _handle_response(res)
|
91
|
+
def _handle_response(res) # rubocop:disable Metrics/MethodLength
|
82
92
|
res = JSON.parse(res.body)
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
|
93
|
+
# get absolute report url
|
94
|
+
absolute_report_html_url = URI.join(@options[:server_url], res['reportHtmlUrl'])
|
95
|
+
|
96
|
+
case res['policyAction']
|
97
|
+
when POLICY_ACTION_FAILURE
|
98
|
+
['Hi! Chelsea here, you have some policy violations to clean up!'\
|
99
|
+
"\nReport URL: #{absolute_report_html_url}",
|
100
|
+
COLOR_FAILURE, 1]
|
101
|
+
when POLICY_ACTION_WARNING
|
102
|
+
['Hi! Chelsea here, you have some policy warnings to peck at!'\
|
103
|
+
"\nReport URL: #{absolute_report_html_url}",
|
104
|
+
COLOR_WARNING, 0]
|
105
|
+
when POLICY_ACTION_NONE
|
106
|
+
['Hi! Chelsea here, no policy violations for this audit!'\
|
107
|
+
"\nReport URL: #{absolute_report_html_url}",
|
108
|
+
COLOR_NONE, 0]
|
87
109
|
else
|
88
|
-
|
89
|
-
|
90
|
-
|
110
|
+
['Hi! Chelsea here, no policy violations for this audit, but unknown policy action!'\
|
111
|
+
"\nReport URL: #{absolute_report_html_url}",
|
112
|
+
COLOR_FAILURE, 1]
|
91
113
|
end
|
92
114
|
end
|
93
115
|
|
@@ -115,33 +137,37 @@ module Chelsea
|
|
115
137
|
res['statusUrl']
|
116
138
|
end
|
117
139
|
|
118
|
-
|
119
|
-
|
120
|
-
def _poll_status
|
140
|
+
def _poll_status # rubocop:disable Metrics/MethodLength
|
121
141
|
return unless @status_url
|
122
142
|
|
123
143
|
loop do
|
124
|
-
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
break
|
129
|
-
end
|
130
|
-
rescue RestClient::ResourceNotFound => _e
|
131
|
-
print '.'
|
132
|
-
sleep(1)
|
144
|
+
res = check_status(@status_url)
|
145
|
+
if res.code == 200
|
146
|
+
puts JSON.parse(res.body)
|
147
|
+
break
|
133
148
|
end
|
149
|
+
rescue RestClient::ResourceNotFound => _e
|
150
|
+
print '.'
|
151
|
+
sleep(1)
|
134
152
|
end
|
135
153
|
end
|
136
154
|
|
137
|
-
def _get_internal_application_id
|
155
|
+
def _get_internal_application_id # rubocop:disable Metrics/MethodLength, Metrics/AbcSize
|
138
156
|
resource = RestClient::Resource.new(
|
139
157
|
_internal_application_id_api_url,
|
140
158
|
user: @options[:username],
|
141
159
|
password: @options[:auth_token]
|
142
160
|
)
|
143
161
|
res = resource.get _headers
|
162
|
+
if res.code != 200
|
163
|
+
puts "failure reading application id: #{@options[:public_application_id]}. response status: #{res.code}"
|
164
|
+
return
|
165
|
+
end
|
144
166
|
body = JSON.parse(res)
|
167
|
+
if body['applications'].empty?
|
168
|
+
puts "failed to get internal application id for IQ application id: #{@options[:public_application_id]}"
|
169
|
+
return
|
170
|
+
end
|
145
171
|
body['applications'][0]['id']
|
146
172
|
end
|
147
173
|
|
@@ -150,7 +176,9 @@ module Chelsea
|
|
150
176
|
end
|
151
177
|
|
152
178
|
def _api_url
|
179
|
+
# rubocop:disable Layout/LineLength
|
153
180
|
"#{@options[:server_url]}/api/v2/scan/applications/#{@internal_application_id}/sources/chelsea?stageId=#{@options[:stage]}"
|
181
|
+
# rubocop:enable Layout/LineLength
|
154
182
|
end
|
155
183
|
|
156
184
|
def _internal_application_id_api_url
|
data/lib/chelsea/oss_index.rb
CHANGED
@@ -21,11 +21,12 @@ require 'rest-client'
|
|
21
21
|
require_relative 'db'
|
22
22
|
|
23
23
|
module Chelsea
|
24
|
+
# OSS Index audit operations
|
24
25
|
class OSSIndex
|
25
26
|
DEFAULT_OPTIONS = {
|
26
27
|
oss_index_username: '',
|
27
28
|
oss_index_user_token: ''
|
28
|
-
}
|
29
|
+
}.freeze
|
29
30
|
def initialize(options: DEFAULT_OPTIONS)
|
30
31
|
@oss_index_user_name = options[:oss_index_user_name]
|
31
32
|
@oss_index_user_token = options[:oss_index_user_token]
|
@@ -37,13 +38,11 @@ module Chelsea
|
|
37
38
|
|
38
39
|
def get_vulns(coordinates)
|
39
40
|
remaining_coordinates, cached_server_response = _cache(coordinates)
|
40
|
-
unless remaining_coordinates['coordinates'].count.positive?
|
41
|
-
return cached_server_response
|
42
|
-
end
|
41
|
+
return cached_server_response unless remaining_coordinates['coordinates'].count.positive?
|
43
42
|
|
44
43
|
remaining_coordinates['coordinates'].each_slice(128).to_a.each do |coords|
|
45
44
|
res_json = JSON.parse(call_oss_index({ 'coordinates' => coords }))
|
46
|
-
cached_server_response
|
45
|
+
cached_server_response.concat(res_json)
|
47
46
|
@db.save_values_to_db(res_json)
|
48
47
|
end
|
49
48
|
|
@@ -57,15 +56,15 @@ module Chelsea
|
|
57
56
|
|
58
57
|
private
|
59
58
|
|
60
|
-
def _cache(coordinates)
|
59
|
+
def _cache(coordinates) # rubocop:disable Metrics/MethodLength
|
61
60
|
new_coords = { 'coordinates' => [] }
|
62
61
|
cached_server_response = []
|
63
62
|
coordinates['coordinates'].each do |coord|
|
64
63
|
record = @db.get_cached_value_from_db(coord)
|
65
|
-
if
|
66
|
-
cached_server_response << record
|
67
|
-
else
|
64
|
+
if record.nil?
|
68
65
|
new_coords['coordinates'].push(coord)
|
66
|
+
else
|
67
|
+
cached_server_response << record
|
69
68
|
end
|
70
69
|
end
|
71
70
|
[new_coords, cached_server_response]
|
data/lib/chelsea/spinner.rb
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
#
|
2
4
|
# Copyright 2019-Present Sonatype Inc.
|
3
5
|
#
|
@@ -18,8 +20,9 @@ require 'tty-spinner'
|
|
18
20
|
require 'pastel'
|
19
21
|
|
20
22
|
module Chelsea
|
23
|
+
# the spinner we use in Chelsea, needs work
|
21
24
|
class Spinner
|
22
|
-
def initialize
|
25
|
+
def initialize
|
23
26
|
@pastel = Pastel.new
|
24
27
|
end
|
25
28
|
|
data/lib/chelsea/version.rb
CHANGED
data/license-excludes.xml
CHANGED
metadata
CHANGED
@@ -1,57 +1,49 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: chelsea
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.28
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Allister Beharry
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2021-01-29 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
|
-
name:
|
14
|
+
name: bundler
|
15
15
|
requirement: !ruby/object:Gem::Requirement
|
16
16
|
requirements:
|
17
|
-
- - "
|
18
|
-
- !ruby/object:Gem::Version
|
19
|
-
version: 0.5.0
|
20
|
-
type: :runtime
|
21
|
-
prerelease: false
|
22
|
-
version_requirements: !ruby/object:Gem::Requirement
|
23
|
-
requirements:
|
24
|
-
- - "~>"
|
17
|
+
- - ">="
|
25
18
|
- !ruby/object:Gem::Version
|
26
|
-
version:
|
27
|
-
-
|
28
|
-
name: tty-spinner
|
29
|
-
requirement: !ruby/object:Gem::Requirement
|
30
|
-
requirements:
|
31
|
-
- - "~>"
|
19
|
+
version: 1.2.0
|
20
|
+
- - "<"
|
32
21
|
- !ruby/object:Gem::Version
|
33
|
-
version:
|
22
|
+
version: '3'
|
34
23
|
type: :runtime
|
35
24
|
prerelease: false
|
36
25
|
version_requirements: !ruby/object:Gem::Requirement
|
37
26
|
requirements:
|
38
|
-
- - "
|
27
|
+
- - ">="
|
39
28
|
- !ruby/object:Gem::Version
|
40
|
-
version:
|
29
|
+
version: 1.2.0
|
30
|
+
- - "<"
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: '3'
|
41
33
|
- !ruby/object:Gem::Dependency
|
42
|
-
name:
|
34
|
+
name: ox
|
43
35
|
requirement: !ruby/object:Gem::Requirement
|
44
36
|
requirements:
|
45
37
|
- - "~>"
|
46
38
|
- !ruby/object:Gem::Version
|
47
|
-
version:
|
39
|
+
version: 2.13.2
|
48
40
|
type: :runtime
|
49
41
|
prerelease: false
|
50
42
|
version_requirements: !ruby/object:Gem::Requirement
|
51
43
|
requirements:
|
52
44
|
- - "~>"
|
53
45
|
- !ruby/object:Gem::Version
|
54
|
-
version:
|
46
|
+
version: 2.13.2
|
55
47
|
- !ruby/object:Gem::Dependency
|
56
48
|
name: pastel
|
57
49
|
requirement: !ruby/object:Gem::Requirement
|
@@ -81,144 +73,137 @@ dependencies:
|
|
81
73
|
- !ruby/object:Gem::Version
|
82
74
|
version: 2.0.2
|
83
75
|
- !ruby/object:Gem::Dependency
|
84
|
-
name:
|
76
|
+
name: slop
|
85
77
|
requirement: !ruby/object:Gem::Requirement
|
86
78
|
requirements:
|
87
|
-
- - "
|
88
|
-
- !ruby/object:Gem::Version
|
89
|
-
version: 1.2.0
|
90
|
-
- - "<"
|
79
|
+
- - "~>"
|
91
80
|
- !ruby/object:Gem::Version
|
92
|
-
version:
|
81
|
+
version: 4.8.1
|
93
82
|
type: :runtime
|
94
83
|
prerelease: false
|
95
84
|
version_requirements: !ruby/object:Gem::Requirement
|
96
85
|
requirements:
|
97
|
-
- - "
|
98
|
-
- !ruby/object:Gem::Version
|
99
|
-
version: 1.2.0
|
100
|
-
- - "<"
|
86
|
+
- - "~>"
|
101
87
|
- !ruby/object:Gem::Version
|
102
|
-
version:
|
88
|
+
version: 4.8.1
|
103
89
|
- !ruby/object:Gem::Dependency
|
104
|
-
name:
|
90
|
+
name: tty-font
|
105
91
|
requirement: !ruby/object:Gem::Requirement
|
106
92
|
requirements:
|
107
93
|
- - "~>"
|
108
94
|
- !ruby/object:Gem::Version
|
109
|
-
version:
|
95
|
+
version: 0.5.0
|
110
96
|
type: :runtime
|
111
97
|
prerelease: false
|
112
98
|
version_requirements: !ruby/object:Gem::Requirement
|
113
99
|
requirements:
|
114
100
|
- - "~>"
|
115
101
|
- !ruby/object:Gem::Version
|
116
|
-
version:
|
102
|
+
version: 0.5.0
|
117
103
|
- !ruby/object:Gem::Dependency
|
118
|
-
name: tty-
|
104
|
+
name: tty-spinner
|
119
105
|
requirement: !ruby/object:Gem::Requirement
|
120
106
|
requirements:
|
121
107
|
- - "~>"
|
122
108
|
- !ruby/object:Gem::Version
|
123
|
-
version: 0.
|
109
|
+
version: 0.9.3
|
124
110
|
type: :runtime
|
125
111
|
prerelease: false
|
126
112
|
version_requirements: !ruby/object:Gem::Requirement
|
127
113
|
requirements:
|
128
114
|
- - "~>"
|
129
115
|
- !ruby/object:Gem::Version
|
130
|
-
version: 0.
|
116
|
+
version: 0.9.3
|
131
117
|
- !ruby/object:Gem::Dependency
|
132
|
-
name:
|
118
|
+
name: tty-table
|
133
119
|
requirement: !ruby/object:Gem::Requirement
|
134
120
|
requirements:
|
135
121
|
- - "~>"
|
136
122
|
- !ruby/object:Gem::Version
|
137
|
-
version:
|
138
|
-
type: :
|
123
|
+
version: 0.11.0
|
124
|
+
type: :runtime
|
139
125
|
prerelease: false
|
140
126
|
version_requirements: !ruby/object:Gem::Requirement
|
141
127
|
requirements:
|
142
128
|
- - "~>"
|
143
129
|
- !ruby/object:Gem::Version
|
144
|
-
version:
|
130
|
+
version: 0.11.0
|
145
131
|
- !ruby/object:Gem::Dependency
|
146
|
-
name:
|
132
|
+
name: byebug
|
147
133
|
requirement: !ruby/object:Gem::Requirement
|
148
134
|
requirements:
|
149
135
|
- - "~>"
|
150
136
|
- !ruby/object:Gem::Version
|
151
|
-
version:
|
137
|
+
version: 11.1.2
|
152
138
|
type: :development
|
153
139
|
prerelease: false
|
154
140
|
version_requirements: !ruby/object:Gem::Requirement
|
155
141
|
requirements:
|
156
142
|
- - "~>"
|
157
143
|
- !ruby/object:Gem::Version
|
158
|
-
version:
|
144
|
+
version: 11.1.2
|
159
145
|
- !ruby/object:Gem::Dependency
|
160
|
-
name:
|
146
|
+
name: rake
|
161
147
|
requirement: !ruby/object:Gem::Requirement
|
162
148
|
requirements:
|
163
149
|
- - "~>"
|
164
150
|
- !ruby/object:Gem::Version
|
165
|
-
version:
|
151
|
+
version: '12.3'
|
166
152
|
type: :development
|
167
153
|
prerelease: false
|
168
154
|
version_requirements: !ruby/object:Gem::Requirement
|
169
155
|
requirements:
|
170
156
|
- - "~>"
|
171
157
|
- !ruby/object:Gem::Version
|
172
|
-
version:
|
158
|
+
version: '12.3'
|
173
159
|
- !ruby/object:Gem::Dependency
|
174
|
-
name:
|
160
|
+
name: rspec
|
175
161
|
requirement: !ruby/object:Gem::Requirement
|
176
162
|
requirements:
|
177
163
|
- - "~>"
|
178
164
|
- !ruby/object:Gem::Version
|
179
|
-
version: 3.
|
165
|
+
version: '3.0'
|
180
166
|
type: :development
|
181
167
|
prerelease: false
|
182
168
|
version_requirements: !ruby/object:Gem::Requirement
|
183
169
|
requirements:
|
184
170
|
- - "~>"
|
185
171
|
- !ruby/object:Gem::Version
|
186
|
-
version: 3.
|
172
|
+
version: '3.0'
|
187
173
|
- !ruby/object:Gem::Dependency
|
188
|
-
name:
|
174
|
+
name: rspec_junit_formatter
|
189
175
|
requirement: !ruby/object:Gem::Requirement
|
190
176
|
requirements:
|
191
177
|
- - "~>"
|
192
178
|
- !ruby/object:Gem::Version
|
193
|
-
version:
|
179
|
+
version: 0.4.1
|
194
180
|
type: :development
|
195
181
|
prerelease: false
|
196
182
|
version_requirements: !ruby/object:Gem::Requirement
|
197
183
|
requirements:
|
198
184
|
- - "~>"
|
199
185
|
- !ruby/object:Gem::Version
|
200
|
-
version:
|
186
|
+
version: 0.4.1
|
201
187
|
- !ruby/object:Gem::Dependency
|
202
|
-
name:
|
188
|
+
name: webmock
|
203
189
|
requirement: !ruby/object:Gem::Requirement
|
204
190
|
requirements:
|
205
|
-
- - "
|
191
|
+
- - "~>"
|
206
192
|
- !ruby/object:Gem::Version
|
207
|
-
version:
|
193
|
+
version: 3.8.3
|
208
194
|
type: :development
|
209
195
|
prerelease: false
|
210
196
|
version_requirements: !ruby/object:Gem::Requirement
|
211
197
|
requirements:
|
212
|
-
- - "
|
198
|
+
- - "~>"
|
213
199
|
- !ruby/object:Gem::Version
|
214
|
-
version:
|
200
|
+
version: 3.8.3
|
215
201
|
description:
|
216
202
|
email:
|
217
203
|
- allister.beharry@gmail.com
|
218
204
|
executables:
|
219
205
|
- chelsea
|
220
206
|
- console
|
221
|
-
- setup
|
222
207
|
extensions: []
|
223
208
|
extra_rdoc_files: []
|
224
209
|
files:
|
@@ -232,6 +217,7 @@ files:
|
|
232
217
|
- ".github/pull_request_template.md"
|
233
218
|
- ".gitignore"
|
234
219
|
- ".rspec"
|
220
|
+
- ".rubocop.yml"
|
235
221
|
- ".vscode/launch.json"
|
236
222
|
- CODE_OF_CONDUCT.md
|
237
223
|
- CONTRIBUTORS.md
|
@@ -242,9 +228,9 @@ files:
|
|
242
228
|
- LICENSE
|
243
229
|
- README.md
|
244
230
|
- Rakefile
|
231
|
+
- SECURITY.md
|
245
232
|
- bin/chelsea
|
246
233
|
- bin/console
|
247
|
-
- bin/setup
|
248
234
|
- chelsea
|
249
235
|
- chelsea.gemspec
|
250
236
|
- docs/images/chelsea.png
|
@@ -282,7 +268,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
282
268
|
requirements:
|
283
269
|
- - ">="
|
284
270
|
- !ruby/object:Gem::Version
|
285
|
-
version:
|
271
|
+
version: 2.6.6
|
286
272
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
287
273
|
requirements:
|
288
274
|
- - ">="
|