shh 0.0.1 → 0.0.2

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.
Files changed (4) hide show
  1. data/bin/shh +1 -1
  2. data/lib/shh/cli.rb +75 -3
  3. data/lib/shh/crypt.rb +25 -0
  4. metadata +22 -1
data/bin/shh CHANGED
@@ -2,4 +2,4 @@
2
2
 
3
3
  $:.unshift File.dirname(__FILE__)+'/../lib'
4
4
  require 'shh'
5
- Shh::Cli.execute(ARGV)
5
+ Shh::Cli.new.execute(*ARGV)
data/lib/shh/cli.rb CHANGED
@@ -1,11 +1,83 @@
1
1
  require 'rubygems'
2
+ require 'pathname2'
2
3
  require 'highline/import'
4
+ require 'shh/crypt'
5
+ require 'yaml'
3
6
 
4
7
  module Shh
5
8
  class Cli
6
- def self.execute args
7
- passphrase = ask('enter your passphrase') { |q| q.echo = false }
8
-
9
+ def execute *args
10
+ passphrase = ask('Enter your passphrase') { |q| q.echo = false }
11
+
12
+ @folder = Pathname.new('secret')
13
+ @folder.mkdir_p
14
+ @crypt = Crypt.new(passphrase)
15
+
16
+ loop do
17
+ choose do |menu|
18
+ menu.layout = :menu_only
19
+ menu.shell = true
20
+ menu.choice('list entries') { list }
21
+ menu.choice('create entry') { |command, details| create details }
22
+ menu.choice('edit entry') { |command, details| edit details }
23
+ menu.choice('view entry') { |command, details| view details }
24
+ menu.choice('quit') { exit }
25
+ end
26
+ end
27
+ end
28
+
29
+ def list
30
+ @folder.entries.each do |child|
31
+ say(child) unless ['.','..'].include?(child.to_s)
32
+ end
33
+ end
34
+
35
+ def create name=''
36
+ persist_entry check_name(name), prompt_loop({})
37
+ end
38
+
39
+ def edit name=''
40
+ name = check_name(name)
41
+ persist_entry name, prompt_loop(load_entry(name))
42
+ end
43
+
44
+ def view name=''
45
+ prompt_loop load_entry(check_name(name)), true
46
+ end
47
+
48
+ private
49
+
50
+ def check_name name
51
+ name = ask('Enter the entry name') unless name.size > 0
52
+ name
53
+ end
54
+
55
+ def load_entry name
56
+ entry = (@folder + name).open('r') {|io| @crypt.decrypt(io) }
57
+ YAML::load(entry)
58
+ end
59
+
60
+ def persist_entry name, entry
61
+ (@folder + name).open('w') {|io| @crypt.encrypt(entry.to_yaml, io) }
62
+ end
63
+
64
+ def prompt_loop hash, read_only=false
65
+ loop do
66
+ choose do |menu|
67
+ menu.layout = :menu_only
68
+ menu.shell = true
69
+ menu.choice('create key') { |command, name| hash[name] = new_value(name) } unless read_only
70
+ menu.choice('list keys') { say(hash.keys.sort.join(',')) }
71
+ menu.choice('show key') { |command, name| say(hash[name]) if hash[name] }
72
+ menu.choice('delete key') { |command, name| hash[name] = nil } unless read_only
73
+ menu.choice('quit') { return hash }
74
+ end
75
+ end
76
+ end
77
+
78
+ def new_value name
79
+ echo = (name =~ /pass/) ? false : true
80
+ ask("Enter new value for #{name}") {|q| q.echo = echo }
9
81
  end
10
82
  end
11
83
  end
data/lib/shh/crypt.rb ADDED
@@ -0,0 +1,25 @@
1
+ require 'crypt/blowfish'
2
+
3
+ module Shh
4
+ class Crypt
5
+ def initialize passphrase
6
+ @blowfish = ::Crypt::Blowfish.new(passphrase)
7
+ end
8
+
9
+ def encrypt text, out_io
10
+ in_io = StringIO.new(text)
11
+ while l = in_io.read(8) do
12
+ while l.size < 8 do l += "\0" end
13
+ out_io.print @blowfish.encrypt_block(l)
14
+ end
15
+ end
16
+
17
+ def decrypt in_io
18
+ out_io = StringIO.new
19
+ while l = in_io.read(8) do
20
+ out_io.print @blowfish.decrypt_block(l)
21
+ end
22
+ out_io.string.gsub("\0",'')
23
+ end
24
+ end
25
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: shh
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.1
4
+ version: 0.0.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Mark Ryall
@@ -32,6 +32,26 @@ dependencies:
32
32
  - !ruby/object:Gem::Version
33
33
  version: 2.1.0
34
34
  version:
35
+ - !ruby/object:Gem::Dependency
36
+ name: crypt
37
+ type: :runtime
38
+ version_requirement:
39
+ version_requirements: !ruby/object:Gem::Requirement
40
+ requirements:
41
+ - - ~>
42
+ - !ruby/object:Gem::Version
43
+ version: 1.1.4
44
+ version:
45
+ - !ruby/object:Gem::Dependency
46
+ name: pathname2
47
+ type: :runtime
48
+ version_requirement:
49
+ version_requirements: !ruby/object:Gem::Requirement
50
+ requirements:
51
+ - - ~>
52
+ - !ruby/object:Gem::Version
53
+ version: 1.6.3
54
+ version:
35
55
  description: |
36
56
  A command line utility that manages accounts and passwords as individual encypted files
37
57
 
@@ -44,6 +64,7 @@ extra_rdoc_files: []
44
64
 
45
65
  files:
46
66
  - lib/shh/cli.rb
67
+ - lib/shh/crypt.rb
47
68
  - lib/shh.rb
48
69
  - bin/shh
49
70
  - README.rdoc