securer_randomer 0.1.5 → 0.1.6
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.
- data/.travis.yml +1 -0
- data/README.md +61 -35
- data/lib/securer_randomer/monkeypatch/secure_random.rb +4 -2
- data/lib/securer_randomer/version.rb +1 -1
- data/securer_randomer.gemspec +1 -1
- metadata +59 -42
- checksums.yaml +0 -7
data/.travis.yml
CHANGED
data/README.md
CHANGED
@@ -7,67 +7,93 @@ Ruby's SecureRandom prefers OpenSSL over other mechanisms (such as
|
|
7
7
|
`/dev/urandom` and `getrandom(2)`). This has recently garnered [some][1]
|
8
8
|
[criticism][2].
|
9
9
|
|
10
|
-
[RbNaCl][3] provides Ruby bindings to a portable crypto
|
11
|
-
|
12
|
-
|
10
|
+
[RbNaCl][3] provides Ruby bindings to [libsodium][4], a portable crypto
|
11
|
+
library—which is a fork of [NaCl][6] by Daniel J. Bernstein—that
|
12
|
+
includes hooks to alternative, OpenSSL-free pseudo-random number generators
|
13
|
+
(PRNGs) such as `getrandom(2)` on modern Linux kernels and `RtlGenRandom()` on
|
14
|
+
Windows.
|
13
15
|
|
14
16
|
This gem monkeypatches RbNaCl into SecureRandom and aims to be "bug-for-bug"
|
15
17
|
compatible with the "stock" implementation of SecureRandom across Ruby
|
16
|
-
versions. It also provides a
|
18
|
+
versions. It also provides a bonus "do what I mean" random number method that
|
17
19
|
can be used instead of Kernel`.rand` and SecureRandom`.random_number`.
|
18
20
|
|
19
21
|
## History
|
20
22
|
|
21
23
|
This gem started out as a very simple monkeypatch to
|
22
|
-
SecureRandom`.random_bytes` and grew as I dug deeper. In newer
|
23
|
-
to patch `.gen_random` instead of `.random_bytes`, and it has
|
24
|
-
|
24
|
+
SecureRandom`.random_bytes` and grew as I dug deeper. In newer rubies, for
|
25
|
+
example, you need to patch `.gen_random` instead of `.random_bytes`, and it has
|
26
|
+
a different calling signature.
|
25
27
|
|
26
|
-
Generating random numbers proved to be rather tricky due to inconsistencies
|
27
|
-
|
28
|
-
|
28
|
+
Generating random numbers proved to be rather tricky due to inconsistencies of
|
29
|
+
of Kernel`.rand` and SecureRandom`.random_number` between Ruby implementations
|
30
|
+
and versions. For example:
|
29
31
|
|
30
32
|
* `Kernel.rand(nil)` and `SecureRandom.random_number(nil)` both return a float
|
31
|
-
such that `
|
33
|
+
`n` such that `0.0 <= n < 1.0` in Ruby 2.3; but
|
32
34
|
`SecureRandom.random_number(nil)` throws an ArgumentError in Ruby 2.2
|
33
35
|
* Kernel`.rand` with an inverted range (e.g. `0..-10`) returns `nil` in Ruby
|
34
36
|
2.2+, but SecureRandom`.random_number` throws an ArgumentError in Ruby 2.2
|
35
|
-
and returns a float such that `
|
37
|
+
and returns a float `n` such that `0.0 <= n < 1.0` in Ruby 2.3
|
36
38
|
|
37
|
-
|
38
|
-
this!
|
39
|
+
Branching logic and tests started to accumulate so I decided it was probably a
|
40
|
+
good idea to gemify this!
|
41
|
+
|
42
|
+
### Why a monkeypatch?
|
43
|
+
|
44
|
+
The concept of monkeypatching in Ruby is a sensitive subject. It has the
|
45
|
+
potential to break things in unexpected ways and make Ruby code more difficult
|
46
|
+
to troubleshoot, and it's these kinds of practices that give Ruby (and
|
47
|
+
Rubyists) a bad name. It was actually way more labor-intensive to write this as
|
48
|
+
a monkeypatch rather than landing it as a completely separate module. So why?
|
49
|
+
|
50
|
+
Simply put, I do not anticipate this gem being a long-term solution! At some
|
51
|
+
point in the hopefully-near future I would like to see the Ruby core team
|
52
|
+
acquiesce to community pressure and modify `securerandom.rb` and `random.c` to
|
53
|
+
not utilize OpenSSL and prefer `getrandom(2)` over `urandom`. And so my goal
|
54
|
+
was not to write some super-maintainable, standalone piece of software, but
|
55
|
+
rather a temporary fix that can be easily dropped into an existing project and
|
56
|
+
easily pulled out at a later date. A monkeypatch is the best way to achieve
|
57
|
+
this.
|
39
58
|
|
40
59
|
## Features
|
41
60
|
|
42
61
|
* SecureRandom`.gen_random` (or `.random_bytes`)
|
43
62
|
|
44
|
-
Monkeypatches SecureRandom such that its various formatter methods (`.uuid`,
|
45
|
-
`.hex`, `.base64`, `.urlsafe_base64`, and `.random_bytes`) use RbNaCl for random
|
46
|
-
byte generation instead of OpenSSL.
|
63
|
+
Monkeypatches SecureRandom such that its various formatter methods (`.uuid`,
|
64
|
+
`.hex`, `.base64`, `.urlsafe_base64`, and `.random_bytes`) use RbNaCl for random
|
65
|
+
byte generation instead of OpenSSL.
|
47
66
|
|
48
67
|
* SecureRandom`.random_number`
|
49
68
|
|
50
|
-
Monkeypatches SecureRandom such that it uses SecurerRandomer`.kernel_rand`
|
51
|
-
instead of OpenSSL
|
52
|
-
|
53
|
-
|
69
|
+
Monkeypatches SecureRandom such that it uses SecurerRandomer`.kernel_rand`
|
70
|
+
instead of OpenSSL to generate random numbers from numeric types and ranges. It
|
71
|
+
is bug-for-bug compatible with "stock" SecureRandom, meaning it "chokes" on the
|
72
|
+
same inputs and throws the same exception types.
|
73
|
+
|
74
|
+
If you prefer to use Kernel`.rand` instead of SecurerRandomer`.kernel_rand`,
|
75
|
+
add this statement to your bootup process after requiring SecurerRandomer:
|
76
|
+
|
77
|
+
```ruby
|
78
|
+
SecurerRandomer::KERNEL_RAND = Kernel.method(:rand)
|
79
|
+
```
|
54
80
|
|
55
81
|
* SecurerRandomer`.kernel_rand`
|
56
82
|
|
57
|
-
A bug-for-bug reimplementation of Kernel`.rand`—meaning it "chokes" on
|
58
|
-
the same inputs and throws the same exception types—that uses RbNaCl as
|
59
|
-
its source of entropy.
|
83
|
+
A bug-for-bug reimplementation of Kernel`.rand`—meaning it "chokes" on
|
84
|
+
the same inputs and throws the same exception types—that uses RbNaCl as
|
85
|
+
its source of entropy.
|
60
86
|
|
61
87
|
* SecurerRandomer`.rand`
|
62
88
|
|
63
|
-
An idealistic, "do what I mean" random number method that accepts a variety of
|
64
|
-
inputs and returns what you might expect. Whereas `Kernel.rand(-5.6)` returns
|
65
|
-
an integer such that `
|
66
|
-
returns a float such that `
|
67
|
-
returns a float such that `
|
68
|
-
returns `nil` and `SecureRandom.random_number(10..0)` returns a float such
|
69
|
-
`
|
70
|
-
integer such that `
|
89
|
+
An idealistic, "do what I mean" random number method that accepts a variety of
|
90
|
+
inputs and returns what you might expect. Whereas `Kernel.rand(-5.6)` returns
|
91
|
+
an integer `n` such that `0 <= n < 5` and `SecureRandom.random_number(-5.6)`
|
92
|
+
returns a float `n` such that `0.0 <= n < 1.0`, **`SecurerRandomer.rand(-5.6)`
|
93
|
+
returns a float `n` such that `0 >= n > -5.6`**. Whereas `Kernel.rand(10..0)`
|
94
|
+
returns `nil` and `SecureRandom.random_number(10..0)` returns a float `n` such
|
95
|
+
that `0.0 <= n < 1.0` (in Ruby 2.3), **`SecurerRandomer.rand(10..0)` returns an
|
96
|
+
integer `n` such that `10 >= n >= 0`**.
|
71
97
|
|
72
98
|
## Installation
|
73
99
|
|
@@ -100,9 +126,8 @@ and 2.3, and JRuby 1.7 and 9.0 (both under Oracle Java 8).
|
|
100
126
|
|
101
127
|
I am neither a cryptologist nor a cryptographer. Although I'm fairly confident
|
102
128
|
in the test suite, serious bugs affecting compatibility, randomness, and
|
103
|
-
performance may be present. If you're cautious, I would recommend
|
104
|
-
|
105
|
-
for random numbers. Bug reports are welcome.
|
129
|
+
performance may be present. If you're cautious, I would recommend setting
|
130
|
+
`SecurerRandomer::KERNEL_RAND = Kernel.method(:rand)` as described above.
|
106
131
|
|
107
132
|
## Development
|
108
133
|
|
@@ -123,3 +148,4 @@ The gem is available as open source under the terms of the [MIT License](http://
|
|
123
148
|
[3]: https://github.com/cryptosphere/rbnacl
|
124
149
|
[4]: https://github.com/jedisct1/libsodium
|
125
150
|
[5]: https://github.com/cryptosphere/rbnacl-libsodium
|
151
|
+
[6]: http://nacl.cr.yp.to
|
@@ -1,6 +1,8 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module SecureRandom
|
4
|
+
KERNEL_RAND = SecurerRandomer.method(:kernel_rand)
|
5
|
+
|
4
6
|
if respond_to?(:gen_random)
|
5
7
|
def self.gen_random(n)
|
6
8
|
RbNaCl::Random.random_bytes(n)
|
@@ -31,7 +33,7 @@ module SecureRandom
|
|
31
33
|
|
32
34
|
raise TypeError unless arg
|
33
35
|
|
34
|
-
|
36
|
+
KERNEL_RAND.call(arg)
|
35
37
|
rescue TypeError
|
36
38
|
raise ArgumentError, "invalid argument - #{n}"
|
37
39
|
end
|
@@ -42,7 +44,7 @@ module SecureRandom
|
|
42
44
|
raise ArgumentError, "comparison of Fixnum with #{n} failed" unless n.is_a?(Numeric)
|
43
45
|
raise FLOAT_ERROR if n.is_a?(Float) and n > 0
|
44
46
|
|
45
|
-
|
47
|
+
KERNEL_RAND.call(n > 0 ? n : 0)
|
46
48
|
end
|
47
49
|
end
|
48
50
|
end
|
data/securer_randomer.gemspec
CHANGED
metadata
CHANGED
@@ -1,110 +1,123 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: securer_randomer
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.6
|
5
|
+
prerelease:
|
5
6
|
platform: ruby
|
6
7
|
authors:
|
7
8
|
- Mike Pastore
|
8
|
-
autorequire:
|
9
|
+
autorequire:
|
9
10
|
bindir: exe
|
10
11
|
cert_chain: []
|
11
|
-
date: 2016-05-
|
12
|
+
date: 2016-05-12 00:00:00.000000000 Z
|
12
13
|
dependencies:
|
13
14
|
- !ruby/object:Gem::Dependency
|
15
|
+
name: bundler
|
14
16
|
requirement: !ruby/object:Gem::Requirement
|
17
|
+
none: false
|
15
18
|
requirements:
|
16
|
-
- -
|
19
|
+
- - ~>
|
17
20
|
- !ruby/object:Gem::Version
|
18
21
|
version: '1.11'
|
19
|
-
name: bundler
|
20
|
-
prerelease: false
|
21
22
|
type: :development
|
23
|
+
prerelease: false
|
22
24
|
version_requirements: !ruby/object:Gem::Requirement
|
25
|
+
none: false
|
23
26
|
requirements:
|
24
|
-
- -
|
27
|
+
- - ~>
|
25
28
|
- !ruby/object:Gem::Version
|
26
29
|
version: '1.11'
|
27
30
|
- !ruby/object:Gem::Dependency
|
31
|
+
name: rake
|
28
32
|
requirement: !ruby/object:Gem::Requirement
|
33
|
+
none: false
|
29
34
|
requirements:
|
30
|
-
- -
|
35
|
+
- - ~>
|
31
36
|
- !ruby/object:Gem::Version
|
32
37
|
version: 11.1.1
|
33
|
-
name: rake
|
34
|
-
prerelease: false
|
35
38
|
type: :development
|
39
|
+
prerelease: false
|
36
40
|
version_requirements: !ruby/object:Gem::Requirement
|
41
|
+
none: false
|
37
42
|
requirements:
|
38
|
-
- -
|
43
|
+
- - ~>
|
39
44
|
- !ruby/object:Gem::Version
|
40
45
|
version: 11.1.1
|
41
46
|
- !ruby/object:Gem::Dependency
|
47
|
+
name: rspec
|
42
48
|
requirement: !ruby/object:Gem::Requirement
|
49
|
+
none: false
|
43
50
|
requirements:
|
44
|
-
- -
|
51
|
+
- - ~>
|
45
52
|
- !ruby/object:Gem::Version
|
46
53
|
version: '3.0'
|
47
|
-
name: rspec
|
48
|
-
prerelease: false
|
49
54
|
type: :development
|
55
|
+
prerelease: false
|
50
56
|
version_requirements: !ruby/object:Gem::Requirement
|
57
|
+
none: false
|
51
58
|
requirements:
|
52
|
-
- -
|
59
|
+
- - ~>
|
53
60
|
- !ruby/object:Gem::Version
|
54
61
|
version: '3.0'
|
55
62
|
- !ruby/object:Gem::Dependency
|
63
|
+
name: rspec-given
|
56
64
|
requirement: !ruby/object:Gem::Requirement
|
65
|
+
none: false
|
57
66
|
requirements:
|
58
|
-
- -
|
67
|
+
- - ~>
|
59
68
|
- !ruby/object:Gem::Version
|
60
69
|
version: 3.8.0
|
61
|
-
name: rspec-given
|
62
|
-
prerelease: false
|
63
70
|
type: :development
|
71
|
+
prerelease: false
|
64
72
|
version_requirements: !ruby/object:Gem::Requirement
|
73
|
+
none: false
|
65
74
|
requirements:
|
66
|
-
- -
|
75
|
+
- - ~>
|
67
76
|
- !ruby/object:Gem::Version
|
68
77
|
version: 3.8.0
|
69
78
|
- !ruby/object:Gem::Dependency
|
79
|
+
name: rubocop
|
70
80
|
requirement: !ruby/object:Gem::Requirement
|
81
|
+
none: false
|
71
82
|
requirements:
|
72
|
-
- -
|
83
|
+
- - ~>
|
73
84
|
- !ruby/object:Gem::Version
|
74
85
|
version: 0.39.0
|
75
|
-
name: rubocop
|
76
|
-
prerelease: false
|
77
86
|
type: :development
|
87
|
+
prerelease: false
|
78
88
|
version_requirements: !ruby/object:Gem::Requirement
|
89
|
+
none: false
|
79
90
|
requirements:
|
80
|
-
- -
|
91
|
+
- - ~>
|
81
92
|
- !ruby/object:Gem::Version
|
82
93
|
version: 0.39.0
|
83
94
|
- !ruby/object:Gem::Dependency
|
95
|
+
name: rbnacl
|
84
96
|
requirement: !ruby/object:Gem::Requirement
|
97
|
+
none: false
|
85
98
|
requirements:
|
86
|
-
- -
|
99
|
+
- - ~>
|
87
100
|
- !ruby/object:Gem::Version
|
88
|
-
version: 3.3
|
89
|
-
name: rbnacl
|
90
|
-
prerelease: false
|
101
|
+
version: '3.3'
|
91
102
|
type: :runtime
|
103
|
+
prerelease: false
|
92
104
|
version_requirements: !ruby/object:Gem::Requirement
|
105
|
+
none: false
|
93
106
|
requirements:
|
94
|
-
- -
|
107
|
+
- - ~>
|
95
108
|
- !ruby/object:Gem::Version
|
96
|
-
version: 3.3
|
97
|
-
description:
|
109
|
+
version: '3.3'
|
110
|
+
description:
|
98
111
|
email:
|
99
112
|
- mike@oobak.org
|
100
113
|
executables: []
|
101
114
|
extensions: []
|
102
115
|
extra_rdoc_files: []
|
103
116
|
files:
|
104
|
-
-
|
105
|
-
-
|
106
|
-
-
|
107
|
-
-
|
117
|
+
- .gitignore
|
118
|
+
- .rspec
|
119
|
+
- .rubocop.yml
|
120
|
+
- .travis.yml
|
108
121
|
- Gemfile
|
109
122
|
- LICENSE.txt
|
110
123
|
- README.md
|
@@ -119,25 +132,29 @@ files:
|
|
119
132
|
homepage: https://github.com/mwpastore/securer_randomer
|
120
133
|
licenses:
|
121
134
|
- MIT
|
122
|
-
|
123
|
-
post_install_message:
|
135
|
+
post_install_message:
|
124
136
|
rdoc_options: []
|
125
137
|
require_paths:
|
126
138
|
- lib
|
127
139
|
required_ruby_version: !ruby/object:Gem::Requirement
|
140
|
+
none: false
|
128
141
|
requirements:
|
129
|
-
- -
|
142
|
+
- - ! '>='
|
130
143
|
- !ruby/object:Gem::Version
|
131
144
|
version: 1.9.3
|
132
145
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
146
|
+
none: false
|
133
147
|
requirements:
|
134
|
-
- -
|
148
|
+
- - ! '>='
|
135
149
|
- !ruby/object:Gem::Version
|
136
150
|
version: '0'
|
151
|
+
segments:
|
152
|
+
- 0
|
153
|
+
hash: 1367148123343509472
|
137
154
|
requirements: []
|
138
|
-
rubyforge_project:
|
139
|
-
rubygems_version:
|
140
|
-
signing_key:
|
141
|
-
specification_version:
|
155
|
+
rubyforge_project:
|
156
|
+
rubygems_version: 1.8.23.2
|
157
|
+
signing_key:
|
158
|
+
specification_version: 3
|
142
159
|
summary: Monkeypatch SecureRandom with RbNaCl
|
143
160
|
test_files: []
|
checksums.yaml
DELETED
@@ -1,7 +0,0 @@
|
|
1
|
-
---
|
2
|
-
SHA1:
|
3
|
-
metadata.gz: 7cba7c11c88f376cd4e607ce3257ead37f85627a
|
4
|
-
data.tar.gz: 9b8f50ff4c3ded6e183525eec67e92f3384ed856
|
5
|
-
SHA512:
|
6
|
-
metadata.gz: eb8dc02d517df6ccc33c3ef75faec746f6ed659d8185115bb147cef400d575212637ebc44df23a68fa430f5472a2020086b023cdcb4f186530935d140caf4602
|
7
|
-
data.tar.gz: f0c6807fad93b80a32318642b16a8ebbb4b43ef090743dbd737283bce4610ddf99a4d5f298ce03a9be682d7e590d1369144fb0f06527200172c293262bcc4e23
|