From 46816622aa679d6aadca7690f6e693e474e2cdb6 Mon Sep 17 00:00:00 2001 From: Erran Carey Date: Mon, 3 Oct 2016 13:34:47 +0100 Subject: [PATCH 1/8] Fix #207 - Define subcommands for describing/running stack tasks --- bin/convection | 60 ++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 60 insertions(+) diff --git a/bin/convection b/bin/convection index 1fd8392..5c141fb 100755 --- a/bin/convection +++ b/bin/convection @@ -63,6 +63,24 @@ module Convection puts @cloud.stacks[stack].to_json(true) end + desc 'describe-tasks [--stacks STACKS]', 'Describe tasks for a given stack' + option :stacks, :type => :array, :desc => 'A ordered space separated list of stacks to diff', default: [] + def describe_tasks + @cloud = Control::Cloud.new + @cloud.configure(File.absolute_path(options['cloudfile'], @cwd)) + + describe_stack_tasks(options[:stacks]) + end + + desc 'run-tasks [--stack STACK]', 'Run tasks for a given stack' + option :stack, :desc => 'The stack to run tasks for', :required => true + def run_tasks + @cloud = Control::Cloud.new + @cloud.configure(File.absolute_path(options['cloudfile'], @cwd)) + + run_stack_tasks(options[:stack]) + end + desc 'validate STACK', 'Validate the rendered template for STACK' def validate(stack) @cloud.configure(File.absolute_path(options['cloudfile'], @cwd)) @@ -74,6 +92,48 @@ module Convection private + def describe_stack_tasks(stacks_to_include) + @cloud.stacks.map do |stack_name, stack| + next if stacks_to_include.any? && stacks_to_include.include?(stack_name) + flattened_tasks = stack.tasks.values.flatten + next if flattened_tasks.empty? + + puts "Stack #{stack_name} (#{stack.cloud_name}) includes the following tasks:" + tasks.each_with_index do |task, index| + puts " #{index}. #{task}" + end + end + end + + def run_stack_tasks(stack_name) + stack = @cloud.stacks[stack_name] + if !stack + say_status(:task_execution_failed, 'No stacks found matching the provided input (--stack).', :red) + exit 1 + elsif stack.tasks.empty? + say_status(:task_execution_failed, "No tasks defined for the stack #{stack_name}. Define them in your Cloudfile.", :red) + exit 1 + end + + puts "The following tasks are available to execute for the stack #{stack_name} (#{stack.cloud_name}):" + tasks.each_with_index do |task, index| + puts " #{index}. #{task}" + end + choices = 0.upto(tasks.length - 1, &:to_s) + choice = ask('Which stack task (by number) would you like to execute?', limited_to: choices) + task = tasks[choice.to_i] + + say_status(:task_in_progress, "Task (#{phase}) #{task} in progress for stack #{stack_name}.", :yellow) + task.call(stack) + + if task.success? + say_status(:task_complete, "Task (#{phase}) #{task} successfully completed for stack #{stack_name}.", :green) + else + say_status(:task_failed, "Task (#{phase}) #{task} failed to complete for stack #{stack_name}.", :red) + exit 1 + end + end + def emit_events(event, *errors) if event.is_a? Model::Event if options[:'very-verbose'] || event.name == :error From 9f6dca3e84fe51702346bacdde39a4e2d9e84ce4 Mon Sep 17 00:00:00 2001 From: Erran Carey Date: Mon, 3 Oct 2016 13:36:18 +0100 Subject: [PATCH 2/8] :sweat_smile: Fix a typo in a local variable name --- bin/convection | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bin/convection b/bin/convection index 5c141fb..bb4ef64 100755 --- a/bin/convection +++ b/bin/convection @@ -99,7 +99,7 @@ module Convection next if flattened_tasks.empty? puts "Stack #{stack_name} (#{stack.cloud_name}) includes the following tasks:" - tasks.each_with_index do |task, index| + flattened_tasks.each_with_index do |task, index| puts " #{index}. #{task}" end end From f0cf7f99ca60465838349a50f08f838566f6bd5f Mon Sep 17 00:00:00 2001 From: Erran Carey Date: Mon, 3 Oct 2016 13:37:57 +0100 Subject: [PATCH 3/8] Use tasks vs. flattened_tasks consistently --- bin/convection | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/bin/convection b/bin/convection index bb4ef64..05e0142 100755 --- a/bin/convection +++ b/bin/convection @@ -95,11 +95,11 @@ module Convection def describe_stack_tasks(stacks_to_include) @cloud.stacks.map do |stack_name, stack| next if stacks_to_include.any? && stacks_to_include.include?(stack_name) - flattened_tasks = stack.tasks.values.flatten - next if flattened_tasks.empty? + tasks = stack.tasks.values.flatten + next if tasks.empty? puts "Stack #{stack_name} (#{stack.cloud_name}) includes the following tasks:" - flattened_tasks.each_with_index do |task, index| + tasks.each_with_index do |task, index| puts " #{index}. #{task}" end end From 403faf0ae018a7ac731d9da46818473fec210af5 Mon Sep 17 00:00:00 2001 From: Erran Carey Date: Mon, 3 Oct 2016 13:40:02 +0100 Subject: [PATCH 4/8] Use Stack#tasks instead a no longer existent tasks local variable --- bin/convection | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/bin/convection b/bin/convection index 05e0142..f8fe243 100755 --- a/bin/convection +++ b/bin/convection @@ -116,12 +116,12 @@ module Convection end puts "The following tasks are available to execute for the stack #{stack_name} (#{stack.cloud_name}):" - tasks.each_with_index do |task, index| + stack.tasks.each_with_index do |task, index| puts " #{index}. #{task}" end - choices = 0.upto(tasks.length - 1, &:to_s) + choices = 0.upto(stack.tasks.length - 1, &:to_s) choice = ask('Which stack task (by number) would you like to execute?', limited_to: choices) - task = tasks[choice.to_i] + task = stack.tasks[choice.to_i] say_status(:task_in_progress, "Task (#{phase}) #{task} in progress for stack #{stack_name}.", :yellow) task.call(stack) From f32402d8f94196e89454fbdf5502498a80cc5e0d Mon Sep 17 00:00:00 2001 From: Erran Carey Date: Mon, 3 Oct 2016 13:41:35 +0100 Subject: [PATCH 5/8] Fix inverted inclusion logic for stacks --- bin/convection | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bin/convection b/bin/convection index f8fe243..2874a4c 100755 --- a/bin/convection +++ b/bin/convection @@ -94,7 +94,7 @@ module Convection def describe_stack_tasks(stacks_to_include) @cloud.stacks.map do |stack_name, stack| - next if stacks_to_include.any? && stacks_to_include.include?(stack_name) + next if stacks_to_include.any? && !stacks_to_include.include?(stack_name) tasks = stack.tasks.values.flatten next if tasks.empty? From c5015670ed8082bd65293b0b61034171817c2309 Mon Sep 17 00:00:00 2001 From: Erran Carey Date: Mon, 3 Oct 2016 13:51:38 +0100 Subject: [PATCH 6/8] Flatten/uniq the stack tasks list --- bin/convection | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/bin/convection b/bin/convection index 2874a4c..477bbdd 100755 --- a/bin/convection +++ b/bin/convection @@ -95,7 +95,7 @@ module Convection def describe_stack_tasks(stacks_to_include) @cloud.stacks.map do |stack_name, stack| next if stacks_to_include.any? && !stacks_to_include.include?(stack_name) - tasks = stack.tasks.values.flatten + tasks = stack.tasks.values.flatten.uniq next if tasks.empty? puts "Stack #{stack_name} (#{stack.cloud_name}) includes the following tasks:" @@ -107,21 +107,22 @@ module Convection def run_stack_tasks(stack_name) stack = @cloud.stacks[stack_name] + tasks = stack.tasks.values.flatten.uniq if !stack say_status(:task_execution_failed, 'No stacks found matching the provided input (--stack).', :red) exit 1 - elsif stack.tasks.empty? + elsif tasks.empty? say_status(:task_execution_failed, "No tasks defined for the stack #{stack_name}. Define them in your Cloudfile.", :red) exit 1 end puts "The following tasks are available to execute for the stack #{stack_name} (#{stack.cloud_name}):" - stack.tasks.each_with_index do |task, index| + tasks.each_with_index do |task, index| puts " #{index}. #{task}" end - choices = 0.upto(stack.tasks.length - 1, &:to_s) + choices = 0.upto(tasks.length - 1, &:to_s) choice = ask('Which stack task (by number) would you like to execute?', limited_to: choices) - task = stack.tasks[choice.to_i] + task = tasks[choice.to_i] say_status(:task_in_progress, "Task (#{phase}) #{task} in progress for stack #{stack_name}.", :yellow) task.call(stack) From 296de62f49de48c7355fba4fc413073cf45adce1 Mon Sep 17 00:00:00 2001 From: Erran Carey Date: Mon, 3 Oct 2016 13:57:14 +0100 Subject: [PATCH 7/8] Do not interpolate phase into manually run task description * Ensure choices is a string array --- bin/convection | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/bin/convection b/bin/convection index 477bbdd..960ca5c 100755 --- a/bin/convection +++ b/bin/convection @@ -120,17 +120,17 @@ module Convection tasks.each_with_index do |task, index| puts " #{index}. #{task}" end - choices = 0.upto(tasks.length - 1, &:to_s) + choices = 0.upto(tasks.length - 1).map(&:to_s) choice = ask('Which stack task (by number) would you like to execute?', limited_to: choices) task = tasks[choice.to_i] - say_status(:task_in_progress, "Task (#{phase}) #{task} in progress for stack #{stack_name}.", :yellow) + say_status(:task_in_progress, "Task #{task} in progress for stack #{stack_name}.", :yellow) task.call(stack) if task.success? - say_status(:task_complete, "Task (#{phase}) #{task} successfully completed for stack #{stack_name}.", :green) + say_status(:task_complete, "Task #{task} successfully completed for stack #{stack_name}.", :green) else - say_status(:task_failed, "Task (#{phase}) #{task} failed to complete for stack #{stack_name}.", :red) + say_status(:task_failed, "Task #{task} failed to complete for stack #{stack_name}.", :red) exit 1 end end From b72d0c129b378738aadefbce1055752b65598772 Mon Sep 17 00:00:00 2001 From: Erran Carey Date: Mon, 3 Oct 2016 14:12:45 +0100 Subject: [PATCH 8/8] Update a few status messages for stack tasks --- bin/convection | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/bin/convection b/bin/convection index 960ca5c..1630466 100755 --- a/bin/convection +++ b/bin/convection @@ -109,10 +109,10 @@ module Convection stack = @cloud.stacks[stack_name] tasks = stack.tasks.values.flatten.uniq if !stack - say_status(:task_execution_failed, 'No stacks found matching the provided input (--stack).', :red) + say_status(:task_failed, 'No stacks found matching the provided input (--stack).', :red) exit 1 elsif tasks.empty? - say_status(:task_execution_failed, "No tasks defined for the stack #{stack_name}. Define them in your Cloudfile.", :red) + say_status(:task_failed, "No tasks defined for the stack #{stack_name}. Define them in your Cloudfile.", :red) exit 1 end @@ -121,7 +121,7 @@ module Convection puts " #{index}. #{task}" end choices = 0.upto(tasks.length - 1).map(&:to_s) - choice = ask('Which stack task (by number) would you like to execute?', limited_to: choices) + choice = ask('Which stack task would you like to execute? (ctrl-c to exit)', limited_to: choices) task = tasks[choice.to_i] say_status(:task_in_progress, "Task #{task} in progress for stack #{stack_name}.", :yellow)