feat: add cask shell completion

This commit is contained in:
Sean Molenaar 2025-03-03 17:54:54 +01:00
parent 035be80dad
commit 55b07d7fed
8 changed files with 122 additions and 1 deletions

View File

@ -22,6 +22,9 @@ require "cask/artifact/prefpane"
require "cask/artifact/qlplugin" require "cask/artifact/qlplugin"
require "cask/artifact/mdimporter" require "cask/artifact/mdimporter"
require "cask/artifact/screen_saver" require "cask/artifact/screen_saver"
require "cask/artifact/bashcompletion"
require "cask/artifact/fishcompletion"
require "cask/artifact/zshcompletion"
require "cask/artifact/service" require "cask/artifact/service"
require "cask/artifact/stage_only" require "cask/artifact/stage_only"
require "cask/artifact/suite" require "cask/artifact/suite"

View File

@ -0,0 +1,25 @@
# typed: strict
# frozen_string_literal: true
require "cask/artifact/shellcompletion"
module Cask
module Artifact
# Artifact corresponding to the `bash_completion` stanza.
class BashCompletion < ShellCompletion
sig { params(target: T.any(String, Pathname)).returns(Pathname) }
def resolve_target(target)
name = if target.to_s.end_with? ".bash"
target
else
new_name = File.basename(target, File.extname(target))
odebug "Renaming completion #{target} to #{new_name}"
new_name
end
config.bash_completion/name
end
end
end
end

View File

@ -0,0 +1,25 @@
# typed: strict
# frozen_string_literal: true
require "cask/artifact/shellcompletion"
module Cask
module Artifact
# Artifact corresponding to the `fish_completion` stanza.
class FishCompletion < ShellCompletion
sig { params(target: T.any(String, Pathname)).returns(Pathname) }
def resolve_target(target)
name = if target.to_s.end_with? ".fish"
target
else
new_name = "#{File.basename(target, File.extname(target))}.fish"
odebug "Renaming completion #{target} to #{new_name}"
new_name
end
config.fish_completion/name
end
end
end
end

View File

@ -0,0 +1,20 @@
# typed: strict
# frozen_string_literal: true
require "cask/artifact/symlinked"
module Cask
module Artifact
class ShellCompletion < Symlinked
sig { params(cask: Cask, source: T.any(String, Pathname)).returns(ShellCompletion) }
def self.from_args(cask, source)
new(cask, source)
end
sig { params(_: T.any(String, Pathname)).returns(Pathname) }
def resolve_target(_)
raise CaskInvalidError, "Shell completion without shell info"
end
end
end
end

View File

@ -0,0 +1,25 @@
# typed: strict
# frozen_string_literal: true
require "cask/artifact/shellcompletion"
module Cask
module Artifact
# Artifact corresponding to the `zsh_completion` stanza.
class ZshCompletion < ShellCompletion
sig { params(target: T.any(String, Pathname)).returns(Pathname) }
def resolve_target(target)
name = if target.to_s.start_with? "_"
target
else
new_name = "_#{File.basename(target, File.extname(target))}"
odebug "Renaming completion #{target} to #{new_name}"
new_name
end
config.zsh_completion/name
end
end
end
end

View File

@ -176,6 +176,21 @@ module Cask
@manpagedir ||= T.let(HOMEBREW_PREFIX/"share/man", T.nilable(Pathname)) @manpagedir ||= T.let(HOMEBREW_PREFIX/"share/man", T.nilable(Pathname))
end end
sig { returns(Pathname) }
def bash_completion
@bash_completion ||= T.let(HOMEBREW_PREFIX/"etc/bash_completion.d", T.nilable(Pathname))
end
sig { returns(Pathname) }
def zsh_completion
@zsh_completion ||= T.let(HOMEBREW_PREFIX/"share/zsh/site-functions", T.nilable(Pathname))
end
sig { returns(Pathname) }
def fish_completion
@fish_completion ||= T.let(HOMEBREW_PREFIX/"share/fish/vendor_completions.d", T.nilable(Pathname))
end
sig { returns(T::Array[String]) } sig { returns(T::Array[String]) }
def languages def languages
[ [

View File

@ -53,6 +53,9 @@ module Cask
Artifact::Suite, Artifact::Suite,
Artifact::VstPlugin, Artifact::VstPlugin,
Artifact::Vst3Plugin, Artifact::Vst3Plugin,
Artifact::ZshCompletion,
Artifact::FishCompletion,
Artifact::BashCompletion,
Artifact::Uninstall, Artifact::Uninstall,
Artifact::Zap, Artifact::Zap,
].freeze ].freeze

View File

@ -16,7 +16,12 @@ module OS
return if artifacts.all?(::Cask::Artifact::Font) return if artifacts.all?(::Cask::Artifact::Font)
install_artifacts = artifacts.reject { |artifact| artifact.instance_of?(::Cask::Artifact::Zap) } install_artifacts = artifacts.reject { |artifact| artifact.instance_of?(::Cask::Artifact::Zap) }
return if install_artifacts.all?(::Cask::Artifact::Binary) return if install_artifacts.all? do |artifact|
artifact.is_a?(::Cask::Artifact::Binary) ||
artifact.is_a?(::Cask::Artifact::ShellCompletion) ||
artifact.is_a?(::Cask::Artifact::Artifact) ||
artifact.is_a?(::Cask::Artifact::Manpage)
end
raise ::Cask::CaskError, "macOS is required for this software." raise ::Cask::CaskError, "macOS is required for this software."
end end