saro-dat 4.3.2 → 4.3.3

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: 0776a19c84f8d1791b89c6cc989077bda261fa7208444838f0486365e0af0287
4
- data.tar.gz: 84d8a9286f34e501de1521184e3f6ddc12d05df401174d87e29ab20454cec604
3
+ metadata.gz: 634a367ca133f87bdf4e936c4bb608734530198a979fd430fb9d5f6b6df391b5
4
+ data.tar.gz: 5e4b3e2d9be43345f9c276a6b630524f422762d5c345cfd4906b9e1a31d9cdd0
5
5
  SHA512:
6
- metadata.gz: b1b7592c0cfbc97a80aa987caa9dd4eff7294eb3c7105e10e69f057955ea854f27f8cf59b544316f3991fef2ce91634c889f6c91a9258d4a67f3a6310ad9d445
7
- data.tar.gz: ae289f220cd1421f033811e2df11c2a4333e3af067a5dd53af56f0998f4bad0e984592d1f9447253827729a4b9b245439b0707cf872f99840e21c13bf320b589
6
+ metadata.gz: a8ba6fc31fd745ecf6afe9bd79995d2fb622df640c90848911399ce6499b4c1cdb88cb28c391be299dd4291f39649d7f943d8ebb5c5e3df4821935006b5987e9
7
+ data.tar.gz: 64305c24d612dd667fb82b8be00c0d78642d66373715220b25052cfc9ac1f86b5570ab8e72fe512ace86bb0cf8d8a9a5019f072af5c3a73a4cac801b39e6e541
data/.idea/saro-dat.iml CHANGED
@@ -14,7 +14,6 @@
14
14
  <orderEntry type="library" scope="PROVIDED" name="base64 (v0.3.0, rbenv: 4.0.5) [gem]" level="application" />
15
15
  <orderEntry type="library" scope="PROVIDED" name="benchmark (v0.5.0, rbenv: 4.0.5) [gem]" level="application" />
16
16
  <orderEntry type="library" scope="PROVIDED" name="bundler (v4.0.12, rbenv: 4.0.5) [gem]" level="application" />
17
- <orderEntry type="library" scope="PROVIDED" name="concurrent-ruby (v1.3.7, rbenv: 4.0.5) [gem]" level="application" />
18
17
  <orderEntry type="library" scope="PROVIDED" name="logger (v1.7.0, rbenv: 4.0.5) [gem]" level="application" />
19
18
  <orderEntry type="library" scope="PROVIDED" name="minitest (v5.27.0, rbenv: 4.0.5) [gem]" level="application" />
20
19
  <orderEntry type="library" scope="PROVIDED" name="openssl (v4.0.2, rbenv: 4.0.5) [gem]" level="application" />
data/.idea/vcs.xml ADDED
@@ -0,0 +1,6 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <project version="4">
3
+ <component name="VcsDirectoryMappings">
4
+ <mapping directory="" vcs="Git" />
5
+ </component>
6
+ </project>
data/PUBLISH.md CHANGED
@@ -9,7 +9,7 @@ bundle install
9
9
  ```
10
10
  gem build saro-dat.gemspec
11
11
  gem signin
12
- gem push saro-dat-4.3.2.gem
12
+ gem push saro-dat-4.3.3.gem
13
13
  ```
14
14
 
15
15
  ## install
data/README.md CHANGED
@@ -1,12 +1,20 @@
1
1
  # DAT - Distributed Access Token
2
2
 
3
- ## Document
3
+ ### Document
4
+ - [DAT Run Online](https://dat.saro.me)
5
+ - [What is DAT](https://dat.saro.me/intro)
6
+ - [Example](https://dat.saro.me/libs/gems-saro-dat)
4
7
 
5
- ### [DAT Run Online](https://dat.saro.me)
6
-
7
- ### [What is DAT](https://dat.saro.me/intro)
8
-
9
- ### [Example](https://dat.saro.me/libs/gems-saro-dat)
8
+ ### Support Platform
9
+ - [Rust](https://github.com/saro-lab/dat-rust)
10
+ - [Java, Kotlin](https://github.com/saro-lab/dat-maven)
11
+ - [Javascript, Typescript](https://github.com/saro-lab/dat-npm)
12
+ - [C#](https://github.com/saro-lab/dat-nuget)
13
+ - [Python](https://github.com/saro-lab/dat-pypi)
14
+ - [Go](https://github.com/saro-lab/dat-go)
15
+ - [Ruby](https://github.com/saro-lab/dat-ruby)
16
+ - [C/C++ (Vcpkg)](https://github.com/saro-lab/dat-vcpkg)
17
+ - [Cert(key) Server (Docker)](https://github.com/saro-lab/dat-cms)
10
18
 
11
19
  ## Support algorithm
12
20
  ### Signature
@@ -32,60 +40,59 @@
32
40
  - mac mini m4 2024 basic (10 core)
33
41
  - [test_bench.rb](test/test_bench.rb)
34
42
  ```
35
- Testing started at ...
36
43
  Performance Test (Plain, Secure)
37
- Plain: CcMjua0RA8I27be6W2lYMBmk5OcPrV8mu3ybrVwBOB2pEPbtfrvH0h0Z0VBhG1ID4zu51sDKxZZGFoku9TzrcPJLbb0ObRiF3NIF
38
- Secure: EEYEOjriFkidJ8lKpYPkt1fwS01sZuJ7ysgCWd7XyarZfP6yrxkR9rciiJSUpuPZlBt0moFlKb0n2ZDivhvxLNjmO1eT8KjzhLlA
44
+ Plain: fCFP97qkmv2cGlQ3GVUpcj6th1TBPNxAoLGiN7XC3XlnQdN1xs4U6qZOYkfkPYcqbXSHCIabTzH8kFI9uY062mqKhjXmy4D8Os4B
45
+ Secure: 9wNnNCLvhuAfgvbcjNLXdKY9qXTqhIHBhgc62B7EgeH7fcDWOmJyah8zH0XcZhmgiDPJw4zTay7ArYosxR9NObjN0YWtKjQDrFme
39
46
 
40
47
  --- Multi-Thread ---
41
- HMAC-SHA256-MFS IV-AES128-GCM Issue * 10000 : 141ms
42
- HMAC-SHA256-MFS IV-AES128-GCM Parse * 10000 : 148ms
43
- HMAC-SHA256-MFS IV-AES256-GCM Issue * 10000 : 126ms
44
- HMAC-SHA256-MFS IV-AES256-GCM Parse * 10000 : 161ms
45
- HMAC-SHA384-MFS IV-AES128-GCM Issue * 10000 : 162ms
46
- HMAC-SHA384-MFS IV-AES128-GCM Parse * 10000 : 155ms
47
- HMAC-SHA384-MFS IV-AES256-GCM Issue * 10000 : 126ms
48
- HMAC-SHA384-MFS IV-AES256-GCM Parse * 10000 : 146ms
49
- HMAC-SHA512-MFS IV-AES128-GCM Issue * 10000 : 124ms
50
- HMAC-SHA512-MFS IV-AES128-GCM Parse * 10000 : 132ms
51
- HMAC-SHA512-MFS IV-AES256-GCM Issue * 10000 : 128ms
52
- HMAC-SHA512-MFS IV-AES256-GCM Parse * 10000 : 149ms
53
- ECDSA-P256 IV-AES128-GCM Issue * 10000 : 171ms
54
- ECDSA-P256 IV-AES128-GCM Parse * 10000 : 188ms
55
- ECDSA-P256 IV-AES256-GCM Issue * 10000 : 158ms
56
- ECDSA-P256 IV-AES256-GCM Parse * 10000 : 188ms
57
- ECDSA-P384 IV-AES128-GCM Issue * 10000 : 260ms
58
- ECDSA-P384 IV-AES128-GCM Parse * 10000 : 422ms
59
- ECDSA-P384 IV-AES256-GCM Issue * 10000 : 259ms
60
- ECDSA-P384 IV-AES256-GCM Parse * 10000 : 415ms
61
- ECDSA-P521 IV-AES128-GCM Issue * 10000 : 307ms
62
- ECDSA-P521 IV-AES128-GCM Parse * 10000 : 475ms
63
- ECDSA-P521 IV-AES256-GCM Issue * 10000 : 311ms
64
- ECDSA-P521 IV-AES256-GCM Parse * 10000 : 481ms
48
+ HMAC-SHA256-MFS IV-AES128-GCM Issue * 10000 : 150ms
49
+ HMAC-SHA256-MFS IV-AES128-GCM Parse * 10000 : 152ms
50
+ HMAC-SHA256-MFS IV-AES256-GCM Issue * 10000 : 138ms
51
+ HMAC-SHA256-MFS IV-AES256-GCM Parse * 10000 : 162ms
52
+ HMAC-SHA384-MFS IV-AES128-GCM Issue * 10000 : 130ms
53
+ HMAC-SHA384-MFS IV-AES128-GCM Parse * 10000 : 145ms
54
+ HMAC-SHA384-MFS IV-AES256-GCM Issue * 10000 : 132ms
55
+ HMAC-SHA384-MFS IV-AES256-GCM Parse * 10000 : 165ms
56
+ HMAC-SHA512-MFS IV-AES128-GCM Issue * 10000 : 130ms
57
+ HMAC-SHA512-MFS IV-AES128-GCM Parse * 10000 : 149ms
58
+ HMAC-SHA512-MFS IV-AES256-GCM Issue * 10000 : 130ms
59
+ HMAC-SHA512-MFS IV-AES256-GCM Parse * 10000 : 150ms
60
+ ECDSA-P256 IV-AES128-GCM Issue * 10000 : 170ms
61
+ ECDSA-P256 IV-AES128-GCM Parse * 10000 : 189ms
62
+ ECDSA-P256 IV-AES256-GCM Issue * 10000 : 155ms
63
+ ECDSA-P256 IV-AES256-GCM Parse * 10000 : 194ms
64
+ ECDSA-P384 IV-AES128-GCM Issue * 10000 : 339ms
65
+ ECDSA-P384 IV-AES128-GCM Parse * 10000 : 441ms
66
+ ECDSA-P384 IV-AES256-GCM Issue * 10000 : 320ms
67
+ ECDSA-P384 IV-AES256-GCM Parse * 10000 : 490ms
68
+ ECDSA-P521 IV-AES128-GCM Issue * 10000 : 352ms
69
+ ECDSA-P521 IV-AES128-GCM Parse * 10000 : 554ms
70
+ ECDSA-P521 IV-AES256-GCM Issue * 10000 : 374ms
71
+ ECDSA-P521 IV-AES256-GCM Parse * 10000 : 529ms
65
72
 
66
73
  --- Single-Thread ---
67
74
  HMAC-SHA256-MFS IV-AES128-GCM Issue * 10000 : 64ms
68
- HMAC-SHA256-MFS IV-AES128-GCM Parse * 10000 : 65ms
69
- HMAC-SHA256-MFS IV-AES256-GCM Issue * 10000 : 60ms
70
- HMAC-SHA256-MFS IV-AES256-GCM Parse * 10000 : 68ms
71
- HMAC-SHA384-MFS IV-AES128-GCM Issue * 10000 : 66ms
72
- HMAC-SHA384-MFS IV-AES128-GCM Parse * 10000 : 83ms
73
- HMAC-SHA384-MFS IV-AES256-GCM Issue * 10000 : 64ms
74
- HMAC-SHA384-MFS IV-AES256-GCM Parse * 10000 : 67ms
75
- HMAC-SHA512-MFS IV-AES128-GCM Issue * 10000 : 62ms
76
- HMAC-SHA512-MFS IV-AES128-GCM Parse * 10000 : 67ms
77
- HMAC-SHA512-MFS IV-AES256-GCM Issue * 10000 : 66ms
78
- HMAC-SHA512-MFS IV-AES256-GCM Parse * 10000 : 68ms
79
- ECDSA-P256 IV-AES128-GCM Issue * 10000 : 192ms
80
- ECDSA-P256 IV-AES128-GCM Parse * 10000 : 403ms
81
- ECDSA-P256 IV-AES256-GCM Issue * 10000 : 188ms
82
- ECDSA-P256 IV-AES256-GCM Parse * 10000 : 404ms
83
- ECDSA-P384 IV-AES128-GCM Issue * 10000 : 1049ms
84
- ECDSA-P384 IV-AES128-GCM Parse * 10000 : 2157ms
85
- ECDSA-P384 IV-AES256-GCM Issue * 10000 : 1060ms
86
- ECDSA-P384 IV-AES256-GCM Parse * 10000 : 2155ms
87
- ECDSA-P521 IV-AES128-GCM Issue * 10000 : 1374ms
88
- ECDSA-P521 IV-AES128-GCM Parse * 10000 : 2428ms
89
- ECDSA-P521 IV-AES256-GCM Issue * 10000 : 1368ms
90
- ECDSA-P521 IV-AES256-GCM Parse * 10000 : 2417ms
75
+ HMAC-SHA256-MFS IV-AES128-GCM Parse * 10000 : 60ms
76
+ HMAC-SHA256-MFS IV-AES256-GCM Issue * 10000 : 58ms
77
+ HMAC-SHA256-MFS IV-AES256-GCM Parse * 10000 : 66ms
78
+ HMAC-SHA384-MFS IV-AES128-GCM Issue * 10000 : 62ms
79
+ HMAC-SHA384-MFS IV-AES128-GCM Parse * 10000 : 61ms
80
+ HMAC-SHA384-MFS IV-AES256-GCM Issue * 10000 : 66ms
81
+ HMAC-SHA384-MFS IV-AES256-GCM Parse * 10000 : 73ms
82
+ HMAC-SHA512-MFS IV-AES128-GCM Issue * 10000 : 58ms
83
+ HMAC-SHA512-MFS IV-AES128-GCM Parse * 10000 : 63ms
84
+ HMAC-SHA512-MFS IV-AES256-GCM Issue * 10000 : 60ms
85
+ HMAC-SHA512-MFS IV-AES256-GCM Parse * 10000 : 67ms
86
+ ECDSA-P256 IV-AES128-GCM Issue * 10000 : 177ms
87
+ ECDSA-P256 IV-AES128-GCM Parse * 10000 : 392ms
88
+ ECDSA-P256 IV-AES256-GCM Issue * 10000 : 172ms
89
+ ECDSA-P256 IV-AES256-GCM Parse * 10000 : 394ms
90
+ ECDSA-P384 IV-AES128-GCM Issue * 10000 : 1055ms
91
+ ECDSA-P384 IV-AES128-GCM Parse * 10000 : 2155ms
92
+ ECDSA-P384 IV-AES256-GCM Issue * 10000 : 1039ms
93
+ ECDSA-P384 IV-AES256-GCM Parse * 10000 : 2160ms
94
+ ECDSA-P521 IV-AES128-GCM Issue * 10000 : 1358ms
95
+ ECDSA-P521 IV-AES128-GCM Parse * 10000 : 2390ms
96
+ ECDSA-P521 IV-AES256-GCM Issue * 10000 : 1381ms
97
+ ECDSA-P521 IV-AES256-GCM Parse * 10000 : 2398ms
91
98
  ```
@@ -51,7 +51,9 @@ module Saro
51
51
  end
52
52
 
53
53
  def encrypt(data)
54
- data = data.encode('utf-8') if data.is_a?(String) && data.encoding != Encoding::BINARY
54
+ if data.is_a?(String) && data.encoding != Encoding::BINARY && data.encoding != Encoding::UTF_8
55
+ data = data.encode('utf-8')
56
+ end
55
57
  return "".b if data.nil? || data.empty?
56
58
 
57
59
  cipher = OpenSSL::Cipher.new(@config[:name])
data/lib/saro/dat/dat.rb CHANGED
@@ -46,8 +46,9 @@ module Saro
46
46
  alias_method :expired?, :expired
47
47
 
48
48
  def body_string
49
- return "" unless @dat.include?('.')
50
- @dat.rpartition('.').first
49
+ idx = @dat.rindex('.')
50
+ return "" unless idx
51
+ @dat[0, idx]
51
52
  end
52
53
  end
53
54
 
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'concurrent-ruby'
4
3
  require 'set'
5
4
  require_relative 'dat_certificate'
6
5
  require_relative 'dat'
@@ -10,16 +9,23 @@ require_relative 'util'
10
9
  module Saro
11
10
  module Dat
12
11
  class DatManager
12
+ # Immutable snapshot of the manager state.
13
+ # Readers access it lock-free via a single ivar read (atomic reference swap);
14
+ # writers rebuild a new frozen snapshot under @write_lock.
15
+ State = Struct.new(:issuer, :certificates, :by_cid)
16
+
17
+ EMPTY_STATE = State.new(nil, [].freeze, {}.freeze).freeze
18
+ private_constant :EMPTY_STATE
19
+
13
20
  def initialize
14
- @issuer = nil
15
- @certificates = []
16
- @lock = Concurrent::ReadWriteLock.new
21
+ @state = EMPTY_STATE
22
+ @write_lock = Mutex.new
17
23
  end
18
24
 
19
25
  def import_certificates(input_certs, clear: false)
20
26
  renew_count = 0
21
- @lock.with_write_lock do
22
- certificates = clear ? [] : @certificates.dup
27
+ @write_lock.synchronize do
28
+ certificates = clear ? [] : @state.certificates.dup
23
29
 
24
30
  before_cids = Set.new(certificates.map(&:cid))
25
31
  seen_cids = Set.new
@@ -29,18 +35,20 @@ module Saro
29
35
  seen_cids.add(cert.cid)
30
36
  next if cert.expired
31
37
  next if before_cids.include?(cert.cid)
32
-
38
+
33
39
  certificates << cert
34
40
  renew_count += 1
35
41
  end
36
42
 
37
43
  certificates.sort_by!(&:dat_issuance_end_seconds)
38
-
44
+
39
45
  # Find latest issuable certificate as issuer
40
46
  issuer = certificates.reverse_each.find(&:issuable)
41
47
 
42
- @issuer = issuer
43
- @certificates = certificates
48
+ by_cid = {}
49
+ certificates.each { |cert| by_cid[cert.cid] = cert }
50
+
51
+ @state = State.new(issuer, certificates.freeze, by_cid.freeze).freeze
44
52
  end
45
53
  renew_count
46
54
  end
@@ -56,15 +64,13 @@ module Saro
56
64
  end
57
65
 
58
66
  def exports(verify_only = false)
59
- @lock.with_read_lock do
60
- @certificates.map { |cert| cert.exports(verify_only) }.join("\n")
61
- end
67
+ @state.certificates.map { |cert| cert.exports(verify_only) }.join("\n")
62
68
  end
63
69
 
64
70
  def issue(plain, secure)
65
- issuer = @lock.with_read_lock { @issuer }
71
+ issuer = @state.issuer
66
72
  raise RuntimeError, "Invalid DAT: Signing Key Does Not Exist" unless issuer
67
-
73
+
68
74
  self.class._issue(issuer, plain, secure)
69
75
  end
70
76
 
@@ -72,12 +78,10 @@ module Saro
72
78
  dat = Saro::Dat::Dat.from_value(dat_input)
73
79
  raise ArgumentError, "Invalid DAT: Format" unless dat.format
74
80
 
75
- certificate = @lock.with_read_lock do
76
- @certificates.find { |c| c.cid == dat.cid }
77
- end
78
-
81
+ certificate = @state.by_cid[dat.cid]
82
+
79
83
  raise ArgumentError, "Invalid DAT: CID(Certificate ID) Not Found" unless certificate
80
-
84
+
81
85
  self.class._parse(certificate, dat)
82
86
  end
83
87
 
@@ -88,8 +92,7 @@ module Saro
88
92
  expire = now + cert.dat_ttl_seconds
89
93
  cid_hex = cert.cid.to_s(16)
90
94
 
91
- plain_bytes = plain.is_a?(String) ? plain.encode('utf-8') : (plain || "".b)
92
- plain_b64 = Saro::Dat::Util.encode_base64_url_str(plain_bytes)
95
+ plain_b64 = Saro::Dat::Util.encode_base64_url_str(plain)
93
96
 
94
97
  encrypted_secure = cert.crypto_key.encrypt(secure)
95
98
  secure_b64 = Saro::Dat::Util.encode_base64_url_str(encrypted_secure)
@@ -137,20 +137,19 @@ module Saro
137
137
 
138
138
  def sign(body)
139
139
  raise ArgumentError, "Signature key is not supported - verifying only key" unless @signing_key
140
- body = body.encode('utf-8') if body.is_a?(String) && body.encoding != Encoding::BINARY
140
+ body = normalize_body(body)
141
141
  raise ArgumentError, "Sign Error - body is empty" if body.nil? || body.empty?
142
142
 
143
143
  if @config[:name] == "HMAC"
144
144
  OpenSSL::HMAC.digest(@config[:hash], @signing_key, body)
145
145
  else
146
- digest = OpenSSL::Digest.new(@config[:hash])
147
- signature_der = @signing_key.dsa_sign_asn1(digest.digest(body))
146
+ signature_der = @signing_key.dsa_sign_asn1(OpenSSL::Digest.digest(@config[:hash], body))
148
147
  der_to_raw_signature(signature_der)
149
148
  end
150
149
  end
151
150
 
152
151
  def verify(body, signature)
153
- body = body.encode('utf-8') if body.is_a?(String) && body.encoding != Encoding::BINARY
152
+ body = normalize_body(body)
154
153
  return false if body.nil? || body.empty?
155
154
 
156
155
  sig_bytes = if signature.is_a?(String) && signature.encoding != Encoding::BINARY
@@ -170,8 +169,7 @@ module Saro
170
169
  else
171
170
  begin
172
171
  der_sig = raw_to_der_signature(sig_bytes)
173
- digest = OpenSSL::Digest.new(@config[:hash])
174
- @verifying_key.dsa_verify_asn1(digest.digest(body), der_sig)
172
+ @verifying_key.dsa_verify_asn1(OpenSSL::Digest.digest(@config[:hash], body), der_sig)
175
173
  rescue StandardError
176
174
  false
177
175
  end
@@ -192,15 +190,23 @@ module Saro
192
190
 
193
191
  private
194
192
 
193
+ # Avoid a needless copy when the body is already UTF-8 encoded bytes.
194
+ def normalize_body(body)
195
+ return body unless body.is_a?(String)
196
+ enc = body.encoding
197
+ return body if enc == Encoding::BINARY || enc == Encoding::UTF_8
198
+ body.encode('utf-8')
199
+ end
200
+
195
201
  def der_to_raw_signature(signature_der)
196
202
  asn1 = OpenSSL::ASN1.decode(signature_der)
197
203
  r = asn1.value[0].value
198
204
  s = asn1.value[1].value
199
-
200
- size = (@verifying_key.group.degree + 7) / 8
205
+
206
+ size = @config[:private_len] # curve byte size: (group.degree + 7) / 8
201
207
  r_bytes = r.to_s(2).rjust(size, "\x00".b)
202
208
  s_bytes = s.to_s(2).rjust(size, "\x00".b)
203
-
209
+
204
210
  r_bytes + s_bytes
205
211
  end
206
212
 
data/lib/saro/dat/util.rb CHANGED
@@ -11,7 +11,8 @@ module Saro
11
11
  return "".b if s.nil?
12
12
  if s.is_a?(String)
13
13
  return "".b if s.empty?
14
- s = s.encode('utf-8') unless s.encoding == Encoding::BINARY
14
+ enc = s.encoding
15
+ s = s.encode('utf-8') unless enc == Encoding::BINARY || enc == Encoding::UTF_8
15
16
  end
16
17
  Base64.urlsafe_encode64(s, padding: false).b
17
18
  end
data/saro-dat.gemspec CHANGED
@@ -2,7 +2,7 @@
2
2
 
3
3
  Gem::Specification.new do |spec|
4
4
  spec.name = "saro-dat"
5
- spec.version = "4.3.2"
5
+ spec.version = "4.3.3"
6
6
  spec.authors = ["marker"]
7
7
  spec.email = ["j@saro.me"]
8
8
 
@@ -27,7 +27,6 @@ Gem::Specification.new do |spec|
27
27
  spec.executables = spec.files.grep(%r{\Aexe/}) { |f| File.basename(f) }
28
28
  spec.require_paths = ["lib"]
29
29
 
30
- spec.add_dependency "concurrent-ruby", "~> 1.3.6"
31
30
  spec.add_dependency "openssl", "~> 4.0.2"
32
31
  spec.add_dependency "base64"
33
32
  spec.add_dependency "logger"
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: saro-dat
3
3
  version: !ruby/object:Gem::Version
4
- version: 4.3.2
4
+ version: 4.3.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - marker
@@ -9,20 +9,6 @@ bindir: exe
9
9
  cert_chain: []
10
10
  date: 1980-01-02 00:00:00.000000000 Z
11
11
  dependencies:
12
- - !ruby/object:Gem::Dependency
13
- name: concurrent-ruby
14
- requirement: !ruby/object:Gem::Requirement
15
- requirements:
16
- - - "~>"
17
- - !ruby/object:Gem::Version
18
- version: 1.3.6
19
- type: :runtime
20
- prerelease: false
21
- version_requirements: !ruby/object:Gem::Requirement
22
- requirements:
23
- - - "~>"
24
- - !ruby/object:Gem::Version
25
- version: 1.3.6
26
12
  - !ruby/object:Gem::Dependency
27
13
  name: openssl
28
14
  requirement: !ruby/object:Gem::Requirement
@@ -118,6 +104,7 @@ files:
118
104
  - ".idea/.gitignore"
119
105
  - ".idea/modules.xml"
120
106
  - ".idea/saro-dat.iml"
107
+ - ".idea/vcs.xml"
121
108
  - ".ruby-version"
122
109
  - Gemfile
123
110
  - LICENSE