varanus 0.1.0 → 0.2.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 +4 -4
- data/.gitignore +1 -0
- data/.rubocop.yml +1 -21
- data/CHANGELOG.md +8 -0
- data/Gemfile +2 -0
- data/Gemfile.lock +28 -1
- data/README.md +46 -13
- data/Rakefile +2 -0
- data/bin/console +1 -0
- data/lib/varanus/error.rb +2 -0
- data/lib/varanus/reports.rb +73 -0
- data/lib/varanus/ssl/csr.rb +51 -9
- data/lib/varanus/ssl.rb +2 -0
- data/lib/varanus/version.rb +3 -1
- data/lib/varanus.rb +10 -0
- data/varanus.gemspec +3 -0
- metadata +18 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 9495d1c66215f0313068a30921d24545643441237139ced9220570e16b771b0f
|
4
|
+
data.tar.gz: cb104ae0cc2e2b8269e0d8914e90978870f402a386e2d9064e542e757fcab188
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 8415fc14216976c5e989d82e676fdbf25868ab2dfe55b645a85b43f162f60e1029a2a68d8f72fe9acd14a2d911e708402ca6160c6a101e2d0e3f233484a8ab05
|
7
|
+
data.tar.gz: 87710705995b46e27314aad6e4eadce44fab7ca7b3e4515cb91b1c65edfe0c85a542c5e2fafb59e39d32f30b563c13bb8d125c9a9d1156c4c8b1dbce82009945
|
data/.gitignore
CHANGED
data/.rubocop.yml
CHANGED
@@ -28,23 +28,12 @@ Naming/FileName:
|
|
28
28
|
Exclude:
|
29
29
|
- Gemfile
|
30
30
|
|
31
|
-
Naming/UncommunicativeMethodParamName:
|
32
|
-
AllowedNames:
|
33
|
-
- gb
|
34
|
-
- id
|
35
|
-
- ip
|
36
|
-
- os
|
37
|
-
- vm
|
38
|
-
|
39
31
|
Style/ClassAndModuleChildren:
|
40
|
-
|
32
|
+
EnforcedStyle: compact
|
41
33
|
|
42
34
|
Style/ConditionalAssignment:
|
43
35
|
Enabled: false
|
44
36
|
|
45
|
-
Style/FrozenStringLiteralComment:
|
46
|
-
Enabled: false
|
47
|
-
|
48
37
|
Style/MethodDefParentheses:
|
49
38
|
EnforcedStyle: require_no_parentheses_except_multiline
|
50
39
|
|
@@ -57,14 +46,5 @@ Style/RescueModifier:
|
|
57
46
|
Style/SymbolArray:
|
58
47
|
EnforcedStyle: brackets
|
59
48
|
|
60
|
-
Style/TrailingCommaInArguments:
|
61
|
-
EnforcedStyleForMultiline: no_comma
|
62
|
-
|
63
|
-
Style/TrailingCommaInArrayLiteral:
|
64
|
-
EnforcedStyleForMultiline: no_comma
|
65
|
-
|
66
|
-
Style/TrailingCommaInHashLiteral:
|
67
|
-
EnforcedStyleForMultiline: no_comma
|
68
|
-
|
69
49
|
Style/WordArray:
|
70
50
|
EnforcedStyle: brackets
|
data/CHANGELOG.md
ADDED
data/Gemfile
CHANGED
data/Gemfile.lock
CHANGED
@@ -1,16 +1,21 @@
|
|
1
1
|
PATH
|
2
2
|
remote: .
|
3
3
|
specs:
|
4
|
-
varanus (0.
|
4
|
+
varanus (0.2.0)
|
5
5
|
faraday
|
6
6
|
faraday_middleware
|
7
|
+
savon (~> 2.0)
|
7
8
|
|
8
9
|
GEM
|
9
10
|
remote: https://rubygems.org/
|
10
11
|
specs:
|
11
12
|
addressable (2.5.2)
|
12
13
|
public_suffix (>= 2.0.2, < 4.0)
|
14
|
+
akami (1.3.1)
|
15
|
+
gyoku (>= 0.4.0)
|
16
|
+
nokogiri
|
13
17
|
ast (2.4.0)
|
18
|
+
builder (3.2.3)
|
14
19
|
crack (0.4.3)
|
15
20
|
safe_yaml (~> 1.0.0)
|
16
21
|
docile (1.3.1)
|
@@ -18,21 +23,31 @@ GEM
|
|
18
23
|
multipart-post (>= 1.2, < 3)
|
19
24
|
faraday_middleware (0.12.2)
|
20
25
|
faraday (>= 0.7.4, < 1.0)
|
26
|
+
gyoku (1.3.1)
|
27
|
+
builder (>= 2.1.2)
|
21
28
|
hashdiff (0.3.7)
|
29
|
+
httpi (2.4.4)
|
30
|
+
rack
|
31
|
+
socksify
|
22
32
|
jaro_winkler (1.5.1)
|
23
33
|
json (2.1.0)
|
24
34
|
metaclass (0.0.4)
|
35
|
+
mini_portile2 (2.3.0)
|
25
36
|
minitest (5.11.3)
|
26
37
|
minitest-rg (5.2.0)
|
27
38
|
minitest (~> 5.0)
|
28
39
|
mocha (1.7.0)
|
29
40
|
metaclass (~> 0.0.1)
|
30
41
|
multipart-post (2.0.0)
|
42
|
+
nokogiri (1.8.5)
|
43
|
+
mini_portile2 (~> 2.3.0)
|
44
|
+
nori (2.6.0)
|
31
45
|
parallel (1.12.1)
|
32
46
|
parser (2.5.3.0)
|
33
47
|
ast (~> 2.4.0)
|
34
48
|
powerpack (0.1.2)
|
35
49
|
public_suffix (3.0.3)
|
50
|
+
rack (2.0.6)
|
36
51
|
rainbow (3.0.0)
|
37
52
|
rake (10.5.0)
|
38
53
|
rubocop (0.60.0)
|
@@ -45,12 +60,24 @@ GEM
|
|
45
60
|
unicode-display_width (~> 1.4.0)
|
46
61
|
ruby-progressbar (1.10.0)
|
47
62
|
safe_yaml (1.0.4)
|
63
|
+
savon (2.12.0)
|
64
|
+
akami (~> 1.2)
|
65
|
+
builder (>= 2.1.2)
|
66
|
+
gyoku (~> 1.2)
|
67
|
+
httpi (~> 2.3)
|
68
|
+
nokogiri (>= 1.8.1)
|
69
|
+
nori (~> 2.4)
|
70
|
+
wasabi (~> 3.4)
|
48
71
|
simplecov (0.16.1)
|
49
72
|
docile (~> 1.1)
|
50
73
|
json (>= 1.8, < 3)
|
51
74
|
simplecov-html (~> 0.10.0)
|
52
75
|
simplecov-html (0.10.2)
|
76
|
+
socksify (1.7.1)
|
53
77
|
unicode-display_width (1.4.0)
|
78
|
+
wasabi (3.5.0)
|
79
|
+
httpi (~> 2.0)
|
80
|
+
nokogiri (>= 1.4.2)
|
54
81
|
webmock (3.4.2)
|
55
82
|
addressable (>= 2.3.6)
|
56
83
|
crack (>= 0.3.2)
|
data/README.md
CHANGED
@@ -7,24 +7,29 @@ Support for Sectigo's other APIs (S/MIME, code signing, device certificates, etc
|
|
7
7
|
be added at a later date. Merge requests to add some of this functionality would be
|
8
8
|
greatly appreciated.
|
9
9
|
|
10
|
-
|
10
|
+
[](https://travis-ci.org/duke-automation/varanus)
|
11
|
+
[](http://badge.fury.io/rb/varanus)
|
12
|
+
[](https://codeclimate.com/github/duke-automation/varanus/maintainability)
|
13
|
+
[](https://codeclimate.com/github/duke-automation/varanus/test_coverage)
|
11
14
|
|
12
|
-
|
15
|
+
## Usage
|
16
|
+
|
17
|
+
#### Generate and sign SSL cert
|
13
18
|
|
14
19
|
```ruby
|
15
|
-
|
20
|
+
key, csr = Varanus::SSL::CSR.generate(['example.com'])
|
21
|
+
varanus = Varanus.new(customer_uri, username, password)
|
22
|
+
id = varanus.ssl.sign csr, org_id
|
23
|
+
begin
|
24
|
+
cert = varanus.ssl.collect id
|
25
|
+
rescue Varanus::Error::StillProcessing
|
26
|
+
sleep 1
|
27
|
+
retry
|
28
|
+
end
|
29
|
+
puts key
|
30
|
+
puts cert
|
16
31
|
```
|
17
32
|
|
18
|
-
And then execute:
|
19
|
-
|
20
|
-
$ bundle
|
21
|
-
|
22
|
-
Or install it yourself as:
|
23
|
-
|
24
|
-
$ gem install varanus
|
25
|
-
|
26
|
-
## Usage
|
27
|
-
|
28
33
|
#### Sign SSL cert from CSR
|
29
34
|
|
30
35
|
```ruby
|
@@ -46,6 +51,18 @@ puts cert
|
|
46
51
|
Varanus.new(customer_uri, username, password).ssl.revoke(id)
|
47
52
|
```
|
48
53
|
|
54
|
+
#### Reports
|
55
|
+
|
56
|
+
Report on all SSL certs
|
57
|
+
```ruby
|
58
|
+
pp Varanus.new(customer_uri, usernams, password).reports.ssl
|
59
|
+
```
|
60
|
+
|
61
|
+
Report on all domains (DCV status)
|
62
|
+
```ruby
|
63
|
+
pp Varanus.new(customer_uri, usernams, password).reports.domains
|
64
|
+
```
|
65
|
+
|
49
66
|
#### Authentication
|
50
67
|
|
51
68
|
Authentication requires the same credentials you use to login to cert-manager.com as well as the ```customer_uri```. If your URL to log into cert-manager.com is https://cert-manager.com/customer/MyCompany then your ```customer_uri``` will be ```'MyCompany'```
|
@@ -56,6 +73,22 @@ Signing a cert requires specifying an ```org_id```. Each department in cert-man
|
|
56
73
|
|
57
74
|
To find the ```org_id```, log into cert-manager.com, go to **Settings** -> **Departments**, then click to edit the department you are interested in. The value you want is in the **OrgID** field.
|
58
75
|
|
76
|
+
## Installation
|
77
|
+
|
78
|
+
Add this line to your application's Gemfile:
|
79
|
+
|
80
|
+
```ruby
|
81
|
+
gem 'varanus'
|
82
|
+
```
|
83
|
+
|
84
|
+
And then execute:
|
85
|
+
|
86
|
+
$ bundle
|
87
|
+
|
88
|
+
Or install it yourself as:
|
89
|
+
|
90
|
+
$ gem install varanus
|
91
|
+
|
59
92
|
## Development
|
60
93
|
|
61
94
|
After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake test` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
|
data/Rakefile
CHANGED
data/bin/console
CHANGED
data/lib/varanus/error.rb
CHANGED
@@ -0,0 +1,73 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# An connection to the Reports API. This should not be initialized directly. Instead,
|
4
|
+
# use Varanus#reports
|
5
|
+
class Varanus::Reports
|
6
|
+
SSL_CERT_STATUSES = {
|
7
|
+
any: 0,
|
8
|
+
requested: 1,
|
9
|
+
downloaded: 2,
|
10
|
+
revoked: 3,
|
11
|
+
expired: 4,
|
12
|
+
pending_download: 5,
|
13
|
+
not_enrolled: 6
|
14
|
+
}.freeze
|
15
|
+
|
16
|
+
# @note Do not call this directly. Use {Varanus#reports} to initialize
|
17
|
+
def initialize varanus
|
18
|
+
@varanus = varanus
|
19
|
+
end
|
20
|
+
|
21
|
+
def domains
|
22
|
+
r = soap_call :get_domain_report, {}
|
23
|
+
format_results r[:report_row_domains]
|
24
|
+
end
|
25
|
+
|
26
|
+
# Return report on SSL request
|
27
|
+
# @param [opts] [Hash]
|
28
|
+
# @option opts [String, Array] :orgs Name(s) of organizations (departments) to limit
|
29
|
+
# the report to. If this is unset, results from all departments are returned.
|
30
|
+
# @option opts [Symbol] :status (:any) One of :any, :requested, :downloaded, :revoked,
|
31
|
+
# :expired, :pending_download, :not_enrolled. :downloaded and :pending_download
|
32
|
+
# mean the cert has been enrolled/signed.
|
33
|
+
# @return [Array<Hash>]
|
34
|
+
def ssl opts = {}
|
35
|
+
msg = { organizationNames: nil, certificateStatus: 0 }
|
36
|
+
|
37
|
+
msg[:organizationNames] = Array(opts[:orgs]).join(',') if opts.include? :orgs
|
38
|
+
if opts.include? :status
|
39
|
+
msg[:certificateStatus] = SSL_CERT_STATUSES[opts[:status]]
|
40
|
+
raise ArgumentError, 'Invalid status' if msg[:certificateStatus].nil?
|
41
|
+
end
|
42
|
+
|
43
|
+
r = soap_call :get_SSL_report, msg
|
44
|
+
format_results r[:reports]
|
45
|
+
end
|
46
|
+
|
47
|
+
private
|
48
|
+
|
49
|
+
def format_results results
|
50
|
+
if results.is_a? Hash
|
51
|
+
[results]
|
52
|
+
else
|
53
|
+
results.to_a
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
57
|
+
def savon
|
58
|
+
@savon ||= Savon.client(
|
59
|
+
namespace: 'http://report.ws.epki.comodo.com/',
|
60
|
+
endpoint: 'https://cert-manager.com:443/ws/ReportService',
|
61
|
+
log: false
|
62
|
+
)
|
63
|
+
end
|
64
|
+
|
65
|
+
def soap_call func, opts = {}
|
66
|
+
msg = opts.dup
|
67
|
+
msg[:authData] = { customerLoginUri: @varanus.customer_uri, login: @varanus.username,
|
68
|
+
password: @varanus.password }
|
69
|
+
|
70
|
+
result = savon.call func, message: msg
|
71
|
+
result.body[(func.to_s.downcase + '_response').to_sym][:return]
|
72
|
+
end
|
73
|
+
end
|
data/lib/varanus/ssl/csr.rb
CHANGED
@@ -1,23 +1,65 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
# Wrapper class around a OpenSSL::X509::Request
|
2
4
|
# Provides helper functions to make reading information from the CSR easier
|
3
5
|
class Varanus::SSL::CSR
|
6
|
+
# Key size used when calling {.generate}
|
7
|
+
DEFAULT_KEY_SIZE = 4096
|
8
|
+
|
9
|
+
# Generate a CSR
|
10
|
+
# @param names [Array<String>] List of DNS names. The first one will be the CN
|
11
|
+
# @param key [OpenSSL::PKey::RSA, OpenSSL::PKey::DSA, nil] Secret key for the cert.
|
12
|
+
# A DSA key will be generated if +nil+ is passed in.
|
13
|
+
# @param subject [Hash] Options for the subject of the cert. By default only CN will
|
14
|
+
# be set
|
15
|
+
# @return [Array(OpenSSL::PKey::PKey, Varanus::SSL::CSR)] The private key for the cert
|
16
|
+
# and CSR
|
17
|
+
def self.generate names, key = nil, subject = {}
|
18
|
+
raise ArgumentError, 'names cannot be empty' if names.empty?
|
19
|
+
|
20
|
+
subject = subject.dup
|
21
|
+
subject['CN'] = names.first
|
22
|
+
|
23
|
+
key ||= OpenSSL::PKey::DSA.new(DEFAULT_KEY_SIZE)
|
24
|
+
|
25
|
+
request = OpenSSL::X509::Request.new
|
26
|
+
request.version = 0
|
27
|
+
request.subject = OpenSSL::X509::Name.parse subject.map { |k, v| "/#{k}=#{v}" }.join
|
28
|
+
|
29
|
+
# Set Subject Alternate Names
|
30
|
+
ef = OpenSSL::X509::ExtensionFactory.new
|
31
|
+
name_str = names.map { |n| "DNS:#{n}" }.join(', ')
|
32
|
+
ext = ef.create_extension('subjectAltName', name_str, false)
|
33
|
+
seq = OpenSSL::ASN1::Sequence([ext])
|
34
|
+
ext_req = OpenSSL::ASN1::Set([seq])
|
35
|
+
request.add_attribute OpenSSL::X509::Attribute.new('extReq', ext_req)
|
36
|
+
|
37
|
+
request.public_key = key.public_key
|
38
|
+
request.sign(key, OpenSSL::Digest::SHA256.new)
|
39
|
+
[key, Varanus::SSL::CSR.new(request)]
|
40
|
+
end
|
41
|
+
|
4
42
|
# Common Name (CN) for cert.
|
5
43
|
# @return [String]
|
6
44
|
attr_reader :cn
|
7
45
|
|
46
|
+
# OpenSSL::X509::Request representation of CSR
|
47
|
+
# @return [OpenSSL::X509::Request]
|
48
|
+
attr_reader :request
|
49
|
+
|
8
50
|
# @param csr [String, OpenSSL::X509::Request]
|
9
51
|
def initialize csr
|
10
52
|
if csr.is_a? OpenSSL::X509::Request
|
11
|
-
@
|
53
|
+
@request = csr
|
12
54
|
@text = csr.to_s
|
13
55
|
else
|
14
56
|
@text = csr.to_s
|
15
|
-
@
|
57
|
+
@request = OpenSSL::X509::Request.new @text
|
16
58
|
end
|
17
59
|
|
18
|
-
raise 'Improperly signed CSR' unless @
|
60
|
+
raise 'Improperly signed CSR' unless @request.verify @request.public_key
|
19
61
|
|
20
|
-
cn_ref = @
|
62
|
+
cn_ref = @request.subject.to_a.find { |a| a[0] == 'CN' }
|
21
63
|
@cn = cn_ref && cn_ref[1].downcase
|
22
64
|
|
23
65
|
_parse_sans
|
@@ -35,13 +77,13 @@ class Varanus::SSL::CSR
|
|
35
77
|
# Key size for the cert
|
36
78
|
# @return [Integer]
|
37
79
|
def key_size
|
38
|
-
case @
|
80
|
+
case @request.public_key
|
39
81
|
when OpenSSL::PKey::RSA
|
40
|
-
@
|
82
|
+
@request.public_key.n.num_bytes * 8
|
41
83
|
when OpenSSL::PKey::DSA
|
42
|
-
@
|
84
|
+
@request.public_key.p.num_bytes * 8
|
43
85
|
else
|
44
|
-
raise "Unknown public key type: #{@
|
86
|
+
raise "Unknown public key type: #{@request.public_key.class}"
|
45
87
|
end
|
46
88
|
end
|
47
89
|
|
@@ -59,7 +101,7 @@ class Varanus::SSL::CSR
|
|
59
101
|
private
|
60
102
|
|
61
103
|
def _parse_sans
|
62
|
-
extensions = @
|
104
|
+
extensions = @request.attributes.select { |at| at.oid == 'extReq' }
|
63
105
|
sans_extensions = extensions.flat_map do |extension|
|
64
106
|
extension.value.value[0].value
|
65
107
|
.select { |ext| ext.first.value == 'subjectAltName' }
|
data/lib/varanus/ssl.rb
CHANGED
data/lib/varanus/version.rb
CHANGED
data/lib/varanus.rb
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
# Interface for Sectigo's (formerly Comodo CA) API.
|
2
4
|
class Varanus
|
3
5
|
attr_reader :customer_uri, :username, :password
|
@@ -12,6 +14,12 @@ class Varanus
|
|
12
14
|
@password = password
|
13
15
|
end
|
14
16
|
|
17
|
+
# Retrieve Reports instance
|
18
|
+
# @return [Varanus::Reports]
|
19
|
+
def reports
|
20
|
+
@reports ||= Reports.new(self)
|
21
|
+
end
|
22
|
+
|
15
23
|
# Retrive SSL instance
|
16
24
|
# @return [Varanus::SSL]
|
17
25
|
def ssl
|
@@ -23,9 +31,11 @@ end
|
|
23
31
|
require 'faraday'
|
24
32
|
require 'faraday_middleware'
|
25
33
|
require 'openssl'
|
34
|
+
require 'savon'
|
26
35
|
|
27
36
|
# Require other files in this gem
|
28
37
|
require 'varanus/error'
|
38
|
+
require 'varanus/reports'
|
29
39
|
require 'varanus/ssl'
|
30
40
|
require 'varanus/ssl/csr'
|
31
41
|
require 'varanus/version'
|
data/varanus.gemspec
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
lib = File.expand_path('lib', __dir__)
|
2
4
|
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
3
5
|
require 'varanus/version'
|
@@ -40,5 +42,6 @@ Gem::Specification.new do |spec|
|
|
40
42
|
|
41
43
|
spec.add_runtime_dependency 'faraday'
|
42
44
|
spec.add_runtime_dependency 'faraday_middleware'
|
45
|
+
spec.add_runtime_dependency 'savon', '~> 2.0'
|
43
46
|
end
|
44
47
|
# rubocop:enable Metrics/BlockLength
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: varanus
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Sean Dilda
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2018-11-
|
11
|
+
date: 2018-11-09 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -164,6 +164,20 @@ dependencies:
|
|
164
164
|
- - ">="
|
165
165
|
- !ruby/object:Gem::Version
|
166
166
|
version: '0'
|
167
|
+
- !ruby/object:Gem::Dependency
|
168
|
+
name: savon
|
169
|
+
requirement: !ruby/object:Gem::Requirement
|
170
|
+
requirements:
|
171
|
+
- - "~>"
|
172
|
+
- !ruby/object:Gem::Version
|
173
|
+
version: '2.0'
|
174
|
+
type: :runtime
|
175
|
+
prerelease: false
|
176
|
+
version_requirements: !ruby/object:Gem::Requirement
|
177
|
+
requirements:
|
178
|
+
- - "~>"
|
179
|
+
- !ruby/object:Gem::Version
|
180
|
+
version: '2.0'
|
167
181
|
description: |
|
168
182
|
This gem provides an interface to Sectigo's (formerly Comodo CA) APIs for working
|
169
183
|
with SSL/TLS certificates as well as its reporting API.
|
@@ -180,6 +194,7 @@ files:
|
|
180
194
|
- ".gitignore"
|
181
195
|
- ".rubocop.yml"
|
182
196
|
- ".travis.yml"
|
197
|
+
- CHANGELOG.md
|
183
198
|
- Gemfile
|
184
199
|
- Gemfile.lock
|
185
200
|
- LICENSE.txt
|
@@ -190,6 +205,7 @@ files:
|
|
190
205
|
- docker-compose.yml
|
191
206
|
- lib/varanus.rb
|
192
207
|
- lib/varanus/error.rb
|
208
|
+
- lib/varanus/reports.rb
|
193
209
|
- lib/varanus/ssl.rb
|
194
210
|
- lib/varanus/ssl/csr.rb
|
195
211
|
- lib/varanus/version.rb
|