Skip to content

Commit 3f3ddb8

Browse files
authored
Merge pull request #20360 from lukarajic/cask-size
Add a flag to `brew info` to view the size of each formula and cask
2 parents f037420 + 0c78875 commit 3f3ddb8

File tree

2 files changed

+78
-1
lines changed

2 files changed

+78
-1
lines changed

Library/Homebrew/cmd/info.rb

Lines changed: 75 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,12 @@
1616
module Homebrew
1717
module Cmd
1818
class Info < AbstractCommand
19+
class NameSize < T::Struct
20+
const :name, String
21+
const :size, Integer
22+
end
23+
private_constant :NameSize
24+
1925
VALID_DAYS = %w[30 90 365].freeze
2026
VALID_FORMULA_CATEGORIES = %w[install install-on-request build-error].freeze
2127
VALID_CATEGORIES = T.let((VALID_FORMULA_CATEGORIES + %w[cask-install os-version]).freeze, T::Array[String])
@@ -67,6 +73,8 @@ class Info < AbstractCommand
6773
description: "Treat all named arguments as formulae."
6874
switch "--cask", "--casks",
6975
description: "Treat all named arguments as casks."
76+
switch "--sizes",
77+
description: "Show the size of installed formulae and casks."
7078

7179
conflicts "--installed", "--eval-all"
7280
conflicts "--installed", "--all"
@@ -79,7 +87,15 @@ class Info < AbstractCommand
7987

8088
sig { override.void }
8189
def run
82-
if args.analytics?
90+
if args.sizes?
91+
if args.no_named?
92+
print_sizes
93+
else
94+
formulae, casks = args.named.to_formulae_to_casks
95+
formulae = T.cast(formulae, T::Array[Formula])
96+
print_sizes(formulae:, casks:)
97+
end
98+
elsif args.analytics?
8399
if args.days.present? && VALID_DAYS.exclude?(args.days)
84100
raise UsageError, "`--days` must be one of #{VALID_DAYS.join(", ")}."
85101
end
@@ -401,6 +417,64 @@ def info_cask(cask)
401417

402418
Cask::Info.info(cask, args:)
403419
end
420+
421+
sig { params(title: String, items: T::Array[NameSize]).void }
422+
def print_sizes_table(title, items)
423+
return if items.blank?
424+
425+
ohai title
426+
427+
total_size = items.sum(&:size)
428+
total_size_str = disk_usage_readable(total_size)
429+
430+
name_width = (items.map { |item| item.name.length } + [5]).max
431+
size_width = (items.map { |item| disk_usage_readable(item.size).length } + [total_size_str.length]).max
432+
433+
items.each do |item|
434+
puts format("%-#{name_width}s %#{size_width}s", item.name,
435+
disk_usage_readable(item.size))
436+
end
437+
438+
puts format("%-#{name_width}s %#{size_width}s", "Total", total_size_str)
439+
end
440+
441+
sig { params(formulae: T::Array[Formula], casks: T::Array[Cask::Cask]).void }
442+
def print_sizes(formulae: [], casks: [])
443+
if formulae.blank? &&
444+
(args.formulae? || (!args.casks? && args.no_named?))
445+
formulae = Formula.installed
446+
end
447+
448+
if casks.blank? &&
449+
(args.casks? || (!args.formulae? && args.no_named?))
450+
casks = Cask::Caskroom.casks
451+
end
452+
453+
unless args.casks?
454+
formula_sizes = formulae.map do |formula|
455+
kegs = formula.installed_kegs
456+
size = kegs.sum(&:disk_usage)
457+
NameSize.new(name: formula.full_name, size:)
458+
end
459+
formula_sizes.sort_by! { |f| -f.size }
460+
print_sizes_table("Formulae sizes:", formula_sizes)
461+
end
462+
463+
return if casks.blank? || args.formulae?
464+
465+
cask_sizes = casks.filter_map do |cask|
466+
installed_version = cask.installed_version
467+
next unless installed_version.present?
468+
469+
versioned_staged_path = cask.caskroom_path.join(installed_version)
470+
next unless versioned_staged_path.exist?
471+
472+
size = versioned_staged_path.children.sum(&:disk_usage)
473+
NameSize.new(name: cask.full_name, size:)
474+
end
475+
cask_sizes.sort_by! { |c| -c.size }
476+
print_sizes_table("Casks sizes:", cask_sizes)
477+
end
404478
end
405479
end
406480
end

Library/Homebrew/sorbet/rbi/dsl/homebrew/cmd/info.rbi

Lines changed: 3 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)