diff --git a/Library/.rubocop.yml b/Library/.rubocop.yml
index 7b099688581355d1213b69c97979dfb25cf0ec75..f1ca45af7fd0ba3ef858deab4554e8baa9492021 100644
--- a/Library/.rubocop.yml
+++ b/Library/.rubocop.yml
@@ -297,15 +297,9 @@ Sorbet/ConstantsFromStrings:
 Style/AccessModifierDeclarations:
   Enabled: false
 
-# don't group nicely documented or private attr_readers
+# Conflicts with type signatures on `attr_*`s.
 Style/AccessorGrouping:
-  Exclude:
-    - 'Homebrew/formula.rb'
-    - 'Homebrew/formulary.rb'
-    - 'Homebrew/migrator.rb'
-    - 'Homebrew/resource.rb'
-    - 'Homebrew/system_command.rb'
-    - 'Homebrew/tap.rb'
+  Enabled: false
 
 # make rspec formatting more flexible
 Style/BlockDelimiters:
diff --git a/Library/Homebrew/bintray.rb b/Library/Homebrew/bintray.rb
index ea50ed3479030b543deee7932ed183075ca5042b..7277cfdebcf11177dce1324a07d895b1e1bb870e 100644
--- a/Library/Homebrew/bintray.rb
+++ b/Library/Homebrew/bintray.rb
@@ -8,6 +8,8 @@ require "json"
 #
 # @api private
 class Bintray
+  extend T::Sig
+
   include Context
 
   API_URL = "https://api.bintray.com"
@@ -15,6 +17,7 @@ class Bintray
   class Error < RuntimeError
   end
 
+  sig { returns(String) }
   def inspect
     "#<Bintray: org=#{@bintray_org}>"
   end
diff --git a/Library/Homebrew/cask/artifact/abstract_artifact.rb b/Library/Homebrew/cask/artifact/abstract_artifact.rb
index 50c2b325e58a9cbc357fde34eccca7f9bbf0be9b..9d6e5d13817f60926585a21bd88561e4316daff3 100644
--- a/Library/Homebrew/cask/artifact/abstract_artifact.rb
+++ b/Library/Homebrew/cask/artifact/abstract_artifact.rb
@@ -7,6 +7,8 @@ module Cask
     #
     # @api private
     class AbstractArtifact
+      extend T::Sig
+
       include Comparable
       extend Predicable
 
@@ -132,6 +134,7 @@ module Cask
         cask.config
       end
 
+      sig { returns(String) }
       def to_s
         "#{summarize} (#{self.class.english_name})"
       end
diff --git a/Library/Homebrew/cask/artifact/abstract_uninstall.rb b/Library/Homebrew/cask/artifact/abstract_uninstall.rb
index baa8467a37acad352814254d8a212a5eda34a285..51505e70c97c983bfd74ec517552803bf9047b4f 100644
--- a/Library/Homebrew/cask/artifact/abstract_uninstall.rb
+++ b/Library/Homebrew/cask/artifact/abstract_uninstall.rb
@@ -15,6 +15,8 @@ module Cask
     #
     # @api private
     class AbstractUninstall < AbstractArtifact
+      extend T::Sig
+
       ORDERED_DIRECTIVES = [
         :early_script,
         :launchctl,
@@ -53,6 +55,7 @@ module Cask
         directives.to_h
       end
 
+      sig { returns(String) }
       def summarize
         to_h.flat_map { |key, val| Array(val).map { |v| "#{key.inspect} => #{v.inspect}" } }.join(", ")
       end
@@ -128,6 +131,7 @@ module Cask
           end
       end
 
+      sig { returns(String) }
       def automation_access_instructions
         "Enable Automation Access for 鈥淭erminal > System Events鈥� in " \
         "鈥淪ystem Preferences > Security > Privacy > Automation鈥� if you haven't already."
diff --git a/Library/Homebrew/cask/artifact/artifact.rb b/Library/Homebrew/cask/artifact/artifact.rb
index f6b350a82dec126ae8cdb4eb707a5e5cb7abca49..8d083a1bd51f5906e6190066f7a3adea0c7b70a0 100644
--- a/Library/Homebrew/cask/artifact/artifact.rb
+++ b/Library/Homebrew/cask/artifact/artifact.rb
@@ -12,6 +12,9 @@ module Cask
     #
     # @api private
     class Artifact < Moved
+      extend T::Sig
+
+      sig { returns(String) }
       def self.english_name
         "Generic Artifact"
       end
diff --git a/Library/Homebrew/cask/artifact/mdimporter.rb b/Library/Homebrew/cask/artifact/mdimporter.rb
index 226a01e1ccd7c54b64c2394cafdc34ed9d41ba6d..5a4ce2d052290054956a09a823aee6fcaed39485 100644
--- a/Library/Homebrew/cask/artifact/mdimporter.rb
+++ b/Library/Homebrew/cask/artifact/mdimporter.rb
@@ -9,6 +9,9 @@ module Cask
     #
     # @api private
     class Mdimporter < Moved
+      extend T::Sig
+
+      sig { returns(String) }
       def self.english_name
         "Spotlight metadata importer"
       end
diff --git a/Library/Homebrew/cask/artifact/moved.rb b/Library/Homebrew/cask/artifact/moved.rb
index 6acb7d7827724849f54bf1d9d59c26754d2cad96..bd9287ad29e894e589d259e9f5955bdea3f38254 100644
--- a/Library/Homebrew/cask/artifact/moved.rb
+++ b/Library/Homebrew/cask/artifact/moved.rb
@@ -9,6 +9,9 @@ module Cask
     #
     # @api private
     class Moved < Relocated
+      extend T::Sig
+
+      sig { returns(String) }
       def self.english_description
         "#{english_name}s"
       end
diff --git a/Library/Homebrew/cask/artifact/prefpane.rb b/Library/Homebrew/cask/artifact/prefpane.rb
index aed47644e1a3936ff7112959433d67c8f22119ee..8dc2df4559d671e6c448935e39491c2f5d8d439b 100644
--- a/Library/Homebrew/cask/artifact/prefpane.rb
+++ b/Library/Homebrew/cask/artifact/prefpane.rb
@@ -9,6 +9,9 @@ module Cask
     #
     # @api private
     class Prefpane < Moved
+      extend T::Sig
+
+      sig { returns(String) }
       def self.english_name
         "Preference Pane"
       end
diff --git a/Library/Homebrew/cask/artifact/qlplugin.rb b/Library/Homebrew/cask/artifact/qlplugin.rb
index e0c26a6dc8cdded31e6ad57ce823dc2612ef5a78..d50956d8ca753ada6426cf69d00278db38b97a04 100644
--- a/Library/Homebrew/cask/artifact/qlplugin.rb
+++ b/Library/Homebrew/cask/artifact/qlplugin.rb
@@ -9,6 +9,9 @@ module Cask
     #
     # @api private
     class Qlplugin < Moved
+      extend T::Sig
+
+      sig { returns(String) }
       def self.english_name
         "QuickLook Plugin"
       end
diff --git a/Library/Homebrew/cask/artifact/relocated.rb b/Library/Homebrew/cask/artifact/relocated.rb
index 5c9dd0dbd5852881303a0e9009fb5433795a0957..f5e61e967798870e692f6ee64b13f4ea6ed9c214 100644
--- a/Library/Homebrew/cask/artifact/relocated.rb
+++ b/Library/Homebrew/cask/artifact/relocated.rb
@@ -12,6 +12,8 @@ module Cask
     #
     # @api private
     class Relocated < AbstractArtifact
+      extend T::Sig
+
       def self.from_args(cask, *args)
         source_string, target_hash = args
 
@@ -49,6 +51,7 @@ module Cask
         end
       end
 
+      sig { returns(String) }
       def summarize
         target_string = @target_string.empty? ? "" : " -> #{@target_string}"
         "#{@source_string}#{target_string}"
diff --git a/Library/Homebrew/cask/artifact/stage_only.rb b/Library/Homebrew/cask/artifact/stage_only.rb
index c67cac6d3b13a3b886365311ed3214c3c48b015d..b475b00a860e05396e6e325a6b306b9c27f3f6d6 100644
--- a/Library/Homebrew/cask/artifact/stage_only.rb
+++ b/Library/Homebrew/cask/artifact/stage_only.rb
@@ -9,16 +9,20 @@ module Cask
     #
     # @api private
     class StageOnly < AbstractArtifact
+      extend T::Sig
+
       def self.from_args(cask, *args)
         raise CaskInvalidError.new(cask.token, "'stage_only' takes only a single argument: true") if args != [true]
 
         new(cask)
       end
 
+      sig { returns(T::Array[T::Boolean]) }
       def to_a
         [true]
       end
 
+      sig { returns(String) }
       def summarize
         "true"
       end
diff --git a/Library/Homebrew/cask/artifact/suite.rb b/Library/Homebrew/cask/artifact/suite.rb
index a236a602e0f9d9f7355faa529f6ae34ef3e72df9..043b4f0b9ef812b7ec30169dc57d0cd00c4f6b77 100644
--- a/Library/Homebrew/cask/artifact/suite.rb
+++ b/Library/Homebrew/cask/artifact/suite.rb
@@ -9,10 +9,14 @@ module Cask
     #
     # @api private
     class Suite < Moved
+      extend T::Sig
+
+      sig { returns(String) }
       def self.english_name
         "App Suite"
       end
 
+      sig { returns(Symbol) }
       def self.dirmethod
         :appdir
       end
diff --git a/Library/Homebrew/cask/artifact/symlinked.rb b/Library/Homebrew/cask/artifact/symlinked.rb
index 68e8dbe181dca226348076881057cea85bf90089..bb423e69d40f8b8aaba0cdbe163f0532ee42d1fe 100644
--- a/Library/Homebrew/cask/artifact/symlinked.rb
+++ b/Library/Homebrew/cask/artifact/symlinked.rb
@@ -9,10 +9,14 @@ module Cask
     #
     # @api private
     class Symlinked < Relocated
+      extend T::Sig
+
+      sig { returns(String) }
       def self.link_type_english_name
         "Symlink"
       end
 
+      sig { returns(String) }
       def self.english_description
         "#{english_name} #{link_type_english_name}s"
       end
diff --git a/Library/Homebrew/cask/audit.rb b/Library/Homebrew/cask/audit.rb
index 7e2297beccc772a6ad8e0f56ede8722ae82a202e..a9603a50e8e17fee1dd6917723975e914db29b81 100644
--- a/Library/Homebrew/cask/audit.rb
+++ b/Library/Homebrew/cask/audit.rb
@@ -13,6 +13,8 @@ module Cask
   #
   # @api private
   class Audit
+    extend T::Sig
+
     extend Predicable
 
     attr_reader :cask, :download
@@ -117,6 +119,7 @@ module Cask
       end
     end
 
+    sig { returns(String) }
     def summary
       summary = ["audit for #{cask}: #{result}"]
 
@@ -416,6 +419,7 @@ module Cask
       core_tap.formula_names
     end
 
+    sig { returns(String) }
     def core_formula_url
       "#{core_tap.default_remote}/blob/HEAD/Formula/#{cask.token}.rb"
     end
diff --git a/Library/Homebrew/cask/cask.rb b/Library/Homebrew/cask/cask.rb
index 8858922a0bad0bb1e06e9080e9c71c1546436df8..92f28cb702ae1802acf0d867c4d0ff48d456caba 100644
--- a/Library/Homebrew/cask/cask.rb
+++ b/Library/Homebrew/cask/cask.rb
@@ -12,6 +12,8 @@ module Cask
   #
   # @api private
   class Cask
+    extend T::Sig
+
     extend Enumerable
     extend Forwardable
     extend Searchable
@@ -64,6 +66,7 @@ module Cask
       define_method(method_name) { |&block| @dsl.send(method_name, &block) }
     end
 
+    sig { returns(T::Array[[String, String]]) }
     def timestamped_versions
       Pathname.glob(metadata_timestamped_path(version: "*", timestamp: "*"))
               .map { |p| p.relative_path_from(p.parent.parent) }
@@ -89,6 +92,7 @@ module Cask
       !versions.empty?
     end
 
+    sig { returns(T.nilable(Time)) }
     def install_time
       _, time = timestamped_versions.last
       return unless time
diff --git a/Library/Homebrew/cask/cask_loader.rb b/Library/Homebrew/cask/cask_loader.rb
index 8ec015a931b4c6e49d06d6e75154f33f3823899e..b49ad9275e0eb709d89c84aaa6e87528ce1d249b 100644
--- a/Library/Homebrew/cask/cask_loader.rb
+++ b/Library/Homebrew/cask/cask_loader.rb
@@ -90,6 +90,8 @@ module Cask
 
     # Loads a cask from a URI.
     class FromURILoader < FromPathLoader
+      extend T::Sig
+
       def self.can_load?(ref)
         uri_regex = ::URI::DEFAULT_PARSER.make_regexp
         return false unless ref.to_s.match?(Regexp.new("\\A#{uri_regex.source}\\Z", uri_regex.options))
@@ -103,6 +105,7 @@ module Cask
 
       attr_reader :url
 
+      sig { params(url: T.any(URI::Generic, String)).void }
       def initialize(url)
         @url = URI(url)
         super Cache.path/File.basename(@url.path)
@@ -177,10 +180,13 @@ module Cask
 
     # Pseudo-loader which raises an error when trying to load the corresponding cask.
     class NullLoader < FromPathLoader
+      extend T::Sig
+
       def self.can_load?(*)
         true
       end
 
+      sig { params(ref: T.any(String, Pathname)).void }
       def initialize(ref)
         token = File.basename(ref, ".rb")
         super CaskLoader.default_path(token)
diff --git a/Library/Homebrew/cask/cmd.rb b/Library/Homebrew/cask/cmd.rb
index 5c62cb73ea60e4aebdcb9a7bd09ac2f5780857fe..c5dc653c5f45ffe8a98c1474310135bad691cb41 100644
--- a/Library/Homebrew/cask/cmd.rb
+++ b/Library/Homebrew/cask/cmd.rb
@@ -38,6 +38,8 @@ module Cask
   #
   # @api private
   class Cmd
+    extend T::Sig
+
     include Context
 
     ALIASES = {
@@ -61,6 +63,7 @@ module Cask
       Cmd::Upgrade   => "brew upgrade --cask",
     }.freeze
 
+    sig { returns(String) }
     def self.description
       max_command_length = Cmd.commands.map(&:length).max
 
diff --git a/Library/Homebrew/cask/cmd/--cache.rb b/Library/Homebrew/cask/cmd/--cache.rb
index 613841f7c3c829f2b845e114b6cf67578d2b0fc2..8a85ba5a8528e648d74a8db22aa808437edb05f4 100644
--- a/Library/Homebrew/cask/cmd/--cache.rb
+++ b/Library/Homebrew/cask/cmd/--cache.rb
@@ -7,18 +7,24 @@ module Cask
     #
     # @api private
     class Cache < AbstractCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(T.any(Integer, Symbol))) }
       def self.min_named
         :cask
       end
 
+      sig { returns(String) }
       def self.description
         "Display the file used to cache a <cask>."
       end
 
+      sig { returns(String) }
       def self.command_name
         "--cache"
       end
 
+      sig { void }
       def run
         casks.each do |cask|
           puts self.class.cached_location(cask)
diff --git a/Library/Homebrew/cask/cmd/abstract_command.rb b/Library/Homebrew/cask/cmd/abstract_command.rb
index cf4ca79a0d6b7a6295fb17e3ec06205c03fbd4eb..acea33ce5811aaa69f208abc9cfaf9ec6fdadae7 100644
--- a/Library/Homebrew/cask/cmd/abstract_command.rb
+++ b/Library/Homebrew/cask/cmd/abstract_command.rb
@@ -9,16 +9,22 @@ module Cask
     #
     # @api private
     class AbstractCommand
+      extend T::Sig
+      extend T::Helpers
+
       include Homebrew::Search
 
+      sig { returns(T.nilable(T.any(Integer, Symbol))) }
       def self.min_named
         nil
       end
 
+      sig { returns(T.nilable(Integer)) }
       def self.max_named
         nil
       end
 
+      sig { returns(String) }
       def self.banner_args
         if min_named == :cask && max_named != 1
           " <cask>"
@@ -29,6 +35,7 @@ module Cask
         end
       end
 
+      sig { returns(String) }
       def self.banner_headline
         "`#{command_name}` [<options>]#{banner_args}"
       end
@@ -72,24 +79,29 @@ module Cask
         end
       end
 
+      sig { returns(String) }
       def self.command_name
         @command_name ||= name.sub(/^.*:/, "").gsub(/(.)([A-Z])/, '\1_\2').downcase
       end
 
+      sig { returns(T::Boolean) }
       def self.abstract?
         name.split("::").last.match?(/^Abstract[^a-z]/)
       end
 
+      sig { returns(T::Boolean) }
       def self.visible?
         true
       end
 
+      sig { returns(String) }
       def self.help
         parser.generate_help_text
       end
 
+      sig { returns(String) }
       def self.short_description
-        description.split(".").first
+        description[/\A[^.]*\./]
       end
 
       def self.run(*args)
diff --git a/Library/Homebrew/cask/cmd/abstract_internal_command.rb b/Library/Homebrew/cask/cmd/abstract_internal_command.rb
index 7ccc3937b7ffba1e519e2edd2dad19a3a725f34f..a0a45e8b1b635cd5d06d8bf035300ec36a05c76a 100644
--- a/Library/Homebrew/cask/cmd/abstract_internal_command.rb
+++ b/Library/Homebrew/cask/cmd/abstract_internal_command.rb
@@ -7,10 +7,14 @@ module Cask
     #
     # @api private
     class AbstractInternalCommand < AbstractCommand
+      extend T::Sig
+
+      sig { returns(String) }
       def self.command_name
         super.sub(/^internal_/i, "_")
       end
 
+      sig { returns(T::Boolean) }
       def self.visible?
         false
       end
diff --git a/Library/Homebrew/cask/cmd/audit.rb b/Library/Homebrew/cask/cmd/audit.rb
index 6deeb84f8e9970d34b3470ade810f8036696d293..dcfd98741c3c4cb5c3bd59a76f2b6eedfa836198 100644
--- a/Library/Homebrew/cask/cmd/audit.rb
+++ b/Library/Homebrew/cask/cmd/audit.rb
@@ -9,6 +9,9 @@ module Cask
     #
     # @api private
     class Audit < AbstractCommand
+      extend T::Sig
+
+      sig { returns(String) }
       def self.description
         <<~EOS
           Check <cask> for Homebrew coding style violations. This should be run before
@@ -37,6 +40,7 @@ module Cask
         end
       end
 
+      sig { void }
       def run
         require "cask/auditor"
 
diff --git a/Library/Homebrew/cask/cmd/cat.rb b/Library/Homebrew/cask/cmd/cat.rb
index fb7944300094abdfcfdf24f50b23dd3abbbb0ae2..d5d2afdc6ae1584c8a7ece5d0fc5ed00b6364412 100644
--- a/Library/Homebrew/cask/cmd/cat.rb
+++ b/Library/Homebrew/cask/cmd/cat.rb
@@ -7,14 +7,19 @@ module Cask
     #
     # @api private
     class Cat < AbstractCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(T.any(Integer, Symbol))) }
       def self.min_named
         :cask
       end
 
+      sig { returns(String) }
       def self.description
         "Dump raw source of a <cask> to the standard output."
       end
 
+      sig { void }
       def run
         casks.each do |cask|
           if Homebrew::EnvConfig.bat?
diff --git a/Library/Homebrew/cask/cmd/create.rb b/Library/Homebrew/cask/cmd/create.rb
index 7ae14dc7d5337977e374eeb58cc45c050df28c8e..c03b1611ff18524e91997c4efc09c710290bc983 100644
--- a/Library/Homebrew/cask/cmd/create.rb
+++ b/Library/Homebrew/cask/cmd/create.rb
@@ -7,14 +7,19 @@ module Cask
     #
     # @api private
     class Create < AbstractCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(T.any(Integer, Symbol))) }
       def self.min_named
         :cask
       end
 
+      sig { override.returns(T.nilable(Integer)) }
       def self.max_named
         1
       end
 
+      sig { returns(String) }
       def self.description
         "Creates the given <cask> and opens it in an editor."
       end
@@ -25,6 +30,7 @@ module Cask
         raise UsageError, "Only one cask can be created at a time."
       end
 
+      sig { void }
       def run
         cask_token = args.named.first
         cask_path = CaskLoader.path(cask_token)
diff --git a/Library/Homebrew/cask/cmd/doctor.rb b/Library/Homebrew/cask/cmd/doctor.rb
index 0c80dcef21e8d115dbca2c50e46f1db50eaad948..c2565191ad8af2090ab6b911d1c4ef3174088374 100644
--- a/Library/Homebrew/cask/cmd/doctor.rb
+++ b/Library/Homebrew/cask/cmd/doctor.rb
@@ -7,14 +7,19 @@ module Cask
     #
     # @api private
     class Doctor < AbstractCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(Integer)) }
       def self.max_named
         0
       end
 
+      sig { returns(String) }
       def self.description
         "Checks for configuration issues."
       end
 
+      sig { void }
       def run
         require "diagnostic"
 
diff --git a/Library/Homebrew/cask/cmd/edit.rb b/Library/Homebrew/cask/cmd/edit.rb
index bea10bf630576a8c6cb52900af88f9f6c744d48b..ca01e711c339b2c96cde97cdfe73d7b79ad2376e 100644
--- a/Library/Homebrew/cask/cmd/edit.rb
+++ b/Library/Homebrew/cask/cmd/edit.rb
@@ -7,14 +7,19 @@ module Cask
     #
     # @api private
     class Edit < AbstractCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(T.any(Integer, Symbol))) }
       def self.min_named
         :cask
       end
 
+      sig { override.returns(T.nilable(Integer)) }
       def self.max_named
         1
       end
 
+      sig { returns(String) }
       def self.description
         "Open the given <cask> for editing."
       end
@@ -25,6 +30,7 @@ module Cask
         raise UsageError, "Only one cask can be edited at a time."
       end
 
+      sig { void }
       def run
         exec_editor cask_path
       rescue CaskUnavailableError => e
diff --git a/Library/Homebrew/cask/cmd/fetch.rb b/Library/Homebrew/cask/cmd/fetch.rb
index d9b33518325ad8221eb1e905cda49c667d40cafe..7add6ae1dc8a0f9949c859b3697484aa131e3f53 100644
--- a/Library/Homebrew/cask/cmd/fetch.rb
+++ b/Library/Homebrew/cask/cmd/fetch.rb
@@ -7,6 +7,9 @@ module Cask
     #
     # @api private
     class Fetch < AbstractCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(T.any(Integer, Symbol))) }
       def self.min_named
         :cask
       end
@@ -18,10 +21,12 @@ module Cask
         end
       end
 
+      sig { returns(String) }
       def self.description
         "Downloads remote application files to local cache."
       end
 
+      sig { void }
       def run
         require "cask/download"
         require "cask/installer"
diff --git a/Library/Homebrew/cask/cmd/help.rb b/Library/Homebrew/cask/cmd/help.rb
index 721ac40842fabd4f5b38d8a48b1176449b49ff4f..7a3a2cba4d27be65d9c9daa5c398c40aaf7d8987 100644
--- a/Library/Homebrew/cask/cmd/help.rb
+++ b/Library/Homebrew/cask/cmd/help.rb
@@ -7,14 +7,19 @@ module Cask
     #
     # @api private
     class Help < AbstractCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(Integer)) }
       def self.max_named
         1
       end
 
+      sig { returns(String) }
       def self.description
         "Print help for `cask` commands."
       end
 
+      sig { void }
       def run
         if args.named.empty?
           puts Cmd.parser.generate_help_text
diff --git a/Library/Homebrew/cask/cmd/home.rb b/Library/Homebrew/cask/cmd/home.rb
index 8087f21faac30c2624aa2ac40901ad657d66dd01..6beaf0ac2cc281d87c28046358fe2a12131bf64b 100644
--- a/Library/Homebrew/cask/cmd/home.rb
+++ b/Library/Homebrew/cask/cmd/home.rb
@@ -7,10 +7,14 @@ module Cask
     #
     # @api private
     class Home < AbstractCommand
+      extend T::Sig
+
+      sig { returns(String) }
       def self.description
         "Opens the homepage of the given <cask>. If no cask is given, opens the Homebrew homepage."
       end
 
+      sig { void }
       def run
         if casks.none?
           odebug "Opening project homepage"
diff --git a/Library/Homebrew/cask/cmd/info.rb b/Library/Homebrew/cask/cmd/info.rb
index e4e0797f72547a54db926b758dc33b54596fe80b..1ffebfa177626a618df074944d000ed7b7324cde 100644
--- a/Library/Homebrew/cask/cmd/info.rb
+++ b/Library/Homebrew/cask/cmd/info.rb
@@ -9,10 +9,14 @@ module Cask
     #
     # @api private
     class Info < AbstractCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(T.any(Integer, Symbol))) }
       def self.min_named
         :cask
       end
 
+      sig { returns(String) }
       def self.description
         "Displays information about the given <cask>."
       end
@@ -42,6 +46,7 @@ module Cask
         end
       end
 
+      sig { void }
       def run
         if args.json == "v1"
           puts JSON.generate(args.named.to_casks.map(&:to_h))
diff --git a/Library/Homebrew/cask/cmd/install.rb b/Library/Homebrew/cask/cmd/install.rb
index a5ad63d19c77168bdcc41a46af53845c7934d445..6dceac276752a3dd76a1d52fa1ddc11c874da517 100644
--- a/Library/Homebrew/cask/cmd/install.rb
+++ b/Library/Homebrew/cask/cmd/install.rb
@@ -7,10 +7,14 @@ module Cask
     #
     # @api private
     class Install < AbstractCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(T.any(Integer, Symbol))) }
       def self.min_named
         :cask
       end
 
+      sig { returns(String) }
       def self.description
         "Installs the given <cask>."
       end
@@ -34,6 +38,7 @@ module Cask
         end
       end
 
+      sig { void }
       def run
         self.class.install_casks(
           *casks,
diff --git a/Library/Homebrew/cask/cmd/internal_help.rb b/Library/Homebrew/cask/cmd/internal_help.rb
index 2091f48f95f3e9166e8527b8d99e3e9e36908dad..3f6476e29a3f1d1b2616f2cca8ed76330038ed3a 100644
--- a/Library/Homebrew/cask/cmd/internal_help.rb
+++ b/Library/Homebrew/cask/cmd/internal_help.rb
@@ -7,14 +7,19 @@ module Cask
     #
     # @api private
     class InternalHelp < AbstractInternalCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(Integer)) }
       def self.max_named
         0
       end
 
+      sig { returns(String) }
       def self.description
         "Print help for unstable internal-use commands."
       end
 
+      sig { void }
       def run
         max_command_len = Cmd.commands.map(&:length).max
         puts "Unstable Internal-use Commands:\n\n"
diff --git a/Library/Homebrew/cask/cmd/internal_stanza.rb b/Library/Homebrew/cask/cmd/internal_stanza.rb
index 95335690e1cb5c58e6070d3f963e787973862d77..3183588b8258c00c99fad7e945c1da51b91790cb 100644
--- a/Library/Homebrew/cask/cmd/internal_stanza.rb
+++ b/Library/Homebrew/cask/cmd/internal_stanza.rb
@@ -9,6 +9,8 @@ module Cask
     #
     # @api private
     class InternalStanza < AbstractInternalCommand
+      extend T::Sig
+
       # Syntax
       #
       #     brew cask _stanza <stanza_name> [ --quiet ] [ --table | --yaml ] [ <cask_token> ... ]
@@ -24,14 +26,17 @@ module Cask
         (DSL::ORDINARY_ARTIFACT_CLASSES.map(&:dsl_key) +
          DSL::ARTIFACT_BLOCK_CLASSES.map(&:dsl_key)).freeze
 
+      sig { override.returns(T.nilable(T.any(Integer, Symbol))) }
       def self.min_named
         1
       end
 
+      sig { returns(String) }
       def self.banner_args
         " <stanza_name> [<cask>]"
       end
 
+      sig { returns(String) }
       def self.description
         <<~EOS
           Extract and render a specific stanza for the given <cask>.
@@ -80,6 +85,7 @@ module Cask
         EOS
       end
 
+      sig { void }
       def run
         if ARTIFACTS.include?(stanza)
           artifact_name = stanza
diff --git a/Library/Homebrew/cask/cmd/list.rb b/Library/Homebrew/cask/cmd/list.rb
index 859d650a9ce0d3a89246079296414cb82cf1070d..7c780c2464c9aa04ffff192817de91b321690583 100644
--- a/Library/Homebrew/cask/cmd/list.rb
+++ b/Library/Homebrew/cask/cmd/list.rb
@@ -9,6 +9,9 @@ module Cask
     #
     # @api private
     class List < AbstractCommand
+      extend T::Sig
+
+      sig { returns(String) }
       def self.description
         "Lists installed casks or the casks provided in the arguments."
       end
@@ -26,6 +29,7 @@ module Cask
         end
       end
 
+      sig { void }
       def run
         self.class.list_casks(
           *casks,
diff --git a/Library/Homebrew/cask/cmd/outdated.rb b/Library/Homebrew/cask/cmd/outdated.rb
index ff35a1f2d6bd651f6bffe18b8d7e7ec94595d11f..791f465333b8a8cc65ec7efe522e56647fd94136 100644
--- a/Library/Homebrew/cask/cmd/outdated.rb
+++ b/Library/Homebrew/cask/cmd/outdated.rb
@@ -7,6 +7,9 @@ module Cask
     #
     # @api private
     class Outdated < AbstractCommand
+      extend T::Sig
+
+      sig { returns(String) }
       def self.description
         "List the outdated installed casks."
       end
@@ -20,6 +23,7 @@ module Cask
         end
       end
 
+      sig { void }
       def run
         outdated_casks = casks(alternative: -> { Caskroom.casks(config: Config.from_args(args)) }).select do |cask|
           odebug "Checking update info of Cask #{cask}"
diff --git a/Library/Homebrew/cask/cmd/reinstall.rb b/Library/Homebrew/cask/cmd/reinstall.rb
index 79e0dccc444daf8c45a19a6b46c66a59825ed4f0..5d0af8617724662b0b3d141665b8e6c55dc35bd8 100644
--- a/Library/Homebrew/cask/cmd/reinstall.rb
+++ b/Library/Homebrew/cask/cmd/reinstall.rb
@@ -7,10 +7,14 @@ module Cask
     #
     # @api private
     class Reinstall < Install
+      extend T::Sig
+
+      sig { returns(String) }
       def self.description
         "Reinstalls the given <cask>."
       end
 
+      sig { void }
       def run
         self.class.reinstall_casks(
           *casks,
diff --git a/Library/Homebrew/cask/cmd/style.rb b/Library/Homebrew/cask/cmd/style.rb
index 1d07156306b8956d9ba2f50f26864d27a9190ccb..f0f1c34995605c824f837b0f03a50e0170a65907 100644
--- a/Library/Homebrew/cask/cmd/style.rb
+++ b/Library/Homebrew/cask/cmd/style.rb
@@ -10,6 +10,9 @@ module Cask
     #
     # @api private
     class Style < AbstractCommand
+      extend T::Sig
+
+      sig { returns(String) }
       def self.description
         "Checks style of the given <cask> using RuboCop."
       end
@@ -21,6 +24,7 @@ module Cask
         end
       end
 
+      sig { void }
       def run
         success = Homebrew::Style.check_style_and_print(
           cask_paths,
diff --git a/Library/Homebrew/cask/cmd/uninstall.rb b/Library/Homebrew/cask/cmd/uninstall.rb
index 8011193348a1bdd5cecb463c69e482e7add7eeb6..4fd6ac898024945bca83146f9c34cef29c7aac7f 100644
--- a/Library/Homebrew/cask/cmd/uninstall.rb
+++ b/Library/Homebrew/cask/cmd/uninstall.rb
@@ -7,10 +7,14 @@ module Cask
     #
     # @api private
     class Uninstall < AbstractCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(T.any(Integer, Symbol))) }
       def self.min_named
         :cask
       end
 
+      sig { returns(String) }
       def self.description
         "Uninstalls the given <cask>."
       end
@@ -23,6 +27,7 @@ module Cask
         end
       end
 
+      sig { void }
       def run
         self.class.uninstall_casks(
           *casks,
diff --git a/Library/Homebrew/cask/cmd/upgrade.rb b/Library/Homebrew/cask/cmd/upgrade.rb
index 56bcbd529c90da4650626c218f02e638bb8df2b9..81994865277ddfa0488757cc8dd8c093e0499ea3 100644
--- a/Library/Homebrew/cask/cmd/upgrade.rb
+++ b/Library/Homebrew/cask/cmd/upgrade.rb
@@ -10,6 +10,9 @@ module Cask
     #
     # @api private
     class Upgrade < AbstractCommand
+      extend T::Sig
+
+      sig { returns(String) }
       def self.description
         "Upgrades all outdated casks or the specified casks."
       end
@@ -36,6 +39,7 @@ module Cask
         end
       end
 
+      sig { void }
       def run
         verbose = ($stdout.tty? || args.verbose?) && !args.quiet?
         self.class.upgrade_casks(
diff --git a/Library/Homebrew/cask/cmd/zap.rb b/Library/Homebrew/cask/cmd/zap.rb
index 2898883ef68bf305fd34e771850ed826cf987613..d5b5dc3c80a2c5b4bf52dbd168f406649f937912 100644
--- a/Library/Homebrew/cask/cmd/zap.rb
+++ b/Library/Homebrew/cask/cmd/zap.rb
@@ -7,10 +7,14 @@ module Cask
     #
     # @api private
     class Zap < AbstractCommand
+      extend T::Sig
+
+      sig { override.returns(T.nilable(T.any(Integer, Symbol))) }
       def self.min_named
         :cask
       end
 
+      sig { returns(String) }
       def self.description
         <<~EOS
           Zaps all files associated with the given <cask>. Implicitly also performs all actions associated with `uninstall`.
@@ -26,6 +30,7 @@ module Cask
         end
       end
 
+      sig { void }
       def run
         require "cask/installer"
 
diff --git a/Library/Homebrew/cask/denylist.rb b/Library/Homebrew/cask/denylist.rb
index 8cbc9c37a2871f60f4f38104153b950b2590a7ec..c6fd811c7d126e2ec7751deb8d068ffe995a6fc5 100644
--- a/Library/Homebrew/cask/denylist.rb
+++ b/Library/Homebrew/cask/denylist.rb
@@ -1,4 +1,4 @@
-# typed: true
+# typed: strict
 # frozen_string_literal: true
 
 module Cask
@@ -6,6 +6,9 @@ module Cask
   #
   # @api private
   module Denylist
+    extend T::Sig
+
+    sig { params(name: String).returns(T.nilable(String)) }
     def self.reason(name)
       case name
       when /^adobe-(after|illustrator|indesign|photoshop|premiere)/
diff --git a/Library/Homebrew/cask/dsl/version.rb b/Library/Homebrew/cask/dsl/version.rb
index a43658b182c6b5f9495afce0c6a1afc358e05d8b..e2574db7290f26e46f08fd89203bb5650ede2bf6 100644
--- a/Library/Homebrew/cask/dsl/version.rb
+++ b/Library/Homebrew/cask/dsl/version.rb
@@ -7,6 +7,8 @@ module Cask
     #
     # @api private
     class Version < ::String
+      extend T::Sig
+
       DIVIDERS = {
         "." => :dots,
         "-" => :hyphens,
@@ -62,6 +64,7 @@ module Cask
 
       attr_reader :raw_version
 
+      sig { params(raw_version: T.nilable(T.any(String, Symbol))).void }
       def initialize(raw_version)
         @raw_version = raw_version
         super(raw_version.to_s)
@@ -73,6 +76,7 @@ module Cask
         raw_version.scan(INVALID_CHARACTERS)
       end
 
+      sig { returns(T::Boolean) }
       def unstable?
         return false if latest?
 
@@ -84,6 +88,7 @@ module Cask
         false
       end
 
+      sig { returns(T::Boolean) }
       def latest?
         to_s == "latest"
       end
@@ -134,6 +139,7 @@ module Cask
 
       private
 
+      sig { returns(T.self_type) }
       def version
         return self if empty? || latest?
 
diff --git a/Library/Homebrew/cask/exceptions.rb b/Library/Homebrew/cask/exceptions.rb
index 645ea8a0e4f923c47a4a942246d494ab66213586..b5576e9dee0fc08390cbd3089ebe7321c7dbd29f 100644
--- a/Library/Homebrew/cask/exceptions.rb
+++ b/Library/Homebrew/cask/exceptions.rb
@@ -11,12 +11,15 @@ module Cask
   #
   # @api private
   class MultipleCaskErrors < CaskError
+    extend T::Sig
+
     def initialize(errors)
       super()
 
       @errors = errors
     end
 
+    sig { returns(String) }
     def to_s
       <<~EOS
         Problems with multiple casks:
@@ -29,12 +32,18 @@ module Cask
   #
   # @api private
   class AbstractCaskErrorWithToken < CaskError
-    attr_reader :token, :reason
+    extend T::Sig
+
+    sig { returns(String) }
+    attr_reader :token
+
+    sig { returns(String) }
+    attr_reader :reason
 
     def initialize(token, reason = nil)
       super()
 
-      @token = token
+      @token = token.to_s
       @reason = reason.to_s
     end
   end
@@ -43,6 +52,9 @@ module Cask
   #
   # @api private
   class CaskNotInstalledError < AbstractCaskErrorWithToken
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       "Cask '#{token}' is not installed."
     end
@@ -52,6 +64,8 @@ module Cask
   #
   # @api private
   class CaskConflictError < AbstractCaskErrorWithToken
+    extend T::Sig
+
     attr_reader :conflicting_cask
 
     def initialize(token, conflicting_cask)
@@ -59,6 +73,7 @@ module Cask
       @conflicting_cask = conflicting_cask
     end
 
+    sig { returns(String) }
     def to_s
       "Cask '#{token}' conflicts with '#{conflicting_cask}'."
     end
@@ -68,6 +83,9 @@ module Cask
   #
   # @api private
   class CaskUnavailableError < AbstractCaskErrorWithToken
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       "Cask '#{token}' is unavailable#{reason.empty? ? "." : ": #{reason}"}"
     end
@@ -77,6 +95,9 @@ module Cask
   #
   # @api private
   class CaskUnreadableError < CaskUnavailableError
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       "Cask '#{token}' is unreadable#{reason.empty? ? "." : ": #{reason}"}"
     end
@@ -86,6 +107,9 @@ module Cask
   #
   # @api private
   class CaskAlreadyCreatedError < AbstractCaskErrorWithToken
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       %Q(Cask '#{token}' already exists. Run #{Formatter.identifier("brew cask edit #{token}")} to edit it.)
     end
@@ -95,6 +119,9 @@ module Cask
   #
   # @api private
   class CaskAlreadyInstalledError < AbstractCaskErrorWithToken
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       <<~EOS
         Cask '#{token}' is already installed.
@@ -109,6 +136,9 @@ module Cask
   #
   # @api private
   class CaskX11DependencyError < AbstractCaskErrorWithToken
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       <<~EOS
         Cask '#{token}' requires XQuartz/X11, which can be installed using Homebrew Cask by running:
@@ -124,6 +154,9 @@ module Cask
   #
   # @api private
   class CaskCyclicDependencyError < AbstractCaskErrorWithToken
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       "Cask '#{token}' includes cyclic dependencies on other Casks#{reason.empty? ? "." : ": #{reason}"}"
     end
@@ -133,6 +166,9 @@ module Cask
   #
   # @api private
   class CaskSelfReferencingDependencyError < CaskCyclicDependencyError
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       "Cask '#{token}' depends on itself."
     end
@@ -142,6 +178,9 @@ module Cask
   #
   # @api private
   class CaskUnspecifiedError < CaskError
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       "This command requires a Cask token."
     end
@@ -151,6 +190,9 @@ module Cask
   #
   # @api private
   class CaskInvalidError < AbstractCaskErrorWithToken
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       "Cask '#{token}' definition is invalid#{reason.empty? ? "." : ": #{reason}"}"
     end
@@ -182,6 +224,9 @@ module Cask
   #
   # @api private
   class CaskSha256MissingError < CaskSha256Error
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       <<~EOS
         Cask '#{token}' requires a checksum:
@@ -194,6 +239,8 @@ module Cask
   #
   # @api private
   class CaskSha256MismatchError < CaskSha256Error
+    extend T::Sig
+
     attr_reader :path
 
     def initialize(token, expected, actual, path)
@@ -201,6 +248,7 @@ module Cask
       @path = path
     end
 
+    sig { returns(String) }
     def to_s
       <<~EOS
         Checksum for Cask '#{token}' does not match.
@@ -218,6 +266,9 @@ module Cask
   #
   # @api private
   class CaskNoShasumError < CaskSha256Error
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       <<~EOS
         Cask '#{token}' does not have a sha256 checksum defined and was not installed.
@@ -230,6 +281,8 @@ module Cask
   #
   # @api private
   class CaskQuarantineError < CaskError
+    extend T::Sig
+
     attr_reader :path, :reason
 
     def initialize(path, reason)
@@ -239,6 +292,7 @@ module Cask
       @reason = reason
     end
 
+    sig { returns(String) }
     def to_s
       s = +"Failed to quarantine #{path}."
 
@@ -256,6 +310,9 @@ module Cask
   #
   # @api private
   class CaskQuarantinePropagationError < CaskQuarantineError
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       s = +"Failed to quarantine one or more files within #{path}."
 
@@ -273,6 +330,9 @@ module Cask
   #
   # @api private
   class CaskQuarantineReleaseError < CaskQuarantineError
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       s = +"Failed to release #{path} from quarantine."
 
diff --git a/Library/Homebrew/cask/installer.rb b/Library/Homebrew/cask/installer.rb
index f0310a11977e64d3a92f975167028744f27b7293..481307d800b6d919447198fc0cbc6d07751689ee 100644
--- a/Library/Homebrew/cask/installer.rb
+++ b/Library/Homebrew/cask/installer.rb
@@ -18,6 +18,8 @@ module Cask
   #
   # @api private
   class Installer
+    extend T::Sig
+
     extend Predicable
     # TODO: it is unwise for Cask::Staged to be a module, when we are
     #       dealing with both staged and unstaged casks here. This should
@@ -142,6 +144,7 @@ module Cask
       Installer.new(installed_cask, binaries: binaries?, verbose: verbose?, force: true, upgrade: upgrade?).uninstall
     end
 
+    sig { returns(String) }
     def summary
       s = +""
       s << "#{Homebrew::EnvConfig.install_badge}  " unless Homebrew::EnvConfig.no_emoji?
diff --git a/Library/Homebrew/cask/quarantine.rb b/Library/Homebrew/cask/quarantine.rb
index 14e74c7af0b0e3b2e688584225bd135d4dd9b13d..de24b35d331fecebc4fbe7575e6bfa6553abf70f 100644
--- a/Library/Homebrew/cask/quarantine.rb
+++ b/Library/Homebrew/cask/quarantine.rb
@@ -9,6 +9,8 @@ module Cask
   #
   # @api private
   module Quarantine
+    extend T::Sig
+
     module_function
 
     QUARANTINE_ATTRIBUTE = "com.apple.quarantine"
@@ -25,6 +27,7 @@ module Cask
     end
     private :xattr
 
+    sig { returns(Symbol) }
     def check_quarantine_support
       odebug "Checking quarantine support"
 
diff --git a/Library/Homebrew/cask/utils.rb b/Library/Homebrew/cask/utils.rb
index 47f804df23393500f18236daeaaec3baa834a2bd..c9e831aebe44ac133e018315030446244bba7078 100644
--- a/Library/Homebrew/cask/utils.rb
+++ b/Library/Homebrew/cask/utils.rb
@@ -13,6 +13,8 @@ module Cask
   #
   # @api private
   module Utils
+    extend T::Sig
+
     def self.gain_permissions_remove(path, command: SystemCommand)
       if path.respond_to?(:rmtree) && path.exist?
         gain_permissions(path, ["-R"], command) do |p|
@@ -72,10 +74,12 @@ module Cask
       end
     end
 
+    sig { params(path: Pathname).returns(T::Boolean) }
     def self.path_occupied?(path)
-      File.exist?(path) || File.symlink?(path)
+      path.exist? || path.symlink?
     end
 
+    sig { returns(String) }
     def self.error_message_with_suggestions
       <<~EOS
         Follow the instructions here:
diff --git a/Library/Homebrew/cli/args.rb b/Library/Homebrew/cli/args.rb
index 1a779dcbdfe6144b215a399225899dbf05af87e6..d8f69c60775308f69c56d084e162e674c08d2f40 100644
--- a/Library/Homebrew/cli/args.rb
+++ b/Library/Homebrew/cli/args.rb
@@ -7,11 +7,14 @@ require "ostruct"
 module Homebrew
   module CLI
     class Args < OpenStruct
+      extend T::Sig
+
       attr_reader :options_only, :flags_only
 
       # undefine tap to allow --tap argument
       undef tap
 
+      sig { void }
       def initialize
         super()
 
@@ -131,6 +134,7 @@ module Homebrew
         flag_with_value.delete_prefix(arg_prefix)
       end
 
+      sig { returns(Context::ContextStruct) }
       def context
         Context::ContextStruct.new(debug: debug?, quiet: quiet?, verbose: verbose?)
       end
diff --git a/Library/Homebrew/cli/parser.rb b/Library/Homebrew/cli/parser.rb
index f9653219f7e11dc345619d375c25612252c7add3..a758d4ece97cb803f295b907128fc3ef8866279b 100644
--- a/Library/Homebrew/cli/parser.rb
+++ b/Library/Homebrew/cli/parser.rb
@@ -14,6 +14,8 @@ OPTION_DESC_WIDTH = 43
 module Homebrew
   module CLI
     class Parser
+      extend T::Sig
+
       attr_reader :processed_options, :hide_from_man_page
 
       def self.from_cmd_path(cmd_path)
@@ -94,6 +96,7 @@ module Homebrew
         ]
       end
 
+      sig { returns(T::Array[[String, String, String]]) }
       def self.global_options
         [
           ["-d", "--debug",   "Display any debugging information."],
@@ -103,6 +106,9 @@ module Homebrew
         ]
       end
 
+      # FIXME: Block should be `T.nilable(T.proc.bind(Parser).void)`.
+      # See https://github.com/sorbet/sorbet/issues/498.
+      sig { params(block: T.proc.bind(Parser).void).void.checked(:never) }
       def initialize(&block)
         @parser = OptionParser.new
 
@@ -331,6 +337,7 @@ module Homebrew
         end
       end
 
+      sig { void }
       def formula_options
         @formula_options = true
       end
@@ -367,6 +374,7 @@ module Homebrew
         end
       end
 
+      sig { void }
       def hide_from_man_page!
         @hide_from_man_page = true
       end
@@ -454,20 +462,24 @@ module Homebrew
       end
 
       def check_named_args(args)
-        min_exception = case @min_named_type
-        when :cask
-          Cask::CaskUnspecifiedError
-        when :formula
-          FormulaUnspecifiedError
-        when :formula_or_cask
-          FormulaOrCaskUnspecifiedError
-        when :keg
-          KegUnspecifiedError
-        else
-          MinNamedArgumentsError.new(@min_named_args)
+        exception = if @min_named_args && args.size < @min_named_args
+          case @min_named_type
+          when :cask
+            Cask::CaskUnspecifiedError
+          when :formula
+            FormulaUnspecifiedError
+          when :formula_or_cask
+            FormulaOrCaskUnspecifiedError
+          when :keg
+            KegUnspecifiedError
+          else
+            MinNamedArgumentsError.new(@min_named_args)
+          end
+        elsif @max_named_args && args.size > @max_named_args
+          MaxNamedArgumentsError.new(@max_named_args)
         end
-        raise min_exception if @min_named_args && args.size < @min_named_args
-        raise MaxNamedArgumentsError, @max_named_args if @max_named_args && args.size > @max_named_args
+
+        raise exception if exception
       end
 
       def process_option(*args)
@@ -535,6 +547,9 @@ module Homebrew
     end
 
     class MaxNamedArgumentsError < UsageError
+      extend T::Sig
+
+      sig { params(maximum: Integer).void }
       def initialize(maximum)
         super case maximum
         when 0
@@ -546,6 +561,9 @@ module Homebrew
     end
 
     class MinNamedArgumentsError < UsageError
+      extend T::Sig
+
+      sig { params(minimum: Integer).void }
       def initialize(minimum)
         super "This command requires at least #{minimum} named #{"argument".pluralize(minimum)}."
       end
diff --git a/Library/Homebrew/cmd/--cache.rb b/Library/Homebrew/cmd/--cache.rb
index 3a5270806547f99a74afeef76b052448cb25ff04..78e6df0fa554b6fac4929e677e2d98b4abf70972 100644
--- a/Library/Homebrew/cmd/--cache.rb
+++ b/Library/Homebrew/cmd/--cache.rb
@@ -6,10 +6,13 @@ require "cli/parser"
 require "cask/download"
 
 module Homebrew
+  extend T::Sig
+
   extend Fetch
 
   module_function
 
+  sig { returns(CLI::Parser) }
   def __cache_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/--caskroom.rb b/Library/Homebrew/cmd/--caskroom.rb
index b53574fd0a045a913988c566db8060202a0c5360..6facedc9c8b2ea46daf103503c305079f036da45 100644
--- a/Library/Homebrew/cmd/--caskroom.rb
+++ b/Library/Homebrew/cmd/--caskroom.rb
@@ -1,9 +1,12 @@
-# typed: false
+# typed: strict
 # frozen_string_literal: true
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def __caskroom_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
@@ -17,6 +20,7 @@ module Homebrew
     end
   end
 
+  sig { void }
   def __caskroom
     args = __caskroom_args.parse
 
diff --git a/Library/Homebrew/cmd/--env.rb b/Library/Homebrew/cmd/--env.rb
index 45b609ca53cc862ad282bc96ffcb570ef0dd90d1..b4448f573eb1482d8d991a92bf5251dd2f4b3f45 100644
--- a/Library/Homebrew/cmd/--env.rb
+++ b/Library/Homebrew/cmd/--env.rb
@@ -7,8 +7,11 @@ require "utils/shell"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def __env_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/--prefix.rb b/Library/Homebrew/cmd/--prefix.rb
index b451a24f7b7b518ac705123d964b759c48d34c04..42410ab30a13bb6fe25ed088e2bba99a66492164 100644
--- a/Library/Homebrew/cmd/--prefix.rb
+++ b/Library/Homebrew/cmd/--prefix.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def __prefix_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/--repository.rb b/Library/Homebrew/cmd/--repository.rb
index 042c39b36d84cd451d442845c22064650defe90e..c27c4589fd10d0fa6e6ab32afefb51fb8d3e05d0 100644
--- a/Library/Homebrew/cmd/--repository.rb
+++ b/Library/Homebrew/cmd/--repository.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def __repository_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/--version.rb b/Library/Homebrew/cmd/--version.rb
index 93595a9a3dda8b3bc49930318290ab8ada844e1b..531b0b119c83db9e49742200715ad0ef861d1ab8 100644
--- a/Library/Homebrew/cmd/--version.rb
+++ b/Library/Homebrew/cmd/--version.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def __version_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/analytics.rb b/Library/Homebrew/cmd/analytics.rb
index 957b175b859e1c0de9b54534653a59331046a670..12e545f3525591cd5bf9f6d3a506ec41e80ccbcf 100644
--- a/Library/Homebrew/cmd/analytics.rb
+++ b/Library/Homebrew/cmd/analytics.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def analytics_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/cleanup.rb b/Library/Homebrew/cmd/cleanup.rb
index c0294392d73c45199119e65e95ba3a60de7397c0..0c7ac6df818ef6f38776d0455dcedac6208d3610 100644
--- a/Library/Homebrew/cmd/cleanup.rb
+++ b/Library/Homebrew/cmd/cleanup.rb
@@ -5,8 +5,11 @@ require "cleanup"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def cleanup_args
     Homebrew::CLI::Parser.new do
       days = Homebrew::EnvConfig::ENVS[:HOMEBREW_CLEANUP_MAX_AGE_DAYS][:default]
diff --git a/Library/Homebrew/cmd/commands.rb b/Library/Homebrew/cmd/commands.rb
index cbcb36a495b143fb02af4251954220b6e3fccbcb..92fed7e063531468df6453caf2c77885389e5b1a 100644
--- a/Library/Homebrew/cmd/commands.rb
+++ b/Library/Homebrew/cmd/commands.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def commands_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/config.rb b/Library/Homebrew/cmd/config.rb
index 562d9a9f1c94889cbcfde97b27f8d00ad1c1b98b..970af3093af9b5fae69e59417aa3794250765d70 100644
--- a/Library/Homebrew/cmd/config.rb
+++ b/Library/Homebrew/cmd/config.rb
@@ -5,8 +5,11 @@ require "system_config"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def config_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/deps.rb b/Library/Homebrew/cmd/deps.rb
index a5f8ade23aa17e8be76e6c25af84d11f875e269a..42e50c984a2a7cef786d4030ae90ef5365cd7878 100644
--- a/Library/Homebrew/cmd/deps.rb
+++ b/Library/Homebrew/cmd/deps.rb
@@ -8,10 +8,13 @@ require "cask/caskroom"
 require "dependencies_helpers"
 
 module Homebrew
+  extend T::Sig
+
   extend DependenciesHelpers
 
   module_function
 
+  sig { returns(CLI::Parser) }
   def deps_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/desc.rb b/Library/Homebrew/cmd/desc.rb
index e9616f1749a7750b1aa94ee3bfb7a66ddbcfb15c..b2b0b8675e70ed683679e2d4ade20202ff8af644 100644
--- a/Library/Homebrew/cmd/desc.rb
+++ b/Library/Homebrew/cmd/desc.rb
@@ -7,10 +7,13 @@ require "description_cache_store"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
   extend Search
 
+  sig { returns(CLI::Parser) }
   def desc_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/doctor.rb b/Library/Homebrew/cmd/doctor.rb
index 5d10f9f6553fc5e67e4e95e36e78c5c4f022d2d0..5a3136f1472543667992ec063581e4c83cc3e56d 100644
--- a/Library/Homebrew/cmd/doctor.rb
+++ b/Library/Homebrew/cmd/doctor.rb
@@ -6,8 +6,11 @@ require "cli/parser"
 require "cask/caskroom"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def doctor_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/fetch.rb b/Library/Homebrew/cmd/fetch.rb
index 9baa5cec4e4d1cb27de07cb6a8ddc33915694c8f..ac03b5df072419e24cc432c6994a5b2d77a996c2 100644
--- a/Library/Homebrew/cmd/fetch.rb
+++ b/Library/Homebrew/cmd/fetch.rb
@@ -6,10 +6,13 @@ require "fetch"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   extend Fetch
 
   module_function
 
+  sig { returns(CLI::Parser) }
   def fetch_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/gist-logs.rb b/Library/Homebrew/cmd/gist-logs.rb
index 7d3064c7e56476760ee8239218932d5a940a0ab7..d590fb35263c8fe29d22f93b4b4f1443ab87a9f3 100644
--- a/Library/Homebrew/cmd/gist-logs.rb
+++ b/Library/Homebrew/cmd/gist-logs.rb
@@ -9,10 +9,13 @@ require "socket"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   extend Install
 
   module_function
 
+  sig { returns(CLI::Parser) }
   def gist_logs_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/home.rb b/Library/Homebrew/cmd/home.rb
index 2c147bb6d666ab26d492bf3a93fc07b3ebcf07cd..2308392968934b0c5691a8ad3b9b7ded477a9919 100644
--- a/Library/Homebrew/cmd/home.rb
+++ b/Library/Homebrew/cmd/home.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def home_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/info.rb b/Library/Homebrew/cmd/info.rb
index ae94558803439bc2920a5ef0a665344e443abd13..74b0f3f46b4850b2fdc4d902a7590f797e1febed 100644
--- a/Library/Homebrew/cmd/info.rb
+++ b/Library/Homebrew/cmd/info.rb
@@ -13,12 +13,15 @@ require "utils/spdx"
 require "deprecate_disable"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
   VALID_DAYS = %w[30 90 365].freeze
   VALID_FORMULA_CATEGORIES = %w[install install-on-request build-error].freeze
   VALID_CATEGORIES = (VALID_FORMULA_CATEGORIES + %w[cask-install os-version]).freeze
 
+  sig { returns(CLI::Parser) }
   def info_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/install.rb b/Library/Homebrew/cmd/install.rb
index 3f72fa2b28a72376cc31eedeebdb4500f696ac67..436f607172e7347d5a44b2cba09b43c6ccdb7e7f 100644
--- a/Library/Homebrew/cmd/install.rb
+++ b/Library/Homebrew/cmd/install.rb
@@ -14,10 +14,13 @@ require "cli/parser"
 require "upgrade"
 
 module Homebrew
+  extend T::Sig
+
   extend Search
 
   module_function
 
+  sig { returns(CLI::Parser) }
   def install_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/leaves.rb b/Library/Homebrew/cmd/leaves.rb
index 7cb1497367da6811c8135f05fbbc98c50aca2017..f4c2c471a748b4cb37c7bf3e9d5d51ff91dfcf71 100644
--- a/Library/Homebrew/cmd/leaves.rb
+++ b/Library/Homebrew/cmd/leaves.rb
@@ -5,8 +5,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def leaves_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/link.rb b/Library/Homebrew/cmd/link.rb
index 6666f5576d4aa892dca812c4098e2aba63123f0e..98a265d6100150762446a68a0dc8a8210aa5a4ec 100644
--- a/Library/Homebrew/cmd/link.rb
+++ b/Library/Homebrew/cmd/link.rb
@@ -7,8 +7,11 @@ require "cli/parser"
 require "unlink"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def link_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/list.rb b/Library/Homebrew/cmd/list.rb
index 8fe034844e49b2f757be85859b9ce8da3f0f9de4..83788413bc8781c6bbd3324624a57805b51f44a7 100644
--- a/Library/Homebrew/cmd/list.rb
+++ b/Library/Homebrew/cmd/list.rb
@@ -7,8 +7,11 @@ require "cli/parser"
 require "cask/cmd"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def list_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/log.rb b/Library/Homebrew/cmd/log.rb
index f2d8b1c4e187d04c6b241e7d86aea558f9e340c6..5a24d9d1beec667635443f7bbd7d918d12ce3942 100644
--- a/Library/Homebrew/cmd/log.rb
+++ b/Library/Homebrew/cmd/log.rb
@@ -5,8 +5,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def log_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/migrate.rb b/Library/Homebrew/cmd/migrate.rb
index f400036c78b9b398aca2def82e867f706d7e0a44..b5bf51a008f439776054a7163519156e4faa30b1 100644
--- a/Library/Homebrew/cmd/migrate.rb
+++ b/Library/Homebrew/cmd/migrate.rb
@@ -5,8 +5,11 @@ require "migrator"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def migrate_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/missing.rb b/Library/Homebrew/cmd/missing.rb
index 4345227585a02434bf43bf45deefa209176fb70e..4ab86a49fcfe4151ea69289cd1df858531be0cad 100644
--- a/Library/Homebrew/cmd/missing.rb
+++ b/Library/Homebrew/cmd/missing.rb
@@ -7,8 +7,11 @@ require "diagnostic"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def missing_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/options.rb b/Library/Homebrew/cmd/options.rb
index 6ecc3c7fc97d3d505b37b85cc462a26eb5b98c4c..b94c0aa6f382115a9ac959d25b1c5be5f2d15de0 100644
--- a/Library/Homebrew/cmd/options.rb
+++ b/Library/Homebrew/cmd/options.rb
@@ -7,8 +7,11 @@ require "cli/parser"
 require "commands"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def options_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/outdated.rb b/Library/Homebrew/cmd/outdated.rb
index 623f4347293f7e0e9805e1ede070b3a546d0d118..d3261a337abde2a9f75d4acf235e4f425fbf6fc2 100644
--- a/Library/Homebrew/cmd/outdated.rb
+++ b/Library/Homebrew/cmd/outdated.rb
@@ -8,8 +8,11 @@ require "cask/cmd"
 require "cask/caskroom"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def outdated_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/pin.rb b/Library/Homebrew/cmd/pin.rb
index 0ca4458d927d18fddab40a8b4e331287831694bc..b777ac3b5f6ff117a9cc09a00b511f4c99a536fe 100644
--- a/Library/Homebrew/cmd/pin.rb
+++ b/Library/Homebrew/cmd/pin.rb
@@ -5,8 +5,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def pin_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/postinstall.rb b/Library/Homebrew/cmd/postinstall.rb
index 1b4885a36a3c00e7dbf4a292e57dcdffb77500c4..4bbee46b66f1273d06feebf7f019c7860a579c09 100644
--- a/Library/Homebrew/cmd/postinstall.rb
+++ b/Library/Homebrew/cmd/postinstall.rb
@@ -6,8 +6,11 @@ require "formula_installer"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def postinstall_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/readall.rb b/Library/Homebrew/cmd/readall.rb
index 5bfa660543755fcb16400c4a995deb5a639a4d9c..7a2361036cc23cd02d70b13ccc917bcbe2c9cd3f 100644
--- a/Library/Homebrew/cmd/readall.rb
+++ b/Library/Homebrew/cmd/readall.rb
@@ -5,8 +5,11 @@ require "readall"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def readall_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/reinstall.rb b/Library/Homebrew/cmd/reinstall.rb
index 93e4c12936f5ad0a751f4ae5d1e1c17041959126..4bc7a230c27a3ba970a88345772beaf22fc81af2 100644
--- a/Library/Homebrew/cmd/reinstall.rb
+++ b/Library/Homebrew/cmd/reinstall.rb
@@ -14,8 +14,11 @@ require "cask/macos"
 require "upgrade"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def reinstall_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/search.rb b/Library/Homebrew/cmd/search.rb
index beaa14edad3441d701812675e8727332a6426b38..7fc967ecb0a7448c800ba8173b4aded8f3feb82d 100644
--- a/Library/Homebrew/cmd/search.rb
+++ b/Library/Homebrew/cmd/search.rb
@@ -8,6 +8,8 @@ require "cli/parser"
 require "search"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
   extend Search
@@ -25,6 +27,7 @@ module Homebrew
     },
   }.freeze
 
+  sig { returns(CLI::Parser) }
   def search_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/switch.rb b/Library/Homebrew/cmd/switch.rb
index 0877f51d09d868b5588b79f4cf86ea65e6796d73..a78ef0a907a9da458ee80c7941fc455f4e11c5c0 100644
--- a/Library/Homebrew/cmd/switch.rb
+++ b/Library/Homebrew/cmd/switch.rb
@@ -6,8 +6,11 @@ require "keg"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def switch_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/tap-info.rb b/Library/Homebrew/cmd/tap-info.rb
index 6c01e4172abfb6a3a9e6bc733e8d140c523ca285..81284e8c0d4f265c0633b1c8b7a8e47175c23588 100644
--- a/Library/Homebrew/cmd/tap-info.rb
+++ b/Library/Homebrew/cmd/tap-info.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def tap_info_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/tap.rb b/Library/Homebrew/cmd/tap.rb
index df6f428ff121c49bb5957a79da0e6d2d73287eb3..86e7a0fc1b115f72396eabccc7e214a70a1f16ce 100644
--- a/Library/Homebrew/cmd/tap.rb
+++ b/Library/Homebrew/cmd/tap.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def tap_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/uninstall.rb b/Library/Homebrew/cmd/uninstall.rb
index 2fadf91c508f8c502cf285bab28b54d9568dfcf2..ce2b3df3c242fd88a3da91a6d008f53c985c2257 100644
--- a/Library/Homebrew/cmd/uninstall.rb
+++ b/Library/Homebrew/cmd/uninstall.rb
@@ -11,8 +11,11 @@ require "cask/cask_loader"
 require "uninstall"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def uninstall_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/unlink.rb b/Library/Homebrew/cmd/unlink.rb
index 2abbc3d9479e20d63a33258abb13b4bba446deb2..1036b8eaf978e4aee9d35424241919dc3b7a1c77 100644
--- a/Library/Homebrew/cmd/unlink.rb
+++ b/Library/Homebrew/cmd/unlink.rb
@@ -6,8 +6,11 @@ require "cli/parser"
 require "unlink"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def unlink_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/unpin.rb b/Library/Homebrew/cmd/unpin.rb
index 77bf7b1576363db60bfb40597c781e196298796c..1f650adae19868a040a81f981f65e2620ed4051d 100644
--- a/Library/Homebrew/cmd/unpin.rb
+++ b/Library/Homebrew/cmd/unpin.rb
@@ -5,8 +5,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def unpin_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/untap.rb b/Library/Homebrew/cmd/untap.rb
index b8f6a9301674395529128162ae7618d0698fd5ea..d3e70e7e5e5a57d0c8342db87855dd1fc3e46886 100644
--- a/Library/Homebrew/cmd/untap.rb
+++ b/Library/Homebrew/cmd/untap.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def untap_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/update-report.rb b/Library/Homebrew/cmd/update-report.rb
index b4efd2d7f5a485be897accd47507d2b381840c55..24406a476428244a6762e5fdbc8f0c44bc5db698 100644
--- a/Library/Homebrew/cmd/update-report.rb
+++ b/Library/Homebrew/cmd/update-report.rb
@@ -10,6 +10,8 @@ require "description_cache_store"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
   def update_preinstall_header(args:)
@@ -19,6 +21,7 @@ module Homebrew
     end
   end
 
+  sig { returns(CLI::Parser) }
   def update_report_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
@@ -413,10 +416,13 @@ class Reporter
 end
 
 class ReporterHub
+  extend T::Sig
+
   extend Forwardable
 
   attr_reader :reporters
 
+  sig { void }
   def initialize
     @hash = {}
     @reporters = []
diff --git a/Library/Homebrew/cmd/upgrade.rb b/Library/Homebrew/cmd/upgrade.rb
index b7a53cbd40bee71014d2247485459e9366bf9b65..ce8ec7bf8a7ef6c39142a6409266766471969e31 100644
--- a/Library/Homebrew/cmd/upgrade.rb
+++ b/Library/Homebrew/cmd/upgrade.rb
@@ -10,8 +10,11 @@ require "cask/utils"
 require "cask/macos"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def upgrade_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/cmd/uses.rb b/Library/Homebrew/cmd/uses.rb
index 8b2f91243636fda93cf8db37a847bf9c709da2b1..ae0a28ed5794f67c71d79cf565a71c9c722da0b5 100644
--- a/Library/Homebrew/cmd/uses.rb
+++ b/Library/Homebrew/cmd/uses.rb
@@ -11,10 +11,13 @@ require "cask/caskroom"
 require "dependencies_helpers"
 
 module Homebrew
+  extend T::Sig
+
   extend DependenciesHelpers
 
   module_function
 
+  sig { returns(CLI::Parser) }
   def uses_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/config.rb b/Library/Homebrew/config.rb
index feecc8373a8788f6ee6900a3642e89b19c37fec5..566be1eae6390f833b56430518c422289ccc1593 100644
--- a/Library/Homebrew/config.rb
+++ b/Library/Homebrew/config.rb
@@ -4,28 +4,36 @@
 raise "HOMEBREW_BREW_FILE was not exported! Please call bin/brew directly!" unless ENV["HOMEBREW_BREW_FILE"]
 
 # Path to `bin/brew` main executable in `HOMEBREW_PREFIX`
-HOMEBREW_BREW_FILE = Pathname.new(ENV["HOMEBREW_BREW_FILE"]).freeze
+HOMEBREW_BREW_FILE = Pathname(ENV["HOMEBREW_BREW_FILE"]).freeze
 
 class MissingEnvironmentVariables < RuntimeError; end
 
-def get_env_or_raise(env)
-  raise MissingEnvironmentVariables, "#{env} was not exported!" unless ENV[env]
+# Helper module for getting environment variables which must be set.
+#
+# @api private
+module EnvVar
+  extend T::Sig
 
-  ENV[env]
+  sig { params(env: String).returns(String) }
+  def self.[](env)
+    raise MissingEnvironmentVariables, "#{env} was not exported!" unless ENV[env]
+
+    ENV.fetch(env)
+  end
 end
 
 require "extend/git_repository"
 
 # Where we link under
-HOMEBREW_PREFIX = Pathname.new(get_env_or_raise("HOMEBREW_PREFIX")).freeze
+HOMEBREW_PREFIX = Pathname(EnvVar["HOMEBREW_PREFIX"]).freeze
 
 # Where `.git` is found
-HOMEBREW_REPOSITORY = Pathname.new(get_env_or_raise("HOMEBREW_REPOSITORY"))
-                              .extend(GitRepositoryExtension)
-                              .freeze
+HOMEBREW_REPOSITORY = Pathname(EnvVar["HOMEBREW_REPOSITORY"])
+                      .extend(GitRepositoryExtension)
+                      .freeze
 
 # Where we store most of Homebrew, taps, and various metadata
-HOMEBREW_LIBRARY = Pathname.new(get_env_or_raise("HOMEBREW_LIBRARY")).freeze
+HOMEBREW_LIBRARY = Pathname(EnvVar["HOMEBREW_LIBRARY"]).freeze
 
 # Where shim scripts for various build and SCM tools are stored
 HOMEBREW_SHIMS_PATH = (HOMEBREW_LIBRARY/"Homebrew/shims").freeze
@@ -43,19 +51,19 @@ HOMEBREW_PINNED_KEGS = (HOMEBREW_PREFIX/"var/homebrew/pinned").freeze
 HOMEBREW_LOCKS = (HOMEBREW_PREFIX/"var/homebrew/locks").freeze
 
 # Where we store built products
-HOMEBREW_CELLAR = Pathname.new(get_env_or_raise("HOMEBREW_CELLAR")).freeze
+HOMEBREW_CELLAR = Pathname(EnvVar["HOMEBREW_CELLAR"]).freeze
 
 # Where downloads (bottles, source tarballs, etc.) are cached
-HOMEBREW_CACHE = Pathname.new(get_env_or_raise("HOMEBREW_CACHE")).freeze
+HOMEBREW_CACHE = Pathname(EnvVar["HOMEBREW_CACHE"]).freeze
 
 # Where brews installed via URL are cached
 HOMEBREW_CACHE_FORMULA = (HOMEBREW_CACHE/"Formula").freeze
 
 # Where build, postinstall, and test logs of formulae are written to
-HOMEBREW_LOGS = Pathname.new(get_env_or_raise("HOMEBREW_LOGS")).expand_path.freeze
+HOMEBREW_LOGS = Pathname(EnvVar["HOMEBREW_LOGS"]).expand_path.freeze
 
 # Must use `/tmp` instead of `TMPDIR` because long paths break Unix domain sockets
-HOMEBREW_TEMP = Pathname.new(get_env_or_raise("HOMEBREW_TEMP")).yield_self do |tmp|
+HOMEBREW_TEMP = Pathname(EnvVar["HOMEBREW_TEMP"]).yield_self do |tmp|
   tmp.mkpath unless tmp.exist?
   tmp.realpath
 end.freeze
diff --git a/Library/Homebrew/cxxstdlib.rb b/Library/Homebrew/cxxstdlib.rb
index 8750b0c187eb113534e33efe4b2a5e4311251d1f..e6ef4838d62b5982fd2061518295f48c33a7ec53 100644
--- a/Library/Homebrew/cxxstdlib.rb
+++ b/Library/Homebrew/cxxstdlib.rb
@@ -5,6 +5,8 @@ require "compilers"
 
 # Combination of C++ standard library and compiler.
 class CxxStdlib
+  extend T::Sig
+
   include CompilerConstants
 
   # Error for when a formula's dependency was built with a different C++ standard library.
@@ -72,6 +74,7 @@ class CxxStdlib
     type.to_s.gsub(/cxx$/, "c++")
   end
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: #{compiler} #{type}>"
   end
diff --git a/Library/Homebrew/debrew.rb b/Library/Homebrew/debrew.rb
index 54a5b9af0325defa1e62fd924f2bbbd58875b3d9..de551abc90d0768d8a061af3adf48626b3ee7c34 100644
--- a/Library/Homebrew/debrew.rb
+++ b/Library/Homebrew/debrew.rb
@@ -41,10 +41,13 @@ module Debrew
 
   # Module for displaying a debugging menu.
   class Menu
+    extend T::Sig
+
     Entry = Struct.new(:name, :action)
 
     attr_accessor :prompt, :entries
 
+    sig { void }
     def initialize
       @entries = []
     end
diff --git a/Library/Homebrew/dependencies.rb b/Library/Homebrew/dependencies.rb
index 2764048ce0389255c7fe4acde67b43f19aad5bbb..b3a12d9bff71c7474bf91ada2fc6bdf186a70bef 100644
--- a/Library/Homebrew/dependencies.rb
+++ b/Library/Homebrew/dependencies.rb
@@ -8,6 +8,8 @@ require "cask_dependent"
 #
 # @api private
 class Dependencies < SimpleDelegator
+  extend T::Sig
+
   def initialize(*args)
     super(args)
   end
@@ -34,6 +36,7 @@ class Dependencies < SimpleDelegator
     build + required + recommended
   end
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: #{to_a}>"
   end
@@ -43,6 +46,8 @@ end
 #
 # @api private
 class Requirements < SimpleDelegator
+  extend T::Sig
+
   def initialize(*args)
     super(Set.new(args))
   end
@@ -59,6 +64,7 @@ class Requirements < SimpleDelegator
     self
   end
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: {#{to_a.join(", ")}}>"
   end
diff --git a/Library/Homebrew/dependency.rb b/Library/Homebrew/dependency.rb
index 99b8a0a1ee78e3c40b777c52b866628ec8d29afd..aa2236147870ae2f55054b45efe373fee9c8e4e9 100644
--- a/Library/Homebrew/dependency.rb
+++ b/Library/Homebrew/dependency.rb
@@ -7,6 +7,8 @@ require "dependable"
 #
 # @api private
 class Dependency
+  extend T::Sig
+
   extend Forwardable
   include Dependable
 
@@ -64,6 +66,7 @@ class Dependency
     env_proc&.call
   end
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: #{name.inspect} #{tags.inspect}>"
   end
@@ -78,6 +81,8 @@ class Dependency
   end
 
   class << self
+    extend T::Sig
+
     # Expand the dependencies of each dependent recursively, optionally yielding
     # `[dependent, dep]` pairs to allow callers to apply arbitrary filters to
     # the list.
@@ -126,16 +131,19 @@ class Dependency
     end
 
     # Prune a dependency and its dependencies recursively.
+    sig { void }
     def prune
       throw(:action, :prune)
     end
 
     # Prune a single dependency but do not prune its dependencies.
+    sig { void }
     def skip
       throw(:action, :skip)
     end
 
     # Keep a dependency, but prune its dependencies.
+    sig { void }
     def keep_but_prune_recursive_deps
       throw(:action, :keep_but_prune_recursive_deps)
     end
diff --git a/Library/Homebrew/dependency_collector.rb b/Library/Homebrew/dependency_collector.rb
index 80b8dbab0feaa9b5c9f493385459c9dcd7107bcb..356437c7a9c58c317240de75deecfab3b64004f9 100644
--- a/Library/Homebrew/dependency_collector.rb
+++ b/Library/Homebrew/dependency_collector.rb
@@ -18,10 +18,13 @@ require "extend/cachable"
 # This class is used by `depends_on` in the formula DSL to turn dependency
 # specifications into the proper kinds of dependencies and requirements.
 class DependencyCollector
+  extend T::Sig
+
   extend Cachable
 
   attr_reader :deps, :requirements
 
+  sig { void }
   def initialize
     @deps = Dependencies.new
     @requirements = Requirements.new
diff --git a/Library/Homebrew/dev-cmd/audit.rb b/Library/Homebrew/dev-cmd/audit.rb
index 7dc0887d62c9e2d0e76a0f75612f83629e444384..e961495ba84b69d851cef9cc424124d0497b7f67 100644
--- a/Library/Homebrew/dev-cmd/audit.rb
+++ b/Library/Homebrew/dev-cmd/audit.rb
@@ -18,8 +18,11 @@ require "cli/parser"
 require "json"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def audit_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/bottle.rb b/Library/Homebrew/dev-cmd/bottle.rb
index 4f6d117609f63bb590864e38012a535f5c72176e..b940b0d93481904c01a58363714d72177f8982f8 100644
--- a/Library/Homebrew/dev-cmd/bottle.rb
+++ b/Library/Homebrew/dev-cmd/bottle.rb
@@ -40,8 +40,11 @@ EOS
 MAXIMUM_STRING_MATCHES = 100
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def bottle_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/bump-cask-pr.rb b/Library/Homebrew/dev-cmd/bump-cask-pr.rb
index a9ecedc589c56f24eab38f0e9b4adc76fe261cda..2bb3e15d272c5f84725b79f16c7c78f5535270d6 100644
--- a/Library/Homebrew/dev-cmd/bump-cask-pr.rb
+++ b/Library/Homebrew/dev-cmd/bump-cask-pr.rb
@@ -6,8 +6,11 @@ require "cli/parser"
 require "utils/tar"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def bump_cask_pr_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/bump-formula-pr.rb b/Library/Homebrew/dev-cmd/bump-formula-pr.rb
index dc4bb5a06b871ef90b75b997702c7c6a1c1ce178..b3f6550f3b0f9664fe3c1436a6ad631b6663d242 100644
--- a/Library/Homebrew/dev-cmd/bump-formula-pr.rb
+++ b/Library/Homebrew/dev-cmd/bump-formula-pr.rb
@@ -7,8 +7,11 @@ require "utils/pypi"
 require "utils/tar"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def bump_formula_pr_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/bump-revision.rb b/Library/Homebrew/dev-cmd/bump-revision.rb
index aa53caaf476d1bc4c0fec25d4d19997f99650c7a..745fef771752a240902cfe542bce5910cb89ca0a 100644
--- a/Library/Homebrew/dev-cmd/bump-revision.rb
+++ b/Library/Homebrew/dev-cmd/bump-revision.rb
@@ -5,8 +5,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def bump_revision_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/bump.rb b/Library/Homebrew/dev-cmd/bump.rb
index 543d75186330da4fc8992f080cdfaaddb4f061b3..e5a9695b8f2ac761ac4beb8b60c0980b4f69fb69 100644
--- a/Library/Homebrew/dev-cmd/bump.rb
+++ b/Library/Homebrew/dev-cmd/bump.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def bump_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/cat.rb b/Library/Homebrew/dev-cmd/cat.rb
index 3415e03e6e30431b9062859208460cabaa12e788..a0410216fe6b72a8cf11b3889d6dd8e5d1490a47 100644
--- a/Library/Homebrew/dev-cmd/cat.rb
+++ b/Library/Homebrew/dev-cmd/cat.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def cat_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/command.rb b/Library/Homebrew/dev-cmd/command.rb
index 7c2f6e37ce07690cd131fc032f4c7810af601846..9beb128138960b3777a4f539977178569564c94c 100644
--- a/Library/Homebrew/dev-cmd/command.rb
+++ b/Library/Homebrew/dev-cmd/command.rb
@@ -5,8 +5,11 @@ require "commands"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def command_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/create.rb b/Library/Homebrew/dev-cmd/create.rb
index 177ba878e80909dfb4b449130a55f2b3201f180b..ecedb06f264f4985234315009e9cb6b789715433 100644
--- a/Library/Homebrew/dev-cmd/create.rb
+++ b/Library/Homebrew/dev-cmd/create.rb
@@ -8,8 +8,11 @@ require "cli/parser"
 require "utils/pypi"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def create_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/dispatch-build-bottle.rb b/Library/Homebrew/dev-cmd/dispatch-build-bottle.rb
index dc80f45fb45cd376bc398e92405d95b06bc62e8a..4353beeb77b24ca95c4e2a1fa0399252e8607847 100644
--- a/Library/Homebrew/dev-cmd/dispatch-build-bottle.rb
+++ b/Library/Homebrew/dev-cmd/dispatch-build-bottle.rb
@@ -5,8 +5,11 @@ require "cli/parser"
 require "utils/github"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def dispatch_build_bottle_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/diy.rb b/Library/Homebrew/dev-cmd/diy.rb
index 31f57440c86a8296a2933d928c00bcca65969305..56c1ee437d94ee6a218070ac976c615dddfaed6e 100644
--- a/Library/Homebrew/dev-cmd/diy.rb
+++ b/Library/Homebrew/dev-cmd/diy.rb
@@ -5,8 +5,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def diy_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/edit.rb b/Library/Homebrew/dev-cmd/edit.rb
index f963aeb23727a55b155b92a607abd807e7ad1a95..5526e9809e917cfcaf1664fc58a78b6de04c7ed1 100644
--- a/Library/Homebrew/dev-cmd/edit.rb
+++ b/Library/Homebrew/dev-cmd/edit.rb
@@ -5,8 +5,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def edit_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/extract.rb b/Library/Homebrew/dev-cmd/extract.rb
index 7bd9820d18ee9d5f30effb5738f9f6dabc34c0ff..63f518f69faa3689f51875c90c421d6d3568f596 100644
--- a/Library/Homebrew/dev-cmd/extract.rb
+++ b/Library/Homebrew/dev-cmd/extract.rb
@@ -76,8 +76,11 @@ ensure
 end
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def extract_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/formula.rb b/Library/Homebrew/dev-cmd/formula.rb
index b5e7ccaec1d9446eed1ac18c3d684446ea02affb..cee7263e9acb5720634f1f1c57541ad978a273c1 100644
--- a/Library/Homebrew/dev-cmd/formula.rb
+++ b/Library/Homebrew/dev-cmd/formula.rb
@@ -5,8 +5,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def formula_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/install-bundler-gems.rb b/Library/Homebrew/dev-cmd/install-bundler-gems.rb
index b15b49ee971a60fc1680c5f33949d163cd9e3631..ce80576cb1264fbcab79252032cf4956346d0004 100644
--- a/Library/Homebrew/dev-cmd/install-bundler-gems.rb
+++ b/Library/Homebrew/dev-cmd/install-bundler-gems.rb
@@ -5,8 +5,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def install_bundler_gems_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/irb.rb b/Library/Homebrew/dev-cmd/irb.rb
index c5a0a29b8b475d2b95a85b5caa3768db6333e17a..b5b09f9b1c3515512945ffd3276c6f45332e765b 100644
--- a/Library/Homebrew/dev-cmd/irb.rb
+++ b/Library/Homebrew/dev-cmd/irb.rb
@@ -16,8 +16,11 @@ class String
 end
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def irb_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/linkage.rb b/Library/Homebrew/dev-cmd/linkage.rb
index 631e9ec65b2454d09bf5c039841c828ed4fed447..4f161f803942155efa3e4408d4d4e014806aa44d 100644
--- a/Library/Homebrew/dev-cmd/linkage.rb
+++ b/Library/Homebrew/dev-cmd/linkage.rb
@@ -6,8 +6,11 @@ require "linkage_checker"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def linkage_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/livecheck.rb b/Library/Homebrew/dev-cmd/livecheck.rb
index d177768026cda2823922605c113716cf48b89b65..2e6ab72334ffc59b6f01caf30474e562142ea13c 100644
--- a/Library/Homebrew/dev-cmd/livecheck.rb
+++ b/Library/Homebrew/dev-cmd/livecheck.rb
@@ -7,6 +7,8 @@ require "livecheck/livecheck"
 require "livecheck/strategy"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
   WATCHLIST_PATH = (
@@ -14,6 +16,7 @@ module Homebrew
     "#{Dir.home}/.brew_livecheck_watchlist"
   ).freeze
 
+  sig { returns(CLI::Parser) }
   def livecheck_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/man.rb b/Library/Homebrew/dev-cmd/man.rb
index 0a17cdc96a92a54521ecaa3ac077f159479cca3b..6a3e27c3728554253d46ee722e107aa2760e8865 100644
--- a/Library/Homebrew/dev-cmd/man.rb
+++ b/Library/Homebrew/dev-cmd/man.rb
@@ -7,12 +7,15 @@ require "ostruct"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
   SOURCE_PATH = (HOMEBREW_LIBRARY_PATH/"manpages").freeze
   TARGET_MAN_PATH = (HOMEBREW_REPOSITORY/"manpages").freeze
   TARGET_DOC_PATH = (HOMEBREW_REPOSITORY/"docs").freeze
 
+  sig { returns(CLI::Parser) }
   def man_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
@@ -210,6 +213,7 @@ module Homebrew
     lines
   end
 
+  sig { returns(String) }
   def global_cask_options_manpage
     lines = ["These options are applicable to subcommands accepting a `--cask` flag and all `cask` commands.\n"]
     lines += Homebrew::CLI::Parser.global_cask_options.map do |_, long, description:, **|
@@ -218,6 +222,7 @@ module Homebrew
     lines.join("\n")
   end
 
+  sig { returns(String) }
   def global_options_manpage
     lines = ["These options are applicable across multiple subcommands.\n"]
     lines += Homebrew::CLI::Parser.global_options.map do |short, long, desc|
@@ -226,6 +231,7 @@ module Homebrew
     lines.join("\n")
   end
 
+  sig { returns(String) }
   def env_vars_manpage
     lines = Homebrew::EnvConfig::ENVS.flat_map do |env, hash|
       entry = "  * `#{env}`:\n    #{hash[:description]}\n"
diff --git a/Library/Homebrew/dev-cmd/mirror.rb b/Library/Homebrew/dev-cmd/mirror.rb
index 7790c32fed97d0965c725d639824d3633a4abfcd..70400ee846efbb06ea3af93c1a224792b02d4e69 100644
--- a/Library/Homebrew/dev-cmd/mirror.rb
+++ b/Library/Homebrew/dev-cmd/mirror.rb
@@ -5,8 +5,11 @@ require "bintray"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def mirror_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/pr-automerge.rb b/Library/Homebrew/dev-cmd/pr-automerge.rb
index 16634dd450a236e9dbafcdc132c48ae53026f7eb..aac304e28870af777ae60691b9af770cbbfe2d37 100644
--- a/Library/Homebrew/dev-cmd/pr-automerge.rb
+++ b/Library/Homebrew/dev-cmd/pr-automerge.rb
@@ -5,8 +5,11 @@ require "cli/parser"
 require "utils/github"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def pr_automerge_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/pr-publish.rb b/Library/Homebrew/dev-cmd/pr-publish.rb
index 86b675293b69928cc0da85358ba0ed5edf3718a9..de376b1cee82db78c2653fddcf6a71268f5f648a 100644
--- a/Library/Homebrew/dev-cmd/pr-publish.rb
+++ b/Library/Homebrew/dev-cmd/pr-publish.rb
@@ -5,8 +5,11 @@ require "cli/parser"
 require "utils/github"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def pr_publish_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/pr-pull.rb b/Library/Homebrew/dev-cmd/pr-pull.rb
index a11704972feeb6e3f606fea52fd92736a85354ab..82a6a7f4aed511ea067159f4c5a7dc0d560acd31 100644
--- a/Library/Homebrew/dev-cmd/pr-pull.rb
+++ b/Library/Homebrew/dev-cmd/pr-pull.rb
@@ -8,8 +8,11 @@ require "tmpdir"
 require "formula"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def pr_pull_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
@@ -418,6 +421,8 @@ module Homebrew
 end
 
 class GitHubArtifactDownloadStrategy < AbstractFileDownloadStrategy
+  extend T::Sig
+
   def fetch
     ohai "Downloading #{url}"
     if cached_location.exist?
@@ -441,6 +446,7 @@ class GitHubArtifactDownloadStrategy < AbstractFileDownloadStrategy
 
   private
 
+  sig { returns(String) }
   def resolved_basename
     "artifact.zip"
   end
diff --git a/Library/Homebrew/dev-cmd/pr-upload.rb b/Library/Homebrew/dev-cmd/pr-upload.rb
index 23ed9e9cef6400f8d48352d003e7a72afe702f75..d26a6c0cfe9f71c03c144279a7159dda36991ff8 100644
--- a/Library/Homebrew/dev-cmd/pr-upload.rb
+++ b/Library/Homebrew/dev-cmd/pr-upload.rb
@@ -5,8 +5,11 @@ require "cli/parser"
 require "bintray"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def pr_upload_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/prof.rb b/Library/Homebrew/dev-cmd/prof.rb
index 2c40d0b7fc6a5c41e3e069e5f4e66d1fa927c40f..add6a5ae01cbf5f6492d9d65ddc4bc3ea4f7efcf 100644
--- a/Library/Homebrew/dev-cmd/prof.rb
+++ b/Library/Homebrew/dev-cmd/prof.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def prof_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/pull.rb b/Library/Homebrew/dev-cmd/pull.rb
index ce279b1f801a6570b65bd37329c5ec85ead18eaa..8c1b8b2b5c7ec24c89c7ddcb30af6985bad5bd56 100644
--- a/Library/Homebrew/dev-cmd/pull.rb
+++ b/Library/Homebrew/dev-cmd/pull.rb
@@ -12,8 +12,11 @@ require "pkg_version"
 require "formula_info"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def pull_args
     Homebrew::CLI::Parser.new do
       hide_from_man_page!
diff --git a/Library/Homebrew/dev-cmd/release-notes.rb b/Library/Homebrew/dev-cmd/release-notes.rb
index 7288d85e12ff339b1c6f392b7d73f8fe3f206824..bde64f84dea844f380b349ad2fd833e75ef35e96 100644
--- a/Library/Homebrew/dev-cmd/release-notes.rb
+++ b/Library/Homebrew/dev-cmd/release-notes.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def release_notes_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/ruby.rb b/Library/Homebrew/dev-cmd/ruby.rb
index 4e4f014d0890eff8cffdf43d169f7f3d1a4b8b21..47475f39e32c4ee66ae6c233247c5fd293dd1186 100644
--- a/Library/Homebrew/dev-cmd/ruby.rb
+++ b/Library/Homebrew/dev-cmd/ruby.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def ruby_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/sh.rb b/Library/Homebrew/dev-cmd/sh.rb
index a1f35adc14ad428d20e7bbdb6ff4c1141e78de26..eb0af7cd84297ff34c1023e6a15b7c699d5b9746 100644
--- a/Library/Homebrew/dev-cmd/sh.rb
+++ b/Library/Homebrew/dev-cmd/sh.rb
@@ -6,8 +6,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def sh_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/sponsors.rb b/Library/Homebrew/dev-cmd/sponsors.rb
index 0e3bece7d21e2d78c9a9fcd7d93f4f7ff9c25fbe..b6d03a839d4df99a3473bde1693182f053ea7691 100644
--- a/Library/Homebrew/dev-cmd/sponsors.rb
+++ b/Library/Homebrew/dev-cmd/sponsors.rb
@@ -5,8 +5,11 @@ require "cli/parser"
 require "utils/github"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def sponsors_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/style.rb b/Library/Homebrew/dev-cmd/style.rb
index 8b3d5439a21e8c3122dba77934ee01cbed865d48..611ab05ce06d23fadc35101edd9e44e7fdc491a8 100644
--- a/Library/Homebrew/dev-cmd/style.rb
+++ b/Library/Homebrew/dev-cmd/style.rb
@@ -7,8 +7,11 @@ require "style"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def style_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/tap-new.rb b/Library/Homebrew/dev-cmd/tap-new.rb
index d9c9f3b5e8aa4c6619d911365daa1113f9ba6853..883263d58a28d66e1db3a63c095ff92e0f11d895 100644
--- a/Library/Homebrew/dev-cmd/tap-new.rb
+++ b/Library/Homebrew/dev-cmd/tap-new.rb
@@ -5,8 +5,11 @@ require "tap"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def tap_new_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/test.rb b/Library/Homebrew/dev-cmd/test.rb
index 087f5f5510480bab3afccaecf29ea7ec4ce5a5c1..8933ec8ae12b05f660b62c99c6248ed05e91108a 100644
--- a/Library/Homebrew/dev-cmd/test.rb
+++ b/Library/Homebrew/dev-cmd/test.rb
@@ -7,8 +7,11 @@ require "timeout"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def test_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/tests.rb b/Library/Homebrew/dev-cmd/tests.rb
index 428177807e6799ba32bda9e6bafe79fa49f2d8a1..c9f47b220a362a6b5e765c25103796006cd3ee36 100644
--- a/Library/Homebrew/dev-cmd/tests.rb
+++ b/Library/Homebrew/dev-cmd/tests.rb
@@ -5,8 +5,11 @@ require "cli/parser"
 require "fileutils"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def tests_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/typecheck.rb b/Library/Homebrew/dev-cmd/typecheck.rb
index c8c45fa88ba9c4581b47531272ed602cd09ad8dc..2914b518c6ea3e2e44b1746ef886eaadaf438849 100644
--- a/Library/Homebrew/dev-cmd/typecheck.rb
+++ b/Library/Homebrew/dev-cmd/typecheck.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def typecheck_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
@@ -13,6 +16,8 @@ module Homebrew
 
         Check for typechecking errors using Sorbet.
       EOS
+      switch "--fix",
+             description: "Automatically fix type errors."
       switch "-q", "--quiet",
              description: "Silence all non-critical errors."
       switch "--update",
@@ -51,6 +56,7 @@ module Homebrew
 
       srb_exec = %w[bundle exec srb tc]
       srb_exec << "--quiet" if args.quiet?
+      srb_exec << "--autocorrect" if args.fix?
       srb_exec += ["--ignore", args.ignore] if args.ignore.present?
       if args.file.present? || args.dir.present?
         cd("sorbet")
diff --git a/Library/Homebrew/dev-cmd/unpack.rb b/Library/Homebrew/dev-cmd/unpack.rb
index e88b9ef2cc851160e5939e3d16a802b4a0311d25..529bfcc046d285ec83408597e110ffa7dd85516e 100644
--- a/Library/Homebrew/dev-cmd/unpack.rb
+++ b/Library/Homebrew/dev-cmd/unpack.rb
@@ -6,8 +6,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def unpack_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/update-license-data.rb b/Library/Homebrew/dev-cmd/update-license-data.rb
index 6d11bca3581f6a06df3d7ccc413f5d0c21f1b4dc..bb3220074bba13becf478cf72cbd0e437763614f 100644
--- a/Library/Homebrew/dev-cmd/update-license-data.rb
+++ b/Library/Homebrew/dev-cmd/update-license-data.rb
@@ -5,8 +5,11 @@ require "cli/parser"
 require "utils/spdx"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def update_license_data_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/update-python-resources.rb b/Library/Homebrew/dev-cmd/update-python-resources.rb
index e109887bbc9006416b6ec2d28762614cd5088828..e8017c3766fac9d86a9781564491308ec4efb5db 100644
--- a/Library/Homebrew/dev-cmd/update-python-resources.rb
+++ b/Library/Homebrew/dev-cmd/update-python-resources.rb
@@ -5,8 +5,11 @@ require "cli/parser"
 require "utils/pypi"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def update_python_resources_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/update-test.rb b/Library/Homebrew/dev-cmd/update-test.rb
index f6c3adce439d97200fd0e03ab561fdf3f8a70fd2..789ec21aa96cfc1600f925346747d34694d0d9fb 100644
--- a/Library/Homebrew/dev-cmd/update-test.rb
+++ b/Library/Homebrew/dev-cmd/update-test.rb
@@ -4,8 +4,11 @@
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def update_test_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/dev-cmd/vendor-gems.rb b/Library/Homebrew/dev-cmd/vendor-gems.rb
index f42945f2b2d9329e3080274b9d24d5a0304e54a6..9f028e5dc7afcbd5e03be25f14d0ef39c3eec6bf 100644
--- a/Library/Homebrew/dev-cmd/vendor-gems.rb
+++ b/Library/Homebrew/dev-cmd/vendor-gems.rb
@@ -5,8 +5,11 @@ require "formula"
 require "cli/parser"
 
 module Homebrew
+  extend T::Sig
+
   module_function
 
+  sig { returns(CLI::Parser) }
   def vendor_gems_args
     Homebrew::CLI::Parser.new do
       usage_banner <<~EOS
diff --git a/Library/Homebrew/diagnostic.rb b/Library/Homebrew/diagnostic.rb
index 0964ca0be1a7a59fd323a5c8687c5d020a025794..2280206eb4e0178b8a949a53973ecc7c76facd74 100644
--- a/Library/Homebrew/diagnostic.rb
+++ b/Library/Homebrew/diagnostic.rb
@@ -48,6 +48,8 @@ module Homebrew
 
     # Diagnostic checks.
     class Checks
+      extend T::Sig
+
       def initialize(verbose: true)
         @verbose = verbose
       end
@@ -71,6 +73,7 @@ module Homebrew
         path.gsub(ENV["HOME"], "~")
       end
 
+      sig { returns(String) }
       def none_string
         "<NONE>"
       end
diff --git a/Library/Homebrew/download_strategy.rb b/Library/Homebrew/download_strategy.rb
index d7a2b69f50266c4f1cde39c0e627354c5bba9605..eb4a48389b7c80ccf9f1165080f49d43fa07d903 100644
--- a/Library/Homebrew/download_strategy.rb
+++ b/Library/Homebrew/download_strategy.rb
@@ -17,6 +17,8 @@ require "utils/curl"
 #
 # @api private
 class AbstractDownloadStrategy
+  extend T::Sig
+
   extend Forwardable
   include FileUtils
   include Context
@@ -55,6 +57,7 @@ class AbstractDownloadStrategy
   # TODO: Deprecate once we have an explicitly documented alternative.
   #
   # @api public
+  sig { void }
   def shutup!
     @quiet = true
   end
@@ -586,6 +589,8 @@ end
 #
 # @api public
 class SubversionDownloadStrategy < VCSDownloadStrategy
+  extend T::Sig
+
   def initialize(url, name, version, **meta)
     super
     @url = @url.sub("svn+http://", "")
@@ -602,6 +607,7 @@ class SubversionDownloadStrategy < VCSDownloadStrategy
   end
 
   # (see AbstractDownloadStrategy#source_modified_time)
+  sig { returns(Time) }
   def source_modified_time
     time = if Version.create(Utils::Svn.version) >= Version.create("1.9")
       out, = silent_command("svn", args: ["info", "--show-item", "last-changed-date"], chdir: cached_location)
@@ -660,6 +666,7 @@ class SubversionDownloadStrategy < VCSDownloadStrategy
     end
   end
 
+  sig { returns(String) }
   def cache_tag
     head? ? "svn-HEAD" : "svn"
   end
@@ -706,6 +713,7 @@ class GitDownloadStrategy < VCSDownloadStrategy
   end
 
   # (see AbstractDownloadStrategy#source_modified_time)
+  sig { returns(Time) }
   def source_modified_time
     out, = silent_command("git", args: ["--git-dir", git_dir, "show", "-s", "--format=%cD"])
     Time.parse(out)
@@ -719,10 +727,12 @@ class GitDownloadStrategy < VCSDownloadStrategy
 
   private
 
+  sig { returns(String) }
   def cache_tag
     "git"
   end
 
+  sig { returns(Integer) }
   def cache_version
     0
   end
@@ -770,6 +780,7 @@ class GitDownloadStrategy < VCSDownloadStrategy
     (cached_location/".gitmodules").exist?
   end
 
+  sig { returns(T::Array[String]) }
   def clone_args
     args = %w[clone]
     args << "--depth" << "1" if shallow_clone?
@@ -783,6 +794,7 @@ class GitDownloadStrategy < VCSDownloadStrategy
     args << @url << cached_location
   end
 
+  sig { returns(String) }
   def refspec
     case @ref_type
     when :branch then "+refs/heads/#{@ref}:refs/remotes/origin/#{@ref}"
@@ -953,6 +965,8 @@ end
 #
 # @api public
 class CVSDownloadStrategy < VCSDownloadStrategy
+  extend T::Sig
+
   def initialize(url, name, version, **meta)
     super
     @url = @url.sub(%r{^cvs://}, "")
@@ -967,6 +981,7 @@ class CVSDownloadStrategy < VCSDownloadStrategy
   end
 
   # (see AbstractDownloadStrategy#source_modified_time)
+  sig { returns(Time) }
   def source_modified_time
     # Filter CVS's files because the timestamp for each of them is the moment
     # of clone.
@@ -987,6 +1002,7 @@ class CVSDownloadStrategy < VCSDownloadStrategy
     { "PATH" => PATH.new("/usr/bin", Formula["cvs"].opt_bin, ENV["PATH"]) }
   end
 
+  sig { returns(String) }
   def cache_tag
     "cvs"
   end
@@ -1026,12 +1042,15 @@ end
 #
 # @api public
 class MercurialDownloadStrategy < VCSDownloadStrategy
+  extend T::Sig
+
   def initialize(url, name, version, **meta)
     super
     @url = @url.sub(%r{^hg://}, "")
   end
 
   # (see AbstractDownloadStrategy#source_modified_time)
+  sig { returns(Time) }
   def source_modified_time
     out, = silent_command("hg",
                           args: ["tip", "--template", "{date|isodate}", "-R", cached_location])
@@ -1051,6 +1070,7 @@ class MercurialDownloadStrategy < VCSDownloadStrategy
     { "PATH" => PATH.new(Formula["mercurial"].opt_bin, ENV["PATH"]) }
   end
 
+  sig { returns(String) }
   def cache_tag
     "hg"
   end
@@ -1081,12 +1101,15 @@ end
 #
 # @api public
 class BazaarDownloadStrategy < VCSDownloadStrategy
+  extend T::Sig
+
   def initialize(url, name, version, **meta)
     super
     @url.sub!(%r{^bzr://}, "")
   end
 
   # (see AbstractDownloadStrategy#source_modified_time)
+  sig { returns(Time) }
   def source_modified_time
     out, = silent_command("bzr", args: ["log", "-l", "1", "--timezone=utc", cached_location])
     timestamp = out.chomp
@@ -1110,6 +1133,7 @@ class BazaarDownloadStrategy < VCSDownloadStrategy
     }
   end
 
+  sig { returns(String) }
   def cache_tag
     "bzr"
   end
@@ -1135,12 +1159,15 @@ end
 #
 # @api public
 class FossilDownloadStrategy < VCSDownloadStrategy
+  extend T::Sig
+
   def initialize(url, name, version, **meta)
     super
     @url = @url.sub(%r{^fossil://}, "")
   end
 
   # (see AbstractDownloadStrategy#source_modified_time)
+  sig { returns(Time) }
   def source_modified_time
     out, = silent_command("fossil", args: ["info", "tip", "-R", cached_location])
     Time.parse(out[/^uuid: +\h+ (.+)$/, 1])
@@ -1162,6 +1189,7 @@ class FossilDownloadStrategy < VCSDownloadStrategy
     { "PATH" => PATH.new(Formula["fossil"].opt_bin, ENV["PATH"]) }
   end
 
+  sig { returns(String) }
   def cache_tag
     "fossil"
   end
diff --git a/Library/Homebrew/env_config.rb b/Library/Homebrew/env_config.rb
index 278cd0f3e9078f94e91598da228a47e75499ce5d..a4e6a4e25fa9289f439fabc942955d16341fb1a9 100644
--- a/Library/Homebrew/env_config.rb
+++ b/Library/Homebrew/env_config.rb
@@ -6,6 +6,8 @@ module Homebrew
   #
   # @api private
   module EnvConfig
+    extend T::Sig
+
     module_function
 
     ENVS = {
@@ -358,10 +360,12 @@ module Homebrew
           .to_s
     end
 
+    sig { returns(T::Array[String]) }
     def cask_opts
       Shellwords.shellsplit(ENV.fetch("HOMEBREW_CASK_OPTS", ""))
     end
 
+    sig { returns(T::Boolean) }
     def cask_opts_binaries?
       cask_opts.reverse_each do |opt|
         return true if opt == "--binaries"
@@ -371,6 +375,7 @@ module Homebrew
       true
     end
 
+    sig { returns(T::Boolean) }
     def cask_opts_quarantine?
       cask_opts.reverse_each do |opt|
         return true if opt == "--quarantine"
@@ -380,6 +385,7 @@ module Homebrew
       true
     end
 
+    sig { returns(T::Boolean) }
     def cask_opts_require_sha?
       cask_opts.include?("--require-sha")
     end
diff --git a/Library/Homebrew/exceptions.rb b/Library/Homebrew/exceptions.rb
index f48dfed1046f5d92bef416de7ee82e3ff2ef2029..fadca48894bd1f2f2a335086637e96f7893874f9 100644
--- a/Library/Homebrew/exceptions.rb
+++ b/Library/Homebrew/exceptions.rb
@@ -6,6 +6,8 @@ require "utils"
 
 # Raised when a command is used wrong.
 class UsageError < RuntimeError
+  extend T::Sig
+
   attr_reader :reason
 
   def initialize(reason = nil)
@@ -14,6 +16,7 @@ class UsageError < RuntimeError
     @reason = reason
   end
 
+  sig { returns(String) }
   def to_s
     s = "Invalid usage"
     s += ": #{reason}" if reason
@@ -78,6 +81,8 @@ end
 
 # Raised when neither a formula nor a cask with the given name is available.
 class FormulaOrCaskUnavailableError < RuntimeError
+  extend T::Sig
+
   attr_reader :name
 
   def initialize(name)
@@ -86,6 +91,7 @@ class FormulaOrCaskUnavailableError < RuntimeError
     @name = name
   end
 
+  sig { returns(String) }
   def to_s
     "No available formula or cask with the name \"#{name}\"."
   end
@@ -93,14 +99,18 @@ end
 
 # Raised when a formula is not available.
 class FormulaUnavailableError < FormulaOrCaskUnavailableError
+  extend T::Sig
+
   attr_accessor :dependent
 
+  sig { returns(T.nilable(String)) }
   def dependent_s
-    "(dependency of #{dependent})" if dependent && dependent != name
+    " (dependency of #{dependent})" if dependent && dependent != name
   end
 
+  sig { returns(String) }
   def to_s
-    "No available formula with the name \"#{name}\" #{dependent_s}"
+    "No available formula with the name \"#{name}\"#{dependent_s}."
   end
 end
 
@@ -108,6 +118,8 @@ end
 #
 # @api private
 module FormulaClassUnavailableErrorModule
+  extend T::Sig
+
   attr_reader :path, :class_name, :class_list
 
   def to_s
@@ -119,6 +131,7 @@ module FormulaClassUnavailableErrorModule
 
   private
 
+  sig { returns(String) }
   def class_list_s
     formula_class_list = class_list.select { |klass| klass < Formula }
     if class_list.empty?
@@ -151,8 +164,11 @@ end
 #
 # @api private
 module FormulaUnreadableErrorModule
+  extend T::Sig
+
   attr_reader :formula_error
 
+  sig { returns(String) }
   def to_s
     "#{name}: " + formula_error.to_s
   end
@@ -327,6 +343,8 @@ end
 
 # Raised when a formula conflicts with another one.
 class FormulaConflictError < RuntimeError
+  extend T::Sig
+
   attr_reader :formula, :conflicts
 
   def initialize(formula, conflicts)
@@ -342,6 +360,7 @@ class FormulaConflictError < RuntimeError
     message.join
   end
 
+  sig { returns(String) }
   def message
     message = []
     message << "Cannot install #{formula.full_name} because conflicting formulae are installed."
@@ -549,6 +568,8 @@ end
 
 # Raised by {Kernel#safe_system} in `utils.rb`.
 class ErrorDuringExecution < RuntimeError
+  extend T::Sig
+
   attr_reader :cmd, :status, :output
 
   def initialize(cmd, status:, output: nil, secrets: [])
@@ -583,6 +604,7 @@ class ErrorDuringExecution < RuntimeError
     super s.freeze
   end
 
+  sig { returns(String) }
   def stderr
     Array(output).select { |type,| type == :stderr }.map(&:last).join
   end
diff --git a/Library/Homebrew/extend/ENV/std.rb b/Library/Homebrew/extend/ENV/std.rb
index 30dfaeef2013135a47276580078b326a847ed819..bea1efc1564efdde67afd1d32763584390413887 100644
--- a/Library/Homebrew/extend/ENV/std.rb
+++ b/Library/Homebrew/extend/ENV/std.rb
@@ -6,6 +6,8 @@ require "extend/ENV/shared"
 
 # @private
 module Stdenv
+  extend T::Sig
+
   include SharedEnvExtension
 
   # @private
@@ -58,6 +60,7 @@ module Stdenv
     []
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_pkg_config_libdir
     PATH.new(
       HOMEBREW_PREFIX/"lib/pkgconfig",
diff --git a/Library/Homebrew/extend/ENV/super.rb b/Library/Homebrew/extend/ENV/super.rb
index 966e5e7c87a1a64f16c148c64d0d9f4ece4aa6d5..4b1ba40b8421412de10d537803cb4c65f58411d2 100644
--- a/Library/Homebrew/extend/ENV/super.rb
+++ b/Library/Homebrew/extend/ENV/super.rb
@@ -15,6 +15,8 @@ require "development_tools"
 # 7. Simpler formulae that *just work*
 # 8. Build-system agnostic configuration of the toolchain
 module Superenv
+  extend T::Sig
+
   include SharedEnvExtension
 
   # @private
@@ -103,6 +105,7 @@ module Superenv
     []
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_path
     path = PATH.new(Superenv.bin)
 
@@ -125,6 +128,7 @@ module Superenv
     []
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_pkg_config_path
     PATH.new(
       deps.map { |d| d.opt_lib/"pkgconfig" },
@@ -132,6 +136,7 @@ module Superenv
     ).existing
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_pkg_config_libdir
     PATH.new(
       homebrew_extra_pkg_config_paths,
@@ -142,6 +147,7 @@ module Superenv
     []
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_aclocal_path
     PATH.new(
       keg_only_deps.map { |d| d.opt_share/"aclocal" },
@@ -154,6 +160,7 @@ module Superenv
     []
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_isystem_paths
     PATH.new(
       HOMEBREW_PREFIX/"include",
@@ -161,6 +168,7 @@ module Superenv
     ).existing
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_include_paths
     PATH.new(keg_only_deps.map(&:opt_include)).existing
   end
@@ -169,6 +177,7 @@ module Superenv
     []
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_library_paths
     paths = [
       keg_only_deps.map(&:opt_lib),
@@ -182,6 +191,7 @@ module Superenv
     deps.map(&:name).join(",")
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_cmake_prefix_path
     PATH.new(
       keg_only_deps.map(&:opt_prefix),
@@ -193,6 +203,7 @@ module Superenv
     []
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_cmake_include_path
     PATH.new(homebrew_extra_cmake_include_paths).existing
   end
@@ -201,6 +212,7 @@ module Superenv
     []
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_cmake_library_path
     PATH.new(homebrew_extra_cmake_library_paths).existing
   end
@@ -209,6 +221,7 @@ module Superenv
     []
   end
 
+  sig { returns(T.nilable(PATH)) }
   def determine_cmake_frameworks_path
     PATH.new(
       deps.map(&:opt_frameworks),
diff --git a/Library/Homebrew/extend/os/linux/development_tools.rb b/Library/Homebrew/extend/os/linux/development_tools.rb
index 4e3bc56c9e10e97fce0388ce7f7783f92af9bdaf..e1120688ebd325020abcce57903153f3a3c22948 100644
--- a/Library/Homebrew/extend/os/linux/development_tools.rb
+++ b/Library/Homebrew/extend/os/linux/development_tools.rb
@@ -3,6 +3,8 @@
 
 class DevelopmentTools
   class << self
+    extend T::Sig
+
     def locate(tool)
       (@locate ||= {}).fetch(tool) do |key|
         @locate[key] = if (path = HOMEBREW_PREFIX/"bin/#{tool}").executable?
@@ -13,6 +15,7 @@ class DevelopmentTools
       end
     end
 
+    sig { returns(Symbol) }
     def default_compiler
       :gcc
     end
diff --git a/Library/Homebrew/extend/os/linux/extend/ENV/super.rb b/Library/Homebrew/extend/os/linux/extend/ENV/super.rb
index a3fda016eff8c5ef6ca59c2009268c32171cc26d..ebf600ad0d4450d1cc421ed1ef29de39f896a6f8 100644
--- a/Library/Homebrew/extend/os/linux/extend/ENV/super.rb
+++ b/Library/Homebrew/extend/os/linux/extend/ENV/super.rb
@@ -2,6 +2,8 @@
 # frozen_string_literal: true
 
 module Superenv
+  extend T::Sig
+
   # @private
   def self.bin
     (HOMEBREW_SHIMS_PATH/"linux/super").realpath
@@ -34,6 +36,7 @@ module Superenv
     )
   end
 
+  sig { returns(T.nilable(String)) }
   def determine_dynamic_linker_path
     path = "#{HOMEBREW_PREFIX}/lib/ld.so"
     return unless File.readable? path
diff --git a/Library/Homebrew/extend/os/linux/requirements/osxfuse_requirement.rb b/Library/Homebrew/extend/os/linux/requirements/osxfuse_requirement.rb
index 1f4d2ce13206a2f447f4670eb8503b7cc3a09ecf..05a764d10cd4b84db78718ab2584489e142580df 100644
--- a/Library/Homebrew/extend/os/linux/requirements/osxfuse_requirement.rb
+++ b/Library/Homebrew/extend/os/linux/requirements/osxfuse_requirement.rb
@@ -4,6 +4,8 @@
 require "requirement"
 
 class OsxfuseRequirement < Requirement
+  extend T::Sig
+
   download "https://github.com/libfuse/libfuse"
 
   satisfy(build_env: false) do
@@ -20,6 +22,7 @@ class OsxfuseRequirement < Requirement
     false
   end
 
+  sig { returns(String) }
   def message
     msg = "libfuse is required for this software.\n"
     if libfuse_formula_exists?
@@ -33,6 +36,7 @@ class OsxfuseRequirement < Requirement
 
   private
 
+  sig { returns(T::Boolean) }
   def libfuse_formula_exists?
     begin
       Formula["libfuse"]
diff --git a/Library/Homebrew/extend/os/mac/development_tools.rb b/Library/Homebrew/extend/os/mac/development_tools.rb
index 15ea337b269d234435c19d19a55da0dc15458c6c..f101a310560acb0df1780139e9837c7de55c82d4 100644
--- a/Library/Homebrew/extend/os/mac/development_tools.rb
+++ b/Library/Homebrew/extend/os/mac/development_tools.rb
@@ -6,6 +6,8 @@ require "os/mac/xcode"
 # @private
 class DevelopmentTools
   class << self
+    extend T::Sig
+
     alias generic_locate locate
     undef installed?, default_compiler, curl_handles_most_https_certificates?,
           subversion_handles_most_https_certificates?
@@ -28,22 +30,26 @@ class DevelopmentTools
       MacOS::Xcode.installed? || MacOS::CLT.installed?
     end
 
+    sig { returns(Symbol) }
     def default_compiler
       :clang
     end
 
+    sig { returns(T::Boolean) }
     def curl_handles_most_https_certificates?
       # The system Curl is too old for some modern HTTPS certificates on
       # older macOS versions.
       ENV["HOMEBREW_SYSTEM_CURL_TOO_OLD"].nil?
     end
 
+    sig { returns(T::Boolean) }
     def subversion_handles_most_https_certificates?
       # The system Subversion is too old for some HTTPS certificates on
       # older macOS versions.
       MacOS.version >= :sierra
     end
 
+    sig { returns(String) }
     def installation_instructions
       <<~EOS
         Install the Command Line Tools:
@@ -51,6 +57,7 @@ class DevelopmentTools
       EOS
     end
 
+    sig { returns(String) }
     def custom_installation_instructions
       <<~EOS
         Install GNU's GCC:
diff --git a/Library/Homebrew/extend/os/mac/extend/ENV/shared.rb b/Library/Homebrew/extend/os/mac/extend/ENV/shared.rb
index 633768d8055c538f4f71db8feaa40eac876170aa..d882025a2bbe9c3a600bca0dc678cd9ab3c55f9e 100644
--- a/Library/Homebrew/extend/os/mac/extend/ENV/shared.rb
+++ b/Library/Homebrew/extend/os/mac/extend/ENV/shared.rb
@@ -2,6 +2,9 @@
 # frozen_string_literal: true
 
 module SharedEnvExtension
+  extend T::Sig
+
+  sig { returns(T::Boolean) }
   def no_weak_imports_support?
     return false unless compiler == :clang
 
diff --git a/Library/Homebrew/extend/os/mac/extend/ENV/super.rb b/Library/Homebrew/extend/os/mac/extend/ENV/super.rb
index 999c916b70c0715d72ef135bcc503c3ea830243e..4e541a2be95bc26f7230333fdd5987d3d678e2c3 100644
--- a/Library/Homebrew/extend/os/mac/extend/ENV/super.rb
+++ b/Library/Homebrew/extend/os/mac/extend/ENV/super.rb
@@ -2,6 +2,8 @@
 # frozen_string_literal: true
 
 module Superenv
+  extend T::Sig
+
   class << self
     undef bin
 
@@ -44,6 +46,7 @@ module Superenv
   end
 
   # @private
+  sig { returns(T::Boolean) }
   def libxml2_include_needed?
     return false if deps.any? { |d| d.name == "libxml2" }
     return false if Pathname("#{self["HOMEBREW_SDKROOT"]}/usr/include/libxml").directory?
diff --git a/Library/Homebrew/extend/os/mac/requirements/osxfuse_requirement.rb b/Library/Homebrew/extend/os/mac/requirements/osxfuse_requirement.rb
index 3ae4716a47fdd8243f6c8cbfb8b5c8e145a1aec9..30510cdb2032ba3f52c7c28755ffaa4b302baa17 100644
--- a/Library/Homebrew/extend/os/mac/requirements/osxfuse_requirement.rb
+++ b/Library/Homebrew/extend/os/mac/requirements/osxfuse_requirement.rb
@@ -4,10 +4,13 @@
 require "requirement"
 
 class OsxfuseRequirement < Requirement
+  extend T::Sig
+
   download "https://osxfuse.github.io/"
 
   satisfy(build_env: false) { self.class.binary_osxfuse_installed? }
 
+  sig { returns(T::Boolean) }
   def self.binary_osxfuse_installed?
     File.exist?("/usr/local/include/osxfuse/fuse.h") &&
       !File.symlink?("/usr/local/include/osxfuse")
diff --git a/Library/Homebrew/extend/pathname.rb b/Library/Homebrew/extend/pathname.rb
index 6c22d6d2010ae6dd4c01edd1e3730ea2514045e5..c237a7133baf65afca5f3a800daa3396ce9cc1e3 100644
--- a/Library/Homebrew/extend/pathname.rb
+++ b/Library/Homebrew/extend/pathname.rb
@@ -5,6 +5,8 @@ require "resource"
 require "metafiles"
 
 module DiskUsageExtension
+  extend T::Sig
+
   def disk_usage
     return @disk_usage if @disk_usage
 
@@ -19,6 +21,7 @@ module DiskUsageExtension
     @file_count
   end
 
+  sig { returns(String) }
   def abv
     out = +""
     compute_disk_usage
@@ -71,6 +74,8 @@ end
 # Homebrew extends Ruby's `Pathname` to make our code more readable.
 # @see https://ruby-doc.org/stdlib-2.6.3/libdoc/pathname/rdoc/Pathname.html Ruby's Pathname API
 class Pathname
+  extend T::Sig
+
   include DiskUsageExtension
 
   # @private
@@ -282,16 +287,19 @@ class Pathname
     Dir.chdir(self) { yield self }
   end
 
+  sig { returns(T::Array[Pathname]) }
   def subdirs
     children.select(&:directory?)
   end
 
   # @private
+  sig { returns(Pathname) }
   def resolved_path
     symlink? ? dirname.join(readlink) : self
   end
 
   # @private
+  sig { returns(T::Boolean) }
   def resolved_path_exists?
     link = readlink
   rescue ArgumentError
@@ -398,18 +406,22 @@ class Pathname
     end
   end
 
+  sig { returns(T::Boolean) }
   def ds_store?
     basename.to_s == ".DS_Store"
   end
 
+  sig { returns(T::Boolean) }
   def binary_executable?
     false
   end
 
+  sig { returns(T::Boolean) }
   def mach_o_bundle?
     false
   end
 
+  sig { returns(T::Boolean) }
   def dylib?
     false
   end
@@ -420,10 +432,13 @@ require "extend/os/pathname"
 # @private
 module ObserverPathnameExtension
   class << self
+    extend T::Sig
+
     include Context
 
     attr_accessor :n, :d
 
+    sig { void }
     def reset_counts!
       @n = @d = 0
       @put_verbose_trimmed_warning = false
diff --git a/Library/Homebrew/formula.rb b/Library/Homebrew/formula.rb
index 7b5e0fde35b1dff19e0eb3a7f10c65e79c2e272f..10e5347b861ed19f9eadcc2c42945b57e00153ed 100644
--- a/Library/Homebrew/formula.rb
+++ b/Library/Homebrew/formula.rb
@@ -52,6 +52,8 @@ require "utils/spdx"
 #   end
 # end</pre>
 class Formula
+  extend T::Sig
+
   include FileUtils
   include Utils::Inreplace
   include Utils::Shebang
@@ -286,6 +288,7 @@ class Formula
     path
   end
 
+  sig { returns(T.nilable(String)) }
   def installed_alias_name
     File.basename(installed_alias_path) if installed_alias_path
   end
@@ -354,6 +357,7 @@ class Formula
 
   # The Bottle object for the currently active {SoftwareSpec}.
   # @private
+  sig { returns(T.nilable(Bottle)) }
   def bottle
     Bottle.new(self, bottle_specification) if bottled?
   end
@@ -407,6 +411,7 @@ class Formula
   end
 
   # The {PkgVersion} for this formula with {version} and {#revision} information.
+  sig { returns(PkgVersion) }
   def pkg_version
     PkgVersion.new(version, revision)
   end
@@ -600,8 +605,9 @@ class Formula
   # The parent of the prefix; the named directory in the cellar containing all
   # installed versions of this software.
   # @private
+  sig { returns(Pathname) }
   def rack
-    Pathname.new("#{HOMEBREW_CELLAR}/#{name}")
+    HOMEBREW_CELLAR/name
   end
 
   # All currently installed prefix directories.
@@ -888,6 +894,7 @@ class Formula
   end
 
   # The prefix, if any, to use in filenames for logging current activity.
+  sig { returns(String) }
   def active_log_prefix
     if active_log_type
       "#{active_log_type}."
@@ -936,6 +943,7 @@ class Formula
   end
 
   # The generated launchd {.plist} service name.
+  sig { returns(String) }
   def plist_name
     "homebrew.mxcl.#{name}"
   end
@@ -958,8 +966,9 @@ class Formula
   # This is the preferred way to refer to a formula in plists or from another
   # formula, as the path is stable even when the software is updated.
   # <pre>args << "--with-readline=#{Formula["readline"].opt_prefix}" if build.with? "readline"</pre>
+  sig { returns(Pathname) }
   def opt_prefix
-    Pathname.new("#{HOMEBREW_PREFIX}/opt/#{name}")
+    HOMEBREW_PREFIX/"opt"/name
   end
 
   def opt_bin
@@ -1004,6 +1013,7 @@ class Formula
   # Defaults to true so overridden version does not have to check if bottles
   # are supported.
   # Replaced by {.pour_bottle?}'s `satisfy` method if it is specified.
+  sig { returns(T::Boolean) }
   def pour_bottle?
     true
   end
@@ -1160,11 +1170,13 @@ class Formula
   # @return [String, Symbol]
   delegate disable_reason: :"self.class"
 
+  sig { returns(T::Boolean) }
   def skip_cxxstdlib_check?
     false
   end
 
   # @private
+  sig { returns(T::Boolean) }
   def require_universal_deps?
     false
   end
@@ -1365,6 +1377,7 @@ class Formula
   end
 
   # @private
+  sig { returns(String) }
   def inspect
     "#<Formula #{name} (#{active_spec_sym}) #{path}>"
   end
@@ -1396,6 +1409,7 @@ class Formula
   # 3rd party installs.
   # Note that there isn't a std_autotools variant because autotools is a lot
   # less consistent and the standard parameters are more memorable.
+  sig { returns(T::Array[String]) }
   def std_cmake_args
     args = %W[
       -DCMAKE_C_FLAGS_RELEASE=-DNDEBUG
@@ -1423,6 +1437,7 @@ class Formula
   end
 
   # Standard parameters for cabal-v2 builds.
+  sig { returns(T::Array[String]) }
   def std_cabal_v2_args
     # cabal-install's dependency-resolution backtracking strategy can
     # easily need more than the default 2,000 maximum number of
@@ -1434,6 +1449,7 @@ class Formula
   end
 
   # Standard parameters for meson builds.
+  sig { returns(T::Array[String]) }
   def std_meson_args
     ["--prefix=#{prefix}", "--libdir=#{lib}", "--buildtype=release", "--wrap-mode=nofallback"]
   end
@@ -1869,6 +1885,7 @@ class Formula
   end
 
   # @private
+  sig { returns(T::Boolean) }
   def test_defined?
     false
   end
diff --git a/Library/Homebrew/formula_creator.rb b/Library/Homebrew/formula_creator.rb
index f30b7082ff52b754455eea78bb3259db66a0add8..fd9472c2db225cc9994ae20065f90dce73e9209a 100644
--- a/Library/Homebrew/formula_creator.rb
+++ b/Library/Homebrew/formula_creator.rb
@@ -9,6 +9,8 @@ module Homebrew
   #
   # @api private
   class FormulaCreator
+    extend T::Sig
+
     attr_reader :args, :url, :sha256, :desc, :homepage
     attr_accessor :name, :version, :tap, :path, :mode, :license
 
@@ -88,6 +90,7 @@ module Homebrew
       path.write ERB.new(template, trim_mode: ">").result(binding)
     end
 
+    sig { returns(String) }
     def template
       <<~ERB
         # Documentation: https://docs.brew.sh/Formula-Cookbook
diff --git a/Library/Homebrew/formula_installer.rb b/Library/Homebrew/formula_installer.rb
index aae10e1af1fa59d56f7bda3cfdcef940059c9e2c..364aed27468efe49c37c87aca7d3f728dc415a7f 100644
--- a/Library/Homebrew/formula_installer.rb
+++ b/Library/Homebrew/formula_installer.rb
@@ -28,6 +28,8 @@ require "unlink"
 #
 # @api private
 class FormulaInstaller
+  extend T::Sig
+
   include FormulaCellarChecks
   extend Predicable
 
@@ -776,6 +778,7 @@ class FormulaInstaller
     unlock
   end
 
+  sig { returns(String) }
   def summary
     s = +""
     s << "#{Homebrew::EnvConfig.install_badge}  " unless Homebrew::EnvConfig.no_emoji?
diff --git a/Library/Homebrew/formula_support.rb b/Library/Homebrew/formula_support.rb
index 287ffd0f0c14ff67fa3a27033162010be0eca87a..fce3bed2bce7bba0a455136a3e2477c6af9f2c8e 100644
--- a/Library/Homebrew/formula_support.rb
+++ b/Library/Homebrew/formula_support.rb
@@ -7,6 +7,8 @@ FormulaConflict = Struct.new(:name, :reason)
 # Used to annotate formulae that duplicate macOS-provided software
 # or cause conflicts when linked in.
 class KegOnlyReason
+  extend T::Sig
+
   attr_reader :reason
 
   def initialize(reason, explanation)
@@ -30,6 +32,7 @@ class KegOnlyReason
     provided_by_macos? || shadowed_by_macos?
   end
 
+  sig { returns(T::Boolean) }
   def applicable?
     # macOS reasons aren't applicable on other OSs
     # (see extend/os/mac/formula_support for override on macOS)
diff --git a/Library/Homebrew/formulary.rb b/Library/Homebrew/formulary.rb
index 3be8bbd3eff8f1fb71a1fa6eabfe58c4e8deae91..efe4ef24b474e732c922e7ee8c78eedcb69badc7 100644
--- a/Library/Homebrew/formulary.rb
+++ b/Library/Homebrew/formulary.rb
@@ -10,10 +10,13 @@ require "tab"
 #
 # @api private
 module Formulary
+  extend T::Sig
+
   extend Cachable
 
   URL_START_REGEX = %r{(https?|ftp|file)://}.freeze
 
+  sig { void }
   def self.enable_factory_cache!
     @factory_cache = true
   end
@@ -208,8 +211,11 @@ module Formulary
 
   # Loads formulae from URLs.
   class FromUrlLoader < FormulaLoader
+    extend T::Sig
+
     attr_reader :url
 
+    sig { params(url: T.any(URI::Generic, String)).void }
     def initialize(url)
       @url = url
       uri = URI(url)
diff --git a/Library/Homebrew/hardware.rb b/Library/Homebrew/hardware.rb
index 11c78eaf58e70a49ce0f592ab9002ff1d091e763..88625b72a3f7de636269c42d0d5521b333d9a72c 100644
--- a/Library/Homebrew/hardware.rb
+++ b/Library/Homebrew/hardware.rb
@@ -13,6 +13,8 @@ module Hardware
     PPC_64BIT_ARCHS   = [:ppc64, :ppc64le, :ppc970].freeze
 
     class << self
+      extend T::Sig
+
       def optimization_flags
         @optimization_flags ||= {
           native:             arch_flag("native"),
@@ -29,6 +31,7 @@ module Hardware
       end
       alias generic_optimization_flags optimization_flags
 
+      sig { returns(Symbol) }
       def arch_32_bit
         if arm?
           :arm
@@ -41,6 +44,7 @@ module Hardware
         end
       end
 
+      sig { returns(Symbol) }
       def arch_64_bit
         if arm?
           :arm64
@@ -70,6 +74,7 @@ module Hardware
         [arch].extend ArchitectureListExtension
       end
 
+      sig { returns(Symbol) }
       def type
         case RUBY_PLATFORM
         when /x86_64/, /i\d86/ then :intel
@@ -79,6 +84,7 @@ module Hardware
         end
       end
 
+      sig { returns(Symbol) }
       def family
         :dunno
       end
@@ -98,6 +104,7 @@ module Hardware
         end
       end
 
+      sig { returns(T::Boolean) }
       def sse4?
         RUBY_PLATFORM.to_s.include?("x86_64")
       end
@@ -156,6 +163,7 @@ module Hardware
         "-march=#{arch}"
       end
 
+      sig { returns(T::Boolean) }
       def in_rosetta2?
         false
       end
diff --git a/Library/Homebrew/keg.rb b/Library/Homebrew/keg.rb
index d46d0dc67ec818e7dd7b3c070ecab0bca865c3ce..d968c0c5e3f890a5e8b1bd08beacbdde7c12fcae 100644
--- a/Library/Homebrew/keg.rb
+++ b/Library/Homebrew/keg.rb
@@ -11,6 +11,8 @@ require "extend/cachable"
 #
 # @api private
 class Keg
+  extend T::Sig
+
   extend Cachable
 
   # Error for when a keg is already linked.
@@ -39,6 +41,9 @@ class Keg
 
   # Error for when a file already exists or belongs to another keg.
   class ConflictError < LinkError
+    extend T::Sig
+
+    sig { returns(String) }
     def suggestion
       conflict = Keg.for(dst)
     rescue NotAKegError, Errno::ENOENT
@@ -50,6 +55,7 @@ class Keg
       EOS
     end
 
+    sig { returns(String) }
     def to_s
       s = []
       s << "Could not symlink #{src}"
@@ -67,6 +73,9 @@ class Keg
 
   # Error for when a directory is not writable.
   class DirectoryNotWritableError < LinkError
+    extend T::Sig
+
+    sig { returns(String) }
     def to_s
       <<~EOS
         Could not symlink #{src}
@@ -226,6 +235,7 @@ class Keg
 
   alias to_path to_s
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}:#{path}>"
   end
@@ -235,6 +245,7 @@ class Keg
   end
   alias eql? ==
 
+  sig { returns(T::Boolean) }
   def empty_installation?
     Pathname.glob("#{path}/*") do |file|
       return false if file.directory? && !file.children.reject(&:ds_store?).empty?
@@ -411,6 +422,7 @@ class Keg
     end
   end
 
+  sig { returns(T::Boolean) }
   def plist_installed?
     !Dir["#{path}/*.plist"].empty?
   end
@@ -419,10 +431,12 @@ class Keg
     (path/"lib/python2.7/site-packages").directory?
   end
 
+  sig { returns(T::Boolean) }
   def python_pth_files_installed?
     !Dir["#{path}/lib/python2.7/site-packages/*.pth"].empty?
   end
 
+  sig { returns(T::Array[Pathname]) }
   def apps
     app_prefix = optlinked? ? opt_record : path
     Pathname.glob("#{app_prefix}/{,libexec/}*.app")
diff --git a/Library/Homebrew/language/node.rb b/Library/Homebrew/language/node.rb
index e30c9ba744a90fbfdba83ee5f3e32d29707ad428..1e5e48f7b5bc5996e872ffc84ab60117376205ac 100644
--- a/Library/Homebrew/language/node.rb
+++ b/Library/Homebrew/language/node.rb
@@ -6,6 +6,9 @@ module Language
   #
   # @api public
   module Node
+    extend T::Sig
+
+    sig { returns(String) }
     def self.npm_cache_config
       "cache=#{HOMEBREW_CACHE}/npm_cache"
     end
@@ -73,6 +76,7 @@ module Language
       args
     end
 
+    sig { returns(T::Array[String]) }
     def self.local_npm_install_args
       setup_npm_environment
       # npm install args for local style module format
diff --git a/Library/Homebrew/language/python.rb b/Library/Homebrew/language/python.rb
index a60343a70442635ec860b0049acad2a61b5efbc7..5b44de4412a990fd65771b168a9a0dab8f636d95 100644
--- a/Library/Homebrew/language/python.rb
+++ b/Library/Homebrew/language/python.rb
@@ -114,6 +114,8 @@ module Language
 
     # Mixin module for {Formula} adding virtualenv support features.
     module Virtualenv
+      extend T::Sig
+
       def self.included(base)
         base.class_eval do
           resource "homebrew-virtualenv" do
@@ -215,6 +217,7 @@ module Language
         venv
       end
 
+      sig { returns(T::Array[String]) }
       def python_names
         %w[python python3 pypy pypy3] + Formula.names.select { |name| name.start_with? "python@" }
       end
diff --git a/Library/Homebrew/linkage_checker.rb b/Library/Homebrew/linkage_checker.rb
index 67ab46e0934d2c0739ca7e2262daa1cd1d03caac..d1a898cfd6d76a65aa14114a0675006eed07ace1 100644
--- a/Library/Homebrew/linkage_checker.rb
+++ b/Library/Homebrew/linkage_checker.rb
@@ -10,6 +10,8 @@ require "fiddle"
 #
 # @api private
 class LinkageChecker
+  extend T::Sig
+
   attr_reader :undeclared_deps, :keg, :formula, :store
 
   def initialize(keg, formula = nil, cache_db:, rebuild_cache: false)
@@ -78,6 +80,7 @@ class LinkageChecker
     puts "Unexpected non-missing linkage detected" if unexpected_present_dylibs.present?
   end
 
+  sig { returns(T::Boolean) }
   def broken_library_linkage?
     issues = [@broken_deps, @unwanted_system_dylibs, @version_conflict_deps]
     [issues, unexpected_broken_dylibs, unexpected_present_dylibs].flatten.any?(&:present?)
diff --git a/Library/Homebrew/locale.rb b/Library/Homebrew/locale.rb
index 7a9ee544caecbf6f86802ecc833bcdf844844281..fcfa56f80f03a99b464ec97c7e22707895c48fb9 100644
--- a/Library/Homebrew/locale.rb
+++ b/Library/Homebrew/locale.rb
@@ -7,7 +7,9 @@
 #
 # @api private
 class Locale
-  # Error when a string cannot be parsed to a {Locale}.
+  extend T::Sig
+
+  # Error when a string cannot be parsed to a `Locale`.
   class ParserError < StandardError
   end
 
@@ -34,6 +36,7 @@ class Locale
     raise ParserError, "'#{string}' cannot be parsed to a #{self}"
   end
 
+  sig { params(string: String).returns(T.nilable(T.attached_class)) }
   def self.try_parse(string)
     return if string.blank?
 
@@ -107,6 +110,7 @@ class Locale
       locale_groups.find { |locales| locales.any? { |locale| include?(locale) } }
   end
 
+  sig { returns(String) }
   def to_s
     [@language, @region, @script].compact.join("-")
   end
diff --git a/Library/Homebrew/messages.rb b/Library/Homebrew/messages.rb
index fee41654da24e3672254b756e21945c9de5aa6be..e212896790d7ee3afb282d93deef636b598a8e3c 100644
--- a/Library/Homebrew/messages.rb
+++ b/Library/Homebrew/messages.rb
@@ -4,8 +4,11 @@
 # A {Messages} object collects messages that may need to be displayed together
 # at the end of a multi-step `brew` command run.
 class Messages
+  extend T::Sig
+
   attr_reader :caveats, :formula_count, :install_times
 
+  sig { void }
   def initialize
     @caveats = []
     @formula_count = 0
diff --git a/Library/Homebrew/migrator.rb b/Library/Homebrew/migrator.rb
index 4713960d2424705fd67fb0afc8bbd510b9eb92f1..688a743bbf5c2f3fd7029a72c4303be922c01ed7 100644
--- a/Library/Homebrew/migrator.rb
+++ b/Library/Homebrew/migrator.rb
@@ -9,6 +9,8 @@ require "tab"
 #
 # @api private
 class Migrator
+  extend T::Sig
+
   include Context
 
   # Error for when a migration is necessary.
@@ -155,6 +157,7 @@ class Migrator
     end
   end
 
+  sig { returns(T::Boolean) }
   def from_same_tap_user?
     formula_tap_user = formula.tap.user if formula.tap
     old_tap_user = nil
diff --git a/Library/Homebrew/mktemp.rb b/Library/Homebrew/mktemp.rb
index 5b7704d97eea3f59000369b7dfd787017fec0615..e5e0277e2c479e71e786628ac2945798a1c984a1 100644
--- a/Library/Homebrew/mktemp.rb
+++ b/Library/Homebrew/mktemp.rb
@@ -4,6 +4,8 @@
 # Performs {Formula#mktemp}'s functionality, and tracks the results.
 # Each instance is only intended to be used once.
 class Mktemp
+  extend T::Sig
+
   include FileUtils
 
   # Path to the tmpdir used in this run, as a {Pathname}.
@@ -16,6 +18,7 @@ class Mktemp
   end
 
   # Instructs this {Mktemp} to retain the staged files.
+  sig { void }
   def retain!
     @retain = true
   end
@@ -26,10 +29,12 @@ class Mktemp
   end
 
   # Instructs this Mktemp to not emit messages when retention is triggered.
+  sig { void }
   def quiet!
     @quiet = true
   end
 
+  sig { returns(String) }
   def to_s
     "[Mktemp: #{tmpdir} retain=#{@retain} quiet=#{@quiet}]"
   end
diff --git a/Library/Homebrew/options.rb b/Library/Homebrew/options.rb
index 9e4a229ed15071808cacb2c4504fe054b3f8ec42..5102e36661c9fe546c5eaa8e066f0132feb38d8c 100644
--- a/Library/Homebrew/options.rb
+++ b/Library/Homebrew/options.rb
@@ -5,6 +5,8 @@
 #
 # @api private
 class Option
+  extend T::Sig
+
   attr_reader :name, :description, :flag
 
   def initialize(name, description = "")
@@ -32,6 +34,7 @@ class Option
     name.hash
   end
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: #{flag.inspect}>"
   end
@@ -41,6 +44,8 @@ end
 #
 # @api private
 class DeprecatedOption
+  extend T::Sig
+
   attr_reader :old, :current
 
   def initialize(old, current)
@@ -48,10 +53,12 @@ class DeprecatedOption
     @current = current
   end
 
+  sig { returns(String) }
   def old_flag
     "--#{old}"
   end
 
+  sig { returns(String) }
   def current_flag
     "--#{current}"
   end
@@ -66,6 +73,8 @@ end
 #
 # @api private
 class Options
+  extend T::Sig
+
   include Enumerable
 
   def self.create(array)
@@ -119,6 +128,7 @@ class Options
 
   alias to_ary to_a
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: #{to_a.inspect}>"
   end
diff --git a/Library/Homebrew/os/linux.rb b/Library/Homebrew/os/linux.rb
index 17d2fee3461bc082216afa87f1ea5d97a527289c..039e6ab98f5dbf6fcb96c14c4f169ccdca4bee08 100644
--- a/Library/Homebrew/os/linux.rb
+++ b/Library/Homebrew/os/linux.rb
@@ -4,8 +4,11 @@
 module OS
   # Helper module for querying system information on Linux.
   module Linux
+    extend T::Sig
+
     module_function
 
+    sig { returns(String) }
     def os_version
       if which("lsb_release")
         description = Utils.popen_read("lsb_release -d")
diff --git a/Library/Homebrew/os/linux/glibc.rb b/Library/Homebrew/os/linux/glibc.rb
index 49df817c37bdfce73e8d104cf1d3f6f6451c255f..77b06fa7576c27b8c32decf2ec5aac7ae6f3f015 100644
--- a/Library/Homebrew/os/linux/glibc.rb
+++ b/Library/Homebrew/os/linux/glibc.rb
@@ -7,6 +7,8 @@ module OS
     #
     # @api private
     module Glibc
+      extend T::Sig
+
       module_function
 
       def system_version
@@ -18,6 +20,7 @@ module OS
         @system_version = Version.new version
       end
 
+      sig { returns(Version) }
       def minimum_version
         Version.new "2.13"
       end
diff --git a/Library/Homebrew/os/linux/kernel.rb b/Library/Homebrew/os/linux/kernel.rb
index fd535699bc83aff8b96f602b9f341667968794a2..d74a7412a4e5ac4efe12da3ef71d520f13b1c966 100644
--- a/Library/Homebrew/os/linux/kernel.rb
+++ b/Library/Homebrew/os/linux/kernel.rb
@@ -7,8 +7,11 @@ module OS
     #
     # @api private
     module Kernel
+      extend T::Sig
+
       module_function
 
+      sig { returns(Version) }
       def minimum_version
         Version.new "2.6.32"
       end
diff --git a/Library/Homebrew/os/mac.rb b/Library/Homebrew/os/mac.rb
index c7cd7e18206edc6f483df02f2a1af5503904fb7e..8f6a58aaa6234b017036fe5b52cdaf30bab6bf35 100644
--- a/Library/Homebrew/os/mac.rb
+++ b/Library/Homebrew/os/mac.rb
@@ -10,6 +10,8 @@ require "os/mac/keg"
 module OS
   # Helper module for querying system information on macOS.
   module Mac
+    extend T::Sig
+
     module_function
 
     # rubocop:disable Naming/ConstantName
@@ -81,6 +83,7 @@ module OS
       @active_developer_dir ||= Utils.popen_read("/usr/bin/xcode-select", "-print-path").strip
     end
 
+    sig { returns(T::Boolean) }
     def sdk_root_needed?
       if MacOS::CLT.installed?
         # If there's no CLT SDK, return false
diff --git a/Library/Homebrew/os/mac/sdk.rb b/Library/Homebrew/os/mac/sdk.rb
index 3a94bc97094eab875216b73877e526db607f2658..b4a7ff98068f9182a21c6011919a29be4d91ad83 100644
--- a/Library/Homebrew/os/mac/sdk.rb
+++ b/Library/Homebrew/os/mac/sdk.rb
@@ -92,6 +92,9 @@ module OS
     #
     # @api private
     class XcodeSDKLocator < BaseSDKLocator
+      extend T::Sig
+
+      sig { returns(Symbol) }
       def source
         :xcode
       end
@@ -115,6 +118,9 @@ module OS
     #
     # @api private
     class CLTSDKLocator < BaseSDKLocator
+      extend T::Sig
+
+      sig { returns(Symbol) }
       def source
         :clt
       end
diff --git a/Library/Homebrew/os/mac/xcode.rb b/Library/Homebrew/os/mac/xcode.rb
index f79ab663847ccb757991c59647372a9461ba5921..a2c833655b62f99cfda7545df86ed1e145fd77d0 100644
--- a/Library/Homebrew/os/mac/xcode.rb
+++ b/Library/Homebrew/os/mac/xcode.rb
@@ -7,15 +7,18 @@ module OS
     #
     # @api private
     module Xcode
+      extend T::Sig
+
       module_function
 
-      DEFAULT_BUNDLE_PATH = Pathname.new("/Applications/Xcode.app").freeze
+      DEFAULT_BUNDLE_PATH = Pathname("/Applications/Xcode.app").freeze
       BUNDLE_ID = "com.apple.dt.Xcode"
       OLD_BUNDLE_ID = "com.apple.Xcode"
 
       # Bump these when a new version is available from the App Store and our
       # CI systems have been updated.
       # This may be a beta version for a beta macOS.
+      sig { returns(String) }
       def latest_version
         latest_stable = "12.2"
         case MacOS.version
@@ -39,6 +42,7 @@ module OS
       # without this. Generally this will be the first Xcode release on that
       # macOS version (which may initially be a beta if that version of macOS is
       # also in beta).
+      sig { returns(String) }
       def minimum_version
         case MacOS.version
         when "11.0"  then "12.0"
@@ -93,8 +97,9 @@ module OS
           end
       end
 
+      sig { returns(Pathname) }
       def toolchain_path
-        Pathname.new("#{prefix}/Toolchains/XcodeDefault.xctoolchain")
+        Pathname("#{prefix}/Toolchains/XcodeDefault.xctoolchain")
       end
 
       def bundle_path
@@ -107,6 +112,7 @@ module OS
         MacOS.app_with_bundle_id(BUNDLE_ID, OLD_BUNDLE_ID)
       end
 
+      sig { returns(T::Boolean) }
       def installed?
         !prefix.nil?
       end
@@ -123,6 +129,7 @@ module OS
         sdk(v)&.path
       end
 
+      sig { returns(String) }
       def update_instructions
         if OS::Mac.prerelease?
           <<~EOS
@@ -174,6 +181,7 @@ module OS
         detect_version_from_clang_version
       end
 
+      sig { returns(String) }
       def detect_version_from_clang_version
         return "dunno" if DevelopmentTools.clang_version.null?
 
@@ -208,6 +216,8 @@ module OS
     #
     # @api private
     module CLT
+      extend T::Sig
+
       module_function
 
       # The original Mavericks CLT package ID
@@ -216,6 +226,7 @@ module OS
       PKG_PATH = "/Library/Developer/CommandLineTools"
 
       # Returns true even if outdated tools are installed.
+      sig { returns(T::Boolean) }
       def installed?
         !version.null?
       end
@@ -240,6 +251,7 @@ module OS
         sdk(v)&.path
       end
 
+      sig { returns(String) }
       def update_instructions
         software_update_location = if MacOS.version >= "10.14"
           "System Preferences"
@@ -262,6 +274,7 @@ module OS
 
       # Bump these when the new version is distributed through Software Update
       # and our CI systems have been updated.
+      sig { returns(String) }
       def latest_clang_version
         case MacOS.version
         when "11.0" then "1200.0.32.27"
@@ -278,6 +291,7 @@ module OS
       # Bump these if things are badly broken (e.g. no SDK for this macOS)
       # without this. Generally this will be the first stable CLT release on
       # that macOS version.
+      sig { returns(String) }
       def minimum_version
         case MacOS.version
         when "11.0"  then "12.0.0"
@@ -295,6 +309,7 @@ module OS
         version < minimum_version
       end
 
+      sig { returns(T::Boolean) }
       def outdated?
         clang_version = detect_clang_version
         return false unless clang_version
diff --git a/Library/Homebrew/os/mac/xquartz.rb b/Library/Homebrew/os/mac/xquartz.rb
index c056a27529c9e2d81e291f282a62fa3819305b5b..00819de600f3edd2f80634722647151e324042ef 100644
--- a/Library/Homebrew/os/mac/xquartz.rb
+++ b/Library/Homebrew/os/mac/xquartz.rb
@@ -7,9 +7,11 @@ module OS
     #
     # @api private
     module XQuartz
+      extend T::Sig
+
       module_function
 
-      DEFAULT_BUNDLE_PATH = Pathname.new("Applications/Utilities/XQuartz.app").freeze
+      DEFAULT_BUNDLE_PATH = Pathname("Applications/Utilities/XQuartz.app").freeze
       FORGE_BUNDLE_ID = "org.macosforge.xquartz.X11"
       FORGE_PKG_ID = "org.macosforge.xquartz.pkg"
 
@@ -52,6 +54,7 @@ module OS
         end
       end
 
+      sig { returns(String) }
       def minimum_version
         # Update this a little later than latest_version to give people
         # time to upgrade.
@@ -59,6 +62,7 @@ module OS
       end
 
       # @see https://www.xquartz.org/releases/index.html
+      sig { returns(String) }
       def latest_version
         "2.7.11"
       end
diff --git a/Library/Homebrew/patch.rb b/Library/Homebrew/patch.rb
index 61d00d6a0809d2cf5d2473103dcf450f92499f4f..1157c61005feba6df428303b3b30792d21d73c38 100644
--- a/Library/Homebrew/patch.rb
+++ b/Library/Homebrew/patch.rb
@@ -60,6 +60,8 @@ end
 #
 # @api private
 class EmbeddedPatch
+  extend T::Sig
+
   attr_writer :owner
   attr_reader :strip
 
@@ -67,6 +69,7 @@ class EmbeddedPatch
     @strip = strip
   end
 
+  sig { returns(T::Boolean) }
   def external?
     false
   end
@@ -79,6 +82,7 @@ class EmbeddedPatch
     Utils.safe_popen_write("patch", *args) { |p| p.write(data) }
   end
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: #{strip.inspect}>"
   end
@@ -88,6 +92,8 @@ end
 #
 # @api private
 class DATAPatch < EmbeddedPatch
+  extend T::Sig
+
   attr_accessor :path
 
   def initialize(strip)
@@ -95,6 +101,7 @@ class DATAPatch < EmbeddedPatch
     @path = nil
   end
 
+  sig { returns(String) }
   def contents
     data = +""
     path.open("rb") do |f|
@@ -128,6 +135,8 @@ end
 #
 # @api private
 class ExternalPatch
+  extend T::Sig
+
   extend Forwardable
 
   attr_reader :resource, :strip
@@ -141,6 +150,7 @@ class ExternalPatch
     @resource = Resource::PatchResource.new(&block)
   end
 
+  sig { returns(T::Boolean) }
   def external?
     true
   end
@@ -181,6 +191,7 @@ class ExternalPatch
     raise BuildError.new(f, cmd, args, ENV.to_hash)
   end
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: #{strip.inspect} #{url.inspect}>"
   end
diff --git a/Library/Homebrew/requirement.rb b/Library/Homebrew/requirement.rb
index 1f10e4aee7fdce0ad832ae00969961888bcdc53d..93863c3086004a7cf5b90f3da87a647a1dfd20f8 100644
--- a/Library/Homebrew/requirement.rb
+++ b/Library/Homebrew/requirement.rb
@@ -12,6 +12,8 @@ require "build_environment"
 #
 # @api private
 class Requirement
+  extend T::Sig
+
   include Dependable
 
   attr_reader :tags, :name, :cask, :download
@@ -35,6 +37,7 @@ class Requirement
   end
 
   # The message to show when the requirement is not met.
+  sig { returns(String) }
   def message
     _, _, class_name = self.class.to_s.rpartition "::"
     s = "#{class_name} unsatisfied!\n"
@@ -121,6 +124,7 @@ class Requirement
     name.hash ^ tags.hash
   end
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: #{tags.inspect}>"
   end
@@ -155,6 +159,8 @@ class Requirement
   end
 
   class << self
+    extend T::Sig
+
     include BuildEnvironment::DSL
 
     attr_reader :env_proc, :build
@@ -241,6 +247,7 @@ class Requirement
     end
 
     # Used to prune requirements when calling expand with a block.
+    sig { void }
     def prune
       throw(:prune, true)
     end
diff --git a/Library/Homebrew/requirements/arch_requirement.rb b/Library/Homebrew/requirements/arch_requirement.rb
index ec6a213174c3088104bde0d3d748d34a105fe899..8c65b44fa6146cb6c2d86837a25b25374656b2f7 100644
--- a/Library/Homebrew/requirements/arch_requirement.rb
+++ b/Library/Homebrew/requirements/arch_requirement.rb
@@ -7,6 +7,8 @@ require "requirement"
 #
 # @api private
 class ArchRequirement < Requirement
+  extend T::Sig
+
   fatal true
 
   attr_reader :arch
@@ -24,6 +26,7 @@ class ArchRequirement < Requirement
     end
   end
 
+  sig { returns(String) }
   def message
     "The #{@arch} architecture is required for this software."
   end
@@ -32,6 +35,7 @@ class ArchRequirement < Requirement
     "#<#{self.class.name}: arch=#{@arch.to_s.inspect} #{tags.inspect}>"
   end
 
+  sig { returns(String) }
   def display_s
     "#{@arch} architecture"
   end
diff --git a/Library/Homebrew/requirements/codesign_requirement.rb b/Library/Homebrew/requirements/codesign_requirement.rb
index 54fb9352a2e0264cededaefc099873fe0d5639a0..06caebda7128fd299f8527ee570bbb4629449e1d 100644
--- a/Library/Homebrew/requirements/codesign_requirement.rb
+++ b/Library/Homebrew/requirements/codesign_requirement.rb
@@ -5,6 +5,8 @@
 #
 # @api private
 class CodesignRequirement < Requirement
+  extend T::Sig
+
   fatal true
 
   def initialize(tags)
@@ -26,6 +28,7 @@ class CodesignRequirement < Requirement
     end
   end
 
+  sig { returns(String) }
   def message
     message = "#{@identity} identity must be available to build with #{@with}"
     message += ":\n#{@url}" if @url.present?
diff --git a/Library/Homebrew/requirements/java_requirement.rb b/Library/Homebrew/requirements/java_requirement.rb
index 3edab63aa8e4ebaceebe14b56b18bcd2b1627b9b..fdee4f4e033c8cad6b8aa309f814bb4e02557793 100644
--- a/Library/Homebrew/requirements/java_requirement.rb
+++ b/Library/Homebrew/requirements/java_requirement.rb
@@ -7,6 +7,8 @@ require "language/java"
 #
 # @api private
 class JavaRequirement < Requirement
+  extend T::Sig
+
   fatal true
 
   attr_reader :java_home, :version
@@ -37,6 +39,7 @@ class JavaRequirement < Requirement
     @cask = suggestion.token
   end
 
+  sig { returns(String) }
   def message
     version_string = " #{@version}" if @version
     s = "Java#{version_string} is required for this software.\n"
@@ -44,6 +47,7 @@ class JavaRequirement < Requirement
     s
   end
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: version=#{@version.inspect} #{tags.inspect}>"
   end
@@ -64,6 +68,9 @@ class JavaRequirement < Requirement
   private
 
   CaskSuggestion = Struct.new(:token, :title) do
+    extend T::Sig
+
+    sig { returns(String) }
     def to_str
       title_string = " #{title}" if title
       <<~EOS
diff --git a/Library/Homebrew/requirements/linux_requirement.rb b/Library/Homebrew/requirements/linux_requirement.rb
index 1a0e496282217d4697fa93287223ffd619d4e4ad..410c39bcc4e5d049ac36fc3ed8c58400b265d06e 100644
--- a/Library/Homebrew/requirements/linux_requirement.rb
+++ b/Library/Homebrew/requirements/linux_requirement.rb
@@ -5,10 +5,13 @@
 #
 # @api private
 class LinuxRequirement < Requirement
+  extend T::Sig
+
   fatal true
 
   satisfy(build_env: false) { OS.linux? }
 
+  sig { returns(String) }
   def message
     "Linux is required for this software."
   end
diff --git a/Library/Homebrew/requirements/macos_requirement.rb b/Library/Homebrew/requirements/macos_requirement.rb
index c00750b9a27c207b6b5496f115dd3d4a214cd222..e628588f0c9227fbba5f5ec68ef2f0d29343fcd7 100644
--- a/Library/Homebrew/requirements/macos_requirement.rb
+++ b/Library/Homebrew/requirements/macos_requirement.rb
@@ -7,6 +7,8 @@ require "requirement"
 #
 # @api private
 class MacOSRequirement < Requirement
+  extend T::Sig
+
   fatal true
 
   attr_reader :comparator, :version
@@ -66,10 +68,12 @@ class MacOSRequirement < Requirement
     end
   end
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: version#{@comparator}#{@version.to_s.inspect} #{tags.inspect}>"
   end
 
+  sig { returns(String) }
   def display_s
     return "macOS" unless version_specified?
 
diff --git a/Library/Homebrew/requirements/tuntap_requirement.rb b/Library/Homebrew/requirements/tuntap_requirement.rb
index 40075a947b11dfad8bc25566eb28f0ad9c76ee52..3599dcff4c7ebe3a6201a959b94485166fe52488 100644
--- a/Library/Homebrew/requirements/tuntap_requirement.rb
+++ b/Library/Homebrew/requirements/tuntap_requirement.rb
@@ -7,10 +7,13 @@ require "requirement"
 #
 # @api private
 class TuntapRequirement < Requirement
+  extend T::Sig
+
   fatal true
   cask "tuntap"
   satisfy(build_env: false) { self.class.binary_tuntap_installed? }
 
+  sig { returns(T::Boolean) }
   def self.binary_tuntap_installed?
     %w[
       /Library/Extensions/tun.kext
diff --git a/Library/Homebrew/requirements/x11_requirement.rb b/Library/Homebrew/requirements/x11_requirement.rb
index 4418f2f8efc5f426fa22352871d4a93971200843..d55a0ef984dfff837c3a23fc94dd69fc55f8ca87 100644
--- a/Library/Homebrew/requirements/x11_requirement.rb
+++ b/Library/Homebrew/requirements/x11_requirement.rb
@@ -7,6 +7,8 @@ require "requirement"
 #
 # @api private
 class X11Requirement < Requirement
+  extend T::Sig
+
   include Comparable
 
   fatal true
@@ -16,10 +18,12 @@ class X11Requirement < Requirement
 
   env { ENV.x11 }
 
+  sig { returns(String) }
   def min_version
     "1.12.2"
   end
 
+  sig { returns(String) }
   def min_xdpyinfo_version
     "1.3.0"
   end
@@ -38,6 +42,7 @@ class X11Requirement < Requirement
     false
   end
 
+  sig { returns(String) }
   def message
     "X11 is required for this software, either Xorg #{min_version} or " \
     "xdpyinfo #{min_xdpyinfo_version}, or newer. #{super}"
@@ -48,6 +53,11 @@ class X11Requirement < Requirement
 
     0
   end
+
+  sig { returns(String) }
+  def inspect
+    "#<#{self.class.name}: #{tags.inspect}>"
+  end
 end
 
 require "extend/os/requirements/x11_requirement"
diff --git a/Library/Homebrew/requirements/xcode_requirement.rb b/Library/Homebrew/requirements/xcode_requirement.rb
index b3e6973cfddb44e041d3e1f7759d810a40481505..775d62fc568bba5314491029f7b32285d0940a50 100644
--- a/Library/Homebrew/requirements/xcode_requirement.rb
+++ b/Library/Homebrew/requirements/xcode_requirement.rb
@@ -7,6 +7,8 @@ require "requirement"
 #
 # @api private
 class XcodeRequirement < Requirement
+  extend T::Sig
+
   fatal true
 
   attr_reader :version
@@ -25,6 +27,7 @@ class XcodeRequirement < Requirement
     MacOS::Xcode.version >= @version
   end
 
+  sig { returns(String) }
   def message
     version = " #{@version}" if @version
     message = <<~EOS
@@ -45,6 +48,7 @@ class XcodeRequirement < Requirement
     end
   end
 
+  sig { returns(String) }
   def inspect
     "#<#{self.class.name}: version>=#{@version.inspect} #{tags.inspect}>"
   end
diff --git a/Library/Homebrew/resource.rb b/Library/Homebrew/resource.rb
index f9c536467c37b9b0c3474310e17cb472e54b1f1a..7e16b3582e12703931cd7ce10e444e329de2a928 100644
--- a/Library/Homebrew/resource.rb
+++ b/Library/Homebrew/resource.rb
@@ -253,6 +253,8 @@ end
 #
 # @api private
 class ResourceStageContext
+  extend T::Sig
+
   extend Forwardable
 
   # The {Resource} that is being staged.
@@ -268,6 +270,7 @@ class ResourceStageContext
     @staging = staging
   end
 
+  sig { returns(String) }
   def to_s
     "<#{self.class}: resource=#{resource} staging=#{staging}>"
   end
diff --git a/Library/Homebrew/rubocops.rb b/Library/Homebrew/rubocops.rb
index e5c5651439ff713c57c80ca276c1d74ea1632574..24a89b54ae9e0d96d61cdaca33c3765459b57d85 100644
--- a/Library/Homebrew/rubocops.rb
+++ b/Library/Homebrew/rubocops.rb
@@ -3,6 +3,8 @@
 
 require_relative "load_path"
 
+require "utils/sorbet"
+
 require "rubocop-performance"
 require "rubocop-rspec"
 require "rubocop-sorbet"
diff --git a/Library/Homebrew/rubocops/cask/ast/cask_header.rb b/Library/Homebrew/rubocops/cask/ast/cask_header.rb
index a869967a5be3fd01fc339549696b706ac69a3d7e..addb8a718c2ccf92bb344c82cbf1f22cb6e1ea6c 100644
--- a/Library/Homebrew/rubocops/cask/ast/cask_header.rb
+++ b/Library/Homebrew/rubocops/cask/ast/cask_header.rb
@@ -7,6 +7,8 @@ module RuboCop
       # This class wraps the AST method node that represents the cask header. It
       # includes various helper methods to aid cops in their analysis.
       class CaskHeader
+        extend T::Sig
+
         def initialize(method_node)
           @method_node = method_node
         end
@@ -25,6 +27,7 @@ module RuboCop
           @source_range ||= method_node.loc.expression
         end
 
+        sig { returns(String) }
         def preferred_header_str
           "cask '#{cask_token}'"
         end
diff --git a/Library/Homebrew/rubocops/cask/extend/string.rb b/Library/Homebrew/rubocops/cask/extend/string.rb
index e89bed3af44edaf4d136f31b2fb278a8588deb00..f4e4ee3be04b286c4432b4e195f1cef9407854b1 100644
--- a/Library/Homebrew/rubocops/cask/extend/string.rb
+++ b/Library/Homebrew/rubocops/cask/extend/string.rb
@@ -3,6 +3,9 @@
 
 # Utility method extensions for String.
 class String
+  extend T::Sig
+
+  sig { returns(String) }
   def undent
     gsub(/^.{#{(slice(/^ +/) || '').length}}/, "")
   end
diff --git a/Library/Homebrew/rubocops/cask/no_dsl_version.rb b/Library/Homebrew/rubocops/cask/no_dsl_version.rb
index 2d2aca942b9e574825d00c80f87a7c490cc084c7..7866e52fe6dc2aa9efd4d8e35f739359b2fabca8 100644
--- a/Library/Homebrew/rubocops/cask/no_dsl_version.rb
+++ b/Library/Homebrew/rubocops/cask/no_dsl_version.rb
@@ -19,6 +19,8 @@ module RuboCop
       #     ...
       #   end
       class NoDslVersion < Cop
+        extend T::Sig
+
         extend Forwardable
         include CaskHelp
 
@@ -56,6 +58,7 @@ module RuboCop
                                                 message:  error_msg)
         end
 
+        sig { returns(String) }
         def error_msg
           format(MESSAGE, preferred: preferred_header_str, current: header_str)
         end
diff --git a/Library/Homebrew/rubocops/patches.rb b/Library/Homebrew/rubocops/patches.rb
index 8d85bd9f93210dc6aee25848de16abfd487f53b4..57c746df52f1fd084c300a2c5f054e497538c578 100644
--- a/Library/Homebrew/rubocops/patches.rb
+++ b/Library/Homebrew/rubocops/patches.rb
@@ -9,6 +9,8 @@ module RuboCop
     module FormulaAudit
       # This cop audits `patch`es in formulae.
       class Patches < FormulaCop
+        extend T::Sig
+
         def audit_formula(node, _class_node, _parent_class_node, body)
           @full_source_content = source_buffer(node).source
 
@@ -121,6 +123,7 @@ module RuboCop
           (send nil? :patch (:sym :DATA))
         AST
 
+        sig { returns(T::Boolean) }
         def patch_end?
           /^__END__$/.match?(@full_source_content)
         end
diff --git a/Library/Homebrew/rubocops/urls.rb b/Library/Homebrew/rubocops/urls.rb
index 3c7b855da05fa191baa0eb2a5b6f4d95027cec8d..62e347666bad0f1a20e05c75ff73f1ff9d6195f5 100644
--- a/Library/Homebrew/rubocops/urls.rb
+++ b/Library/Homebrew/rubocops/urls.rb
@@ -294,6 +294,8 @@ module RuboCop
       #
       # @api private
       class PyPiUrls < FormulaCop
+        extend T::Sig
+
         def audit_formula(_node, _class_node, _parent_class_node, body_node)
           urls = find_every_func_call_by_name(body_node, :url)
           mirrors = find_every_func_call_by_name(body_node, :mirror)
@@ -312,6 +314,7 @@ module RuboCop
           end
         end
 
+        sig { params(url: String).returns(String) }
         def get_pypi_url(url)
           package_file = File.basename(url)
           package_name = package_file.match(/^(.+)-[a-z0-9.]+$/)[1]
diff --git a/Library/Homebrew/sandbox.rb b/Library/Homebrew/sandbox.rb
index 54d0a76682709f500e6c94d2b7d460ac1c4a50af..2f79ae6a869b471764373e333ad47917c9832162 100644
--- a/Library/Homebrew/sandbox.rb
+++ b/Library/Homebrew/sandbox.rb
@@ -8,13 +8,17 @@ require "tempfile"
 #
 # @api private
 class Sandbox
+  extend T::Sig
+
   SANDBOX_EXEC = "/usr/bin/sandbox-exec"
   private_constant :SANDBOX_EXEC
 
+  sig { returns(T::Boolean) }
   def self.available?
     OS.mac? && File.executable?(SANDBOX_EXEC)
   end
 
+  sig { void }
   def initialize
     @profile = SandboxProfile.new
   end
@@ -146,6 +150,8 @@ class Sandbox
 
   # Configuration profile for a sandbox.
   class SandboxProfile
+    extend T::Sig
+
     SEATBELT_ERB = <<~ERB
       (version 1)
       (debug deny) ; log all denied operations to /var/log/system.log
@@ -169,6 +175,7 @@ class Sandbox
 
     attr_reader :rules
 
+    sig { void }
     def initialize
       @rules = []
     end
diff --git a/Library/Homebrew/software_spec.rb b/Library/Homebrew/software_spec.rb
index 8a6ed260e6441f4ce06a3082edf0fabbbb78a96d..14067d5a6e021607c7bb2328e8212f56c92c83cb 100644
--- a/Library/Homebrew/software_spec.rb
+++ b/Library/Homebrew/software_spec.rb
@@ -14,6 +14,8 @@ require "global"
 require "os/mac/version"
 
 class SoftwareSpec
+  extend T::Sig
+
   extend Forwardable
 
   PREDEFINED_OPTIONS = {
@@ -78,6 +80,7 @@ class SoftwareSpec
     @bottle_disable_reason.unneeded?
   end
 
+  sig { returns(T::Boolean) }
   def bottle_disabled?
     @bottle_disable_reason ? true : false
   end
@@ -247,6 +250,8 @@ end
 
 class Bottle
   class Filename
+    extend T::Sig
+
     attr_reader :name, :version, :tag, :rebuild
 
     def self.create(formula, tag, rebuild)
@@ -260,11 +265,13 @@ class Bottle
       @rebuild = rebuild
     end
 
+    sig { returns(String) }
     def to_s
       "#{name}--#{version}#{extname}"
     end
     alias to_str to_s
 
+    sig { returns(String) }
     def json
       "#{name}--#{version}.#{tag}.bottle.json"
     end
@@ -273,6 +280,7 @@ class Bottle
       ERB::Util.url_encode("#{name}-#{version}#{extname}")
     end
 
+    sig { returns(String) }
     def extname
       s = rebuild.positive? ? ".#{rebuild}" : ""
       ".#{tag}.bottle#{s}.tar.gz"
@@ -327,12 +335,15 @@ class Bottle
 end
 
 class BottleSpecification
+  extend T::Sig
+
   DEFAULT_PREFIX = Homebrew::DEFAULT_PREFIX
 
   attr_rw :prefix, :cellar, :rebuild
   attr_accessor :tap
   attr_reader :checksum, :collector, :root_url_specs
 
+  sig { void }
   def initialize
     @rebuild = 0
     @prefix = Homebrew::DEFAULT_PREFIX
@@ -355,6 +366,7 @@ class BottleSpecification
   end
 
   # Does the {Bottle} this {BottleSpecification} belongs to need to be relocated?
+  sig { returns(T::Boolean) }
   def skip_relocation?
     cellar == :any_skip_relocation
   end
diff --git a/Library/Homebrew/style.rb b/Library/Homebrew/style.rb
index 40a11b50cfc6923929d2e96a5ef312adedb22a00..3f10decf18912c4acbed1fc32c96734d7c2dc9e0 100644
--- a/Library/Homebrew/style.rb
+++ b/Library/Homebrew/style.rb
@@ -269,6 +269,8 @@ module Homebrew
 
     # Source location of a style offense.
     class LineLocation
+      extend T::Sig
+
       attr_reader :line, :column
 
       def initialize(json)
@@ -276,6 +278,7 @@ module Homebrew
         @column = json["column"]
       end
 
+      sig { returns(String) }
       def to_s
         "#{line}: col #{column}"
       end
diff --git a/Library/Homebrew/system_command.rb b/Library/Homebrew/system_command.rb
index 3d83ec5c0a205f9c773d09d54d3492edc8e82692..a9ef6cf6b56624ee4573cd750ebe9c94cb6a64ca 100644
--- a/Library/Homebrew/system_command.rb
+++ b/Library/Homebrew/system_command.rb
@@ -15,6 +15,8 @@ using HashValidator
 #
 # @api private
 class SystemCommand
+  extend T::Sig
+
   # Helper functions for calling {SystemCommand.run}.
   module Mixin
     def system_command(*args)
@@ -39,6 +41,7 @@ class SystemCommand
     run(command, **options, must_succeed: true)
   end
 
+  sig { returns(SystemCommand::Result) }
   def run!
     puts redact_secrets(command.shelljoin.gsub('\=', "="), @secrets) if verbose? || debug?
 
diff --git a/Library/Homebrew/system_config.rb b/Library/Homebrew/system_config.rb
index 02230bb9b4e558920038dedfc92d200c3849570c..6702c71635f4fbbddc076de8da86efb4cd3105f5 100644
--- a/Library/Homebrew/system_config.rb
+++ b/Library/Homebrew/system_config.rb
@@ -12,6 +12,8 @@ require "system_command"
 # @api private
 module SystemConfig
   class << self
+    extend T::Sig
+
     include SystemCommand::Mixin
 
     def clang
@@ -30,34 +32,42 @@ module SystemConfig
       end
     end
 
+    sig { returns(String) }
     def head
       HOMEBREW_REPOSITORY.git_head || "(none)"
     end
 
+    sig { returns(String) }
     def last_commit
       HOMEBREW_REPOSITORY.git_last_commit || "never"
     end
 
+    sig { returns(String) }
     def origin
       HOMEBREW_REPOSITORY.git_origin || "(none)"
     end
 
+    sig { returns(String) }
     def core_tap_head
       CoreTap.instance.git_head || "(none)"
     end
 
+    sig { returns(String) }
     def core_tap_last_commit
       CoreTap.instance.git_last_commit || "never"
     end
 
+    sig { returns(String) }
     def core_tap_branch
       CoreTap.instance.git_branch || "(none)"
     end
 
+    sig { returns(String) }
     def core_tap_origin
       CoreTap.instance.remote || "(none)"
     end
 
+    sig { returns(String) }
     def describe_clang
       return "N/A" if clang.null?
 
@@ -76,6 +86,7 @@ module SystemConfig
       end
     end
 
+    sig { returns(String) }
     def describe_homebrew_ruby_version
       case RUBY_VERSION
       when /^1\.[89]/, /^2\.0/
@@ -85,20 +96,24 @@ module SystemConfig
       end
     end
 
+    sig { returns(String) }
     def describe_homebrew_ruby
       "#{describe_homebrew_ruby_version} => #{RUBY_PATH}"
     end
 
+    sig { returns(T.nilable(String)) }
     def hardware
       return if Hardware::CPU.type == :dunno
 
       "CPU: #{Hardware.cores_as_words}-core #{Hardware::CPU.bits}-bit #{Hardware::CPU.family}"
     end
 
+    sig { returns(String) }
     def kernel
       `uname -m`.chomp
     end
 
+    sig { returns(String) }
     def describe_java
       return "N/A" unless which "java"
 
@@ -108,12 +123,14 @@ module SystemConfig
       err[/java version "([\d._]+)"/, 1] || "N/A"
     end
 
+    sig { returns(String) }
     def describe_git
       return "N/A" unless Utils::Git.available?
 
       "#{Utils::Git.version} => #{Utils::Git.path}"
     end
 
+    sig { returns(String) }
     def describe_curl
       out, = system_command(curl_executable, args: ["--version"])
 
diff --git a/Library/Homebrew/tab.rb b/Library/Homebrew/tab.rb
index 4d6a4a77287dd7255b23db17c89b589ad07c576f..8b732cae14220205a0d70eecb1b84ea74160b6d3 100644
--- a/Library/Homebrew/tab.rb
+++ b/Library/Homebrew/tab.rb
@@ -12,6 +12,8 @@ require "extend/cachable"
 # hash and creates an attribute for each key and value. Rather than calling
 # `new` directly, use one of the class methods like {Tab.create}.
 class Tab < OpenStruct
+  extend T::Sig
+
   extend Cachable
 
   FILENAME = "INSTALL_RECEIPT.json"
@@ -324,6 +326,7 @@ class Tab < OpenStruct
     versions["version_scheme"] || 0
   end
 
+  sig { returns(Time) }
   def source_modified_time
     Time.at(super || 0)
   end
@@ -362,6 +365,7 @@ class Tab < OpenStruct
     tabfile.atomic_write(to_json)
   end
 
+  sig { returns(String) }
   def to_s
     s = []
     s << if poured_from_bottle
diff --git a/Library/Homebrew/tap.rb b/Library/Homebrew/tap.rb
index 3e40bad395f2e684f0871d54d9cad8da2169b082..2eae5745e265fe3872035330e61574f9a7cdf655 100644
--- a/Library/Homebrew/tap.rb
+++ b/Library/Homebrew/tap.rb
@@ -12,6 +12,8 @@ require "description_cache_store"
 # {#user} represents the GitHub username and {#repo} represents the repository
 # name without the leading `homebrew-`.
 class Tap
+  extend T::Sig
+
   extend Cachable
 
   TAP_DIRECTORY = (HOMEBREW_LIBRARY/"Taps").freeze
@@ -123,6 +125,7 @@ class Tap
   end
 
   # The default remote path to this {Tap}.
+  sig { returns(String) }
   def default_remote
     "https://github.com/#{full_name}"
   end
@@ -176,6 +179,7 @@ class Tap
 
   # The issues URL of this {Tap}.
   # e.g. `https://github.com/user/homebrew-repo/issues`
+  sig { returns(T.nilable(String)) }
   def issues_url
     return unless official? || !custom_remote?
 
@@ -186,6 +190,7 @@ class Tap
     name
   end
 
+  sig { returns(String) }
   def version_string
     return "N/A" unless installed?
 
@@ -227,6 +232,7 @@ class Tap
   end
 
   # @private
+  sig { returns(T::Boolean) }
   def core_tap?
     false
   end
@@ -595,6 +601,7 @@ class Tap
   end
 
   # An array of all tap cmd directory {Pathname}s.
+  sig { returns(T::Array[Pathname]) }
   def self.cmd_directories
     Pathname.glob TAP_DIRECTORY/"*/*/cmd"
   end
@@ -633,7 +640,10 @@ end
 
 # A specialized {Tap} class for the core formulae.
 class CoreTap < Tap
+  extend T::Sig
+
   # @private
+  sig { void }
   def initialize
     super "Homebrew", "core"
   end
@@ -660,26 +670,31 @@ class CoreTap < Tap
   end
 
   # @private
+  sig { void }
   def uninstall
     raise "Tap#uninstall is not available for CoreTap"
   end
 
   # @private
+  sig { void }
   def pin
     raise "Tap#pin is not available for CoreTap"
   end
 
   # @private
+  sig { void }
   def unpin
     raise "Tap#unpin is not available for CoreTap"
   end
 
   # @private
+  sig { returns(T::Boolean) }
   def pinned?
     false
   end
 
   # @private
+  sig { returns(T::Boolean) }
   def core_tap?
     true
   end
diff --git a/Library/Homebrew/test/exceptions_spec.rb b/Library/Homebrew/test/exceptions_spec.rb
index e938c843c77af1dc576bd4e87c74fc97eb824c67..fee12d3fbb0e41618aef07f0d8b4f5c5f0d31eb5 100644
--- a/Library/Homebrew/test/exceptions_spec.rb
+++ b/Library/Homebrew/test/exceptions_spec.rb
@@ -48,12 +48,12 @@ describe FormulaUnavailableError do
 
     it "returns a string if there is a dependent" do
       subject.dependent = "foobar"
-      expect(subject.dependent_s).to eq("(dependency of foobar)")
+      expect(subject.dependent_s).to eq(" (dependency of foobar)")
     end
   end
 
   context "without a dependent" do
-    its(:to_s) { is_expected.to eq('No available formula with the name "foo" ') }
+    its(:to_s) { is_expected.to eq('No available formula with the name "foo".') }
   end
 
   context "with a dependent" do
@@ -62,7 +62,7 @@ describe FormulaUnavailableError do
     end
 
     its(:to_s) {
-      expect(subject.to_s).to eq('No available formula with the name "foo" (dependency of foobar)')
+      expect(subject.to_s).to eq('No available formula with the name "foo" (dependency of foobar).')
     }
   end
 end
diff --git a/Library/Homebrew/test/rubocop_spec.rb b/Library/Homebrew/test/rubocop_spec.rb
index 83ae2ddf683bde0030722927d1b96b516fff7410..1526df75062899a445569d476462af7f8b109802 100644
--- a/Library/Homebrew/test/rubocop_spec.rb
+++ b/Library/Homebrew/test/rubocop_spec.rb
@@ -10,11 +10,12 @@ describe "RuboCop" do
         ENV.delete(key) if key.start_with?("HOMEBREW_")
       end
 
-      ENV["XDG_CACHE_HOME"] = "#{HOMEBREW_CACHE}/style"
+      ENV["XDG_CACHE_HOME"] = (HOMEBREW_CACHE.realpath/"style").to_s
     end
 
     it "loads all Formula cops without errors" do
-      stdout, _, status = Open3.capture3("rubocop", TEST_FIXTURE_DIR/"testball.rb")
+      stdout, stderr, status = Open3.capture3("rubocop", TEST_FIXTURE_DIR/"testball.rb")
+      expect(stderr).to be_empty
       expect(stdout).to include("no offenses detected")
       expect(status).to be_a_success
     end
diff --git a/Library/Homebrew/unpack_strategy/air.rb b/Library/Homebrew/unpack_strategy/air.rb
index 8d6e73cd1ca6e58fea75448d7deaefab312ceab4..9f8bd8c473cdde24f8f4e790385cf123590422a1 100644
--- a/Library/Homebrew/unpack_strategy/air.rb
+++ b/Library/Homebrew/unpack_strategy/air.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking Adobe Air archives.
   class Air
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".air"]
     end
@@ -28,6 +31,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       system_command! AIR_APPLICATION_INSTALLER,
                       args:    ["-silent", "-location", unpack_dir, path],
diff --git a/Library/Homebrew/unpack_strategy/bazaar.rb b/Library/Homebrew/unpack_strategy/bazaar.rb
index f50957a124d986738b0bf03e956c9387f01d52ec..12fbd503d06ed5bdedc54c053cdc20ae3ce91d75 100644
--- a/Library/Homebrew/unpack_strategy/bazaar.rb
+++ b/Library/Homebrew/unpack_strategy/bazaar.rb
@@ -6,6 +6,8 @@ require_relative "directory"
 module UnpackStrategy
   # Strategy for unpacking Bazaar archives.
   class Bazaar < Directory
+    extend T::Sig
+
     using Magic
 
     def self.can_extract?(path)
@@ -14,11 +16,12 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       super
 
       # The export command doesn't work on checkouts (see https://bugs.launchpad.net/bzr/+bug/897511).
-      FileUtils.rm_r unpack_dir/".bzr"
+      (unpack_dir/".bzr").rmtree
     end
   end
 end
diff --git a/Library/Homebrew/unpack_strategy/bzip2.rb b/Library/Homebrew/unpack_strategy/bzip2.rb
index 79d25aaa5b2b20adb2d362d7205ae6899e803eb5..6b05e4dc15c7a1361272c14551b4fff0e93316e4 100644
--- a/Library/Homebrew/unpack_strategy/bzip2.rb
+++ b/Library/Homebrew/unpack_strategy/bzip2.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking bzip2 archives.
   class Bzip2
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".bz2"]
     end
@@ -18,6 +21,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       FileUtils.cp path, unpack_dir/basename, preserve: true
       quiet_flags = verbose ? [] : ["-q"]
diff --git a/Library/Homebrew/unpack_strategy/cab.rb b/Library/Homebrew/unpack_strategy/cab.rb
index 00b0831288e96b570947fc387a359ee0dd6afa12..89feaf0df6335a18fc3e66ecde1c1a137f3753e5 100644
--- a/Library/Homebrew/unpack_strategy/cab.rb
+++ b/Library/Homebrew/unpack_strategy/cab.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking Cabinet archives.
   class Cab
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".cab"]
     end
@@ -16,6 +19,7 @@ module UnpackStrategy
       path.magic_number.match?(/\AMSCF/n)
     end
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       system_command! "cabextract",
                       args:    ["-d", unpack_dir, "--", path],
diff --git a/Library/Homebrew/unpack_strategy/compress.rb b/Library/Homebrew/unpack_strategy/compress.rb
index 8e83fa057a537b7901f36ec1106444d5147c44a7..65f9ea8728ed30f0dd3ac8993f68fc78340ef3b4 100644
--- a/Library/Homebrew/unpack_strategy/compress.rb
+++ b/Library/Homebrew/unpack_strategy/compress.rb
@@ -6,8 +6,11 @@ require_relative "tar"
 module UnpackStrategy
   # Strategy for unpacking compress archives.
   class Compress < Tar
+    extend T::Sig
+
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".Z"]
     end
diff --git a/Library/Homebrew/unpack_strategy/directory.rb b/Library/Homebrew/unpack_strategy/directory.rb
index 0e8c68b59362425978d799df0395c4e8a616c359..02772dcc68fcf2b9b426c76f85b6d714242895bd 100644
--- a/Library/Homebrew/unpack_strategy/directory.rb
+++ b/Library/Homebrew/unpack_strategy/directory.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking directories.
   class Directory
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       []
     end
@@ -18,6 +21,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       path.children.each do |child|
         system_command! "cp",
diff --git a/Library/Homebrew/unpack_strategy/dmg.rb b/Library/Homebrew/unpack_strategy/dmg.rb
index 1d2e8de5ce4a157a83b1f9929e4b8e945d497c28..db6f3285d56e62257169b314fea39f1b949db868 100644
--- a/Library/Homebrew/unpack_strategy/dmg.rb
+++ b/Library/Homebrew/unpack_strategy/dmg.rb
@@ -6,6 +6,8 @@ require "tempfile"
 module UnpackStrategy
   # Strategy for unpacking disk images.
   class Dmg
+    extend T::Sig
+
     include UnpackStrategy
 
     # Helper module for listing the contents of a volume mounted from a disk image.
@@ -54,6 +56,8 @@ module UnpackStrategy
 
     # Strategy for unpacking a volume mounted from a disk image.
     class Mount
+      extend T::Sig
+
       using Bom
       include UnpackStrategy
 
@@ -82,6 +86,7 @@ module UnpackStrategy
 
       private
 
+      sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
       def extract_to_dir(unpack_dir, basename:, verbose:)
         Tempfile.open(["", ".bom"]) do |bomfile|
           bomfile.close
@@ -105,6 +110,7 @@ module UnpackStrategy
     end
     private_constant :Mount
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".dmg"]
     end
@@ -116,6 +122,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       mount(verbose: verbose) do |mounts|
         raise "No mounts found in '#{path}'; perhaps this is a bad disk image?" if mounts.empty?
diff --git a/Library/Homebrew/unpack_strategy/executable.rb b/Library/Homebrew/unpack_strategy/executable.rb
index a592cce52f537a40f5dd9b40771cd9e58baf8d33..1daeb7d0f70f0142ea25bb688402a10160f1cccf 100644
--- a/Library/Homebrew/unpack_strategy/executable.rb
+++ b/Library/Homebrew/unpack_strategy/executable.rb
@@ -6,8 +6,11 @@ require_relative "uncompressed"
 module UnpackStrategy
   # Strategy for unpacking executables.
   class Executable < Uncompressed
+    extend T::Sig
+
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".sh", ".bash"]
     end
diff --git a/Library/Homebrew/unpack_strategy/fossil.rb b/Library/Homebrew/unpack_strategy/fossil.rb
index f421ee1be8cdae9c7a89489d53eae9a3f4c20191..869a05628591e4d0fcb206b3f6d94fcb3a4a9371 100644
--- a/Library/Homebrew/unpack_strategy/fossil.rb
+++ b/Library/Homebrew/unpack_strategy/fossil.rb
@@ -6,11 +6,14 @@ require "system_command"
 module UnpackStrategy
   # Strategy for unpacking Fossil repositories.
   class Fossil
+    extend T::Sig
+
     include UnpackStrategy
     extend SystemCommand::Mixin
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       []
     end
@@ -25,6 +28,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       args = if @ref_type && @ref
         [@ref]
diff --git a/Library/Homebrew/unpack_strategy/generic_unar.rb b/Library/Homebrew/unpack_strategy/generic_unar.rb
index 7b0a0a53bdd8453fd3b336e81718715f80d1956e..4628cd517d74562a48ca50d434edf07dced7e1ec 100644
--- a/Library/Homebrew/unpack_strategy/generic_unar.rb
+++ b/Library/Homebrew/unpack_strategy/generic_unar.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking archives with `unar`.
   class GenericUnar
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       []
     end
@@ -22,6 +25,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       system_command! "unar",
                       args:    [
diff --git a/Library/Homebrew/unpack_strategy/gzip.rb b/Library/Homebrew/unpack_strategy/gzip.rb
index 4797fbaa24621a4e320ceb0238654e7dfbd85db6..983d995a98bbb05b8cb37b71c1686742bf702faf 100644
--- a/Library/Homebrew/unpack_strategy/gzip.rb
+++ b/Library/Homebrew/unpack_strategy/gzip.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking gzip archives.
   class Gzip
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".gz"]
     end
@@ -18,6 +21,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       FileUtils.cp path, unpack_dir/basename, preserve: true
       quiet_flags = verbose ? [] : ["-q"]
diff --git a/Library/Homebrew/unpack_strategy/jar.rb b/Library/Homebrew/unpack_strategy/jar.rb
index ee05a876a185e120ddf3bdafe5e3d6921e253366..d4170a8689c159fb18ccc8a36dc1069e8a3bd60c 100644
--- a/Library/Homebrew/unpack_strategy/jar.rb
+++ b/Library/Homebrew/unpack_strategy/jar.rb
@@ -6,8 +6,11 @@ require_relative "uncompressed"
 module UnpackStrategy
   # Strategy for unpacking Java archives.
   class Jar < Uncompressed
+    extend T::Sig
+
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".apk", ".jar"]
     end
diff --git a/Library/Homebrew/unpack_strategy/lha.rb b/Library/Homebrew/unpack_strategy/lha.rb
index 70c3e5f70927bb07b11f72d09b895b1e43b8909f..7b92af7290b92eb0aae98b65413f7bbf91dc6faa 100644
--- a/Library/Homebrew/unpack_strategy/lha.rb
+++ b/Library/Homebrew/unpack_strategy/lha.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking LHa archives.
   class Lha
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".lha", ".lzh"]
     end
@@ -22,6 +25,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       system_command! "lha",
                       args:    ["xq2w=#{unpack_dir}", path],
diff --git a/Library/Homebrew/unpack_strategy/lua_rock.rb b/Library/Homebrew/unpack_strategy/lua_rock.rb
index 1336b856decf7821bdc8d663e2dd5f579962292d..6150e2788e179571b18e9b2517bd9536b2182e2f 100644
--- a/Library/Homebrew/unpack_strategy/lua_rock.rb
+++ b/Library/Homebrew/unpack_strategy/lua_rock.rb
@@ -6,8 +6,11 @@ require_relative "uncompressed"
 module UnpackStrategy
   # Strategy for unpacking LuaRock archives.
   class LuaRock < Uncompressed
+    extend T::Sig
+
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".rock"]
     end
diff --git a/Library/Homebrew/unpack_strategy/lzip.rb b/Library/Homebrew/unpack_strategy/lzip.rb
index a27663e4d5772ca155897e439cd7668094f40284..71f561c9df3f120a109a9b3ecc2af9df02890e90 100644
--- a/Library/Homebrew/unpack_strategy/lzip.rb
+++ b/Library/Homebrew/unpack_strategy/lzip.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking lzip archives.
   class Lzip
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".lz"]
     end
@@ -22,6 +25,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       FileUtils.cp path, unpack_dir/basename, preserve: true
       quiet_flags = verbose ? [] : ["-q"]
diff --git a/Library/Homebrew/unpack_strategy/lzma.rb b/Library/Homebrew/unpack_strategy/lzma.rb
index e14de8e993255603d0f6d1261934429eb73774fa..21a9cd4e31af6fe467aa43f095a43610257201e5 100644
--- a/Library/Homebrew/unpack_strategy/lzma.rb
+++ b/Library/Homebrew/unpack_strategy/lzma.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking LZMA archives.
   class Lzma
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".lzma"]
     end
@@ -16,6 +19,7 @@ module UnpackStrategy
       path.magic_number.match?(/\A\]\000\000\200\000/n)
     end
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       FileUtils.cp path, unpack_dir/basename, preserve: true
       quiet_flags = verbose ? [] : ["-q"]
diff --git a/Library/Homebrew/unpack_strategy/microsoft_office_xml.rb b/Library/Homebrew/unpack_strategy/microsoft_office_xml.rb
index 5d97e6f2226af232172bacb24efa666fd33f2bdf..616d78bc061bb060119dc4d7e3755f31600e9213 100644
--- a/Library/Homebrew/unpack_strategy/microsoft_office_xml.rb
+++ b/Library/Homebrew/unpack_strategy/microsoft_office_xml.rb
@@ -6,8 +6,11 @@ require_relative "uncompressed"
 module UnpackStrategy
   # Strategy for unpacking Microsoft Office documents.
   class MicrosoftOfficeXml < Uncompressed
+    extend T::Sig
+
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [
         ".doc", ".docx",
diff --git a/Library/Homebrew/unpack_strategy/otf.rb b/Library/Homebrew/unpack_strategy/otf.rb
index 1a0538d9428b81f3715db564541be321ccc9cdd1..e94eb150290837fb5b7ec81bf987f78c2021634b 100644
--- a/Library/Homebrew/unpack_strategy/otf.rb
+++ b/Library/Homebrew/unpack_strategy/otf.rb
@@ -6,8 +6,11 @@ require_relative "uncompressed"
 module UnpackStrategy
   # Strategy for unpacking OpenType fonts.
   class Otf < Uncompressed
+    extend T::Sig
+
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".otf"]
     end
diff --git a/Library/Homebrew/unpack_strategy/p7zip.rb b/Library/Homebrew/unpack_strategy/p7zip.rb
index 5aca009f538d801c041d3497a5d6b5da87293ced..3a5ef46f00d2b6e4f70c050b35a8f7e554769e43 100644
--- a/Library/Homebrew/unpack_strategy/p7zip.rb
+++ b/Library/Homebrew/unpack_strategy/p7zip.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking P7ZIP archives.
   class P7Zip
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".7z"]
     end
@@ -22,6 +25,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       system_command! "7zr",
                       args:    ["x", "-y", "-bd", "-bso0", path, "-o#{unpack_dir}"],
diff --git a/Library/Homebrew/unpack_strategy/pax.rb b/Library/Homebrew/unpack_strategy/pax.rb
index e914d41baf4301dc59acc525f9f028a4408b261a..4067132c80a9b62eb292d83af9c38171f461d9b3 100644
--- a/Library/Homebrew/unpack_strategy/pax.rb
+++ b/Library/Homebrew/unpack_strategy/pax.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking pax archives.
   class Pax
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".pax"]
     end
@@ -18,6 +21,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       system_command! "pax",
                       args:    ["-rf", path],
diff --git a/Library/Homebrew/unpack_strategy/pkg.rb b/Library/Homebrew/unpack_strategy/pkg.rb
index 20bf5057e816e5a2eed1afc195bdcb04455fdfc2..220b86a58c9d6df0187e798ea40d45bf0e417309 100644
--- a/Library/Homebrew/unpack_strategy/pkg.rb
+++ b/Library/Homebrew/unpack_strategy/pkg.rb
@@ -6,8 +6,11 @@ require_relative "uncompressed"
 module UnpackStrategy
   # Strategy for unpacking macOS package installers.
   class Pkg < Uncompressed
+    extend T::Sig
+
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".pkg", ".mkpg"]
     end
diff --git a/Library/Homebrew/unpack_strategy/rar.rb b/Library/Homebrew/unpack_strategy/rar.rb
index 71e2dd66a20061236029a89b90f8d992409bbe84..7cd1d026357c211b4635809470c875cb36dacdd0 100644
--- a/Library/Homebrew/unpack_strategy/rar.rb
+++ b/Library/Homebrew/unpack_strategy/rar.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking RAR archives.
   class Rar
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".rar"]
     end
@@ -22,6 +25,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       system_command! "unrar",
                       args:    ["x", "-inul", path, unpack_dir],
diff --git a/Library/Homebrew/unpack_strategy/self_extracting_executable.rb b/Library/Homebrew/unpack_strategy/self_extracting_executable.rb
index c74166d77194c131bfecc1d93acda8eb8f856e6c..0e99278711db3b40290d4a7fa7a5a21d9da9c968 100644
--- a/Library/Homebrew/unpack_strategy/self_extracting_executable.rb
+++ b/Library/Homebrew/unpack_strategy/self_extracting_executable.rb
@@ -6,8 +6,11 @@ require_relative "generic_unar"
 module UnpackStrategy
   # Strategy for unpacking self-extracting executables.
   class SelfExtractingExecutable < GenericUnar
+    extend T::Sig
+
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       []
     end
diff --git a/Library/Homebrew/unpack_strategy/sit.rb b/Library/Homebrew/unpack_strategy/sit.rb
index 5fabbbbfc88545cdfb3db6a1504a7530c690877d..687e7d0e64025c9aa492fdc777a95b2e4f5a8d40 100644
--- a/Library/Homebrew/unpack_strategy/sit.rb
+++ b/Library/Homebrew/unpack_strategy/sit.rb
@@ -6,8 +6,11 @@ require_relative "generic_unar"
 module UnpackStrategy
   # Strategy for unpacking Stuffit archives.
   class Sit < GenericUnar
+    extend T::Sig
+
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".sit"]
     end
diff --git a/Library/Homebrew/unpack_strategy/tar.rb b/Library/Homebrew/unpack_strategy/tar.rb
index a31550b75def94b119912690fdfeb5f1809c759b..a40ad8f45ecf281f2c28a73795dc2d4c291e78d9 100644
--- a/Library/Homebrew/unpack_strategy/tar.rb
+++ b/Library/Homebrew/unpack_strategy/tar.rb
@@ -6,11 +6,14 @@ require "system_command"
 module UnpackStrategy
   # Strategy for unpacking tar archives.
   class Tar
+    extend T::Sig
+
     include UnpackStrategy
     extend SystemCommand::Mixin
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [
         ".tar",
@@ -33,6 +36,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       Dir.mktmpdir do |tmpdir|
         tar_path = path
diff --git a/Library/Homebrew/unpack_strategy/ttf.rb b/Library/Homebrew/unpack_strategy/ttf.rb
index b45755a428cdcbcff17012c5379aa7b35b839e6a..38b44879de5fb184d524bb816afe9f0b6cb1212b 100644
--- a/Library/Homebrew/unpack_strategy/ttf.rb
+++ b/Library/Homebrew/unpack_strategy/ttf.rb
@@ -6,8 +6,11 @@ require_relative "uncompressed"
 module UnpackStrategy
   # Strategy for unpacking TrueType fonts.
   class Ttf < Uncompressed
+    extend T::Sig
+
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".ttc", ".ttf"]
     end
diff --git a/Library/Homebrew/unpack_strategy/uncompressed.rb b/Library/Homebrew/unpack_strategy/uncompressed.rb
index 1c869d998e732d3bb8bab29a45e980fcddcaa736..16ced6ca1669fca5fb76d145ae1189c1cb6bd271 100644
--- a/Library/Homebrew/unpack_strategy/uncompressed.rb
+++ b/Library/Homebrew/unpack_strategy/uncompressed.rb
@@ -4,6 +4,8 @@
 module UnpackStrategy
   # Strategy for unpacking uncompressed files.
   class Uncompressed
+    extend T::Sig
+
     include UnpackStrategy
 
     def extract_nestedly(prioritise_extension: false, **options)
@@ -12,6 +14,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       FileUtils.cp path, unpack_dir/basename, preserve: true, verbose: verbose
     end
diff --git a/Library/Homebrew/unpack_strategy/xar.rb b/Library/Homebrew/unpack_strategy/xar.rb
index 2f5f4794a3ba6c5f8bf7853d6f9229cc146e57e5..ce35a0683ab56f2a77784a4872ad5c1d034c1f92 100644
--- a/Library/Homebrew/unpack_strategy/xar.rb
+++ b/Library/Homebrew/unpack_strategy/xar.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking xar archives.
   class Xar
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".xar"]
     end
@@ -18,6 +21,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       system_command! "xar",
                       args:    ["-x", "-f", path, "-C", unpack_dir],
diff --git a/Library/Homebrew/unpack_strategy/xz.rb b/Library/Homebrew/unpack_strategy/xz.rb
index 86f50d2a38a9922122cadf5847963bdec3f73a97..ec81be5673d64935122a21e8e28d4e9ba95097ee 100644
--- a/Library/Homebrew/unpack_strategy/xz.rb
+++ b/Library/Homebrew/unpack_strategy/xz.rb
@@ -4,10 +4,13 @@
 module UnpackStrategy
   # Strategy for unpacking xz archives.
   class Xz
+    extend T::Sig
+
     include UnpackStrategy
 
     using Magic
 
+    sig { returns(T::Array[String]) }
     def self.extensions
       [".xz"]
     end
@@ -22,6 +25,7 @@ module UnpackStrategy
 
     private
 
+    sig { override.params(unpack_dir: Pathname, basename: Pathname, verbose: T::Boolean).returns(T.untyped) }
     def extract_to_dir(unpack_dir, basename:, verbose:)
       FileUtils.cp path, unpack_dir/basename, preserve: true
       quiet_flags = verbose ? [] : ["-q"]
diff --git a/Library/Homebrew/utils.rb b/Library/Homebrew/utils.rb
index 45f46f3962fa74ab5443e34c79ba30a7daffac75..a66263ac4e309620da5611e57f826e39e5be7dc9 100644
--- a/Library/Homebrew/utils.rb
+++ b/Library/Homebrew/utils.rb
@@ -80,6 +80,8 @@ module Homebrew
 end
 
 module Kernel
+  extend T::Sig
+
   def require?(path)
     return false if path.nil?
 
@@ -383,6 +385,7 @@ module Kernel
     trap("INT", std_trap)
   end
 
+  sig { returns(String) }
   def capture_stderr
     old = $stderr
     $stderr = StringIO.new
@@ -500,6 +503,7 @@ module Kernel
     end
   end
 
+  sig { returns(String) }
   def shell_profile
     Utils::Shell.profile
   end
diff --git a/Library/Homebrew/utils/analytics.rb b/Library/Homebrew/utils/analytics.rb
index 9524db7218cd3056cd61627da48dd158c1263aaf..5ae0e106f5bb9a35ac505b2e191b5c2adfea0002 100644
--- a/Library/Homebrew/utils/analytics.rb
+++ b/Library/Homebrew/utils/analytics.rb
@@ -9,6 +9,8 @@ module Utils
   # @api private
   module Analytics
     class << self
+      extend T::Sig
+
       include Context
 
       def report(type, metadata = {})
@@ -191,6 +193,7 @@ module Utils
         get_analytics(json, args: args)
       end
 
+      sig { returns(String) }
       def custom_prefix_label
         "custom-prefix"
       end
@@ -339,16 +342,19 @@ module Utils
         format("%<percent>.2f", percent: percent)
       end
 
+      sig { returns(String) }
       def formula_path
         "formula"
       end
       alias generic_formula_path formula_path
 
+      sig { returns(String) }
       def analytics_path
         "analytics"
       end
       alias generic_analytics_path analytics_path
 
+      sig { returns(String) }
       def cask_path
         "cask"
       end
diff --git a/Library/Homebrew/utils/bottles.rb b/Library/Homebrew/utils/bottles.rb
index fff38c4561a314a103ee31d72af39f7985ad4ea0..99c727cbd1a82e50540d60810af120e42490664c 100644
--- a/Library/Homebrew/utils/bottles.rb
+++ b/Library/Homebrew/utils/bottles.rb
@@ -9,6 +9,8 @@ module Utils
   # @api private
   module Bottles
     class << self
+      extend T::Sig
+
       def tag
         @tag ||= "#{ENV["HOMEBREW_PROCESSOR"]}_#{ENV["HOMEBREW_SYSTEM"]}".downcase.to_sym
       end
@@ -30,6 +32,7 @@ module Utils
         bottle_ext && bottle_url_ext && bottle_ext != bottle_url_ext
       end
 
+      sig { returns(Regexp) }
       def native_regex
         /(\.#{Regexp.escape(tag.to_s)}\.bottle\.(\d+\.)?tar\.gz)$/o
       end
@@ -93,10 +96,13 @@ module Utils
 
     # Collector for bottle specifications.
     class Collector
+      extend T::Sig
+
       extend Forwardable
 
       def_delegators :@checksums, :keys, :[], :[]=, :key?, :each_key
 
+      sig { void }
       def initialize
         @checksums = {}
       end
diff --git a/Library/Homebrew/utils/gems.rb b/Library/Homebrew/utils/gems.rb
index 866054123f212ac4918bc000c7211fba4d58d166..0985d6de2d076b6869b18367afadd87a2d2a982a 100644
--- a/Library/Homebrew/utils/gems.rb
+++ b/Library/Homebrew/utils/gems.rb
@@ -1,4 +1,4 @@
-# typed: false
+# typed: true
 # frozen_string_literal: true
 
 # Never `require` anything in this file (except English). It needs to be able to
@@ -57,7 +57,7 @@ module Homebrew
 
     # Add necessary Ruby and Gem binary directories to PATH.
     gem_bindir ||= Gem.bindir
-    paths = ENV["PATH"].split(":")
+    paths = ENV.fetch("PATH").split(":")
     paths.unshift(gem_bindir) unless paths.include?(gem_bindir)
     paths.unshift(ruby_bindir) unless paths.include?(ruby_bindir)
     ENV["PATH"] = paths.compact.join(":")
@@ -85,8 +85,8 @@ module Homebrew
   end
 
   def find_in_path(executable)
-    ENV["PATH"].split(":").find do |path|
-      File.executable?("#{path}/#{executable}")
+    ENV.fetch("PATH").split(":").find do |path|
+      File.executable?(File.join(path, executable))
     end
   end
 
@@ -104,9 +104,9 @@ module Homebrew
   def install_bundler_gems!
     install_bundler!
 
-    ENV["BUNDLE_GEMFILE"] = "#{ENV["HOMEBREW_LIBRARY"]}/Homebrew/Gemfile"
+    ENV["BUNDLE_GEMFILE"] = File.join(ENV.fetch("HOMEBREW_LIBRARY"), "Homebrew", "Gemfile")
     @bundle_installed ||= begin
-      bundle = "#{find_in_path(:bundle)}/bundle"
+      bundle = File.join(find_in_path("bundle"), "bundle")
       bundle_check_output = `#{bundle} check 2>&1`
       bundle_check_failed = !$CHILD_STATUS.success?
 
diff --git a/Library/Homebrew/utils/gems.rbi b/Library/Homebrew/utils/gems.rbi
new file mode 100644
index 0000000000000000000000000000000000000000..47c3ced643e480c48589779cce146279c1fa2241
--- /dev/null
+++ b/Library/Homebrew/utils/gems.rbi
@@ -0,0 +1,27 @@
+# typed: strict
+
+module Homebrew
+  sig { returns(String) }
+  def ruby_bindir; end
+
+  sig { returns(String) }
+  def gem_user_bindir; end
+
+  sig { params(message: String).void }
+  def ohai_if_defined(message); end
+
+  sig { params(message: String).returns(T.noreturn) }
+  def odie_if_defined(message); end
+
+  sig { params(name: String, version: T.nilable(String), executable: String, setup_gem_environment: T::Boolean).void }
+  def install_gem_setup_path!(name, version: nil, executable: name, setup_gem_environment: true); end
+
+  sig { params(executable: String).returns(T.nilable(String)) }
+  def find_in_path(executable); end
+
+  sig { void }
+  def install_bundler!; end
+
+  sig { void }
+  def install_bundler_gems!; end
+end
diff --git a/Library/Homebrew/utils/github.rb b/Library/Homebrew/utils/github.rb
index 124ba702555c5b798c8cc149d4e4d0787eed25c3..dc2e263c599f45adfa87f29a64ed41bb6120d7cb 100644
--- a/Library/Homebrew/utils/github.rb
+++ b/Library/Homebrew/utils/github.rb
@@ -10,6 +10,8 @@ require "utils/shell"
 #
 # @api private
 module GitHub
+  extend T::Sig
+
   module_function
 
   API_URL = "https://api.github.com"
@@ -129,6 +131,7 @@ module GitHub
     end
   end
 
+  sig { returns(Symbol) }
   def api_credentials_type
     if Homebrew::EnvConfig.github_api_token
       :env_token
diff --git a/Library/Homebrew/utils/github/actions.rb b/Library/Homebrew/utils/github/actions.rb
index 3dc7bf64019a958053949a5ec9e7dad038c9ec66..b3e2a1e2b3e31d0fe5f8e4cb7b8fbeeeadae0bad 100644
--- a/Library/Homebrew/utils/github/actions.rb
+++ b/Library/Homebrew/utils/github/actions.rb
@@ -17,6 +17,8 @@ module GitHub
 
     # Helper class for formatting annotations on GitHub Actions.
     class Annotation
+      extend T::Sig
+
       def self.path_relative_to_workspace(path)
         workspace = Pathname(ENV.fetch("GITHUB_WORKSPACE", Dir.pwd)).realpath
         path = Pathname(path)
@@ -35,6 +37,7 @@ module GitHub
         @column = Integer(column) if column
       end
 
+      sig { returns(String) }
       def to_s
         file = "file=#{Actions.escape(@file.to_s)}" if @file
         line = "line=#{@line}" if @line
diff --git a/Library/Homebrew/utils/sorbet.rb b/Library/Homebrew/utils/sorbet.rb
index cbc85f546552a8fdfdb1b170604dfd0033aea67f..2f91f50bb8cfe45aa1b67d9edef27f3281ac3384 100644
--- a/Library/Homebrew/utils/sorbet.rb
+++ b/Library/Homebrew/utils/sorbet.rb
@@ -1,4 +1,4 @@
-# typed: strict
+# typed: true
 # frozen_string_literal: true
 
 if ENV["HOMEBREW_SORBET_RUNTIME"]
@@ -7,7 +7,11 @@ if ENV["HOMEBREW_SORBET_RUNTIME"]
   require "sorbet-runtime"
 else
   # Explicitly prevent `sorbet-runtime` from being loaded.
-  ENV["GEM_SKIP"] = "sorbet-runtime"
+  def gem(name, *)
+    raise Gem::LoadError if name == "sorbet-runtime"
+
+    super
+  end
 
   require "sorbet-runtime-stub"
 end
diff --git a/Library/Homebrew/version.rb b/Library/Homebrew/version.rb
index 07ef21714c035760be71f312b92e89060d58024d..08c0d760218289625421659a41c5d50a50c33297 100644
--- a/Library/Homebrew/version.rb
+++ b/Library/Homebrew/version.rb
@@ -7,6 +7,8 @@ require "version/null"
 #
 # @api private
 class Version
+  extend T::Sig
+
   include Comparable
 
   def self.formula_optionally_versioned_regex(name, full: true)
@@ -15,6 +17,8 @@ class Version
 
   # A part of a {Version}.
   class Token
+    extend T::Sig
+
     include Comparable
 
     def self.create(val)
@@ -48,6 +52,7 @@ class Version
       @value = value
     end
 
+    sig { returns(String) }
     def inspect
       "#<#{self.class.name} #{value.inspect}>"
     end
@@ -69,6 +74,7 @@ class Version
     end
     alias to_str to_s
 
+    sig { returns(T::Boolean) }
     def numeric?
       false
     end
@@ -76,6 +82,8 @@ class Version
 
   # A pseudo-token representing the absence of a token.
   class NullToken < Token
+    extend T::Sig
+
     def initialize
       super(nil)
     end
@@ -95,10 +103,12 @@ class Version
       end
     end
 
+    sig { returns(T::Boolean) }
     def null?
       true
     end
 
+    sig { returns(String) }
     def inspect
       "#<#{self.class.name}>"
     end
@@ -133,6 +143,7 @@ class Version
   # A token consisting of only numbers.
   class NumericToken < Token
     PATTERN = /[0-9]+/i.freeze
+    extend T::Sig
 
     def initialize(value)
       super
@@ -153,6 +164,7 @@ class Version
       end
     end
 
+    sig { returns(T::Boolean) }
     def numeric?
       true
     end
@@ -588,6 +600,8 @@ end
 #
 # @api private
 class HeadVersion < Version
+  extend T::Sig
+
   attr_reader :commit
 
   def initialize(*)
@@ -604,6 +618,7 @@ class HeadVersion < Version
     end
   end
 
+  sig { returns(T::Boolean) }
   def head?
     true
   end
diff --git a/Library/Homebrew/version/null.rb b/Library/Homebrew/version/null.rb
index f08d0765af2efc06f9722eabd46e073ca1026be3..cf7217987564aa0e873c94a3868757908871cdc6 100644
--- a/Library/Homebrew/version/null.rb
+++ b/Library/Homebrew/version/null.rb
@@ -4,6 +4,8 @@
 class Version
   # Represents the absence of a version.
   NULL = Class.new do
+    extend T::Sig
+
     include Comparable
 
     def <=>(_other)
@@ -18,19 +20,23 @@ class Version
       false
     end
 
+    sig { returns(T::Boolean) }
     def detected_from_url?
       false
     end
 
+    sig { returns(T::Boolean) }
     def head?
       false
     end
 
+    sig { returns(T::Boolean) }
     def null?
       true
     end
 
     # For {OS::Mac::Version} compatibility.
+    sig { returns(T::Boolean) }
     def requires_nehalem_cpu?
       false
     end
@@ -51,27 +57,33 @@ class Version
       NULL_TOKEN
     end
 
+    sig { returns(Version) }
     def major_minor
       self
     end
 
+    sig { returns(Version) }
     def major_minor_patch
       self
     end
 
+    sig { returns(Float) }
     def to_f
       Float::NAN
     end
 
+    sig { returns(Integer) }
     def to_i
       0
     end
 
+    sig { returns(String) }
     def to_s
       ""
     end
     alias_method :to_str, :to_s
 
+    sig { returns(String) }
     def inspect
       "#<Version::NULL>"
     end
diff --git a/docs/Manpage.md b/docs/Manpage.md
index 4fb7f93ab72197ff600aca35b5dc349f9c6eb6c1..5574ec9d87170636a56a55b0f6c77c634bdfdd89 100644
--- a/docs/Manpage.md
+++ b/docs/Manpage.md
@@ -70,58 +70,58 @@ Homebrew Cask provides a friendly CLI workflow for the administration of macOS a
 Commands:
 
 - `--cache`  
-  Display the file used to cache a *`cask`*
+  Display the file used to cache a *`cask`*.
 
 - `audit`  
-  Check *`cask`* for Homebrew coding style violations
+  Check *`cask`* for Homebrew coding style violations.
 
 - `cat`  
-  Dump raw source of a *`cask`* to the standard output
+  Dump raw source of a *`cask`* to the standard output.
 
 - `create`  
-  Creates the given *`cask`* and opens it in an editor
+  Creates the given *`cask`* and opens it in an editor.
 
 - `doctor`  
-  Checks for configuration issues
+  Checks for configuration issues.
 
 - `edit`  
-  Open the given *`cask`* for editing
+  Open the given *`cask`* for editing.
 
 - `fetch`  
-  Downloads remote application files to local cache
+  Downloads remote application files to local cache.
 
 - `help`  
-  Print help for `cask` commands
+  Print help for `cask` commands.
 
 - `home`  
-  Opens the homepage of the given *`cask`*
+  Opens the homepage of the given *`cask`*.
 
 - `info`  
-  Displays information about the given *`cask`*
+  Displays information about the given *`cask`*.
 
 - `install`  
-  Installs the given *`cask`*
+  Installs the given *`cask`*.
 
 - `list`  
-  Lists installed casks or the casks provided in the arguments
+  Lists installed casks or the casks provided in the arguments.
 
 - `outdated`  
-  List the outdated installed casks
+  List the outdated installed casks.
 
 - `reinstall`  
-  Reinstalls the given *`cask`*
+  Reinstalls the given *`cask`*.
 
 - `style`  
-  Checks style of the given *`cask`* using RuboCop
+  Checks style of the given *`cask`* using RuboCop.
 
 - `uninstall`  
-  Uninstalls the given *`cask`*
+  Uninstalls the given *`cask`*.
 
 - `upgrade`  
-  Upgrades all outdated casks or the specified casks
+  Upgrades all outdated casks or the specified casks.
 
 - `zap`  
-  Zaps all files associated with the given *`cask`*
+  Zaps all files associated with the given *`cask`*.
 
 See also: `man brew`
 
@@ -1279,6 +1279,8 @@ Run Homebrew's unit and integration tests.
 
 Check for typechecking errors using Sorbet.
 
+* `--fix`:
+  Automatically fix type errors.
 * `-q`, `--quiet`:
   Silence all non-critical errors.
 * `--update`:
diff --git a/manpages/brew.1 b/manpages/brew.1
index d62b6a866412998d8c5221fadeba958757c8064f..30dbbc65e4d3f58457b95b082e99a1210878036e 100644
--- a/manpages/brew.1
+++ b/manpages/brew.1
@@ -70,109 +70,109 @@ Commands:
 \fB\-\-cache\fR
 .
 .br
-Display the file used to cache a \fIcask\fR
+Display the file used to cache a \fIcask\fR\.
 .
 .IP "\(bu" 4
 \fBaudit\fR
 .
 .br
-Check \fIcask\fR for Homebrew coding style violations
+Check \fIcask\fR for Homebrew coding style violations\.
 .
 .IP "\(bu" 4
 \fBcat\fR
 .
 .br
-Dump raw source of a \fIcask\fR to the standard output
+Dump raw source of a \fIcask\fR to the standard output\.
 .
 .IP "\(bu" 4
 \fBcreate\fR
 .
 .br
-Creates the given \fIcask\fR and opens it in an editor
+Creates the given \fIcask\fR and opens it in an editor\.
 .
 .IP "\(bu" 4
 \fBdoctor\fR
 .
 .br
-Checks for configuration issues
+Checks for configuration issues\.
 .
 .IP "\(bu" 4
 \fBedit\fR
 .
 .br
-Open the given \fIcask\fR for editing
+Open the given \fIcask\fR for editing\.
 .
 .IP "\(bu" 4
 \fBfetch\fR
 .
 .br
-Downloads remote application files to local cache
+Downloads remote application files to local cache\.
 .
 .IP "\(bu" 4
 \fBhelp\fR
 .
 .br
-Print help for \fBcask\fR commands
+Print help for \fBcask\fR commands\.
 .
 .IP "\(bu" 4
 \fBhome\fR
 .
 .br
-Opens the homepage of the given \fIcask\fR
+Opens the homepage of the given \fIcask\fR\.
 .
 .IP "\(bu" 4
 \fBinfo\fR
 .
 .br
-Displays information about the given \fIcask\fR
+Displays information about the given \fIcask\fR\.
 .
 .IP "\(bu" 4
 \fBinstall\fR
 .
 .br
-Installs the given \fIcask\fR
+Installs the given \fIcask\fR\.
 .
 .IP "\(bu" 4
 \fBlist\fR
 .
 .br
-Lists installed casks or the casks provided in the arguments
+Lists installed casks or the casks provided in the arguments\.
 .
 .IP "\(bu" 4
 \fBoutdated\fR
 .
 .br
-List the outdated installed casks
+List the outdated installed casks\.
 .
 .IP "\(bu" 4
 \fBreinstall\fR
 .
 .br
-Reinstalls the given \fIcask\fR
+Reinstalls the given \fIcask\fR\.
 .
 .IP "\(bu" 4
 \fBstyle\fR
 .
 .br
-Checks style of the given \fIcask\fR using RuboCop
+Checks style of the given \fIcask\fR using RuboCop\.
 .
 .IP "\(bu" 4
 \fBuninstall\fR
 .
 .br
-Uninstalls the given \fIcask\fR
+Uninstalls the given \fIcask\fR\.
 .
 .IP "\(bu" 4
 \fBupgrade\fR
 .
 .br
-Upgrades all outdated casks or the specified casks
+Upgrades all outdated casks or the specified casks\.
 .
 .IP "\(bu" 4
 \fBzap\fR
 .
 .br
-Zaps all files associated with the given \fIcask\fR
+Zaps all files associated with the given \fIcask\fR\.
 .
 .IP "" 0
 .
@@ -1777,6 +1777,10 @@ Randomise tests with the specified \fIvalue\fR instead of a random seed\.
 Check for typechecking errors using Sorbet\.
 .
 .TP
+\fB\-\-fix\fR
+Automatically fix type errors\.
+.
+.TP
 \fB\-q\fR, \fB\-\-quiet\fR
 Silence all non\-critical errors\.
 .