From 11df6c7ae14e77c3fc3e38963aba57c0bc34185d Mon Sep 17 00:00:00 2001 From: Chris Roberts Date: Tue, 26 Jan 2021 16:39:03 -0800 Subject: [PATCH] Store option parser instance and then extract flags from the result --- .../commands/serve/service/command_service.rb | 49 +++++++++++++------ 1 file changed, 33 insertions(+), 16 deletions(-) diff --git a/plugins/commands/serve/service/command_service.rb b/plugins/commands/serve/service/command_service.rb index 40552a6f9..16d015588 100644 --- a/plugins/commands/serve/service/command_service.rb +++ b/plugins/commands/serve/service/command_service.rb @@ -47,24 +47,41 @@ module VagrantPlugins if !plugin raise "Failed to locate command plugin for: #{plugin_name}" end - $stashed_opts = nil + + # Create a new anonymous class based on the command class + # so we can modify the setup behavior klass = Class.new(plugin.call) - klass.class_eval { def parse_options(opts); $stashed_opts = opts; nil; end }; - klass.new(['-h'], {}).execute - flags = [] - $stashed_opts.flags.each do |opt| - flags.append( - Hashicorp::Vagrant::Sdk::Command::Flag.new( - long_name: opt[:long_name], - description: opt[:description], - type: Hashicorp::Vagrant::Sdk::Command::Flag::Type::BOOL - )) - # Hashicorp::Vagrant::Sdk::Command::Flag.new( - # long_name: "test", short_name: "t", - # description: "does this even work?", default_value: "true", - # type: Hashicorp::Vagrant::Sdk::Command::Flag::Type::BOOL - # ) + + # Update the option parsing to store the provided options, and then return + # a nil value. The nil return will force the command to call help and not + # actually execute anything. + klass.class_eval do + def parse_options(opts) + Thread.current.thread_variable_set(:command_options, opts) + nil + end end + + # Execute the command to populate our options + klass.new([], {}).execute + + # Now we can build our list of flags + flags = Thread.current.thread_variable_get(:command_options).top.list.find_all { |o| + o.is_a?(OptionParser::Switch) + }.map { |o| + Hashicorp::Vagrant::Sdk::Command::Flag.new( + description: o.desc.join(" "), + long_name: o.long.first, + short_name: o.short.first, + type: o.is_a?(OptionParser::Switch::NoArgument) ? + Hashicorp::Vagrant::Sdk::Command::Flag::Type::BOOL : + Hashicorp::Vagrant::Sdk::Command::Flag::Type::STRING + ) + } + + # Clean our option data out of the thread + Thread.current.thread_variable_set(:command_options, nil) + Hashicorp::Vagrant::Sdk::Command::FlagsResp.new( flags: flags )