tfa 0.0.3 → 0.0.4
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/lib/tfa/add_command.rb +1 -4
- data/lib/tfa/console.rb +9 -10
- data/lib/tfa/show_command.rb +2 -4
- data/lib/tfa/storage.rb +33 -0
- data/lib/tfa/totp_command.rb +15 -5
- data/lib/tfa/usage_command.rb +1 -0
- data/lib/tfa/version.rb +1 -1
- data/lib/tfa.rb +1 -0
- data/spec/lib/show_command_spec.rb +17 -7
- data/spec/lib/totp_command_spec.rb +22 -8
- metadata +2 -1
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 414adc245dc71f49bbb95a5458410235771fe475
|
4
|
+
data.tar.gz: 0e6000d5e9a261ab11281be9927e0038d6de2af2
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 5645d6a5f42cebf8923148d85fc5be2b20e7f26666cc3075972d8ff4ce93ec66ff647b5c6544fb7dd6ed5ce3410cf0bc5879b48f40b44ceb0976dd6d7019fff9
|
7
|
+
data.tar.gz: 111d469cf45c8a343fd451b3c890f1b14d2c79533ec5be96a93ee5a31ed042a5d54f07ec1446bc3e2304317def1a1c7ab649fa609aa3c26a4c6a7b374846bf38
|
data/lib/tfa/add_command.rb
CHANGED
data/lib/tfa/console.rb
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
module TFA
|
2
2
|
class Console
|
3
3
|
def initialize(filename = "tfa")
|
4
|
-
@storage =
|
4
|
+
@storage = Storage.new(filename)
|
5
5
|
end
|
6
6
|
|
7
7
|
def run(arguments)
|
@@ -12,15 +12,14 @@ module TFA
|
|
12
12
|
private
|
13
13
|
|
14
14
|
def command_for(command_name)
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
UsageCommand.new(@storage)
|
15
|
+
registry[command_name].call
|
16
|
+
end
|
17
|
+
|
18
|
+
def registry
|
19
|
+
Hash.new { |x, y| lambda { UsageCommand.new(@storage) } }.tap do |commands|
|
20
|
+
commands['add'] = lambda { AddCommand.new(@storage) }
|
21
|
+
commands['show'] = lambda { ShowCommand.new(@storage) }
|
22
|
+
commands['totp'] = lambda { TotpCommand.new(@storage) }
|
24
23
|
end
|
25
24
|
end
|
26
25
|
end
|
data/lib/tfa/show_command.rb
CHANGED
data/lib/tfa/storage.rb
ADDED
@@ -0,0 +1,33 @@
|
|
1
|
+
module TFA
|
2
|
+
class Storage
|
3
|
+
def initialize(filename)
|
4
|
+
@storage = PStore.new(File.join(Dir.home, ".#{filename}.pstore"))
|
5
|
+
end
|
6
|
+
|
7
|
+
def all_secrets
|
8
|
+
open_readonly do |storage|
|
9
|
+
storage.roots.map { |key| { key => storage[key] } }
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
def secret_for(key)
|
14
|
+
open_readonly do |storage|
|
15
|
+
storage[key]
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
def save(key, value)
|
20
|
+
@storage.transaction do
|
21
|
+
@storage[key] = value
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
private
|
26
|
+
|
27
|
+
def open_readonly
|
28
|
+
@storage.transaction(true) do
|
29
|
+
yield @storage
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
data/lib/tfa/totp_command.rb
CHANGED
@@ -5,16 +5,26 @@ module TFA
|
|
5
5
|
end
|
6
6
|
|
7
7
|
def run(arguments)
|
8
|
-
|
9
|
-
|
8
|
+
return password_for(secret_for(arguments.first)) if arguments.any?
|
9
|
+
all_passwords
|
10
10
|
end
|
11
11
|
|
12
12
|
private
|
13
13
|
|
14
|
-
def
|
15
|
-
|
16
|
-
|
14
|
+
def password_for(secret)
|
15
|
+
::ROTP::TOTP.new(secret).now
|
16
|
+
end
|
17
|
+
|
18
|
+
def all_passwords
|
19
|
+
secrets = @storage.all_secrets
|
20
|
+
secrets.each do |hash|
|
21
|
+
hash[hash.keys.first] = password_for(hash[hash.keys.first])
|
17
22
|
end
|
23
|
+
secrets
|
24
|
+
end
|
25
|
+
|
26
|
+
def secret_for(key)
|
27
|
+
@storage.secret_for(key)
|
18
28
|
end
|
19
29
|
end
|
20
30
|
end
|
data/lib/tfa/usage_command.rb
CHANGED
data/lib/tfa/version.rb
CHANGED
data/lib/tfa.rb
CHANGED
@@ -1,16 +1,26 @@
|
|
1
1
|
module TFA
|
2
2
|
describe ShowCommand do
|
3
3
|
subject { ShowCommand.new(storage) }
|
4
|
-
let(:storage) {
|
4
|
+
let(:storage) { Storage.new(Tempfile.new('blah').path) }
|
5
5
|
|
6
|
-
|
7
|
-
secret
|
8
|
-
|
9
|
-
|
6
|
+
describe "#run" do
|
7
|
+
context "when looking up the secret for a specific key" do
|
8
|
+
it "retrieves the secret associated with the key given" do
|
9
|
+
secret = SecureRandom.uuid
|
10
|
+
storage.save('production', secret)
|
11
|
+
result = subject.run(['production'])
|
12
|
+
expect(result).to eql(secret)
|
13
|
+
end
|
10
14
|
end
|
11
15
|
|
12
|
-
|
13
|
-
|
16
|
+
context "when a specific name is not given" do
|
17
|
+
it "returns all the secrets" do
|
18
|
+
storage.save('development', "1")
|
19
|
+
storage.save('staging', "2")
|
20
|
+
storage.save('production', "3")
|
21
|
+
expect(subject.run([])).to eql([{"development" => "1"}, { "staging" => "2" }, { "production" => "3" }])
|
22
|
+
end
|
23
|
+
end
|
14
24
|
end
|
15
25
|
end
|
16
26
|
end
|
@@ -2,18 +2,32 @@ module TFA
|
|
2
2
|
describe TotpCommand do
|
3
3
|
subject { TotpCommand.new(storage) }
|
4
4
|
let(:secret) { ::ROTP::Base32.random_base32 }
|
5
|
-
let(:storage) {
|
5
|
+
let(:storage) { Storage.new(Tempfile.new('test').path) }
|
6
6
|
|
7
|
-
|
8
|
-
|
9
|
-
storage['development'] = secret
|
10
|
-
end
|
7
|
+
def code_for(secret)
|
8
|
+
::ROTP::TOTP.new(secret).now
|
11
9
|
end
|
12
10
|
|
13
11
|
describe "#run" do
|
14
|
-
|
15
|
-
|
16
|
-
|
12
|
+
context "when a single key is given" do
|
13
|
+
it "returns a time based one time password for the authentication secret given" do
|
14
|
+
storage.save('development', secret)
|
15
|
+
expect(subject.run(["development"])).to eql(code_for(secret))
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
context "when no arguments are given" do
|
20
|
+
let(:development_secret) { ::ROTP::Base32.random_base32 }
|
21
|
+
let(:staging_secret) { ::ROTP::Base32.random_base32 }
|
22
|
+
|
23
|
+
it "returns the one time password for all keys" do
|
24
|
+
storage.save('development', development_secret)
|
25
|
+
storage.save('staging', staging_secret)
|
26
|
+
expect(subject.run([])).to eql([
|
27
|
+
{ 'development' => code_for(development_secret) },
|
28
|
+
{ 'staging' => code_for(staging_secret) }
|
29
|
+
])
|
30
|
+
end
|
17
31
|
end
|
18
32
|
end
|
19
33
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: tfa
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- mo khan
|
@@ -86,6 +86,7 @@ files:
|
|
86
86
|
- lib/tfa/add_command.rb
|
87
87
|
- lib/tfa/console.rb
|
88
88
|
- lib/tfa/show_command.rb
|
89
|
+
- lib/tfa/storage.rb
|
89
90
|
- lib/tfa/totp_command.rb
|
90
91
|
- lib/tfa/usage_command.rb
|
91
92
|
- lib/tfa/version.rb
|