module CLI::Mastermind::UserInterface
Wraps methods from CLI::UI in a slightly nicer DSL @see github.com/Shopify/cli-ui
Public Instance Methods
Ask the user for some text. @see github.com/Shopify/cli-ui#free-form-text-prompts
@param question [String] the question to ask the user @param default [String] the default answer @params opts [Hash] Additional options passed to CLI::UI.ask @option opts [Boolean] :is_file (nil) Use file autocompletion (tab completion) @option opts [Boolean] :allow_empty (true) Allow the answer to be empty @return [String] the user's answer
# File lib/cli/mastermind/user_interface.rb, line 77 def ask(question, default: nil, **opts) CLI::UI.ask(question, default: default, **opts) end
Capture the output of the given command and print them in a cli-ui friendly way. This command is an ease of use wrapper around a common capture construct.
The command given can be a single string, an array of strings, or individual arguments. The command and any kwargs given are passed to IO.popen to capture output.
Optionally, a block may be passed to modify the output of the line prior to printing.
@param command [Array<String>] the command to execute @param kwargs [Hash] additional arguments to be passed into IO.popen
@yieldparam line [String] a line of output to be processed
@see IO.popen @see Open3.popen
# File lib/cli/mastermind/user_interface.rb, line 186 def capture_command_output(*command, **kwargs, &block) # Default block returns what's passed in block ||= -> line { line } IO.popen(command.flatten, **kwargs) { |io| io.each_line { |line| print block.call(line) } } end
Performs a set of actions concurrently Yields an AsyncSpinners
objects which inherits from CLI::UI::SpinGroup
. The only difference between the two is that AsyncSpinners
provides a mechanism for exfiltrating results by using await
instead of the usual add
.
@see AsyncSpinners
@yieldparam group [AsyncSpinners]
# File lib/cli/mastermind/user_interface.rb, line 42 def concurrently group = AsyncSpinners.new yield group group.wait group.results end
Ask the user a yes/no question
@see github.com/Shopify/cli-ui#interactive-prompts
@param question [String] the question to ask the user @return [Boolean] how the user answered
# File lib/cli/mastermind/user_interface.rb, line 86 def confirm(question) CLI::UI.confirm(question) end
Enables cli-ui's STDOUT Router for fancy UIs
# File lib/cli/mastermind/user_interface.rb, line 5 def enable_ui CLI::UI::StdoutRouter.enable end
Opens a CLI::UI frame with the given args
@see github.com/Shopify/cli-ui#nested-framing
# File lib/cli/mastermind/user_interface.rb, line 63 def frame(*args) return yield unless ui_enabled? CLI::UI::Frame.open(*args) { yield } end
Display an interactive list of options for the user to select. If less than 2 options would be displayed, the default value is automatically returned unless multiple:
is true
.
@param question [String] The question to ask the user @param options [Array<#to_s>,Hash<#to_s>] the options to display @param default [String] The default value for this question. Assumed to exist
within the given options.
@param opts [Hash] additional options passed into CLI::UI::Prompt.ask
. @option opts [Boolean] :multiple (false) Whether multiple selections should be made. @option opts [Boolean] :filter_ui (true) Enable option filtering @option opts [Boolean] :select_ui (true) Enable long-form option selection
@see github.com/Shopify/cli-ui#interactive-prompts
# File lib/cli/mastermind/user_interface.rb, line 104 def select(question, options:, default: options.first, **opts) default_value = nil options = case options when Array default_text = default o = options - [default] o.zip(o).to_h when Hash # Handle the "default" default. Otherwise, we expect the default # is the default value if default.is_a? Array default_text, default = default else default_text = options.invert[default] end default_text = default_text # dup so that we don't change whatever was passed in options.dup.tap { |o| o.delete(default_text) } end # Ensure all keys are strings for CLI::UI default_text = default_text.to_s options.transform_keys!(&:to_s) # work around a bug in CLI::UI with multi-select and block invocation if opts[:multiple] # Put default at the beginning so it shows in the expected order keys = [default_text] + options.keys # Put default back into the options so it can be pulled out options[default_text] = default response = Array(CLI::UI::Prompt.ask(question, options: keys, **opts)) return response.map { |resp| options[resp] } end return default unless options.count > 0 CLI::UI::Prompt.ask(question, **opts) do |handler| handler.option(default_text) { default } options.each do |(text, value)| handler.option(text) { value } end end end
Display a spinner with a title
while data is being loaded
@see github.com/Shopify/cli-ui#spinner-groups
@param title [String] the title to display @param block [#call] passed to the underlying spinner implementation. @return the result of calling the given block
# File lib/cli/mastermind/user_interface.rb, line 22 def spinner(title, &block) return yield unless ui_enabled? results = concurrently do |actions| actions.await(title, &block) end results[title] end
Uses CLI::UI.fmt
to format a string @see github.com/Shopify/cli-ui#symbolglyph-formatting
@param string [String] the string to format @return [String] the formatted string
# File lib/cli/mastermind/user_interface.rb, line 57 def stylize(string) CLI::UI.fmt string end
Titleize the given string
.
Replaces any dashes (-) or underscores (_) in the string
with spaces and then capitalizes each word.
@example titleize('foo') => 'Foo' @example titleize('foo bar') => 'Foo Bar' @example titleize('foo-bar') => 'Foo Bar' @example titleize('foo_bar') => 'Foo Bar'
@param string [String] the string to titleize.
# File lib/cli/mastermind/user_interface.rb, line 165 def titleize(string) string.gsub(/[-_-]/, ' ').split(' ').map(&:capitalize).join(' ') end
@private @return [Boolean] if the StdoutRouter is enabled
# File lib/cli/mastermind/user_interface.rb, line 11 def ui_enabled? CLI::UI::StdoutRouter.enabled? end