leap_cli 1.5.6 → 1.6.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.
- data/bin/leap +29 -6
- data/lib/leap/platform.rb +36 -1
- data/lib/leap_cli/commands/ca.rb +97 -20
- data/lib/leap_cli/commands/compile.rb +49 -8
- data/lib/leap_cli/commands/db.rb +13 -4
- data/lib/leap_cli/commands/deploy.rb +138 -29
- data/lib/leap_cli/commands/env.rb +76 -0
- data/lib/leap_cli/commands/facts.rb +10 -3
- data/lib/leap_cli/commands/inspect.rb +2 -2
- data/lib/leap_cli/commands/list.rb +10 -10
- data/lib/leap_cli/commands/node.rb +7 -132
- data/lib/leap_cli/commands/node_init.rb +169 -0
- data/lib/leap_cli/commands/pre.rb +4 -27
- data/lib/leap_cli/commands/ssh.rb +152 -0
- data/lib/leap_cli/commands/test.rb +22 -13
- data/lib/leap_cli/commands/user.rb +12 -4
- data/lib/leap_cli/commands/vagrant.rb +4 -4
- data/lib/leap_cli/config/filter.rb +175 -0
- data/lib/leap_cli/config/manager.rb +130 -61
- data/lib/leap_cli/config/node.rb +32 -0
- data/lib/leap_cli/config/object.rb +69 -44
- data/lib/leap_cli/config/object_list.rb +44 -39
- data/lib/leap_cli/config/secrets.rb +24 -12
- data/lib/leap_cli/config/tag.rb +7 -0
- data/lib/{core_ext → leap_cli/core_ext}/boolean.rb +0 -0
- data/lib/{core_ext → leap_cli/core_ext}/hash.rb +0 -0
- data/lib/{core_ext → leap_cli/core_ext}/json.rb +0 -0
- data/lib/{core_ext → leap_cli/core_ext}/nil.rb +0 -0
- data/lib/{core_ext → leap_cli/core_ext}/string.rb +0 -0
- data/lib/leap_cli/core_ext/yaml.rb +29 -0
- data/lib/leap_cli/exceptions.rb +24 -0
- data/lib/leap_cli/leapfile.rb +60 -10
- data/lib/{lib_ext → leap_cli/lib_ext}/capistrano_connections.rb +0 -0
- data/lib/{lib_ext → leap_cli/lib_ext}/gli.rb +0 -0
- data/lib/leap_cli/log.rb +1 -1
- data/lib/leap_cli/logger.rb +18 -1
- data/lib/leap_cli/markdown_document_listener.rb +1 -1
- data/lib/leap_cli/override/json.rb +11 -0
- data/lib/leap_cli/path.rb +20 -6
- data/lib/leap_cli/remote/leap_plugin.rb +2 -2
- data/lib/leap_cli/remote/puppet_plugin.rb +1 -1
- data/lib/leap_cli/remote/rsync_plugin.rb +1 -1
- data/lib/leap_cli/remote/tasks.rb +1 -1
- data/lib/leap_cli/ssh_key.rb +63 -1
- data/lib/leap_cli/util/remote_command.rb +19 -2
- data/lib/leap_cli/util/secret.rb +1 -1
- data/lib/leap_cli/util/x509.rb +3 -2
- data/lib/leap_cli/util.rb +11 -3
- data/lib/leap_cli/version.rb +2 -2
- data/lib/leap_cli.rb +24 -14
- data/vendor/certificate_authority/lib/certificate_authority/certificate.rb +85 -29
- data/vendor/certificate_authority/lib/certificate_authority/distinguished_name.rb +5 -0
- data/vendor/certificate_authority/lib/certificate_authority/extensions.rb +406 -41
- data/vendor/certificate_authority/lib/certificate_authority/key_material.rb +0 -34
- data/vendor/certificate_authority/lib/certificate_authority/serial_number.rb +6 -0
- data/vendor/certificate_authority/lib/certificate_authority/signing_request.rb +36 -1
- metadata +25 -24
- data/lib/leap_cli/commands/shell.rb +0 -89
- data/lib/leap_cli/config/macros.rb +0 -430
- data/lib/leap_cli/constants.rb +0 -7
- data/lib/leap_cli/requirements.rb +0 -19
- data/lib/lib_ext/markdown_document_listener.rb +0 -122
data/bin/leap
CHANGED
@@ -1,7 +1,13 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
2
|
|
3
|
-
if ARGV.include?('--debug')
|
4
|
-
|
3
|
+
if ARGV.include?('--debug') || ARGV.include?('-d')
|
4
|
+
DEBUG=true
|
5
|
+
begin
|
6
|
+
require 'debugger'
|
7
|
+
rescue LoadError
|
8
|
+
end
|
9
|
+
else
|
10
|
+
DEBUG=false
|
5
11
|
end
|
6
12
|
|
7
13
|
begin
|
@@ -18,7 +24,6 @@ rescue LoadError
|
|
18
24
|
# This allows you to run the command directly while developing the gem, and also lets you
|
19
25
|
# run from anywhere (I like to link 'bin/leap' to /usr/local/bin/leap).
|
20
26
|
#
|
21
|
-
require 'rubygems'
|
22
27
|
base_dir = File.expand_path('..', File.dirname(File.symlink?(__FILE__) ? File.readlink(__FILE__) : __FILE__))
|
23
28
|
require File.join(base_dir, 'lib','leap_cli','load_paths')
|
24
29
|
require 'leap_cli'
|
@@ -27,7 +32,7 @@ end
|
|
27
32
|
require 'gli'
|
28
33
|
require 'highline'
|
29
34
|
require 'forwardable'
|
30
|
-
require 'lib_ext/gli' # our custom extensions to gli
|
35
|
+
require 'leap_cli/lib_ext/gli' # our custom extensions to gli
|
31
36
|
|
32
37
|
#
|
33
38
|
# Typically, GLI and Highline methods are loaded into the global namespace.
|
@@ -78,9 +83,27 @@ module LeapCli::Commands
|
|
78
83
|
exit(0)
|
79
84
|
end
|
80
85
|
|
86
|
+
# disable GLI error catching
|
87
|
+
ENV['GLI_DEBUG'] = "true"
|
88
|
+
def error_message(msg)
|
89
|
+
end
|
90
|
+
|
81
91
|
# load commands and run
|
82
92
|
commands_from('leap_cli/commands')
|
83
93
|
ORIGINAL_ARGV = ARGV.dup
|
84
|
-
|
85
|
-
|
94
|
+
begin
|
95
|
+
exit_status = run(ARGV)
|
96
|
+
exit(LeapCli::Util.exit_status || exit_status)
|
97
|
+
rescue StandardError => exc
|
98
|
+
if exc.respond_to? :log
|
99
|
+
exc.log
|
100
|
+
else
|
101
|
+
puts
|
102
|
+
LeapCli.log :error, "%s: %s" % [exc.class, exc.message]
|
103
|
+
puts
|
104
|
+
end
|
105
|
+
if DEBUG
|
106
|
+
raise exc
|
107
|
+
end
|
108
|
+
end
|
86
109
|
end
|
data/lib/leap/platform.rb
CHANGED
@@ -16,10 +16,25 @@ module Leap
|
|
16
16
|
attr_accessor :monitor_username
|
17
17
|
attr_accessor :reserved_usernames
|
18
18
|
|
19
|
+
attr_accessor :hiera_path
|
20
|
+
attr_accessor :files_dir
|
21
|
+
attr_accessor :leap_dir
|
22
|
+
attr_accessor :init_path
|
23
|
+
|
24
|
+
attr_accessor :default_puppet_tags
|
25
|
+
|
19
26
|
def define(&block)
|
20
|
-
# some
|
27
|
+
# some defaults:
|
21
28
|
@reserved_usernames = []
|
29
|
+
@hiera_path = '/etc/leap/hiera.yaml'
|
30
|
+
@leap_dir = '/srv/leap'
|
31
|
+
@files_dir = '/srv/leap/files'
|
32
|
+
@init_path = '/srv/leap/initialized'
|
33
|
+
@default_puppet_tags = []
|
34
|
+
|
22
35
|
self.instance_eval(&block)
|
36
|
+
|
37
|
+
@version ||= Versionomy.parse("0.0")
|
23
38
|
end
|
24
39
|
|
25
40
|
def version=(version)
|
@@ -44,10 +59,30 @@ module Leap
|
|
44
59
|
# return true if the platform version is within the specified range.
|
45
60
|
#
|
46
61
|
def version_in_range?(range)
|
62
|
+
if range.is_a? String
|
63
|
+
range = range.split('..')
|
64
|
+
end
|
47
65
|
minimum_platform_version = Versionomy.parse(range.first)
|
48
66
|
maximum_platform_version = Versionomy.parse(range.last)
|
49
67
|
@version >= minimum_platform_version && @version <= maximum_platform_version
|
50
68
|
end
|
69
|
+
|
70
|
+
def major_version
|
71
|
+
if @version.major == 0
|
72
|
+
"#{@version.major}.#{@version.minor}"
|
73
|
+
else
|
74
|
+
@version.major
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
def method_missing(method, *args)
|
79
|
+
puts
|
80
|
+
puts "WARNING:"
|
81
|
+
puts " leap_cli is out of date and does not understand `#{method}`."
|
82
|
+
puts " called from: #{caller.first}"
|
83
|
+
puts " please upgrade to a newer leap_cli"
|
84
|
+
end
|
85
|
+
|
51
86
|
end
|
52
87
|
|
53
88
|
end
|
data/lib/leap_cli/commands/ca.rb
CHANGED
@@ -1,6 +1,6 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
|
1
|
+
autoload :OpenSSL, 'openssl'
|
2
|
+
autoload :CertificateAuthority, 'certificate_authority'
|
3
|
+
autoload :Date, 'date'
|
4
4
|
require 'digest/md5'
|
5
5
|
|
6
6
|
module LeapCli; module Commands
|
@@ -36,6 +36,7 @@ module LeapCli; module Commands
|
|
36
36
|
|
37
37
|
nodes = manager.filter!(args)
|
38
38
|
nodes.each_node do |node|
|
39
|
+
warn_if_commercial_cert_will_soon_expire(node)
|
39
40
|
if !node.x509.use
|
40
41
|
remove_file!([:node_x509_key, node.name])
|
41
42
|
remove_file!([:node_x509_cert, node.name])
|
@@ -81,9 +82,19 @@ module LeapCli; module Commands
|
|
81
82
|
# http://www.redkestrel.co.uk/Articles/CSR.html
|
82
83
|
#
|
83
84
|
cert.desc "Creates a CSR for use in buying a commercial X.509 certificate."
|
84
|
-
cert.long_desc "Unless specified, the CSR is created for the provider's primary domain.
|
85
|
+
cert.long_desc "Unless specified, the CSR is created for the provider's primary domain. "+
|
86
|
+
"The properties used for this CSR come from `provider.ca.server_certificates`, "+
|
87
|
+
"but may be overridden here."
|
85
88
|
cert.command :csr do |csr|
|
86
89
|
csr.flag 'domain', :arg_name => 'DOMAIN', :desc => 'Specify what domain to create the CSR for.'
|
90
|
+
csr.flag ['organization', 'O'], :arg_name => 'ORGANIZATION', :desc => "Override default O in distinguished name."
|
91
|
+
csr.flag ['unit', 'OU'], :arg_name => 'UNIT', :desc => "Set OU in distinguished name."
|
92
|
+
csr.flag 'email', :arg_name => 'EMAIL', :desc => "Set emailAddress in distinguished name."
|
93
|
+
csr.flag ['locality', 'L'], :arg_name => 'LOCALITY', :desc => "Set L in distinguished name."
|
94
|
+
csr.flag ['state', 'ST'], :arg_name => 'STATE', :desc => "Set ST in distinguished name."
|
95
|
+
csr.flag ['country', 'C'], :arg_name => 'COUNTRY', :desc => "Set C in distinguished name."
|
96
|
+
csr.flag :bits, :arg_name => 'BITS', :desc => "Override default certificate bit length"
|
97
|
+
csr.flag :digest, :arg_name => 'DIGEST', :desc => "Override default signature digest"
|
87
98
|
csr.action do |global_options,options,args|
|
88
99
|
assert_config! 'provider.domain'
|
89
100
|
assert_config! 'provider.name'
|
@@ -97,24 +108,25 @@ module LeapCli; module Commands
|
|
97
108
|
|
98
109
|
# RSA key
|
99
110
|
keypair = CertificateAuthority::MemoryKeyMaterial.new
|
100
|
-
|
101
|
-
|
111
|
+
bit_size = (options[:bits] || server_certificates.bit_size).to_i
|
112
|
+
log :generating, "%s bit RSA key" % bit_size do
|
113
|
+
keypair.generate_key(bit_size)
|
102
114
|
write_file! [:commercial_key, domain], keypair.private_key.to_pem
|
103
115
|
end
|
104
116
|
|
105
117
|
# CSR
|
106
118
|
dn = CertificateAuthority::DistinguishedName.new
|
107
|
-
|
108
|
-
dn.
|
109
|
-
dn.
|
110
|
-
dn.
|
111
|
-
dn.
|
112
|
-
dn.
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
|
117
|
-
csr
|
119
|
+
dn.common_name = domain
|
120
|
+
dn.organization = options[:organization] || provider.name[provider.default_language]
|
121
|
+
dn.ou = options[:organizational_unit] # optional
|
122
|
+
dn.email_address = options[:email] # optional
|
123
|
+
dn.country = options[:country] || server_certificates['country'] # optional
|
124
|
+
dn.state = options[:state] || server_certificates['state'] # optional
|
125
|
+
dn.locality = options[:locality] || server_certificates['locality'] # optional
|
126
|
+
|
127
|
+
digest = options[:digest] || server_certificates.digest
|
128
|
+
log :generating, "CSR with #{digest} digest and #{print_dn(dn)}" do
|
129
|
+
csr = create_csr(dn, keypair, digest)
|
118
130
|
request = csr.to_x509_csr
|
119
131
|
write_file! [:commercial_csr, domain], csr.to_pem
|
120
132
|
end
|
@@ -191,7 +203,7 @@ module LeapCli; module Commands
|
|
191
203
|
return true
|
192
204
|
else
|
193
205
|
cert = load_certificate_file([:node_x509_cert, node.name])
|
194
|
-
if cert.not_after < months_from_yesterday(
|
206
|
+
if cert.not_after < months_from_yesterday(2)
|
195
207
|
log :updating, "cert for node '#{node.name}' because it will expire soon"
|
196
208
|
return true
|
197
209
|
end
|
@@ -208,11 +220,12 @@ module LeapCli; module Commands
|
|
208
220
|
ips << $1 if value =~ /^IP Address:(.*)$/
|
209
221
|
dns_names << $1 if value =~ /^DNS:(.*)$/
|
210
222
|
end
|
223
|
+
dns_names.sort!
|
211
224
|
if ips.first != node.ip_address
|
212
225
|
log :updating, "cert for node '#{node.name}' because ip_address has changed (from #{ips.first} to #{node.ip_address})"
|
213
226
|
return true
|
214
227
|
elsif dns_names != dns_names_for_node(node)
|
215
|
-
log :updating, "cert for node '#{node.name}' because domain name aliases have changed
|
228
|
+
log :updating, "cert for node '#{node.name}' because domain name aliases have changed\n from: #{dns_names.inspect}\n to: #{dns_names_for_node(node).inspect})"
|
216
229
|
return true
|
217
230
|
end
|
218
231
|
end
|
@@ -221,6 +234,22 @@ module LeapCli; module Commands
|
|
221
234
|
return false
|
222
235
|
end
|
223
236
|
|
237
|
+
def warn_if_commercial_cert_will_soon_expire(node)
|
238
|
+
dns_names_for_node(node).each do |domain|
|
239
|
+
if file_exists?([:commercial_cert, domain])
|
240
|
+
cert = load_certificate_file([:commercial_cert, domain])
|
241
|
+
path = Path.relative_path([:commercial_cert, domain])
|
242
|
+
if cert.not_after < Time.now.utc
|
243
|
+
log :error, "the commercial certificate '#{path}' has EXPIRED! " +
|
244
|
+
"You should renew it with `leap cert csr --domain #{domain}`."
|
245
|
+
elsif cert.not_after < months_from_yesterday(2)
|
246
|
+
log :warning, "the commercial certificate '#{path}' will expire soon. "+
|
247
|
+
"You should renew it with `leap cert csr --domain #{domain}`."
|
248
|
+
end
|
249
|
+
end
|
250
|
+
end
|
251
|
+
end
|
252
|
+
|
224
253
|
def generate_cert_for_node(node)
|
225
254
|
return if node.x509.use == false
|
226
255
|
|
@@ -261,6 +290,43 @@ module LeapCli; module Commands
|
|
261
290
|
yield cert.key_material.private_key.to_pem, cert.to_pem
|
262
291
|
end
|
263
292
|
|
293
|
+
#
|
294
|
+
# creates a CSR and returns it.
|
295
|
+
# with the correct extReq attribute so that the CA
|
296
|
+
# doens't generate certs with extensions we don't want.
|
297
|
+
#
|
298
|
+
def create_csr(dn, keypair, digest)
|
299
|
+
csr = CertificateAuthority::SigningRequest.new
|
300
|
+
csr.distinguished_name = dn
|
301
|
+
csr.key_material = keypair
|
302
|
+
csr.digest = digest
|
303
|
+
|
304
|
+
# define extensions manually (library doesn't support setting these on CSRs)
|
305
|
+
extensions = []
|
306
|
+
extensions << CertificateAuthority::Extensions::BasicConstraints.new.tap {|basic|
|
307
|
+
basic.ca = false
|
308
|
+
}
|
309
|
+
extensions << CertificateAuthority::Extensions::KeyUsage.new.tap {|keyusage|
|
310
|
+
keyusage.usage = ["digitalSignature", "keyEncipherment"]
|
311
|
+
}
|
312
|
+
extensions << CertificateAuthority::Extensions::ExtendedKeyUsage.new.tap {|extkeyusage|
|
313
|
+
extkeyusage.usage = [ "serverAuth"]
|
314
|
+
}
|
315
|
+
|
316
|
+
# convert extensions to attribute 'extReq'
|
317
|
+
# aka "Requested Extensions"
|
318
|
+
factory = OpenSSL::X509::ExtensionFactory.new
|
319
|
+
attrval = OpenSSL::ASN1::Set([OpenSSL::ASN1::Sequence(
|
320
|
+
extensions.map{|e| factory.create_ext(e.openssl_identifier, e.to_s, e.critical)}
|
321
|
+
)])
|
322
|
+
attrs = [
|
323
|
+
OpenSSL::X509::Attribute.new("extReq", attrval),
|
324
|
+
]
|
325
|
+
csr.attributes = attrs
|
326
|
+
|
327
|
+
return csr
|
328
|
+
end
|
329
|
+
|
264
330
|
def ca_root
|
265
331
|
@ca_root ||= begin
|
266
332
|
load_certificate_file(:ca_cert, :ca_key)
|
@@ -381,8 +447,10 @@ module LeapCli; module Commands
|
|
381
447
|
names = [node.domain.internal, node.domain.full]
|
382
448
|
if node['dns'] && node.dns['aliases'] && node.dns.aliases.any?
|
383
449
|
names += node.dns.aliases
|
384
|
-
names.compact!
|
385
450
|
end
|
451
|
+
names.compact!
|
452
|
+
names.sort!
|
453
|
+
names.uniq!
|
386
454
|
return names
|
387
455
|
end
|
388
456
|
|
@@ -403,6 +471,15 @@ module LeapCli; module Commands
|
|
403
471
|
cert_serial_number(domain_name).to_s(36)
|
404
472
|
end
|
405
473
|
|
474
|
+
# prints CertificateAuthority::DistinguishedName fields
|
475
|
+
def print_dn(dn)
|
476
|
+
fields = {}
|
477
|
+
[:common_name, :locality, :state, :country, :organization, :organizational_unit, :email_address].each do |attr|
|
478
|
+
fields[attr] = dn.send(attr) if dn.send(attr)
|
479
|
+
end
|
480
|
+
fields.inspect
|
481
|
+
end
|
482
|
+
|
406
483
|
##
|
407
484
|
## TIME HELPERS
|
408
485
|
##
|
@@ -3,11 +3,20 @@ module LeapCli
|
|
3
3
|
module Commands
|
4
4
|
|
5
5
|
desc "Compile generated files."
|
6
|
-
command :compile do |c|
|
6
|
+
command [:compile, :c] do |c|
|
7
7
|
c.desc 'Compiles node configuration files into hiera files used for deployment.'
|
8
|
+
c.arg_name 'ENVIRONMENT', :optional => true
|
8
9
|
c.command :all do |all|
|
9
10
|
all.action do |global_options,options,args|
|
10
|
-
|
11
|
+
environment = args.first
|
12
|
+
if !LeapCli.leapfile.environment.nil? && !environment.nil? && environment != LeapCli.leapfile.environment
|
13
|
+
bail! "You cannot specify an ENVIRONMENT argument while the environment is pinned."
|
14
|
+
end
|
15
|
+
if environment && manager.environment_names.include?(environment)
|
16
|
+
compile_hiera_files(manager.filter([environment]))
|
17
|
+
else
|
18
|
+
compile_hiera_files(manager.filter)
|
19
|
+
end
|
11
20
|
end
|
12
21
|
end
|
13
22
|
|
@@ -29,7 +38,10 @@ module LeapCli
|
|
29
38
|
|
30
39
|
# export generated files
|
31
40
|
manager.export_nodes(nodes)
|
32
|
-
|
41
|
+
# a "clean" export of secrets will also remove keys that are no longer used,
|
42
|
+
# but this should not be done if we are not examining all possible nodes.
|
43
|
+
clean_export = nodes.nil?
|
44
|
+
manager.export_secrets(clean_export)
|
33
45
|
end
|
34
46
|
|
35
47
|
def update_compiled_ssh_configs
|
@@ -50,14 +62,16 @@ module LeapCli
|
|
50
62
|
# keys, and every monitor node has a copy of the private monitor key.
|
51
63
|
#
|
52
64
|
def generate_monitor_ssh_keys
|
53
|
-
priv_key_file = :monitor_priv_key
|
54
|
-
pub_key_file = :monitor_pub_key
|
65
|
+
priv_key_file = path(:monitor_priv_key)
|
66
|
+
pub_key_file = path(:monitor_pub_key)
|
55
67
|
unless file_exists?(priv_key_file, pub_key_file)
|
56
|
-
|
68
|
+
ensure_dir(File.dirname(priv_key_file))
|
69
|
+
ensure_dir(File.dirname(pub_key_file))
|
70
|
+
cmd = %(ssh-keygen -N '' -C 'monitor' -t rsa -b 4096 -f '%s') % priv_key_file
|
57
71
|
assert_run! cmd
|
58
72
|
if file_exists?(priv_key_file, pub_key_file)
|
59
|
-
log :created,
|
60
|
-
log :created,
|
73
|
+
log :created, priv_key_file
|
74
|
+
log :created, pub_key_file
|
61
75
|
else
|
62
76
|
log :failed, 'to create monitor ssh keys'
|
63
77
|
end
|
@@ -75,6 +89,9 @@ module LeapCli
|
|
75
89
|
if keys.empty?
|
76
90
|
bail! "You must have at least one public SSH user key configured in order to proceed. See `leap help add-user`."
|
77
91
|
end
|
92
|
+
if file_exists?(path(:monitor_pub_key))
|
93
|
+
keys << path(:monitor_pub_key)
|
94
|
+
end
|
78
95
|
keys.sort.each do |keyfile|
|
79
96
|
ssh_type, ssh_key = File.read(keyfile).strip.split(" ")
|
80
97
|
buffer << ssh_type
|
@@ -87,6 +104,30 @@ module LeapCli
|
|
87
104
|
write_file!(:authorized_keys, buffer.string)
|
88
105
|
end
|
89
106
|
|
107
|
+
#
|
108
|
+
# generates the known_hosts file.
|
109
|
+
#
|
110
|
+
# we do a 'late' binding on the hostnames and ip part of the ssh pub key record in order to allow
|
111
|
+
# for the possibility that the hostnames or ip has changed in the node configuration.
|
112
|
+
#
|
113
|
+
def update_known_hosts
|
114
|
+
buffer = StringIO.new
|
115
|
+
buffer << "#\n"
|
116
|
+
buffer << "# This file is automatically generated by the command `leap`. You should NOT modify this file.\n"
|
117
|
+
buffer << "# Instead, rerun `leap node init` on whatever node is causing SSH problems.\n"
|
118
|
+
buffer << "#\n"
|
119
|
+
manager.nodes.keys.sort.each do |node_name|
|
120
|
+
node = manager.nodes[node_name]
|
121
|
+
hostnames = [node.name, node.domain.internal, node.domain.full, node.ip_address].join(',')
|
122
|
+
pub_key = read_file([:node_ssh_pub_key,node.name])
|
123
|
+
if pub_key
|
124
|
+
buffer << [hostnames, pub_key].join(' ')
|
125
|
+
buffer << "\n"
|
126
|
+
end
|
127
|
+
end
|
128
|
+
write_file!(:known_hosts, buffer.string)
|
129
|
+
end
|
130
|
+
|
90
131
|
##
|
91
132
|
## ZONE FILE
|
92
133
|
##
|
data/lib/leap_cli/commands/db.rb
CHANGED
@@ -2,14 +2,23 @@ module LeapCli; module Commands
|
|
2
2
|
|
3
3
|
desc 'Database commands.'
|
4
4
|
command :db do |db|
|
5
|
-
db.desc 'Destroy all the databases.'
|
5
|
+
db.desc 'Destroy all the databases. If present, limit to FILTER nodes.'
|
6
|
+
db.arg_name 'FILTER', :optional => true
|
6
7
|
db.command :destroy do |destroy|
|
7
8
|
destroy.action do |global_options,options,args|
|
8
9
|
say 'You are about to permanently destroy all database data.'
|
9
10
|
return unless agree("Continue? ")
|
10
|
-
nodes = manager.
|
11
|
-
|
12
|
-
|
11
|
+
nodes = manager.filter(args)
|
12
|
+
if nodes.any?
|
13
|
+
nodes = nodes[:services => 'couchdb']
|
14
|
+
end
|
15
|
+
if nodes.any?
|
16
|
+
ssh_connect(nodes, connect_options(options)) do |ssh|
|
17
|
+
ssh.run('/etc/init.d/bigcouch stop && test ! -z "$(ls /opt/bigcouch/var/lib/ 2> /dev/null)" && rm -r /opt/bigcouch/var/lib/* && echo "db destroyed" || echo "db already destroyed"')
|
18
|
+
ssh.run('grep ^seq_file /etc/leap/tapicero.yaml | cut -f2 -d\" | xargs rm -v')
|
19
|
+
end
|
20
|
+
else
|
21
|
+
say 'No nodes'
|
13
22
|
end
|
14
23
|
end
|
15
24
|
end
|