Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Library/Homebrew/bundle.rb
Original file line number Diff line number Diff line change
Expand Up @@ -101,7 +101,7 @@ def which_formula?(name)
which(name).present?
end

sig { params(block: T.proc.returns(T.anything)).returns(T.untyped) }
sig { type_parameters(:U).params(block: T.proc.returns(T.type_parameter(:U))).returns(T.type_parameter(:U)) }
def exchange_uid_if_needed!(&block)
euid = Process.euid
uid = Process.uid
Expand Down
6 changes: 3 additions & 3 deletions Library/Homebrew/cache_store.rb
Original file line number Diff line number Diff line change
Expand Up @@ -22,9 +22,9 @@ class CacheStoreDatabase
.returns(T.type_parameter(:U))
}
def self.use(type, &_blk)
@db_type_reference_hash ||= T.let({}, T.nilable(T::Hash[T.untyped, T.untyped]))
@db_type_reference_hash[type] ||= {}
type_ref = @db_type_reference_hash[type]
@db_type_reference_hash ||= T.let({}, T.nilable(T::Hash[Symbol, { count: Integer, db: CacheStoreDatabase }]))
@db_type_reference_hash[type] ||= { count: 0, db: CacheStoreDatabase.new(type) }
type_ref = @db_type_reference_hash.fetch(type)

type_ref[:count] ||= 0
type_ref[:count] += 1
Expand Down
2 changes: 1 addition & 1 deletion Library/Homebrew/cask/artifact/app.rb
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ module Artifact
# Artifact corresponding to the `app` stanza.
class App < Moved
sig {
params(
override.params(
adopt: T::Boolean,
auto_updates: T.nilable(T::Boolean),
force: T::Boolean,
Expand Down
15 changes: 8 additions & 7 deletions Library/Homebrew/cask/artifact/artifact.rb
Original file line number Diff line number Diff line change
Expand Up @@ -12,20 +12,21 @@ def self.english_name
"Generic Artifact"
end

sig { params(cask: Cask, args: T.untyped).returns(T.attached_class) }
def self.from_args(cask, *args)
source, options = args

sig { params(cask: Cask, source: T.nilable(String), target_hash: T.anything).returns(Relocated) }
def self.from_args(cask, source = nil, **target_hash)
raise CaskInvalidError.new(cask.token, "No source provided for #{english_name}.") if source.blank?

unless options&.key?(:target)
unless target_hash.key?(:target)
raise CaskInvalidError.new(cask.token, "#{english_name} '#{source}' requires a target.")
end

new(cask, source, **options)
new(cask, source, **target_hash)
end

sig { params(target: T.any(String, Pathname)).returns(Pathname) }
# FIXME: This is a pre-existing violation
# rubocop:disable Sorbet/AllowIncompatibleOverride
sig { override(allow_incompatible: true).params(target: T.any(String, Pathname)).returns(Pathname) }
# rubocop:enable Sorbet/AllowIncompatibleOverride
def resolve_target(target)
super(target, base_dir: nil)
end
Expand Down
5 changes: 4 additions & 1 deletion Library/Homebrew/cask/artifact/bashcompletion.rb
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,10 @@ module Cask
module Artifact
# Artifact corresponding to the `bash_completion` stanza.
class BashCompletion < ShellCompletion
sig { params(target: T.any(String, Pathname)).returns(Pathname) }
# FIXME: This is a pre-existing violation
# rubocop:disable Sorbet/AllowIncompatibleOverride
sig { override(allow_incompatible: true).params(target: T.any(String, Pathname)).returns(Pathname) }
# rubocop:enable Sorbet/AllowIncompatibleOverride
def resolve_target(target)
name = if File.extname(target).nil?
target
Expand Down
5 changes: 3 additions & 2 deletions Library/Homebrew/cask/artifact/binary.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# typed: true # rubocop:todo Sorbet/StrictSigil
# typed: strict
# frozen_string_literal: true

require "cask/artifact/symlinked"
Expand All @@ -7,7 +7,8 @@ module Cask
module Artifact
# Artifact corresponding to the `binary` stanza.
class Binary < Symlinked
def link(command: nil, **options)
sig { override.params(command: T.class_of(SystemCommand), force: T::Boolean, adopt: T::Boolean, _options: T.anything).void }
def link(command:, force: false, adopt: false, **_options)
super
return if source.executable?

Expand Down
5 changes: 4 additions & 1 deletion Library/Homebrew/cask/artifact/fishcompletion.rb
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,10 @@ module Cask
module Artifact
# Artifact corresponding to the `fish_completion` stanza.
class FishCompletion < ShellCompletion
sig { params(target: T.any(String, Pathname)).returns(Pathname) }
# FIXME: This is a pre-existing violation
# rubocop:disable Sorbet/AllowIncompatibleOverride
sig { override(allow_incompatible: true).params(target: T.any(String, Pathname)).returns(Pathname) }
# rubocop:enable Sorbet/AllowIncompatibleOverride
def resolve_target(target)
name = if target.to_s.end_with? ".fish"
target
Expand Down
34 changes: 20 additions & 14 deletions Library/Homebrew/cask/artifact/installer.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# typed: true # rubocop:todo Sorbet/StrictSigil
# typed: strict
# frozen_string_literal: true

require "cask/artifact/abstract_artifact"
Expand All @@ -8,12 +8,13 @@ module Cask
module Artifact
# Artifact corresponding to the `installer` stanza.
class Installer < AbstractArtifact
VALID_KEYS = Set.new([
:manual,
:script,
]).freeze
VALID_KEYS = T.let(
Set.new([:manual, :script]).freeze,
T::Set[Symbol],
)

def install_phase(command: nil, **_)
sig { params(command: T.class_of(SystemCommand), _options: T.anything).void }
def install_phase(command:, **_options)
if manual_install
puts <<~EOS
Cask #{cask} only provides a manual installer. To run it and complete the installation:
Expand All @@ -35,6 +36,7 @@ def install_phase(command: nil, **_)
end
end

sig { params(cask: Cask, args: DirectivesType).returns(Installer) }
def self.from_args(cask, **args)
raise CaskInvalidError.new(cask, "'installer' stanza requires an argument.") if args.empty?

Expand All @@ -59,18 +61,23 @@ def self.from_args(cask, **args)
new(cask, **args)
end

attr_reader :path, :args
sig { returns(Pathname) }
attr_reader :path

sig { returns(T::Hash[Symbol, DirectivesType]) }
attr_reader :args

sig { returns(T::Boolean) }
attr_reader :manual_install

sig { params(cask: Cask, args: DirectivesType).void }
def initialize(cask, **args)
super

if args.key?(:manual)
@path = Pathname(args[:manual])
@args = []
@manual_install = true
if (manual = T.cast(args[:manual], T.nilable(String)))
@path = T.let(Pathname(manual), Pathname)
@args = T.let({}, T::Hash[Symbol, DirectivesType])
@manual_install = T.let(true, T::Boolean)
else
path, @args = self.class.read_script_arguments(
args[:script], self.class.dsl_key.to_s, { must_succeed: true, sudo: false }, print_stdout: true
Expand All @@ -85,10 +92,9 @@ def initialize(cask, **args)
sig { override.returns(String) }
def summarize = path.to_s

sig { returns(T::Hash[Symbol, T.anything]) }
def to_h
{ path: }.tap do |h|
h[:args] = args unless manual_install
end
manual_install ? { path: } : { path:, args: }
end
end
end
Expand Down
11 changes: 7 additions & 4 deletions Library/Homebrew/cask/artifact/keyboard_layout.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# typed: true # rubocop:todo Sorbet/StrictSigil
# typed: strict
# frozen_string_literal: true

require "cask/artifact/moved"
Expand All @@ -7,19 +7,22 @@ module Cask
module Artifact
# Artifact corresponding to the `keyboard_layout` stanza.
class KeyboardLayout < Moved
def install_phase(**options)
sig { override.params(command: T.class_of(SystemCommand), options: T.anything).void }
def install_phase(command:, **options)
super
delete_keyboard_layout_cache(**options)
end

def uninstall_phase(**options)
sig { override.params(command: T.class_of(SystemCommand), options: T.anything).void }
def uninstall_phase(command:, **options)
super
delete_keyboard_layout_cache(**options)
end

private

def delete_keyboard_layout_cache(command: nil, **_)
sig { params(command: T.class_of(SystemCommand), _options: T.anything).void }
def delete_keyboard_layout_cache(command:, **_options)
command.run!(
"/bin/rm",
args: ["-f", "--", "/System/Library/Caches/com.apple.IntlDataCache.le*"],
Expand Down
11 changes: 9 additions & 2 deletions Library/Homebrew/cask/artifact/manpage.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# typed: true # rubocop:todo Sorbet/StrictSigil
# typed: strict
# frozen_string_literal: true

require "cask/artifact/symlinked"
Expand All @@ -7,22 +7,29 @@ module Cask
module Artifact
# Artifact corresponding to the `manpage` stanza.
class Manpage < Symlinked
sig { returns(String) }
attr_reader :section

def self.from_args(cask, source)
sig { params(cask: Cask, source: String, _target_hash: T.anything).returns(Manpage) }
def self.from_args(cask, source, **_target_hash)
section = source.to_s[/\.([1-8]|n|l)(?:\.gz)?$/, 1]

raise CaskInvalidError, "'#{source}' is not a valid man page name" unless section

new(cask, source, section)
end

sig { params(cask: Cask, source: String, section: String).void }
def initialize(cask, source, section)
@section = section

super(cask, source)
end

# FIXME: This is a pre-existing violation
# rubocop:disable Sorbet/AllowIncompatibleOverride
sig { override(allow_incompatible: true).params(target: T.any(String, Pathname)).returns(Pathname) }
# rubocop:enable Sorbet/AllowIncompatibleOverride
def resolve_target(target)
config.manpagedir.join("man#{section}", target)
end
Expand Down
30 changes: 26 additions & 4 deletions Library/Homebrew/cask/artifact/mdimporter.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# typed: true # rubocop:todo Sorbet/StrictSigil
# typed: strict
# frozen_string_literal: true

require "cask/artifact/moved"
Expand All @@ -12,14 +12,36 @@ def self.english_name
"Spotlight metadata importer"
end

def install_phase(**options)
sig {
override.params(
adopt: T::Boolean,
auto_updates: T.nilable(T::Boolean),
force: T::Boolean,
verbose: T::Boolean,
predecessor: T.nilable(Cask),
successor: T.nilable(Cask),
reinstall: T::Boolean,
command: T.class_of(SystemCommand),
).void
}
def install_phase(
adopt: false,
auto_updates: false,
force: false,
verbose: false,
predecessor: nil,
successor: nil,
reinstall: false,
command: SystemCommand
)
super
reload_spotlight(**options)
reload_spotlight(command:)
end

private

def reload_spotlight(command: nil, **_)
sig { params(command: T.class_of(SystemCommand)).void }
def reload_spotlight(command:)
command.run!("/usr/bin/mdimport", args: ["-r", target])
end
end
Expand Down
50 changes: 41 additions & 9 deletions Library/Homebrew/cask/artifact/moved.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# typed: true # rubocop:todo Sorbet/StrictSigil
# typed: strict
# frozen_string_literal: true

require "cask/artifact/relocated"
Expand All @@ -13,14 +13,37 @@ def self.english_description
"#{english_name}s"
end

def install_phase(**options)
move(**options)
sig {
overridable.params(
adopt: T::Boolean,
auto_updates: T.nilable(T::Boolean),
force: T::Boolean,
verbose: T::Boolean,
predecessor: T.nilable(Cask),
successor: T.nilable(Cask),
reinstall: T::Boolean,
command: T.class_of(SystemCommand),
).void
}
def install_phase(
adopt: false,
auto_updates: false,
force: false,
verbose: false,
predecessor: nil,
successor: nil,
reinstall: false,
command: SystemCommand
)
move(adopt:, auto_updates:, force:, verbose:, predecessor:, successor:, reinstall:, command:)
end

def uninstall_phase(**options)
move_back(**options)
sig { overridable.params(command: T.class_of(SystemCommand), options: T.anything).void }
def uninstall_phase(command:, **options)
move_back(command:, **options)
end

sig { overridable.returns(String) }
def summarize_installed
if target.exist?
"#{printable_target} (#{target.abv})"
Expand All @@ -31,8 +54,13 @@ def summarize_installed

private

def move(adopt: false, auto_updates: false, force: false, verbose: false, predecessor: nil, reinstall: false,
command: nil, **options)
sig {
params(command: T.class_of(SystemCommand), adopt: T::Boolean, auto_updates: T.nilable(T::Boolean),
force: T::Boolean, verbose: T::Boolean, predecessor: T.nilable(Cask), reinstall: T::Boolean,
options: T.anything).void
}
def move(command:, adopt: false, auto_updates: false, force: false, verbose: false, predecessor: nil,
reinstall: false, **options)
unless source.exist?
raise CaskError, "It seems the #{self.class.english_name} source '#{source}' is not there."
end
Expand Down Expand Up @@ -128,12 +156,14 @@ def move(adopt: false, auto_updates: false, force: false, verbose: false, predec
end

# Performs any actions necessary after the source has been moved to the target location.
sig { params(command: T.class_of(SystemCommand)).void }
def post_move(command)
FileUtils.ln_sf target, source

add_altname_metadata(target, source.basename, command:)
end

sig { params(cask: T.nilable(Cask)).returns(T::Boolean) }
def matching_artifact?(cask)
return false unless cask

Expand All @@ -142,7 +172,8 @@ def matching_artifact?(cask)
end
end

def move_back(skip: false, force: false, adopt: false, command: nil, **options)
sig { params(command: T.class_of(SystemCommand), skip: T::Boolean, force: T::Boolean, adopt: T::Boolean, options: T.anything).void }
def move_back(command:, skip: false, force: false, adopt: false, **options)
FileUtils.rm source if source.symlink? && source.dirname.join(source.readlink) == target

if Utils.path_occupied?(source)
Expand Down Expand Up @@ -178,7 +209,8 @@ def move_back(skip: false, force: false, adopt: false, command: nil, **options)
delete(target, force:, command:, **options)
end

def delete(target, force: false, successor: nil, command: nil, **_)
sig { params(target: Pathname, command: T.class_of(SystemCommand), force: T::Boolean, successor: T.nilable(Cask), _options: T.anything).void }
def delete(target, command:, force: false, successor: nil, **_options)
ohai "Removing #{self.class.english_name} '#{target}'"
raise CaskError, "Cannot remove undeletable #{self.class.english_name}." if undeletable?(target)

Expand Down
Loading
Loading