rotp 1.3.3 → 1.4.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.
- data/Gemfile +0 -2
- data/README.markdown +16 -4
- data/Rakefile +5 -7
- data/lib/rotp/totp.rb +11 -2
- data/lib/rotp/version.rb +1 -1
- data/rotp.gemspec +4 -0
- data/spec/base_spec.rb +1 -1
- data/spec/spec_helper.rb +2 -0
- data/spec/totp_spec.rb +18 -0
- metadata +48 -7
data/Gemfile
CHANGED
data/README.markdown
CHANGED
@@ -44,7 +44,7 @@ This is compatible with Google Authenticator apps available for Android and iPho
|
|
44
44
|
|
45
45
|
### Generating a Base32 Secret key
|
46
46
|
|
47
|
-
ROTP.random_base32 # returns a 16 character base32 secret. Compatible with Google Authenticator
|
47
|
+
ROTP::Base32.random_base32 # returns a 16 character base32 secret. Compatible with Google Authenticator
|
48
48
|
|
49
49
|
### Google Authenticator Compatible
|
50
50
|
|
@@ -71,17 +71,29 @@ Now run the following and compare the output
|
|
71
71
|
totp = ROTP::TOTP.new("JBSWY3DPEHPK3PXP")
|
72
72
|
p "Current OTP: #{totp.now}"
|
73
73
|
|
74
|
+
### Testing
|
75
|
+
|
76
|
+
bundle install
|
77
|
+
bundle exec rspec spec/*
|
78
|
+
|
74
79
|
### Contributors
|
75
80
|
|
76
81
|
git shortlog -s -n
|
77
82
|
|
78
|
-
|
79
|
-
|
80
|
-
1 Micah Gates
|
83
|
+
37 Mark Percival
|
84
|
+
5 David Vrensk
|
81
85
|
1 Nathan Reynolds
|
86
|
+
1 Shai Rosenfeld
|
87
|
+
1 Shai Rosenfeld & Michael Brodhead
|
88
|
+
1 Michael Brodhead & Shai Rosenfeld
|
89
|
+
1 Micah Gates
|
82
90
|
|
83
91
|
### Changelog
|
84
92
|
|
93
|
+
#### 1.4.0
|
94
|
+
|
95
|
+
- Added clock drift support via 'verify_with_drift' for TOTP
|
96
|
+
|
85
97
|
####1.3.0
|
86
98
|
|
87
99
|
- Added support for Ruby 1.9.x
|
data/Rakefile
CHANGED
@@ -1,12 +1,10 @@
|
|
1
1
|
require 'bundler'
|
2
2
|
Bundler::GemHelper.install_tasks
|
3
|
-
require
|
3
|
+
require "rspec/core/rake_task"
|
4
4
|
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
test.pattern = 'test/**/test_*.rb'
|
9
|
-
test.verbose = true
|
5
|
+
RSpec::Core::RakeTask.new(:rspec) do |spec|
|
6
|
+
spec.pattern = 'spec/**/*_spec.rb'
|
7
|
+
spec.rspec_opts = ['-cfs --backtrace']
|
10
8
|
end
|
11
9
|
|
12
|
-
task :default => :
|
10
|
+
task :default => :rspec
|
data/lib/rotp/totp.rb
CHANGED
@@ -32,6 +32,16 @@ module ROTP
|
|
32
32
|
super(otp, self.at(time))
|
33
33
|
end
|
34
34
|
|
35
|
+
# Verifies the OTP passed in against the current time OTP
|
36
|
+
# and adjacent intervals up to +drift+.
|
37
|
+
# @param [String/Integer] otp the OTP to check against
|
38
|
+
# @param [Integer] drift the number of seconds that the client
|
39
|
+
# and server are allowed to drift apart
|
40
|
+
def verify_with_drift(otp, drift, time = Time.now)
|
41
|
+
drift_intervals = drift / interval
|
42
|
+
(-drift_intervals..drift_intervals).any? { |n| verify(otp, time + n * interval) }
|
43
|
+
end
|
44
|
+
|
35
45
|
# Returns the provisioning URI for the OTP
|
36
46
|
# This can then be encoded in a QR Code and used
|
37
47
|
# to provision the Google Authenticator app
|
@@ -44,8 +54,7 @@ module ROTP
|
|
44
54
|
private
|
45
55
|
|
46
56
|
def timecode(time)
|
47
|
-
|
48
|
-
i / (interval * 1000)
|
57
|
+
time.utc.to_i / interval
|
49
58
|
end
|
50
59
|
|
51
60
|
end
|
data/lib/rotp/version.rb
CHANGED
data/rotp.gemspec
CHANGED
@@ -19,4 +19,8 @@ Gem::Specification.new do |s|
|
|
19
19
|
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
20
20
|
s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
|
21
21
|
s.require_paths = ["lib"]
|
22
|
+
|
23
|
+
s.add_development_dependency('rspec')
|
24
|
+
s.add_development_dependency('timecop')
|
25
|
+
s.add_development_dependency('rake')
|
22
26
|
end
|
data/spec/base_spec.rb
CHANGED
data/spec/spec_helper.rb
CHANGED
data/spec/totp_spec.rb
CHANGED
@@ -14,4 +14,22 @@ describe ROTP::TOTP do
|
|
14
14
|
it "should verify a string" do
|
15
15
|
subject.verify("160864", @now).should be_true
|
16
16
|
end
|
17
|
+
|
18
|
+
context "with drift" do
|
19
|
+
it "should verify a number" do
|
20
|
+
subject.verify_with_drift(160864, 0, @now).should be_true
|
21
|
+
end
|
22
|
+
it "should verify a string" do
|
23
|
+
subject.verify_with_drift("160864", 0, @now).should be_true
|
24
|
+
end
|
25
|
+
it "should verify a slightly old number" do
|
26
|
+
subject.verify_with_drift(subject.at(@now - 30), 60, @now).should be_true
|
27
|
+
end
|
28
|
+
it "should verify a slightly new number" do
|
29
|
+
subject.verify_with_drift(subject.at(@now - 60), 60, @now).should be_true
|
30
|
+
end
|
31
|
+
it "should reject a number that is outside the allowed drift" do
|
32
|
+
subject.verify_with_drift(subject.at(@now - 60), 30, @now).should be_false
|
33
|
+
end
|
34
|
+
end
|
17
35
|
end
|
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rotp
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
hash:
|
4
|
+
hash: 7
|
5
5
|
prerelease:
|
6
6
|
segments:
|
7
7
|
- 1
|
8
|
-
-
|
9
|
-
-
|
10
|
-
version: 1.
|
8
|
+
- 4
|
9
|
+
- 0
|
10
|
+
version: 1.4.0
|
11
11
|
platform: ruby
|
12
12
|
authors:
|
13
13
|
- Mark Percival
|
@@ -15,9 +15,50 @@ autorequire:
|
|
15
15
|
bindir: bin
|
16
16
|
cert_chain: []
|
17
17
|
|
18
|
-
date: 2012-05-
|
19
|
-
dependencies:
|
20
|
-
|
18
|
+
date: 2012-05-20 00:00:00 Z
|
19
|
+
dependencies:
|
20
|
+
- !ruby/object:Gem::Dependency
|
21
|
+
name: rspec
|
22
|
+
prerelease: false
|
23
|
+
requirement: &id001 !ruby/object:Gem::Requirement
|
24
|
+
none: false
|
25
|
+
requirements:
|
26
|
+
- - ">="
|
27
|
+
- !ruby/object:Gem::Version
|
28
|
+
hash: 3
|
29
|
+
segments:
|
30
|
+
- 0
|
31
|
+
version: "0"
|
32
|
+
type: :development
|
33
|
+
version_requirements: *id001
|
34
|
+
- !ruby/object:Gem::Dependency
|
35
|
+
name: timecop
|
36
|
+
prerelease: false
|
37
|
+
requirement: &id002 !ruby/object:Gem::Requirement
|
38
|
+
none: false
|
39
|
+
requirements:
|
40
|
+
- - ">="
|
41
|
+
- !ruby/object:Gem::Version
|
42
|
+
hash: 3
|
43
|
+
segments:
|
44
|
+
- 0
|
45
|
+
version: "0"
|
46
|
+
type: :development
|
47
|
+
version_requirements: *id002
|
48
|
+
- !ruby/object:Gem::Dependency
|
49
|
+
name: rake
|
50
|
+
prerelease: false
|
51
|
+
requirement: &id003 !ruby/object:Gem::Requirement
|
52
|
+
none: false
|
53
|
+
requirements:
|
54
|
+
- - ">="
|
55
|
+
- !ruby/object:Gem::Version
|
56
|
+
hash: 3
|
57
|
+
segments:
|
58
|
+
- 0
|
59
|
+
version: "0"
|
60
|
+
type: :development
|
61
|
+
version_requirements: *id003
|
21
62
|
description: Works for both HOTP and TOTP, and includes QR Code provisioning
|
22
63
|
email:
|
23
64
|
- mark@markpercival.us
|