From 06aaeafa4f923530e41733eca7a31a54c0ffedac Mon Sep 17 00:00:00 2001 From: Douglas Eichelberger Date: Sat, 7 Dec 2024 08:09:15 -0800 Subject: [PATCH] Minor CLI code improvements --- Library/Homebrew/cli/args.rb | 14 +++---- Library/Homebrew/cli/error.rb | 73 ++++++++++++++++++++++++++++++++++ Library/Homebrew/cli/parser.rb | 66 +----------------------------- 3 files changed, 79 insertions(+), 74 deletions(-) create mode 100644 Library/Homebrew/cli/error.rb diff --git a/Library/Homebrew/cli/args.rb b/Library/Homebrew/cli/args.rb index 1a6b0aa618c70..f391a8726e465 100644 --- a/Library/Homebrew/cli/args.rb +++ b/Library/Homebrew/cli/args.rb @@ -161,22 +161,18 @@ def option_to_name(option) sig { returns(T::Array[String]) } def cli_args - return @cli_args if @cli_args - - @cli_args = [] - @processed_options.each do |short, long| + @cli_args ||= @processed_options.filter_map do |short, long| option = long || short switch = :"#{option_to_name(option)}?" flag = option_to_name(option).to_sym if @table[switch] == true || @table[flag] == true - @cli_args << option + option elsif @table[flag].instance_of? String - @cli_args << "#{option}=#{@table[flag]}" + "#{option}=#{@table[flag]}" elsif @table[flag].instance_of? Array - @cli_args << "#{option}=#{@table[flag].join(",")}" + "#{option}=#{@table[flag].join(",")}" end - end - @cli_args.freeze + end.freeze end sig { params(method_name: Symbol, _include_private: T::Boolean).returns(T::Boolean) } diff --git a/Library/Homebrew/cli/error.rb b/Library/Homebrew/cli/error.rb new file mode 100644 index 0000000000000..0ee539961254a --- /dev/null +++ b/Library/Homebrew/cli/error.rb @@ -0,0 +1,73 @@ +# typed: strict +# frozen_string_literal: true + +require "utils/formatter" + +module Homebrew + module CLI + class OptionConstraintError < UsageError + sig { params(arg1: String, arg2: String, missing: T::Boolean).void } + def initialize(arg1, arg2, missing: false) + message = if missing + "`#{arg2}` cannot be passed without `#{arg1}`." + else + "`#{arg1}` and `#{arg2}` should be passed together." + end + super message + end + end + + class OptionConflictError < UsageError + sig { params(args: T::Array[String]).void } + def initialize(args) + args_list = args.map { Formatter.option(_1) }.join(" and ") + super "Options #{args_list} are mutually exclusive." + end + end + + class InvalidConstraintError < UsageError + sig { params(arg1: String, arg2: String).void } + def initialize(arg1, arg2) + super "`#{arg1}` and `#{arg2}` cannot be mutually exclusive and mutually dependent simultaneously." + end + end + + class MaxNamedArgumentsError < UsageError + sig { params(maximum: Integer, types: T::Array[Symbol]).void } + def initialize(maximum, types: []) + super case maximum + when 0 + "This command does not take named arguments." + else + types << :named if types.empty? + arg_types = types.map { |type| type.to_s.tr("_", " ") } + .to_sentence two_words_connector: " or ", last_word_connector: " or " + + "This command does not take more than #{maximum} #{arg_types} #{Utils.pluralize("argument", maximum)}." + end + end + end + + class MinNamedArgumentsError < UsageError + sig { params(minimum: Integer, types: T::Array[Symbol]).void } + def initialize(minimum, types: []) + types << :named if types.empty? + arg_types = types.map { |type| type.to_s.tr("_", " ") } + .to_sentence two_words_connector: " or ", last_word_connector: " or " + + super "This command requires at least #{minimum} #{arg_types} #{Utils.pluralize("argument", minimum)}." + end + end + + class NumberOfNamedArgumentsError < UsageError + sig { params(minimum: Integer, types: T::Array[Symbol]).void } + def initialize(minimum, types: []) + types << :named if types.empty? + arg_types = types.map { |type| type.to_s.tr("_", " ") } + .to_sentence two_words_connector: " or ", last_word_connector: " or " + + super "This command requires exactly #{minimum} #{arg_types} #{Utils.pluralize("argument", minimum)}." + end + end + end +end diff --git a/Library/Homebrew/cli/parser.rb b/Library/Homebrew/cli/parser.rb index c486fb5258884..b1a9465ee481b 100644 --- a/Library/Homebrew/cli/parser.rb +++ b/Library/Homebrew/cli/parser.rb @@ -5,6 +5,7 @@ require "env_config" require "cask/config" require "cli/args" +require "cli/error" require "commands" require "optparse" require "utils/tty" @@ -734,71 +735,6 @@ def value_for_env(env) end end end - - class OptionConstraintError < UsageError - sig { params(arg1: String, arg2: String, missing: T::Boolean).void } - def initialize(arg1, arg2, missing: false) - message = if missing - "`#{arg2}` cannot be passed without `#{arg1}`." - else - "`#{arg1}` and `#{arg2}` should be passed together." - end - super message - end - end - - class OptionConflictError < UsageError - sig { params(args: T::Array[String]).void } - def initialize(args) - args_list = args.map { Formatter.option(_1) }.join(" and ") - super "Options #{args_list} are mutually exclusive." - end - end - - class InvalidConstraintError < UsageError - sig { params(arg1: String, arg2: String).void } - def initialize(arg1, arg2) - super "`#{arg1}` and `#{arg2}` cannot be mutually exclusive and mutually dependent simultaneously." - end - end - - class MaxNamedArgumentsError < UsageError - sig { params(maximum: Integer, types: T::Array[Symbol]).void } - def initialize(maximum, types: []) - super case maximum - when 0 - "This command does not take named arguments." - else - types << :named if types.empty? - arg_types = types.map { |type| type.to_s.tr("_", " ") } - .to_sentence two_words_connector: " or ", last_word_connector: " or " - - "This command does not take more than #{maximum} #{arg_types} #{Utils.pluralize("argument", maximum)}." - end - end - end - - class MinNamedArgumentsError < UsageError - sig { params(minimum: Integer, types: T::Array[Symbol]).void } - def initialize(minimum, types: []) - types << :named if types.empty? - arg_types = types.map { |type| type.to_s.tr("_", " ") } - .to_sentence two_words_connector: " or ", last_word_connector: " or " - - super "This command requires at least #{minimum} #{arg_types} #{Utils.pluralize("argument", minimum)}." - end - end - - class NumberOfNamedArgumentsError < UsageError - sig { params(minimum: Integer, types: T::Array[Symbol]).void } - def initialize(minimum, types: []) - types << :named if types.empty? - arg_types = types.map { |type| type.to_s.tr("_", " ") } - .to_sentence two_words_connector: " or ", last_word_connector: " or " - - super "This command requires exactly #{minimum} #{arg_types} #{Utils.pluralize("argument", minimum)}." - end - end end end