bosh_cli 1.0.3 → 1.5.0.pre.1113
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/bosh +0 -9
- data/lib/cli.rb +69 -64
- data/lib/cli/backup_destination_path.rb +33 -0
- data/lib/cli/base_command.rb +57 -56
- data/lib/cli/blob_manager.rb +12 -12
- data/lib/cli/changeset_helper.rb +6 -7
- data/lib/cli/client/director.rb +724 -0
- data/lib/cli/command_handler.rb +6 -7
- data/lib/cli/commands/backup.rb +39 -0
- data/lib/cli/commands/biff.rb +42 -21
- data/lib/cli/commands/blob_management.rb +1 -1
- data/lib/cli/commands/cloudcheck.rb +11 -13
- data/lib/cli/commands/deployment.rb +53 -37
- data/lib/cli/commands/help.rb +3 -2
- data/lib/cli/commands/job_management.rb +67 -103
- data/lib/cli/commands/job_rename.rb +6 -8
- data/lib/cli/commands/log_management.rb +78 -55
- data/lib/cli/commands/maintenance.rb +36 -30
- data/lib/cli/commands/misc.rb +72 -51
- data/lib/cli/commands/package.rb +2 -2
- data/lib/cli/commands/property_management.rb +10 -12
- data/lib/cli/commands/release.rb +236 -133
- data/lib/cli/commands/snapshot.rb +93 -0
- data/lib/cli/commands/ssh.rb +216 -213
- data/lib/cli/commands/stemcell.rb +46 -34
- data/lib/cli/commands/task.rb +2 -2
- data/lib/cli/commands/user.rb +27 -3
- data/lib/cli/commands/vm.rb +28 -0
- data/lib/cli/commands/vms.rb +81 -23
- data/lib/cli/config.rb +6 -2
- data/lib/cli/core_ext.rb +31 -30
- data/lib/cli/deployment_helper.rb +134 -159
- data/lib/cli/deployment_manifest.rb +66 -0
- data/lib/cli/deployment_manifest_compiler.rb +0 -3
- data/lib/cli/event_log_renderer.rb +10 -10
- data/lib/cli/file_with_progress_bar.rb +52 -0
- data/lib/cli/job_builder.rb +1 -1
- data/lib/cli/job_command_args.rb +23 -0
- data/lib/cli/job_property_collection.rb +4 -7
- data/lib/cli/job_property_validator.rb +22 -12
- data/lib/cli/job_state.rb +54 -0
- data/lib/cli/line_wrap.rb +54 -0
- data/lib/cli/packaging_helper.rb +10 -10
- data/lib/cli/release.rb +18 -15
- data/lib/cli/release_builder.rb +9 -4
- data/lib/cli/release_compiler.rb +9 -9
- data/lib/cli/release_tarball.rb +3 -6
- data/lib/cli/resurrection.rb +31 -0
- data/lib/cli/runner.rb +56 -30
- data/lib/cli/stemcell.rb +25 -10
- data/lib/cli/task_log_renderer.rb +1 -1
- data/lib/cli/task_tracker.rb +10 -9
- data/lib/cli/validation.rb +3 -1
- data/lib/cli/version.rb +1 -1
- data/lib/cli/version_calc.rb +5 -18
- data/lib/cli/versions_index.rb +1 -1
- data/lib/cli/vm_state.rb +43 -0
- data/lib/cli/yaml_helper.rb +26 -35
- metadata +75 -208
- data/Rakefile +0 -56
- data/lib/cli/director.rb +0 -628
- data/spec/assets/biff/bad_gateway_config.yml +0 -28
- data/spec/assets/biff/good_simple_config.yml +0 -63
- data/spec/assets/biff/good_simple_golden_config.yml +0 -63
- data/spec/assets/biff/good_simple_template.erb +0 -69
- data/spec/assets/biff/ip_out_of_range.yml +0 -63
- data/spec/assets/biff/multiple_subnets_config.yml +0 -40
- data/spec/assets/biff/network_only_template.erb +0 -34
- data/spec/assets/biff/no_cc_config.yml +0 -27
- data/spec/assets/biff/no_range_config.yml +0 -27
- data/spec/assets/biff/no_subnet_config.yml +0 -16
- data/spec/assets/biff/ok_network_config.yml +0 -30
- data/spec/assets/biff/properties_template.erb +0 -6
- data/spec/assets/config/atmos/config/final.yml +0 -6
- data/spec/assets/config/atmos/config/private.yml +0 -4
- data/spec/assets/config/bad-providers/config/final.yml +0 -5
- data/spec/assets/config/bad-providers/config/private.yml +0 -4
- data/spec/assets/config/deprecation/config/final.yml +0 -5
- data/spec/assets/config/deprecation/config/private.yml +0 -2
- data/spec/assets/config/local/config/final.yml +0 -5
- data/spec/assets/config/local/config/private.yml +0 -1
- data/spec/assets/config/s3/config/final.yml +0 -5
- data/spec/assets/config/s3/config/private.yml +0 -5
- data/spec/assets/config/swift-hp/config/final.yml +0 -6
- data/spec/assets/config/swift-hp/config/private.yml +0 -7
- data/spec/assets/config/swift-rackspace/config/final.yml +0 -6
- data/spec/assets/config/swift-rackspace/config/private.yml +0 -6
- data/spec/assets/deployment.MF +0 -0
- data/spec/assets/plugins/bosh/cli/commands/echo.rb +0 -43
- data/spec/assets/plugins/bosh/cli/commands/ruby.rb +0 -24
- data/spec/assets/release/jobs/cacher.tgz +0 -0
- data/spec/assets/release/jobs/cacher/config/file1.conf +0 -0
- data/spec/assets/release/jobs/cacher/config/file2.conf +0 -0
- data/spec/assets/release/jobs/cacher/job.MF +0 -6
- data/spec/assets/release/jobs/cacher/monit +0 -1
- data/spec/assets/release/jobs/cleaner.tgz +0 -0
- data/spec/assets/release/jobs/cleaner/job.MF +0 -4
- data/spec/assets/release/jobs/cleaner/monit +0 -1
- data/spec/assets/release/jobs/sweeper.tgz +0 -0
- data/spec/assets/release/jobs/sweeper/config/test.conf +0 -1
- data/spec/assets/release/jobs/sweeper/job.MF +0 -5
- data/spec/assets/release/jobs/sweeper/monit +0 -1
- data/spec/assets/release/packages/mutator.tar.gz +0 -0
- data/spec/assets/release/packages/stuff.tgz +0 -0
- data/spec/assets/release/release.MF +0 -17
- data/spec/assets/release_invalid_checksum.tgz +0 -0
- data/spec/assets/release_invalid_jobs.tgz +0 -0
- data/spec/assets/release_no_name.tgz +0 -0
- data/spec/assets/release_no_version.tgz +0 -0
- data/spec/assets/stemcell/image +0 -1
- data/spec/assets/stemcell/stemcell.MF +0 -6
- data/spec/assets/stemcell_invalid_mf.tgz +0 -0
- data/spec/assets/stemcell_no_image.tgz +0 -0
- data/spec/assets/valid_release.tgz +0 -0
- data/spec/assets/valid_stemcell.tgz +0 -0
- data/spec/spec_helper.rb +0 -28
- data/spec/unit/base_command_spec.rb +0 -87
- data/spec/unit/biff_spec.rb +0 -172
- data/spec/unit/blob_manager_spec.rb +0 -288
- data/spec/unit/cache_spec.rb +0 -36
- data/spec/unit/cli_commands_spec.rb +0 -356
- data/spec/unit/config_spec.rb +0 -125
- data/spec/unit/core_ext_spec.rb +0 -81
- data/spec/unit/dependency_helper_spec.rb +0 -52
- data/spec/unit/deployment_manifest_compiler_spec.rb +0 -63
- data/spec/unit/deployment_manifest_spec.rb +0 -153
- data/spec/unit/director_spec.rb +0 -471
- data/spec/unit/director_task_spec.rb +0 -48
- data/spec/unit/event_log_renderer_spec.rb +0 -171
- data/spec/unit/hash_changeset_spec.rb +0 -73
- data/spec/unit/job_builder_spec.rb +0 -455
- data/spec/unit/job_property_collection_spec.rb +0 -111
- data/spec/unit/job_property_validator_spec.rb +0 -7
- data/spec/unit/job_rename_spec.rb +0 -200
- data/spec/unit/package_builder_spec.rb +0 -593
- data/spec/unit/release_builder_spec.rb +0 -120
- data/spec/unit/release_spec.rb +0 -173
- data/spec/unit/release_tarball_spec.rb +0 -29
- data/spec/unit/runner_spec.rb +0 -7
- data/spec/unit/ssh_spec.rb +0 -84
- data/spec/unit/stemcell_spec.rb +0 -17
- data/spec/unit/task_tracker_spec.rb +0 -131
- data/spec/unit/version_calc_spec.rb +0 -27
- data/spec/unit/versions_index_spec.rb +0 -144
data/lib/cli/commands/help.rb
CHANGED
|
@@ -78,6 +78,8 @@ module Bosh::Cli::Command
|
|
|
78
78
|
end
|
|
79
79
|
end
|
|
80
80
|
|
|
81
|
+
err("No help found for command `#{keywords.join(' ')}'. Run 'bosh help --all' to see all available BOSH commands.") if good_matches.empty?
|
|
82
|
+
|
|
81
83
|
self.class.list_commands(good_matches)
|
|
82
84
|
end
|
|
83
85
|
|
|
@@ -87,8 +89,7 @@ module Bosh::Cli::Command
|
|
|
87
89
|
|
|
88
90
|
commands.each_with_index do |command, i|
|
|
89
91
|
nl if i > 0
|
|
90
|
-
|
|
91
|
-
say("#{command.usage_with_params.columnize(70, margin).green}")
|
|
92
|
+
say("#{command.usage_with_params.columnize(70).make_green}")
|
|
92
93
|
say(command.desc.columnize(help_column_width).indent(help_indent))
|
|
93
94
|
if command.has_options?
|
|
94
95
|
say(command.options_summary.indent(help_indent))
|
|
@@ -1,125 +1,89 @@
|
|
|
1
1
|
# Copyright (c) 2009-2012 VMware, Inc.
|
|
2
|
+
require 'cli/job_state'
|
|
3
|
+
require 'cli/vm_state'
|
|
4
|
+
|
|
5
|
+
module Bosh::Cli
|
|
6
|
+
module Command
|
|
7
|
+
class JobManagement < Base
|
|
8
|
+
FORCE = 'Proceed even when there are other manifest changes'
|
|
9
|
+
|
|
10
|
+
# bosh start
|
|
11
|
+
usage 'start'
|
|
12
|
+
desc 'Start job/instance'
|
|
13
|
+
option '--force', FORCE
|
|
14
|
+
def start_job(job, index = nil)
|
|
15
|
+
change_job_state(:start, job, index)
|
|
16
|
+
end
|
|
2
17
|
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
# bosh stop
|
|
18
|
-
usage "stop"
|
|
19
|
-
desc "Stop job/instance"
|
|
20
|
-
option "--soft", "Stop process only"
|
|
21
|
-
option "--hard", "Power off VM"
|
|
22
|
-
option "--force", FORCE
|
|
23
|
-
def stop_job(job, index = nil)
|
|
24
|
-
change_job_state(:stop, job, index)
|
|
25
|
-
end
|
|
26
|
-
|
|
27
|
-
# bosh restart
|
|
28
|
-
usage "restart"
|
|
29
|
-
desc "Restart job/instance (soft stop + start)"
|
|
30
|
-
option "--force", FORCE
|
|
31
|
-
def restart_job(job, index = nil)
|
|
32
|
-
change_job_state(:restart, job, index)
|
|
33
|
-
end
|
|
34
|
-
|
|
35
|
-
# bosh recreate
|
|
36
|
-
usage "recreate"
|
|
37
|
-
desc "Recreate job/instance (hard stop + start)"
|
|
38
|
-
option "--force", FORCE
|
|
39
|
-
def recreate_job(job, index = nil)
|
|
40
|
-
change_job_state(:recreate, job, index)
|
|
41
|
-
end
|
|
18
|
+
# bosh stop
|
|
19
|
+
usage 'stop'
|
|
20
|
+
desc 'Stop job/instance'
|
|
21
|
+
option '--soft', 'Stop process only'
|
|
22
|
+
option '--hard', 'Power off VM'
|
|
23
|
+
option '--force', FORCE
|
|
24
|
+
def stop_job(job, index = nil)
|
|
25
|
+
if hard?
|
|
26
|
+
change_job_state(:detach, job, index)
|
|
27
|
+
else
|
|
28
|
+
change_job_state(:stop, job, index)
|
|
29
|
+
end
|
|
30
|
+
end
|
|
42
31
|
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
32
|
+
# bosh restart
|
|
33
|
+
usage 'restart'
|
|
34
|
+
desc 'Restart job/instance (soft stop + start)'
|
|
35
|
+
option '--force', FORCE
|
|
36
|
+
def restart_job(job, index = nil)
|
|
37
|
+
change_job_state(:restart, job, index)
|
|
38
|
+
end
|
|
47
39
|
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
40
|
+
# bosh recreate
|
|
41
|
+
usage 'recreate'
|
|
42
|
+
desc 'Recreate job/instance (hard stop + start)'
|
|
43
|
+
option '--force', FORCE
|
|
44
|
+
def recreate_job(job, index = nil)
|
|
45
|
+
change_job_state(:recreate, job, index)
|
|
51
46
|
end
|
|
52
47
|
|
|
53
|
-
|
|
54
|
-
soft = options[:soft]
|
|
55
|
-
force = options[:force]
|
|
48
|
+
private
|
|
56
49
|
|
|
57
|
-
|
|
58
|
-
|
|
50
|
+
def change_job_state(state, job, index = nil)
|
|
51
|
+
check_arguments(state, job)
|
|
52
|
+
index = valid_index_for(job, index)
|
|
53
|
+
vm_state = VmState.new(self, force?)
|
|
54
|
+
job_state = JobState.new(self, vm_state)
|
|
55
|
+
status, task_id, completion_desc =job_state.change(state, job, index)
|
|
56
|
+
task_report(status, task_id, completion_desc)
|
|
59
57
|
end
|
|
60
58
|
|
|
61
|
-
|
|
62
|
-
|
|
59
|
+
def hard?
|
|
60
|
+
options[:hard]
|
|
63
61
|
end
|
|
64
62
|
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
op_desc = nil
|
|
68
|
-
new_state = nil
|
|
69
|
-
completion_desc = nil
|
|
70
|
-
|
|
71
|
-
case operation
|
|
72
|
-
when :start
|
|
73
|
-
op_desc = "start #{job_desc}"
|
|
74
|
-
new_state = "started"
|
|
75
|
-
completion_desc = "#{job_desc.green} has been started"
|
|
76
|
-
when :stop
|
|
77
|
-
if hard
|
|
78
|
-
op_desc = "stop #{job_desc} and power off its VM(s)"
|
|
79
|
-
completion_desc = "#{job_desc.green} has been stopped, " +
|
|
80
|
-
"VM(s) powered off"
|
|
81
|
-
new_state = "detached"
|
|
82
|
-
else
|
|
83
|
-
op_desc = "stop #{job_desc}"
|
|
84
|
-
completion_desc = "#{job_desc.green} has been stopped, " +
|
|
85
|
-
"VM(s) still running"
|
|
86
|
-
new_state = "stopped"
|
|
87
|
-
end
|
|
88
|
-
when :restart
|
|
89
|
-
op_desc = "restart #{job_desc}"
|
|
90
|
-
new_state = "restart"
|
|
91
|
-
completion_desc = "#{job_desc.green} has been restarted"
|
|
92
|
-
when :recreate
|
|
93
|
-
op_desc = "recreate #{job_desc}"
|
|
94
|
-
new_state = "recreate"
|
|
95
|
-
completion_desc = "#{job_desc.green} has been recreated"
|
|
96
|
-
else
|
|
97
|
-
err("Unknown operation: `#{operation}'")
|
|
63
|
+
def soft?
|
|
64
|
+
options[:soft]
|
|
98
65
|
end
|
|
99
66
|
|
|
100
|
-
|
|
67
|
+
def force?
|
|
68
|
+
options[:force]
|
|
69
|
+
end
|
|
101
70
|
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
71
|
+
def check_arguments(operation, job)
|
|
72
|
+
auth_required
|
|
73
|
+
job_must_exist_in_deployment(job)
|
|
105
74
|
|
|
106
|
-
if
|
|
107
|
-
err(
|
|
108
|
-
"are present. Please use `--force' to override.")
|
|
75
|
+
if hard? && soft?
|
|
76
|
+
err('Cannot handle both --hard and --soft options, please choose one')
|
|
109
77
|
end
|
|
110
|
-
|
|
111
|
-
|
|
78
|
+
|
|
79
|
+
if !hard_and_soft_options_allowed?(operation) && (hard? || soft?)
|
|
80
|
+
err("--hard and --soft options only make sense for `stop' operation")
|
|
112
81
|
end
|
|
113
82
|
end
|
|
114
83
|
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
status, task_id = director.change_job_state(
|
|
119
|
-
manifest["name"], manifest_yaml, job, index, new_state)
|
|
120
|
-
|
|
121
|
-
task_report(status, task_id, completion_desc)
|
|
84
|
+
def hard_and_soft_options_allowed?(operation)
|
|
85
|
+
operation == :stop || operation == :detach
|
|
86
|
+
end
|
|
122
87
|
end
|
|
123
|
-
|
|
124
88
|
end
|
|
125
89
|
end
|
|
@@ -2,8 +2,6 @@
|
|
|
2
2
|
|
|
3
3
|
module Bosh::Cli::Command
|
|
4
4
|
class JobRename < Base
|
|
5
|
-
include Bosh::Cli::DeploymentHelper
|
|
6
|
-
|
|
7
5
|
# bosh rename
|
|
8
6
|
usage "rename job"
|
|
9
7
|
desc "Renames a job. NOTE, your deployment manifest must also be " +
|
|
@@ -12,14 +10,14 @@ module Bosh::Cli::Command
|
|
|
12
10
|
def rename(old_name, new_name)
|
|
13
11
|
auth_required
|
|
14
12
|
manifest_yaml = prepare_deployment_manifest(:yaml => true)
|
|
15
|
-
manifest =
|
|
13
|
+
manifest = Psych.load(manifest_yaml)
|
|
16
14
|
|
|
17
15
|
force = options[:force]
|
|
18
|
-
say("You are about to rename `#{old_name.
|
|
16
|
+
say("You are about to rename `#{old_name.make_green}' to `#{new_name.make_green}'")
|
|
19
17
|
|
|
20
18
|
unless confirmed?
|
|
21
19
|
nl
|
|
22
|
-
say("Job rename canceled".
|
|
20
|
+
say("Job rename canceled".make_green)
|
|
23
21
|
exit(0)
|
|
24
22
|
end
|
|
25
23
|
|
|
@@ -33,7 +31,7 @@ module Bosh::Cli::Command
|
|
|
33
31
|
|
|
34
32
|
def sanity_check_job_rename(manifest_yaml, old_name, new_name)
|
|
35
33
|
# Makes sure the new deployment manifest contains the renamed job
|
|
36
|
-
manifest =
|
|
34
|
+
manifest = Psych.load(manifest_yaml)
|
|
37
35
|
new_jobs = manifest["jobs"].map { |job| job["name"] }
|
|
38
36
|
unless new_jobs.include?(new_name)
|
|
39
37
|
err("Please update your deployment manifest to include the " +
|
|
@@ -52,7 +50,7 @@ module Bosh::Cli::Command
|
|
|
52
50
|
"`#{manifest["name"]}'")
|
|
53
51
|
end
|
|
54
52
|
|
|
55
|
-
current_manifest =
|
|
53
|
+
current_manifest = Psych.load(current_deployment["manifest"])
|
|
56
54
|
jobs = current_manifest["jobs"].map { |job| job["name"] }
|
|
57
55
|
unless jobs.include?(old_name)
|
|
58
56
|
err("Trying to rename a non existent job `#{old_name}'")
|
|
@@ -99,7 +97,7 @@ module Bosh::Cli::Command
|
|
|
99
97
|
end
|
|
100
98
|
|
|
101
99
|
# Now the manifests should be the same
|
|
102
|
-
manifest =
|
|
100
|
+
manifest = Psych.load(manifest_yaml)
|
|
103
101
|
if deployment_changed?(current_manifest.dup, manifest.dup)
|
|
104
102
|
err("You cannot have any other changes to your manifest during " +
|
|
105
103
|
"rename. Please revert the above changes and retry.")
|
|
@@ -2,78 +2,101 @@
|
|
|
2
2
|
|
|
3
3
|
module Bosh::Cli::Command
|
|
4
4
|
class LogManagement < Base
|
|
5
|
-
include Bosh::Cli::DeploymentHelper
|
|
6
|
-
|
|
7
5
|
# bosh logs
|
|
8
|
-
usage
|
|
9
|
-
desc
|
|
10
|
-
option
|
|
11
|
-
option
|
|
12
|
-
option
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
option
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
6
|
+
usage 'logs'
|
|
7
|
+
desc 'Fetch job or agent logs from a BOSH-managed VM'
|
|
8
|
+
option '--agent', 'fetch agent logs'
|
|
9
|
+
option '--job', 'fetch job logs'
|
|
10
|
+
option '--only filter1,filter2,...', Array,
|
|
11
|
+
'only fetch logs that satisfy',
|
|
12
|
+
'given filters (defined in job spec)'
|
|
13
|
+
option '--all', 'fetch all files in the job or agent log directory'
|
|
14
|
+
option '--dir destination_directory', String, 'download directory'
|
|
15
|
+
def fetch_logs(job, index = nil)
|
|
16
|
+
index = valid_index_for(job, index)
|
|
17
|
+
check_arguments(index)
|
|
18
|
+
|
|
19
|
+
resource_id = fetch_log_resource_id(index, job)
|
|
20
|
+
log_file_path = log_file_destination(index, job)
|
|
21
|
+
download_logs(log_file_path, resource_id)
|
|
22
|
+
end
|
|
20
23
|
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
+
def fetch_log_resource_id(index, job)
|
|
25
|
+
resource_id = director.fetch_logs(deployment_name, job, index, log_type, filters)
|
|
26
|
+
err('Error retrieving logs') if resource_id.nil?
|
|
24
27
|
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
err("You can't use --job and --agent together")
|
|
28
|
-
end
|
|
29
|
-
log_type = "agent"
|
|
30
|
-
else
|
|
31
|
-
log_type = "job"
|
|
32
|
-
end
|
|
33
|
-
|
|
34
|
-
if options[:only]
|
|
35
|
-
if options[:all]
|
|
36
|
-
err("You can't use --only and --all together")
|
|
37
|
-
end
|
|
38
|
-
filters = options[:only].join(",")
|
|
39
|
-
elsif options[:all]
|
|
40
|
-
filters = "all"
|
|
41
|
-
else
|
|
42
|
-
filters = nil
|
|
43
|
-
end
|
|
44
|
-
|
|
45
|
-
if options[:agent] && filters && filters != "all"
|
|
46
|
-
err("Custom filtering is not supported for agent logs")
|
|
47
|
-
end
|
|
28
|
+
resource_id
|
|
29
|
+
end
|
|
48
30
|
|
|
49
|
-
|
|
31
|
+
private
|
|
50
32
|
|
|
51
|
-
|
|
52
|
-
|
|
33
|
+
def agent_logs_wanted?
|
|
34
|
+
options[:agent]
|
|
35
|
+
end
|
|
53
36
|
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
37
|
+
def job_logs_wanted?
|
|
38
|
+
options[:job]
|
|
39
|
+
end
|
|
57
40
|
|
|
58
|
-
|
|
59
|
-
say("Downloading log bundle (#{resource_id.to_s.
|
|
41
|
+
def download_logs(log_file_path, resource_id)
|
|
42
|
+
say("Downloading log bundle (#{resource_id.to_s.make_green})...")
|
|
60
43
|
|
|
61
44
|
begin
|
|
62
|
-
time = Time.now.strftime("%Y-%m-%d@%H-%M-%S")
|
|
63
|
-
log_file = File.join(Dir.pwd, "#{job}.#{index}.#{time}.tgz")
|
|
64
|
-
|
|
65
45
|
tmp_file = director.download_resource(resource_id)
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
say("Logs saved in `#{log_file.green}'")
|
|
46
|
+
FileUtils.mv(tmp_file, log_file_path)
|
|
47
|
+
say("Logs saved in `#{log_file_path.make_green}'")
|
|
69
48
|
rescue Bosh::Cli::DirectorError => e
|
|
70
49
|
err("Unable to download logs from director: #{e}")
|
|
71
50
|
ensure
|
|
72
|
-
FileUtils.rm_rf(tmp_file) if File.exists?(tmp_file)
|
|
51
|
+
FileUtils.rm_rf(tmp_file) if tmp_file && File.exists?(tmp_file)
|
|
52
|
+
end
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
def check_arguments(index)
|
|
56
|
+
auth_required
|
|
57
|
+
no_track_unsupported
|
|
58
|
+
|
|
59
|
+
err('Job index is expected to be a positive integer') if index !~ /^\d+$/
|
|
60
|
+
|
|
61
|
+
if agent_logs_wanted? && options[:only]
|
|
62
|
+
err('Custom filtering is not supported for agent logs')
|
|
73
63
|
end
|
|
64
|
+
end
|
|
65
|
+
|
|
66
|
+
def log_type
|
|
67
|
+
err("You can't use --job and --agent together") if job_logs_wanted? && agent_logs_wanted?
|
|
74
68
|
|
|
69
|
+
if agent_logs_wanted?
|
|
70
|
+
'agent'
|
|
71
|
+
else
|
|
72
|
+
'job'
|
|
73
|
+
end
|
|
75
74
|
end
|
|
76
75
|
|
|
76
|
+
def filters
|
|
77
|
+
if options[:only]
|
|
78
|
+
err("You can't use --only and --all together") if options[:all]
|
|
79
|
+
filter = options[:only].join(',')
|
|
80
|
+
elsif options[:all]
|
|
81
|
+
filter = 'all'
|
|
82
|
+
else
|
|
83
|
+
filter = nil
|
|
84
|
+
end
|
|
85
|
+
filter
|
|
86
|
+
end
|
|
87
|
+
|
|
88
|
+
def log_file_destination(index, job)
|
|
89
|
+
time = Time.now.strftime('%Y-%m-%d@%H-%M-%S')
|
|
90
|
+
File.join(log_directory, "#{job}.#{index}.#{time}.tgz")
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
def log_directory
|
|
94
|
+
options[:dir] || Dir.pwd
|
|
95
|
+
end
|
|
96
|
+
|
|
97
|
+
def deployment_name
|
|
98
|
+
prepare_deployment_manifest['name']
|
|
99
|
+
end
|
|
77
100
|
end
|
|
78
101
|
end
|
|
79
102
|
|
|
@@ -8,8 +8,8 @@ module Bosh::Cli::Command
|
|
|
8
8
|
STEMCELLS_TO_KEEP = 2
|
|
9
9
|
|
|
10
10
|
# bosh cleanup
|
|
11
|
-
usage
|
|
12
|
-
desc
|
|
11
|
+
usage 'cleanup'
|
|
12
|
+
desc 'Cleanup releases and stemcells'
|
|
13
13
|
def cleanup
|
|
14
14
|
target_required
|
|
15
15
|
auth_required
|
|
@@ -17,16 +17,16 @@ module Bosh::Cli::Command
|
|
|
17
17
|
releases_to_keep = RELEASES_TO_KEEP
|
|
18
18
|
stemcells_to_keep = STEMCELLS_TO_KEEP
|
|
19
19
|
|
|
20
|
-
release_wording = pluralize(releases_to_keep,
|
|
21
|
-
stemcell_wording = pluralize(stemcells_to_keep,
|
|
20
|
+
release_wording = pluralize(releases_to_keep, 'latest version')
|
|
21
|
+
stemcell_wording = pluralize(stemcells_to_keep, 'latest version')
|
|
22
22
|
|
|
23
23
|
desc = <<-EOS.gsub(/^ */, "")
|
|
24
24
|
Cleanup command will attempt to delete old unused
|
|
25
25
|
release versions and stemcells from your currently
|
|
26
|
-
targeted director at #{target_name.
|
|
26
|
+
targeted director at #{target_name.make_green}.
|
|
27
27
|
|
|
28
|
-
Only #{release_wording.
|
|
29
|
-
and #{stemcell_wording.
|
|
28
|
+
Only #{release_wording.make_green} of each release
|
|
29
|
+
and #{stemcell_wording.make_green} of each stemcell will be kept.
|
|
30
30
|
|
|
31
31
|
Releases and stemcells that are in use will not be affected.
|
|
32
32
|
EOS
|
|
@@ -35,7 +35,7 @@ module Bosh::Cli::Command
|
|
|
35
35
|
say(desc)
|
|
36
36
|
nl
|
|
37
37
|
|
|
38
|
-
err(
|
|
38
|
+
err('Cleanup canceled') unless confirmed?
|
|
39
39
|
|
|
40
40
|
nl
|
|
41
41
|
cleanup_stemcells(stemcells_to_keep)
|
|
@@ -43,48 +43,54 @@ module Bosh::Cli::Command
|
|
|
43
43
|
cleanup_releases(releases_to_keep)
|
|
44
44
|
|
|
45
45
|
nl
|
|
46
|
-
say(
|
|
46
|
+
say('Cleanup complete'.make_green)
|
|
47
47
|
end
|
|
48
48
|
|
|
49
49
|
private
|
|
50
50
|
|
|
51
51
|
def cleanup_stemcells(n_to_keep)
|
|
52
52
|
stemcells_by_name = director.list_stemcells.inject({}) do |h, stemcell|
|
|
53
|
-
h[stemcell[
|
|
54
|
-
h[stemcell[
|
|
53
|
+
h[stemcell['name']] ||= []
|
|
54
|
+
h[stemcell['name']] << stemcell
|
|
55
55
|
h
|
|
56
56
|
end
|
|
57
57
|
|
|
58
58
|
delete_list = []
|
|
59
|
-
say(
|
|
59
|
+
say('Deleting old stemcells')
|
|
60
60
|
|
|
61
61
|
stemcells_by_name.each_pair do |name, stemcells|
|
|
62
62
|
stemcells.sort! do |sc1, sc2|
|
|
63
|
-
version_cmp(sc1[
|
|
63
|
+
version_cmp(sc1['version'], sc2['version'])
|
|
64
64
|
end
|
|
65
65
|
delete_list += stemcells[0...(-n_to_keep)]
|
|
66
66
|
end
|
|
67
67
|
|
|
68
68
|
if delete_list.size > 0
|
|
69
69
|
delete_list.each do |stemcell|
|
|
70
|
-
name, version = stemcell[
|
|
70
|
+
name, version = stemcell['name'], stemcell['version']
|
|
71
71
|
desc = "#{name}/#{version}"
|
|
72
72
|
perform(desc) do
|
|
73
73
|
director.delete_stemcell(name, version, :quiet => true)
|
|
74
74
|
end
|
|
75
75
|
end
|
|
76
76
|
else
|
|
77
|
-
say(
|
|
77
|
+
say(' none found'.make_yellow)
|
|
78
78
|
end
|
|
79
79
|
end
|
|
80
80
|
|
|
81
81
|
def cleanup_releases(n_to_keep)
|
|
82
82
|
delete_list = []
|
|
83
|
-
say(
|
|
83
|
+
say('Deleting old release versions')
|
|
84
84
|
|
|
85
85
|
director.list_releases.each do |release|
|
|
86
|
-
name = release[
|
|
87
|
-
versions = release[
|
|
86
|
+
name = release['name']
|
|
87
|
+
versions = if release['versions']
|
|
88
|
+
release['versions']
|
|
89
|
+
else
|
|
90
|
+
release['release_versions'].map { |release_version| release_version['version'] }
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
versions.sort! { |v1, v2| version_cmp(v1, v2) }
|
|
88
94
|
|
|
89
95
|
versions[0...(-n_to_keep)].each do |version|
|
|
90
96
|
delete_list << [name, version]
|
|
@@ -100,33 +106,33 @@ module Bosh::Cli::Command
|
|
|
100
106
|
end
|
|
101
107
|
end
|
|
102
108
|
else
|
|
103
|
-
say(
|
|
109
|
+
say(' none found'.make_yellow)
|
|
104
110
|
end
|
|
105
111
|
end
|
|
106
112
|
|
|
107
113
|
def refresh(message)
|
|
108
|
-
say("\r",
|
|
109
|
-
say(
|
|
110
|
-
say("\r#{message}",
|
|
114
|
+
say("\r", '')
|
|
115
|
+
say(' ' * 80, '')
|
|
116
|
+
say("\r#{message}", '')
|
|
111
117
|
end
|
|
112
118
|
|
|
113
119
|
def perform(desc)
|
|
114
|
-
say(" #{desc.
|
|
115
|
-
say(
|
|
120
|
+
say(" #{desc.make_yellow.ljust(40)}", '')
|
|
121
|
+
say(' IN PROGRESS...'.make_yellow, '')
|
|
116
122
|
|
|
117
123
|
status, task_id = yield
|
|
118
124
|
responses = {
|
|
119
|
-
:done =>
|
|
120
|
-
:non_trackable =>
|
|
121
|
-
:track_timeout =>
|
|
122
|
-
:error =>
|
|
125
|
+
:done => 'DELETED'.make_green,
|
|
126
|
+
:non_trackable => 'CANNOT TRACK'.make_red,
|
|
127
|
+
:track_timeout => 'TIMED OUT'.make_red,
|
|
128
|
+
:error => 'ERROR'.make_red,
|
|
123
129
|
}
|
|
124
130
|
|
|
125
|
-
refresh(" #{desc.
|
|
131
|
+
refresh(" #{desc.make_yellow.ljust(50)}#{responses[status]}\n")
|
|
126
132
|
|
|
127
133
|
if status == :error
|
|
128
134
|
result = director.get_task_result(task_id)
|
|
129
|
-
say(" #{result.to_s.
|
|
135
|
+
say(" #{result.to_s.make_red}")
|
|
130
136
|
end
|
|
131
137
|
|
|
132
138
|
status == :done
|