lib/app-rb/cli.rb in app-rb-0.6.0 vs lib/app-rb/cli.rb in app-rb-0.7.0
- old
+ new
@@ -1,6 +1,7 @@
require 'yaml'
+require 'openssl'
module AppRb
class Cli
def initialize(args)
@args = args
@@ -10,53 +11,128 @@
def run
if @args.count < 2
usage
exit
end
- config = Config.new(YAML.load(File.read(@args[0])))
- command = @args[1]
+ if File.exists?(@args[0])
+ config_path = @args.shift
+ end
- if AppRb::Util.compare_versions(config.tool_version, AppRb::VERSION) > 0
+ if @args[0] == "--vault" && File.exists?(@args[1])
+ @args.shift
+ @vault_file = @args.shift
+ elsif File.exists?(File.join(Dir.pwd, "vault.key"))
+ @vault_file = File.join(Dir.pwd, "vault.key")
+ else
+ @vault_file = nil
+ end
+
+ command = @args.shift
+ config = Config.new(read_yaml(config_path)) if config_path
+
+ if config && AppRb::Util.compare_versions(config.tool_version, AppRb::VERSION) > 0
puts "FATAL: need at least '#{config.tool_version}' tool version but current version is '#{AppRb::VERSION}'"
exit -1
end
- if command == "deploy" || command == "d"
+ if %w[deploy d].index(command)
Command.new(config).deploy(@args[2])
- elsif command == "status" || command == "s"
+ elsif %w[status s].index(command)
Command.new(config).status
elsif command == "redeploy"
Command.new(config).redeploy
elsif command == "clean"
Command.new(config).clean
elsif command == "stop"
Command.new(config).stop
- elsif command == "run" || command == "r"
+ elsif %w[run r].index(command)
Command.new(config).run(@args[2..-1].join(" "))
elsif command == "cd"
Command.new(config).cd
+ elsif %w[encrypt en e].index(command)
+ puts encrypt(@args.shift)
+ elsif %w[decrypt de].index(command)
+ puts decrypt(@args.shift)
else
puts "FATAL: unknown command '#{command}'"
exit -1
end
end
private
+ MARKER = "__VAULT:"
+ def read_yaml(file)
+ unvault = proc { |o|
+ if o.is_a?(Array)
+ o.map { |i| unvault.call(i) }
+ elsif o.is_a?(Hash)
+ o.map { |k, v| [k, unvault.call(v)] }.to_h
+ elsif o.is_a?(String) && o.index(MARKER) == 0
+ decrypt(o)
+ else
+ o
+ end
+ }
+ unvault.call(YAML.load(File.read(file)))
+ end
+
+ def die(msg = nil)
+ if msg
+ puts "FATAL: #{msg}"
+ else
+ puts "exit with status code -1"
+ end
+ exit -1
+ end
+
+ def bin_to_hex(s)
+ s.unpack('H*').first
+ end
+
+ def hex_to_bin(s)
+ s.scan(/../).map { |x| x.hex }.pack('c*')
+ end
+
+ def encrypt(string)
+ die "missed vault file" unless @vault_file
+ die "string encrypted yet" if string.index(MARKER) == 0
+ cipher = OpenSSL::Cipher::AES256.new :CBC
+ cipher.encrypt
+ iv = cipher.random_iv
+ cipher.key = Digest::SHA256.digest(File.read(@vault_file).strip)
+ MARKER + bin_to_hex(cipher.update(string) + cipher.final) + ":" + bin_to_hex(iv)
+ end
+
+ def decrypt(string)
+ die "missed vault file" unless @vault_file
+ die "string not encrypted" unless string.index(MARKER) == 0
+ cipher = OpenSSL::Cipher::AES256.new :CBC
+ cipher.decrypt
+ cipher.iv = hex_to_bin(string.sub(MARKER, "").split(":")[1])
+ cipher.key = Digest::SHA256.digest(File.read(@vault_file).strip)
+ cipher.update(hex_to_bin(string.sub(MARKER, "").split(":")[0])) + cipher.final
+ end
+
def usage
puts "Just deploy your apps with docker and consul. Nothing else."
puts "Version: #{AppRb::VERSION}"
puts ""
- puts " app-rb <yml> <command>"
+ puts " app-rb <yml> [options] <command>"
puts ""
- puts "Usage:"
+ puts "Options:"
+ puts " --vault <vault-file> - vault file (<pwd>/vault.key by default)"
+ puts ""
+ puts "Commands:"
puts " deploy [hash] - deploy new version of app"
puts " status - status of app"
- puts " stop - stop app"
+ puts " stop - stop app completely"
puts " run <cmd> [args] - one time command"
puts " cd - go to run node"
+ puts " encrypt <string> - encrypt script using vault-file"
+ puts " decrypt <string> - decrypt script using vault-file"
puts ""
- puts "Advanced:"
+ puts "Advanced commands:"
puts " redeploy - redeploy app"
puts " clean - stop and remove not current containers"
end
end
end