diff --git a/Library/Homebrew/cli/args.rb b/Library/Homebrew/cli/args.rb index cc7a571764..b152473f79 100644 --- a/Library/Homebrew/cli/args.rb +++ b/Library/Homebrew/cli/args.rb @@ -35,6 +35,7 @@ module Homebrew def freeze_named_args!(named_args) # Reset cache values reliant on named_args @formulae = nil + @formulae_and_casks = nil @resolved_formulae = nil @resolved_formulae_casks = nil @formulae_paths = nil @@ -90,6 +91,24 @@ module Homebrew end.uniq(&:name).freeze end + def formulae_and_casks + @formulae_and_casks ||= begin + formulae_and_casks = [] + + downcased_unique_named.each do |name| + formulae_and_casks << Formulary.factory(name, spec) + rescue FormulaUnavailableError + begin + formulae_and_casks << Cask::CaskLoader.load(name) + rescue Cask::CaskUnavailableError + raise "No available formula or cask with the name \"#{name}\"" + end + end + + formulae_and_casks.freeze + end + end + def resolved_formulae require "formula" diff --git a/Library/Homebrew/cmd/deps.rb b/Library/Homebrew/cmd/deps.rb index 03412059f9..65cac3f797 100644 --- a/Library/Homebrew/cmd/deps.rb +++ b/Library/Homebrew/cmd/deps.rb @@ -3,6 +3,7 @@ require "formula" require "ostruct" require "cli/parser" +require "cask/caskroom" module Homebrew extend DependenciesHelpers @@ -64,51 +65,68 @@ module Homebrew Formulary.enable_factory_cache! recursive = !args.send("1?") - installed = args.installed? || args.formulae.all?(&:opt_or_installed_prefix_keg) + installed = args.installed? || dependents(args.formulae_and_casks).all?(&:any_version_installed?) @use_runtime_dependencies = installed && recursive && + !args.tree? && !args.include_build? && !args.include_test? && !args.include_optional? && !args.skip_recommended? if args.tree? - if args.installed? - puts_deps_tree Formula.installed.sort, recursive + dependents = if args.named.present? + sorted_dependents(args.formulae_and_casks) + elsif args.installed? + sorted_dependents(Formula.installed + Cask::Caskroom.casks) else - raise FormulaUnspecifiedError if args.no_named? - - puts_deps_tree args.formulae, recursive + raise FormulaUnspecifiedError end + + puts_deps_tree dependents, recursive return elsif args.all? - puts_deps Formula.sort, recursive + puts_deps sorted_dependents(Formula.to_a + Cask::Cask.to_a), recursive return elsif !args.no_named? && args.for_each? - puts_deps args.formulae, recursive + puts_deps sorted_dependents(args.formulae_and_casks), recursive return end if args.no_named? raise FormulaUnspecifiedError unless args.installed? - puts_deps Formula.installed.sort, recursive + puts_deps sorted_dependents(Formula.installed + Cask::Caskroom.casks), recursive return end - all_deps = deps_for_formulae(args.formulae, recursive, &(args.union? ? :| : :&)) - all_deps = condense_requirements(all_deps) - all_deps.select!(&:installed?) if args.installed? + dependents = dependents(args.formulae_and_casks) + + all_deps = deps_for_dependents(dependents, recursive, &(args.union? ? :| : :&)) + condense_requirements(all_deps) all_deps.map!(&method(:dep_display_name)) all_deps.uniq! all_deps.sort! unless args.n? puts all_deps end - def condense_requirements(deps) - return deps if args.include_requirements? + def dependents(formulae_or_casks) + formulae_or_casks.map do |formula_or_cask| + if formula_or_cask.is_a?(Formula) + formula_or_cask + else + Dependent.new(formula_or_cask) + end + end + end - deps.select { |dep| dep.is_a? Dependency } + def sorted_dependents(formulae_or_casks) + dependents(formulae_or_casks).sort_by(&:name) + end + + def condense_requirements(deps) + deps.select! { |dep| dep.is_a?(Dependency) } unless args.include_requirements? + deps.select! { |dep| dep.is_a?(Requirement) || dep.installed? } if args.installed? end def dep_display_name(dep) @@ -136,41 +154,41 @@ module Homebrew str end - def deps_for_formula(f, recursive = false) + def deps_for_dependent(d, recursive = false) includes, ignores = argv_includes_ignores(ARGV) - deps = f.runtime_dependencies if @use_runtime_dependencies + deps = d.runtime_dependencies if @use_runtime_dependencies if recursive - deps ||= recursive_includes(Dependency, f, includes, ignores) - reqs = recursive_includes(Requirement, f, includes, ignores) + deps ||= recursive_includes(Dependency, d, includes, ignores) + reqs = recursive_includes(Requirement, d, includes, ignores) else - deps ||= reject_ignores(f.deps, ignores, includes) - reqs = reject_ignores(f.requirements, ignores, includes) + deps ||= reject_ignores(d.deps, ignores, includes) + reqs = reject_ignores(d.requirements, ignores, includes) end deps + reqs.to_a end - def deps_for_formulae(formulae, recursive = false, &block) - formulae.map { |f| deps_for_formula(f, recursive) }.reduce(&block) + def deps_for_dependents(dependents, recursive = false, &block) + dependents.map { |d| deps_for_dependent(d, recursive) }.reduce(&block) end - def puts_deps(formulae, recursive = false) - formulae.each do |f| - deps = deps_for_formula(f, recursive) - deps = condense_requirements(deps) + def puts_deps(dependents, recursive = false) + dependents.each do |d| + deps = deps_for_dependent(d, recursive) + condense_requirements(deps) deps.sort_by!(&:name) deps.map!(&method(:dep_display_name)) - puts "#{f.full_name}: #{deps.join(" ")}" + puts "#{d.full_name}: #{deps.join(" ")}" end end - def puts_deps_tree(formulae, recursive = false) - formulae.each do |f| - puts f.full_name + def puts_deps_tree(dependents, recursive = false) + dependents.each do |d| + puts d.full_name @dep_stack = [] - recursive_deps_tree(f, "", recursive) + recursive_deps_tree(d, "", recursive) puts end end @@ -211,4 +229,61 @@ module Homebrew @dep_stack.pop end + + class Dependent + def initialize(cask) + @cask = cask + end + + def name + @cask.token + end + + def full_name + @cask.full_name + end + + def runtime_dependencies + recursive_dependencies + end + + def deps + @deps ||= begin + @cask.depends_on.formula.map do |f| + Dependency.new f + end + end + end + + def requirements + @requirements ||= begin + requirements = [] + dsl_reqs = @cask.depends_on + + dsl_reqs.arch&.each do |arch| + requirements << ArchRequirement.new([:x86_64]) if arch[:bits] == 64 + requirements << ArchRequirement.new([arch[:type]]) + end + dsl_reqs.cask.each do |cask_ref| + requirements << Requirement.new([{ cask: cask_ref }]) + end + requirements << dsl_reqs.macos if dsl_reqs.macos + requirements << X11Requirement.new if dsl_reqs.x11 + + requirements + end + end + + def recursive_dependencies(&block) + Dependency.expand(self, &block) + end + + def recursive_requirements(&block) + Requirement.expand(self, &block) + end + + def any_version_installed? + @cask.installed? + end + end end diff --git a/Library/Homebrew/dependencies.rb b/Library/Homebrew/dependencies.rb index cd88377eed..ceac7f54e5 100644 --- a/Library/Homebrew/dependencies.rb +++ b/Library/Homebrew/dependencies.rb @@ -84,7 +84,7 @@ module DependenciesHelpers [includes, ignores] end - def recursive_includes(klass, formula, includes, ignores) + def recursive_includes(klass, root_dependent, includes, ignores) type = if klass == Dependency :dependencies elsif klass == Requirement @@ -93,7 +93,7 @@ module DependenciesHelpers raise ArgumentError, "Invalid class argument: #{klass}" end - formula.send("recursive_#{type}") do |dependent, dep| + root_dependent.send("recursive_#{type}") do |dependent, dep| if dep.recommended? klass.prune if ignores.include?("recommended?") || dependent.build.without?(dep) elsif dep.optional? diff --git a/Library/Homebrew/requirement.rb b/Library/Homebrew/requirement.rb index 0c42c3721a..138bff8a94 100644 --- a/Library/Homebrew/requirement.rb +++ b/Library/Homebrew/requirement.rb @@ -135,7 +135,11 @@ class Requirement klass = self.class.name || self.class.to_s klass.sub!(/(Dependency|Requirement)$/, "") klass.sub!(/^(\w+::)*/, "") - klass.downcase + return klass.downcase if klass.present? + + return @cask if @cask.present? + + "" end def which(cmd)