From 3483ee72d5cb5f3cadbab06a6f13c7c859125f9d Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Sun, 10 Jul 2022 15:24:14 +0200 Subject: [PATCH 01/25] add DSL to generate completions --- Library/Homebrew/formula.rb | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 17488e0ed1..89c2252154 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1625,6 +1625,21 @@ class Formula end private :extract_macho_slice_from + def generate_completions(base_name = name, shells = [:bash, :zsh, :fish], binary = bin/base_name, cmd = "completion", shell_as_flag = false) + completion_script_path_map = { + :bash => bash_completion/base_name, + :zsh => zsh_completion/"_#{base_name}", + :fish => fish_completion/"#{base_name}.fish", + } + + shells.each do |shell| + script_path = completion_script_path_map[shell] + shell_parameter = shell_as_flag ? "--#{shell.to_s}" : shell.to_s + script_path.dirname.mkpath + script_path.write Utils.safe_popen_read(binary, cmd, shell_parameter) + end + end + # an array of all core {Formula} names # @private def self.core_names From 1dcfeb5516a91dd4d9eedf66241d252707711c80 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Sun, 10 Jul 2022 15:45:07 +0200 Subject: [PATCH 02/25] fix style --- Library/Homebrew/formula.rb | 14 +++++++++----- 1 file changed, 9 insertions(+), 5 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 89c2252154..2fcb158d3c 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1625,16 +1625,20 @@ class Formula end private :extract_macho_slice_from - def generate_completions(base_name = name, shells = [:bash, :zsh, :fish], binary = bin/base_name, cmd = "completion", shell_as_flag = false) + def generate_completions(base_name = name, + shells = [:bash, :zsh, :fish], + binary = bin/base_name, + cmd = "completion", + shell_as_flag: false) completion_script_path_map = { - :bash => bash_completion/base_name, - :zsh => zsh_completion/"_#{base_name}", - :fish => fish_completion/"#{base_name}.fish", + bash: bash_completion/base_name, + zsh: zsh_completion/"_#{base_name}", + fish: fish_completion/"#{base_name}.fish", } shells.each do |shell| script_path = completion_script_path_map[shell] - shell_parameter = shell_as_flag ? "--#{shell.to_s}" : shell.to_s + shell_parameter = shell_as_flag ? "--#{shell}" : shell.to_s script_path.dirname.mkpath script_path.write Utils.safe_popen_read(binary, cmd, shell_parameter) end From 665e68a82fb8b6479633592a07fb68e066b6b05f Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Mon, 11 Jul 2022 15:08:44 +0200 Subject: [PATCH 03/25] switch to named args --- Library/Homebrew/formula.rb | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 2fcb158d3c..2cf1f0684d 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1625,10 +1625,10 @@ class Formula end private :extract_macho_slice_from - def generate_completions(base_name = name, - shells = [:bash, :zsh, :fish], - binary = bin/base_name, - cmd = "completion", + def generate_completions(base_name: name, + shells: [:bash, :zsh, :fish], + binary: bin/base_name, + cmd: "completion", shell_as_flag: false) completion_script_path_map = { bash: bash_completion/base_name, From e5f2ddf012ba22636ef97a3d19813b6f085cc9ba Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Mon, 11 Jul 2022 15:21:57 +0200 Subject: [PATCH 04/25] add typecheck --- Library/Homebrew/formula.rb | 3 +++ 1 file changed, 3 insertions(+) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 2cf1f0684d..5817143e67 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1625,6 +1625,9 @@ class Formula end private :extract_macho_slice_from + sig { + params(base_name: String, shells: T::Array[Symbol], binary: Pathname, cmd: String, shell_as_flag: T::Boolean).void + } def generate_completions(base_name: name, shells: [:bash, :zsh, :fish], binary: bin/base_name, From ad5a1a81383aeb02b7983fcd554846b4c92b3379 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Mon, 11 Jul 2022 15:35:48 +0200 Subject: [PATCH 05/25] add docs --- Library/Homebrew/formula.rb | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 5817143e67..6353483f21 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1625,6 +1625,15 @@ class Formula end private :extract_macho_slice_from + # Generate shell completions for a formula for bash, zsh, and fish, using the formula's binary. + # + # @param base_name [String] the base name of the generated completion script. Defaults to the formula name. + # @param shells [Array] the shells to generate completion scripts for. Defaults to `[:bash, :zsh, :fish]`. + # @param binary [Pathname] the binary to use for generating the completion scripts. Defaults to the binary with the + # name of the formula. + # @param cmd [String] the command to pass to the `binary`. Defaults to 'completion'. + # @param shell_as_flag [Boolean] specify if `shells` should each be passed as flags to the `binary`. + # Defaults to `false`. sig { params(base_name: String, shells: T::Array[Symbol], binary: Pathname, cmd: String, shell_as_flag: T::Boolean).void } From 32b68838f9e5518d5b5dff64f183e942744c63cc Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Wed, 13 Jul 2022 14:11:17 +0200 Subject: [PATCH 06/25] switch to more flexible shell_prefix arg --- Library/Homebrew/formula.rb | 14 +++++++++++--- 1 file changed, 11 insertions(+), 3 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 6353483f21..4de200ddeb 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1635,13 +1635,14 @@ class Formula # @param shell_as_flag [Boolean] specify if `shells` should each be passed as flags to the `binary`. # Defaults to `false`. sig { - params(base_name: String, shells: T::Array[Symbol], binary: Pathname, cmd: String, shell_as_flag: T::Boolean).void + params(base_name: String, shells: T::Array[Symbol], binary: Pathname, cmd: String, + shell_prefix: T.nilable(T.any(Symbol, String))).void } def generate_completions(base_name: name, shells: [:bash, :zsh, :fish], binary: bin/base_name, cmd: "completion", - shell_as_flag: false) + shell_prefix: nil) completion_script_path_map = { bash: bash_completion/base_name, zsh: zsh_completion/"_#{base_name}", @@ -1650,7 +1651,14 @@ class Formula shells.each do |shell| script_path = completion_script_path_map[shell] - shell_parameter = shell_as_flag ? "--#{shell}" : shell.to_s + shell_parameter = if shell_prefix.nil? + shell.to_s + elsif shell_prefix == :flag + "--#{shell}" + else + "#{shell_prefix}#{shell}" + end + script_path.dirname.mkpath script_path.write Utils.safe_popen_read(binary, cmd, shell_parameter) end From 9528c6a8ac21396be7506ba090a979366e9e7344 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Sun, 24 Jul 2022 22:50:14 +0200 Subject: [PATCH 07/25] always set SHELL env variable --- Library/Homebrew/formula.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 4de200ddeb..760600282a 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1660,7 +1660,7 @@ class Formula end script_path.dirname.mkpath - script_path.write Utils.safe_popen_read(binary, cmd, shell_parameter) + script_path.write Utils.safe_popen_read({ "SHELL" => shell }, binary, cmd, shell_parameter) end end From 92bccd2074e7278e3bc71cd2f4c4c92b4b103875 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Sun, 24 Jul 2022 22:54:28 +0200 Subject: [PATCH 08/25] apply naming suggestions --- Library/Homebrew/formula.rb | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 760600282a..1cc3052df0 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1638,11 +1638,11 @@ class Formula params(base_name: String, shells: T::Array[Symbol], binary: Pathname, cmd: String, shell_prefix: T.nilable(T.any(Symbol, String))).void } - def generate_completions(base_name: name, - shells: [:bash, :zsh, :fish], - binary: bin/base_name, - cmd: "completion", - shell_prefix: nil) + def generate_completions_from_executable(base_name: name, + shells: [:bash, :zsh, :fish], + executable: bin/base_name, + cmd: "completion", + shell_parameter: nil) completion_script_path_map = { bash: bash_completion/base_name, zsh: zsh_completion/"_#{base_name}", @@ -1651,16 +1651,16 @@ class Formula shells.each do |shell| script_path = completion_script_path_map[shell] - shell_parameter = if shell_prefix.nil? + shell_parameter = if shell_parameter.nil? shell.to_s - elsif shell_prefix == :flag + elsif shell_parameter == :flag "--#{shell}" else - "#{shell_prefix}#{shell}" + "#{shell_parameter}#{shell}" end script_path.dirname.mkpath - script_path.write Utils.safe_popen_read({ "SHELL" => shell }, binary, cmd, shell_parameter) + script_path.write Utils.safe_popen_read({ "SHELL" => shell }, executable, cmd, shell_parameter) end end From 1c059e1da0b80ccff1c81de4610cbf68efdf87a0 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Sun, 24 Jul 2022 23:03:28 +0200 Subject: [PATCH 09/25] extend shell_parameter argument --- Library/Homebrew/formula.rb | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 1cc3052df0..876ca764f5 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1642,7 +1642,7 @@ class Formula shells: [:bash, :zsh, :fish], executable: bin/base_name, cmd: "completion", - shell_parameter: nil) + shell_parameter_format: nil) completion_script_path_map = { bash: bash_completion/base_name, zsh: zsh_completion/"_#{base_name}", @@ -1651,12 +1651,16 @@ class Formula shells.each do |shell| script_path = completion_script_path_map[shell] - shell_parameter = if shell_parameter.nil? + shell_parameter = if shell_parameter_format.nil? shell.to_s - elsif shell_parameter == :flag + elsif shell_parameter_format == :flag "--#{shell}" + elsif shell_parameter_format == :arg + "--shell=#{shell}" + elsif shell_parameter_format == :none + nil else - "#{shell_parameter}#{shell}" + "#{shell_parameter_format}#{shell}" end script_path.dirname.mkpath From dff3fc9d2f9db62ec555e75b7902e699a828c6a4 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Wed, 27 Jul 2022 16:58:29 +0200 Subject: [PATCH 10/25] fix symbol in SHELL env --- Library/Homebrew/formula.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 876ca764f5..f54935939f 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1664,7 +1664,7 @@ class Formula end script_path.dirname.mkpath - script_path.write Utils.safe_popen_read({ "SHELL" => shell }, executable, cmd, shell_parameter) + script_path.write Utils.safe_popen_read({ "SHELL" => shell.to_s }, executable, cmd, shell_parameter) end end From b2d94dc897f25083cddb994c9b981834d9df6fd0 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Sun, 31 Jul 2022 21:01:42 +0200 Subject: [PATCH 11/25] update arg names in docs and signature --- Library/Homebrew/formula.rb | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index f54935939f..fd2ccb0a65 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1625,18 +1625,19 @@ class Formula end private :extract_macho_slice_from - # Generate shell completions for a formula for bash, zsh, and fish, using the formula's binary. + # Generate shell completions for a formula for bash, zsh, and fish, using the formula's executable. # # @param base_name [String] the base name of the generated completion script. Defaults to the formula name. # @param shells [Array] the shells to generate completion scripts for. Defaults to `[:bash, :zsh, :fish]`. - # @param binary [Pathname] the binary to use for generating the completion scripts. Defaults to the binary with the - # name of the formula. + # @param executable [Pathname] the executable to use for generating the completion scripts. Defaults to the + # executable with the name of the formula. # @param cmd [String] the command to pass to the `binary`. Defaults to 'completion'. - # @param shell_as_flag [Boolean] specify if `shells` should each be passed as flags to the `binary`. - # Defaults to `false`. + # @param shell_parameter_format [String]/[Symbol] specify how `shells` should each be passed + # to the `executable`. Takes either a String representing a prefix, or one of [:flag, :arg, :none]. + # Defaults to plainly passing the shell. sig { - params(base_name: String, shells: T::Array[Symbol], binary: Pathname, cmd: String, - shell_prefix: T.nilable(T.any(Symbol, String))).void + params(base_name: String, shells: T::Array[Symbol], executable: Pathname, cmd: String, + shell_parameter_format: T.nilable(T.any(Symbol, String))).void } def generate_completions_from_executable(base_name: name, shells: [:bash, :zsh, :fish], From b792a4f645b613ba7e9337777dabbfd92dbfc3a5 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Sun, 31 Jul 2022 21:48:02 +0200 Subject: [PATCH 12/25] fix TypeError --- Library/Homebrew/formula.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index fd2ccb0a65..cf1ad0deb1 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1659,7 +1659,7 @@ class Formula elsif shell_parameter_format == :arg "--shell=#{shell}" elsif shell_parameter_format == :none - nil + "" else "#{shell_parameter_format}#{shell}" end From e4486019641ab43268d473ed4c8ec2e95f49f483 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Wed, 10 Aug 2022 15:08:17 +0200 Subject: [PATCH 13/25] rename `cmd` to `subcmd` --- Library/Homebrew/formula.rb | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index cf1ad0deb1..44ca74df61 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1631,18 +1631,18 @@ class Formula # @param shells [Array] the shells to generate completion scripts for. Defaults to `[:bash, :zsh, :fish]`. # @param executable [Pathname] the executable to use for generating the completion scripts. Defaults to the # executable with the name of the formula. - # @param cmd [String] the command to pass to the `binary`. Defaults to 'completion'. + # @param subcmd [String] the command to pass to the `executable`. Defaults to 'completion'. # @param shell_parameter_format [String]/[Symbol] specify how `shells` should each be passed # to the `executable`. Takes either a String representing a prefix, or one of [:flag, :arg, :none]. # Defaults to plainly passing the shell. sig { - params(base_name: String, shells: T::Array[Symbol], executable: Pathname, cmd: String, + params(base_name: String, shells: T::Array[Symbol], executable: Pathname, subcmd: String, shell_parameter_format: T.nilable(T.any(Symbol, String))).void } def generate_completions_from_executable(base_name: name, shells: [:bash, :zsh, :fish], executable: bin/base_name, - cmd: "completion", + subcmd: "completion", shell_parameter_format: nil) completion_script_path_map = { bash: bash_completion/base_name, @@ -1665,7 +1665,7 @@ class Formula end script_path.dirname.mkpath - script_path.write Utils.safe_popen_read({ "SHELL" => shell.to_s }, executable, cmd, shell_parameter) + script_path.write Utils.safe_popen_read({ "SHELL" => shell.to_s }, executable, subcmd, shell_parameter) end end From 55a26ce4cc0045116aa5d397b55d487e8118b7db Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Wed, 10 Aug 2022 15:11:06 +0200 Subject: [PATCH 14/25] make `executable` and `subcmd` mandatory args --- Library/Homebrew/formula.rb | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 44ca74df61..4a25fa042e 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1627,22 +1627,21 @@ class Formula # Generate shell completions for a formula for bash, zsh, and fish, using the formula's executable. # + # @param executable [Pathname] the executable to use for generating the completion scripts. + # @param subcmd [String] the command to pass to the `executable`. # @param base_name [String] the base name of the generated completion script. Defaults to the formula name. # @param shells [Array] the shells to generate completion scripts for. Defaults to `[:bash, :zsh, :fish]`. - # @param executable [Pathname] the executable to use for generating the completion scripts. Defaults to the - # executable with the name of the formula. - # @param subcmd [String] the command to pass to the `executable`. Defaults to 'completion'. # @param shell_parameter_format [String]/[Symbol] specify how `shells` should each be passed # to the `executable`. Takes either a String representing a prefix, or one of [:flag, :arg, :none]. # Defaults to plainly passing the shell. sig { - params(base_name: String, shells: T::Array[Symbol], executable: Pathname, subcmd: String, + params(executable: Pathname, subcmd: String, base_name: String, shells: T::Array[Symbol], shell_parameter_format: T.nilable(T.any(Symbol, String))).void } - def generate_completions_from_executable(base_name: name, + def generate_completions_from_executable(executable, + subcmd, + base_name: name, shells: [:bash, :zsh, :fish], - executable: bin/base_name, - subcmd: "completion", shell_parameter_format: nil) completion_script_path_map = { bash: bash_completion/base_name, From 08bf179f7ac68ea6a112c1f8aebe9f6e440f8239 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Wed, 10 Aug 2022 15:14:06 +0200 Subject: [PATCH 15/25] fix documentation --- Library/Homebrew/formula.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 4a25fa042e..a50da9a0f4 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1628,10 +1628,10 @@ class Formula # Generate shell completions for a formula for bash, zsh, and fish, using the formula's executable. # # @param executable [Pathname] the executable to use for generating the completion scripts. - # @param subcmd [String] the command to pass to the `executable`. + # @param subcmd [String] the subcommand to pass to the `executable`. # @param base_name [String] the base name of the generated completion script. Defaults to the formula name. # @param shells [Array] the shells to generate completion scripts for. Defaults to `[:bash, :zsh, :fish]`. - # @param shell_parameter_format [String]/[Symbol] specify how `shells` should each be passed + # @param shell_parameter_format [String, Symbol] specify how `shells` should each be passed # to the `executable`. Takes either a String representing a prefix, or one of [:flag, :arg, :none]. # Defaults to plainly passing the shell. sig { From 3786887146e8bf5bed920947d660be5c38d913e8 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Wed, 10 Aug 2022 15:40:54 +0200 Subject: [PATCH 16/25] add examples --- Library/Homebrew/formula.rb | 42 +++++++++++++++++++++++++++++++++++++ 1 file changed, 42 insertions(+) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index a50da9a0f4..6cfe0e44ba 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1634,6 +1634,48 @@ class Formula # @param shell_parameter_format [String, Symbol] specify how `shells` should each be passed # to the `executable`. Takes either a String representing a prefix, or one of [:flag, :arg, :none]. # Defaults to plainly passing the shell. + # + # @example Using default values for optional arguments + # generate_completions_from_executable(bin/"foo", "completions") + # translates to + # + # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", "completions", "bash") + # + # (zsh_completion/"_foo").write Utils.safe_popen_read({ "SHELL" => "zsh" }, bin/"foo", "completions", "zsh") + # + # (fish_completion/"foo.fish").write Utils.safe_popen_read({ "SHELL" => "fish" }, bin/"foo", "completions", "fish") + # + # @example Selecting shells and using a different base_name + # generate_completions_from_executable(bin/"foo", "completions", shells: [:bash, :zsh], base_name: "bar") + # translates to + # + # (bash_completion/"bar").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", "completions", "bash") + # + # (zsh_completion/"_bar").write Utils.safe_popen_read({ "SHELL" => "zsh" }, bin/"foo", "completions", "zsh") + # + # @example Using predefined shell_parameter_format :flag + # generate_completions_from_executable(bin/"foo", "completions", shell_parameter_format: :flag, shells: [:bash]) + # translates to + # + # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", "completions", "--bash") + # + # @example Using predefined shell_parameter_format :arg + # generate_completions_from_executable(bin/"foo", "completions", shell_parameter_format: :arg, shells: [:bash]) + # translates to + # + # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", "completions", "--shell=bash") + # + # @example Using predefined shell_parameter_format :none + # generate_completions_from_executable(bin/"foo", "completions", shell_parameter_format: :none, shells: [:bash]) + # translates to + # + # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", "completions") + # + # @example Using custom shell_parameter_format + # generate_completions_from_executable(bin/"foo", "completions", shell_parameter_format: "--selected-shell=", shells: [:bash]) + # translates to + # + # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", "completions", "--selected-shell=bash") sig { params(executable: Pathname, subcmd: String, base_name: String, shells: T::Array[Symbol], shell_parameter_format: T.nilable(T.any(Symbol, String))).void From 074bc3c24760cfa55080701347a0628a9c82d34b Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Wed, 10 Aug 2022 18:00:44 +0200 Subject: [PATCH 17/25] fix style --- Library/Homebrew/formula.rb | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 6cfe0e44ba..672793ffb8 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1663,7 +1663,8 @@ class Formula # generate_completions_from_executable(bin/"foo", "completions", shell_parameter_format: :arg, shells: [:bash]) # translates to # - # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", "completions", "--shell=bash") + # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", + # "completions", "--shell=bash") # # @example Using predefined shell_parameter_format :none # generate_completions_from_executable(bin/"foo", "completions", shell_parameter_format: :none, shells: [:bash]) @@ -1672,10 +1673,12 @@ class Formula # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", "completions") # # @example Using custom shell_parameter_format - # generate_completions_from_executable(bin/"foo", "completions", shell_parameter_format: "--selected-shell=", shells: [:bash]) + # generate_completions_from_executable(bin/"foo", "completions", shell_parameter_format: "--selected-shell=", + # shells: [:bash]) # translates to # - # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", "completions", "--selected-shell=bash") + # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", + # "completions", "--selected-shell=bash") sig { params(executable: Pathname, subcmd: String, base_name: String, shells: T::Array[Symbol], shell_parameter_format: T.nilable(T.any(Symbol, String))).void From 00471be51432248c1f008f414f0e826704522d99 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Wed, 10 Aug 2022 19:07:19 +0200 Subject: [PATCH 18/25] add test --- Library/Homebrew/test/formula_spec.rb | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/Library/Homebrew/test/formula_spec.rb b/Library/Homebrew/test/formula_spec.rb index f9e3f93116..9d7df566cb 100644 --- a/Library/Homebrew/test/formula_spec.rb +++ b/Library/Homebrew/test/formula_spec.rb @@ -1693,4 +1693,28 @@ describe Formula do expect(f.test).to eq(2) end end + + describe "#generate_completions_from_executable" do + let(:f) do + Class.new(Testball) do + def install + bin.mkpath + (bin/"foo").write <<-EOF + echo completion + EOF + + FileUtils.chmod "+x", bin/"foo" + + generate_completions_from_executable(bin/"foo", "test") + end + end.new + end + + it "generates completion scripts" do + f.brew { f.install } + expect(f.bash_completion/"foo").to be_a_file + expect(f.zsh_completion/"_foo").to be_a_file + expect(f.fish_completion/"foo.fish").to be_a_file + end + end end From d819c949b4f85ed6a6642c3ae6c655d0b7615141 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Wed, 10 Aug 2022 20:21:05 +0200 Subject: [PATCH 19/25] fix test --- Library/Homebrew/test/formula_spec.rb | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/Library/Homebrew/test/formula_spec.rb b/Library/Homebrew/test/formula_spec.rb index 9b9f735215..668edab59c 100644 --- a/Library/Homebrew/test/formula_spec.rb +++ b/Library/Homebrew/test/formula_spec.rb @@ -2015,9 +2015,9 @@ describe Formula do it "generates completion scripts" do f.brew { f.install } - expect(f.bash_completion/"foo").to be_a_file - expect(f.zsh_completion/"_foo").to be_a_file - expect(f.fish_completion/"foo.fish").to be_a_file + expect(f.bash_completion/"testball").to be_a_file + expect(f.zsh_completion/"_testball").to be_a_file + expect(f.fish_completion/"testball.fish").to be_a_file end end end From a666b1bce8733472f2253bc56183dda7bbe376dd Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Wed, 10 Aug 2022 22:31:43 +0200 Subject: [PATCH 20/25] fix style --- Library/Homebrew/test/formula_spec.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Library/Homebrew/test/formula_spec.rb b/Library/Homebrew/test/formula_spec.rb index 668edab59c..bada984de5 100644 --- a/Library/Homebrew/test/formula_spec.rb +++ b/Library/Homebrew/test/formula_spec.rb @@ -1996,7 +1996,7 @@ describe Formula do }.to raise_error("ignore_missing_libraries is available on Linux only") end end - + describe "#generate_completions_from_executable" do let(:f) do Class.new(Testball) do From 19530b223995716908fbd602c31b521a94c49bdc Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Thu, 11 Aug 2022 14:02:32 +0200 Subject: [PATCH 21/25] make subcmd optional again, formulae like `certigo` need it --- Library/Homebrew/formula.rb | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index dd7cbfbb71..0392f05957 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1625,7 +1625,7 @@ class Formula # Generate shell completions for a formula for bash, zsh, and fish, using the formula's executable. # # @param executable [Pathname] the executable to use for generating the completion scripts. - # @param subcmd [String] the subcommand to pass to the `executable`. + # @param subcmd [String] the subcommand to pass to the `executable`, if any. Defaults to `nil`. # @param base_name [String] the base name of the generated completion script. Defaults to the formula name. # @param shells [Array] the shells to generate completion scripts for. Defaults to `[:bash, :zsh, :fish]`. # @param shell_parameter_format [String, Symbol] specify how `shells` should each be passed @@ -1677,11 +1677,11 @@ class Formula # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", # "completions", "--selected-shell=bash") sig { - params(executable: Pathname, subcmd: String, base_name: String, shells: T::Array[Symbol], + params(executable: Pathname, subcmd: T.nilable(String), base_name: String, shells: T::Array[Symbol], shell_parameter_format: T.nilable(T.any(Symbol, String))).void } def generate_completions_from_executable(executable, - subcmd, + subcmd = nil, base_name: name, shells: [:bash, :zsh, :fish], shell_parameter_format: nil) @@ -1705,8 +1705,13 @@ class Formula "#{shell_parameter_format}#{shell}" end + popen_read_args = %w[] + popen_read_args << executable + popen_read_args << subcmd if subcmd.present? + popen_read_args << shell_parameter + script_path.dirname.mkpath - script_path.write Utils.safe_popen_read({ "SHELL" => shell.to_s }, executable, subcmd, shell_parameter) + script_path.write Utils.safe_popen_read({ "SHELL" => shell.to_s }, *popen_read_args) end end From a79e8c3692cd6dd4237ac93bfc8cf85a48074c8b Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Thu, 11 Aug 2022 14:26:17 +0200 Subject: [PATCH 22/25] allow `subcmd` to take an array, formulae like circleci need it --- Library/Homebrew/formula.rb | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 0392f05957..cd7122cbf3 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1625,7 +1625,7 @@ class Formula # Generate shell completions for a formula for bash, zsh, and fish, using the formula's executable. # # @param executable [Pathname] the executable to use for generating the completion scripts. - # @param subcmd [String] the subcommand to pass to the `executable`, if any. Defaults to `nil`. + # @param subcmd [String] the subcommand(s) to pass to the `executable`, if any. Defaults to `nil`. # @param base_name [String] the base name of the generated completion script. Defaults to the formula name. # @param shells [Array] the shells to generate completion scripts for. Defaults to `[:bash, :zsh, :fish]`. # @param shell_parameter_format [String, Symbol] specify how `shells` should each be passed @@ -1677,7 +1677,7 @@ class Formula # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", # "completions", "--selected-shell=bash") sig { - params(executable: Pathname, subcmd: T.nilable(String), base_name: String, shells: T::Array[Symbol], + params(executable: Pathname, subcmd: T.nilable(T.any(String, T::Array[String])), base_name: String, shells: T::Array[Symbol], shell_parameter_format: T.nilable(T.any(Symbol, String))).void } def generate_completions_from_executable(executable, @@ -1709,6 +1709,7 @@ class Formula popen_read_args << executable popen_read_args << subcmd if subcmd.present? popen_read_args << shell_parameter + popen_read_args.flatten! script_path.dirname.mkpath script_path.write Utils.safe_popen_read({ "SHELL" => shell.to_s }, *popen_read_args) From fa22a167d31993b8e19b92f8037f327305a9a12b Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Thu, 11 Aug 2022 18:12:08 +0200 Subject: [PATCH 23/25] refactor to variable length `commands` arg --- Library/Homebrew/formula.rb | 12 +++++------- 1 file changed, 5 insertions(+), 7 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index cd7122cbf3..162d93fbac 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1624,8 +1624,8 @@ class Formula # Generate shell completions for a formula for bash, zsh, and fish, using the formula's executable. # - # @param executable [Pathname] the executable to use for generating the completion scripts. - # @param subcmd [String] the subcommand(s) to pass to the `executable`, if any. Defaults to `nil`. + # @param commands [Pathname, String] the path to the executable and any passed subcommand(s) + # to use for generating the completion scripts. # @param base_name [String] the base name of the generated completion script. Defaults to the formula name. # @param shells [Array] the shells to generate completion scripts for. Defaults to `[:bash, :zsh, :fish]`. # @param shell_parameter_format [String, Symbol] specify how `shells` should each be passed @@ -1677,11 +1677,10 @@ class Formula # (bash_completion/"foo").write Utils.safe_popen_read({ "SHELL" => "bash" }, bin/"foo", # "completions", "--selected-shell=bash") sig { - params(executable: Pathname, subcmd: T.nilable(T.any(String, T::Array[String])), base_name: String, shells: T::Array[Symbol], + params(commands: T.any(Pathname, String), base_name: String, shells: T::Array[Symbol], shell_parameter_format: T.nilable(T.any(Symbol, String))).void } - def generate_completions_from_executable(executable, - subcmd = nil, + def generate_completions_from_executable(*commands, base_name: name, shells: [:bash, :zsh, :fish], shell_parameter_format: nil) @@ -1706,8 +1705,7 @@ class Formula end popen_read_args = %w[] - popen_read_args << executable - popen_read_args << subcmd if subcmd.present? + popen_read_args << commands popen_read_args << shell_parameter popen_read_args.flatten! From 2369a58665d151035cb8047343a10fb9e0f40806 Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Thu, 11 Aug 2022 20:59:51 +0200 Subject: [PATCH 24/25] simplify --- Library/Homebrew/formula.rb | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index 162d93fbac..e8220d1fa0 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1704,13 +1704,8 @@ class Formula "#{shell_parameter_format}#{shell}" end - popen_read_args = %w[] - popen_read_args << commands - popen_read_args << shell_parameter - popen_read_args.flatten! - script_path.dirname.mkpath - script_path.write Utils.safe_popen_read({ "SHELL" => shell.to_s }, *popen_read_args) + script_path.write Utils.safe_popen_read({ "SHELL" => shell.to_s }, *commands, shell_parameter) end end From 873954cb71dc76dd2e1e5c57c18a1a31b3cf2c0c Mon Sep 17 00:00:00 2001 From: Max Eisner <4730112+max-ae@users.noreply.github.com> Date: Thu, 11 Aug 2022 21:32:03 +0200 Subject: [PATCH 25/25] Revert "simplify" This reverts commit 2369a58665d151035cb8047343a10fb9e0f40806. --- Library/Homebrew/formula.rb | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb index e8220d1fa0..162d93fbac 100644 --- a/Library/Homebrew/formula.rb +++ b/Library/Homebrew/formula.rb @@ -1704,8 +1704,13 @@ class Formula "#{shell_parameter_format}#{shell}" end + popen_read_args = %w[] + popen_read_args << commands + popen_read_args << shell_parameter + popen_read_args.flatten! + script_path.dirname.mkpath - script_path.write Utils.safe_popen_read({ "SHELL" => shell.to_s }, *commands, shell_parameter) + script_path.write Utils.safe_popen_read({ "SHELL" => shell.to_s }, *popen_read_args) end end