cmd/update-report: use better wording where appropriate.

From reading https://github.com/orgs/Homebrew/discussions/3328: I
initially thought we should just change "Updated" to "Modified" when
appropriate. After conversation with Bo98, though, I thought more and
saw that we're already checking for outdated formulae here so, rather
than ever traverse through the formula history, look at the outdated
formula and list them unless we've set
`HOMEBREW_UPDATE_REPORT_ALL_FORMULAE` in which case we show the
modifications.

While we're here, also do a bit of reformatting and renaming to better
clarify intent.
This commit is contained in:
Mike McQuaid 2022-06-03 19:16:15 +01:00
parent 5bf52d1ffe
commit 04c8e02418
No known key found for this signature in database
GPG Key ID: 3338A31AFDB1D829
8 changed files with 240 additions and 202 deletions

View File

@ -1,7 +1,6 @@
# typed: false # typed: false
# frozen_string_literal: true # frozen_string_literal: true
require "formula_versions"
require "migrator" require "migrator"
require "formulary" require "formulary"
require "descriptions" require "descriptions"
@ -204,6 +203,7 @@ module Homebrew
hub.dump(updated_formula_report: !args.auto_update?) unless args.quiet? hub.dump(updated_formula_report: !args.auto_update?) unless args.quiet?
hub.reporters.each(&:migrate_tap_migration) hub.reporters.each(&:migrate_tap_migration)
hub.reporters.each { |r| r.migrate_formula_rename(force: args.force?, verbose: args.verbose?) } hub.reporters.each { |r| r.migrate_formula_rename(force: args.force?, verbose: args.verbose?) }
CacheStoreDatabase.use(:descriptions) do |db| CacheStoreDatabase.use(:descriptions) do |db|
DescriptionCacheStore.new(db) DescriptionCacheStore.new(db)
.update_from_report!(hub) .update_from_report!(hub)
@ -212,32 +212,6 @@ module Homebrew
CaskDescriptionCacheStore.new(db) CaskDescriptionCacheStore.new(db)
.update_from_report!(hub) .update_from_report!(hub)
end end
if !args.auto_update? && !args.quiet?
outdated_formulae = Formula.installed.count(&:outdated?)
outdated_casks = Cask::Caskroom.casks.count(&:outdated?)
update_pronoun = if (outdated_formulae + outdated_casks) == 1
"it"
else
"them"
end
msg = ""
if outdated_formulae.positive?
msg += "#{Tty.bold}#{outdated_formulae}#{Tty.reset} outdated #{"formula".pluralize(outdated_formulae)}"
end
if outdated_casks.positive?
msg += " and " if msg.present?
msg += "#{Tty.bold}#{outdated_casks}#{Tty.reset} outdated #{"cask".pluralize(outdated_casks)}"
end
if msg.present?
puts
puts <<~EOS
You have #{msg} installed.
You can upgrade #{update_pronoun} with #{Tty.bold}brew upgrade#{Tty.reset}
or list #{update_pronoun} with #{Tty.bold}brew outdated#{Tty.reset}.
EOS
end
end
end end
puts if args.auto_update? puts if args.auto_update?
elsif !args.auto_update? && !ENV["HOMEBREW_UPDATE_FAILED"] && !ENV["HOMEBREW_MIGRATE_LINUXBREW_FORMULAE"] elsif !args.auto_update? && !ENV["HOMEBREW_UPDATE_FAILED"] && !ENV["HOMEBREW_MIGRATE_LINUXBREW_FORMULAE"]
@ -369,24 +343,6 @@ class Reporter
when "M" when "M"
name = tap.formula_file_to_name(src) name = tap.formula_file_to_name(src)
# Skip filtering unchanged formulae versions by default (as it's slow).
unless Homebrew::EnvConfig.update_report_version_changed_formulae?
@report[:M] << name
next
end
begin
formula = Formulary.factory(tap.path/src)
new_version = formula.pkg_version
old_version = FormulaVersions.new(formula).formula_at_revision(@initial_revision, &:pkg_version)
next if new_version == old_version
rescue FormulaUnavailableError
# Don't care if the formula isn't available right now.
nil
rescue Exception => e # rubocop:disable Lint/RescueException
onoe "#{e.message}\n#{e.backtrace.join "\n"}" if Homebrew::EnvConfig.developer?
end
@report[:M] << name @report[:M] << name
when /^R\d{0,3}/ when /^R\d{0,3}/
src_full_name = tap.formula_file_to_name(src) src_full_name = tap.formula_file_to_name(src)
@ -571,7 +527,7 @@ class ReporterHub
@reporters = [] @reporters = []
end end
def select_formula(key) def select_formula_or_cask(key)
@hash.fetch(key, []) @hash.fetch(key, [])
end end
@ -586,70 +542,155 @@ class ReporterHub
def dump(updated_formula_report: true) def dump(updated_formula_report: true)
# Key Legend: Added (A), Copied (C), Deleted (D), Modified (M), Renamed (R) # Key Legend: Added (A), Copied (C), Deleted (D), Modified (M), Renamed (R)
dump_formula_report :A, "New Formulae" unless Homebrew::EnvConfig.update_report_all_formulae?
if updated_formula_report dump_formula_or_cask_report :A, "New Formulae"
dump_formula_report :M, "Updated Formulae" dump_formula_or_cask_report :AC, "New Casks"
else dump_formula_or_cask_report :R, "Renamed Formulae"
updated = select_formula(:M).count
ohai "Updated Formulae", "Updated #{updated} #{"formula".pluralize(updated)}." if updated.positive?
end end
dump_formula_report :R, "Renamed Formulae"
dump_formula_report :D, "Deleted Formulae" dump_formula_or_cask_report :D, "Deleted Formulae"
dump_formula_report :AC, "New Casks" dump_formula_or_cask_report :DC, "Deleted Casks"
if updated_formula_report
dump_formula_report :MC, "Updated Casks" outdated_formulae = nil
else outdated_casks = nil
updated = select_formula(:MC).count
ohai "Updated Casks", "Updated #{updated} #{"cask".pluralize(updated)}." if updated.positive? if updated_formula_report && Homebrew::EnvConfig.update_report_all_formulae?
dump_formula_or_cask_report :M, "Modified Formulae"
dump_formula_or_cask_report :MC, "Modified Casks"
elsif updated_formula_report
outdated_formulae = Formula.installed.select(&:outdated?).map(&:name)
output_dump_formula_or_cask_report "Outdated Formulae", outdated_formulae
outdated_casks = Cask::Caskroom.casks.select(&:outdated?).map(&:token)
output_dump_formula_or_cask_report "Outdated Casks", outdated_casks
elsif Homebrew::EnvConfig.update_report_all_formulae?
if (changed_formulae = select_formula_or_cask(:M).count) && changed_formulae.positive?
ohai "Modified Formulae", "Modified #{changed_formulae} #{"formula".pluralize(changed_formulae)}."
end end
dump_formula_report :DC, "Deleted Casks"
if (changed_casks = select_formula_or_cask(:MC).count) && changed_casks.positive?
ohai "Modified Casks", "Modified #{changed_casks} #{"cask".pluralize(changed_casks)}."
end
else
outdated_formulae = Formula.installed.select(&:outdated?).map(&:name)
outdated_casks = Cask::Caskroom.casks.select(&:outdated?).map(&:token)
end
return if outdated_formulae.blank? && outdated_casks.blank?
outdated_formulae = outdated_formulae.count
outdated_casks = outdated_casks.count
update_pronoun = if (outdated_formulae + outdated_casks) == 1
"it"
else
"them"
end
msg = ""
if outdated_formulae.positive?
msg += "#{Tty.bold}#{outdated_formulae}#{Tty.reset} outdated #{"formula".pluralize(outdated_formulae)}"
end
if outdated_casks.positive?
msg += " and " if msg.present?
msg += "#{Tty.bold}#{outdated_casks}#{Tty.reset} outdated #{"cask".pluralize(outdated_casks)}"
end
return if msg.blank?
puts
puts <<~EOS
You have #{msg} installed.
You can upgrade #{update_pronoun} with #{Tty.bold}brew upgrade#{Tty.reset}
or list #{update_pronoun} with #{Tty.bold}brew outdated#{Tty.reset}.
EOS
end end
private private
def dump_formula_report(key, title) def dump_formula_or_cask_report(key, title)
only_installed = !Homebrew::EnvConfig.update_report_all_formulae? report_all = Homebrew::EnvConfig.update_report_all_formulae?
formulae = select_formula(key).sort.map do |name, new_name| formulae_or_casks = select_formula_or_cask(key).sort.map do |name, new_name|
# Format list items of renamed formulae # Format list items of formulae
case key case key
when :R when :R
unless only_installed if report_all
name = pretty_installed(name) if installed?(name) name = pretty_installed(name) if installed?(name)
new_name = pretty_installed(new_name) if installed?(new_name) new_name = pretty_installed(new_name) if installed?(new_name)
"#{name} -> #{new_name}" "#{name} -> #{new_name}"
end end
when :A when :A
name if !only_installed && !installed?(name) name if report_all && !installed?(name)
when :AC when :AC
name.split("/").last if !only_installed && !cask_installed?(name) name.split("/").last if report_all && !cask_installed?(name)
when :MC, :DC when :MC
name = name.split("/").last name = name.split("/").last
if cask_installed?(name) if cask_installed?(name)
if cask_outdated?(name)
pretty_outdated(name)
else
pretty_installed(name) pretty_installed(name)
elsif !only_installed end
elsif report_all
name
end
when :DC
name = name.split("/").last
if cask_installed?(name)
pretty_uninstalled(name)
elsif report_all
name
end
when :M
if installed?(name)
if outdated?(name)
pretty_outdated(name)
else
pretty_installed(name)
end
elsif report_all
name
end
when :D
if installed?(name)
pretty_uninstalled(name)
elsif report_all
name name
end end
else else
if installed?(name) raise ArgumentError, ":#{key} passed to dump_formula_or_cask_report!"
pretty_installed(name)
elsif !only_installed
name
end
end end
end.compact end.compact
return if formulae.empty? output_dump_formula_or_cask_report title, formulae_or_casks
end
# Dump formula list. def output_dump_formula_or_cask_report(title, formulae_or_casks)
ohai title, Formatter.columns(formulae.sort) return if formulae_or_casks.blank?
ohai title, Formatter.columns(formulae_or_casks.sort)
end end
def installed?(formula) def installed?(formula)
(HOMEBREW_CELLAR/formula.split("/").last).directory? (HOMEBREW_CELLAR/formula.split("/").last).directory?
end end
def outdated?(formula)
Formula[formula].outdated?
rescue FormulaUnavailableError
false
end
def cask_installed?(cask) def cask_installed?(cask)
(Cask::Caskroom.path/cask).directory? (Cask::Caskroom.path/cask).directory?
end end
def cask_outdated?(cask)
Cask::CaskLoader.load(cask).outdated?
rescue Cask::CaskError
false
end
end end

View File

@ -48,13 +48,13 @@ class DescriptionCacheStore < CacheStore
return populate_if_empty! if database.empty? return populate_if_empty! if database.empty?
return if report.empty? return if report.empty?
renamings = report.select_formula(:R) renamings = report.select_formula_or_cask(:R)
alterations = report.select_formula(:A) + alterations = report.select_formula_or_cask(:A) +
report.select_formula(:M) + report.select_formula_or_cask(:M) +
renamings.map(&:last) renamings.map(&:last)
update_from_formula_names!(alterations) update_from_formula_names!(alterations)
delete_from_formula_names!(report.select_formula(:D) + delete_from_formula_names!(report.select_formula_or_cask(:D) +
renamings.map(&:first)) renamings.map(&:first))
end end
@ -114,11 +114,11 @@ class CaskDescriptionCacheStore < DescriptionCacheStore
return populate_if_empty! if database.empty? return populate_if_empty! if database.empty?
return if report.empty? return if report.empty?
alterations = report.select_formula(:AC) + alterations = report.select_formula_or_cask(:AC) +
report.select_formula(:MC) report.select_formula_or_cask(:MC)
update_from_cask_tokens!(alterations) update_from_cask_tokens!(alterations)
delete_from_cask_tokens!(report.select_formula(:DC)) delete_from_cask_tokens!(report.select_formula_or_cask(:DC))
end end
# Use an array of cask tokens to update the {CaskDescriptionCacheStore}. # Use an array of cask tokens to update the {CaskDescriptionCacheStore}.

View File

@ -331,12 +331,8 @@ module Homebrew
default: HOMEBREW_DEFAULT_TEMP, default: HOMEBREW_DEFAULT_TEMP,
}, },
HOMEBREW_UPDATE_REPORT_ALL_FORMULAE: { HOMEBREW_UPDATE_REPORT_ALL_FORMULAE: {
description: "If set, `brew update` lists updates to all software.", description: "If set, `brew update` lists changes to all formulae and cask files rather than only showing " \
boolean: true, "when they are installed or outdated.",
},
HOMEBREW_UPDATE_REPORT_VERSION_CHANGED_FORMULAE: {
description: "If set, `brew update` only lists updates to formulae with differing versions. " \
"Note this is slower than the default behaviour.",
boolean: true, boolean: true,
}, },
HOMEBREW_UPDATE_TO_TAG: { HOMEBREW_UPDATE_TO_TAG: {

View File

@ -52,39 +52,39 @@ describe "brew update-report" do
specify "without Formula changes" do specify "without Formula changes" do
perform_update("update_git_diff_output_without_formulae_changes") perform_update("update_git_diff_output_without_formulae_changes")
expect(hub.select_formula(:M)).to be_empty expect(hub.select_formula_or_cask(:M)).to be_empty
expect(hub.select_formula(:A)).to be_empty expect(hub.select_formula_or_cask(:A)).to be_empty
expect(hub.select_formula(:D)).to be_empty expect(hub.select_formula_or_cask(:D)).to be_empty
end end
specify "with Formula changes" do specify "with Formula changes" do
perform_update("update_git_diff_output_with_formulae_changes") perform_update("update_git_diff_output_with_formulae_changes")
expect(hub.select_formula(:M)).to eq(%w[xar yajl]) expect(hub.select_formula_or_cask(:M)).to eq(%w[xar yajl])
expect(hub.select_formula(:A)).to eq(%w[antiword bash-completion ddrescue dict lua]) expect(hub.select_formula_or_cask(:A)).to eq(%w[antiword bash-completion ddrescue dict lua])
end end
specify "with removed Formulae" do specify "with removed Formulae" do
perform_update("update_git_diff_output_with_removed_formulae") perform_update("update_git_diff_output_with_removed_formulae")
expect(hub.select_formula(:D)).to eq(%w[libgsasl]) expect(hub.select_formula_or_cask(:D)).to eq(%w[libgsasl])
end end
specify "with changed file type" do specify "with changed file type" do
perform_update("update_git_diff_output_with_changed_filetype") perform_update("update_git_diff_output_with_changed_filetype")
expect(hub.select_formula(:M)).to eq(%w[elixir]) expect(hub.select_formula_or_cask(:M)).to eq(%w[elixir])
expect(hub.select_formula(:A)).to eq(%w[libbson]) expect(hub.select_formula_or_cask(:A)).to eq(%w[libbson])
expect(hub.select_formula(:D)).to eq(%w[libgsasl]) expect(hub.select_formula_or_cask(:D)).to eq(%w[libgsasl])
end end
specify "with renamed Formula" do specify "with renamed Formula" do
allow(tap).to receive(:formula_renames).and_return("cv" => "progress") allow(tap).to receive(:formula_renames).and_return("cv" => "progress")
perform_update("update_git_diff_output_with_formula_rename") perform_update("update_git_diff_output_with_formula_rename")
expect(hub.select_formula(:A)).to be_empty expect(hub.select_formula_or_cask(:A)).to be_empty
expect(hub.select_formula(:D)).to be_empty expect(hub.select_formula_or_cask(:D)).to be_empty
expect(hub.select_formula(:R)).to eq([["cv", "progress"]]) expect(hub.select_formula_or_cask(:R)).to eq([["cv", "progress"]])
end end
context "when updating a Tap other than the core Tap" do context "when updating a Tap other than the core Tap" do
@ -101,34 +101,34 @@ describe "brew update-report" do
specify "with restructured Tap" do specify "with restructured Tap" do
perform_update("update_git_diff_output_with_restructured_tap") perform_update("update_git_diff_output_with_restructured_tap")
expect(hub.select_formula(:A)).to be_empty expect(hub.select_formula_or_cask(:A)).to be_empty
expect(hub.select_formula(:D)).to be_empty expect(hub.select_formula_or_cask(:D)).to be_empty
expect(hub.select_formula(:R)).to be_empty expect(hub.select_formula_or_cask(:R)).to be_empty
end end
specify "with renamed Formula and restructured Tap" do specify "with renamed Formula and restructured Tap" do
allow(tap).to receive(:formula_renames).and_return("xchat" => "xchat2") allow(tap).to receive(:formula_renames).and_return("xchat" => "xchat2")
perform_update("update_git_diff_output_with_formula_rename_and_restructuring") perform_update("update_git_diff_output_with_formula_rename_and_restructuring")
expect(hub.select_formula(:A)).to be_empty expect(hub.select_formula_or_cask(:A)).to be_empty
expect(hub.select_formula(:D)).to be_empty expect(hub.select_formula_or_cask(:D)).to be_empty
expect(hub.select_formula(:R)).to eq([%w[foo/bar/xchat foo/bar/xchat2]]) expect(hub.select_formula_or_cask(:R)).to eq([%w[foo/bar/xchat foo/bar/xchat2]])
end end
specify "with simulated 'homebrew/php' restructuring" do specify "with simulated 'homebrew/php' restructuring" do
perform_update("update_git_diff_simulate_homebrew_php_restructuring") perform_update("update_git_diff_simulate_homebrew_php_restructuring")
expect(hub.select_formula(:A)).to be_empty expect(hub.select_formula_or_cask(:A)).to be_empty
expect(hub.select_formula(:D)).to be_empty expect(hub.select_formula_or_cask(:D)).to be_empty
expect(hub.select_formula(:R)).to be_empty expect(hub.select_formula_or_cask(:R)).to be_empty
end end
specify "with Formula changes" do specify "with Formula changes" do
perform_update("update_git_diff_output_with_tap_formulae_changes") perform_update("update_git_diff_output_with_tap_formulae_changes")
expect(hub.select_formula(:A)).to eq(%w[foo/bar/lua]) expect(hub.select_formula_or_cask(:A)).to eq(%w[foo/bar/lua])
expect(hub.select_formula(:M)).to eq(%w[foo/bar/git]) expect(hub.select_formula_or_cask(:M)).to eq(%w[foo/bar/git])
expect(hub.select_formula(:D)).to be_empty expect(hub.select_formula_or_cask(:D)).to be_empty
end end
end end
end end

View File

@ -25,7 +25,7 @@ describe DescriptionCacheStore do
end end
describe "#update_from_report!" do describe "#update_from_report!" do
let(:report) { double(select_formula: [], empty?: false) } let(:report) { double(select_formula_or_cask: [], empty?: false) }
it "reads from the report" do it "reads from the report" do
expect(database).to receive(:empty?).at_least(:once).and_return(false) expect(database).to receive(:empty?).at_least(:once).and_return(false)
@ -60,7 +60,7 @@ describe DescriptionCacheStore do
let(:database) { double("database") } let(:database) { double("database") }
describe "#update_from_report!" do describe "#update_from_report!" do
let(:report) { double(select_formula: [], empty?: false) } let(:report) { double(select_formula_or_cask: [], empty?: false) }
it "reads from the report" do it "reads from the report" do
expect(database).to receive(:empty?).at_least(:once).and_return(false) expect(database).to receive(:empty?).at_least(:once).and_return(false)

View File

@ -248,6 +248,16 @@ module Kernel
end end
end end
def pretty_outdated(f)
if !$stdout.tty?
f.to_s
elsif Homebrew::EnvConfig.no_emoji?
Formatter.error("#{Tty.bold}#{f} (outdated)#{Tty.reset}")
else
"#{Tty.bold}#{f} #{Formatter.warning("")}#{Tty.reset}"
end
end
def pretty_uninstalled(f) def pretty_uninstalled(f)
if !$stdout.tty? if !$stdout.tty?
f.to_s f.to_s

View File

@ -2172,10 +2172,7 @@ example, run `export HOMEBREW_NO_INSECURE_REDIRECT=1` rather than just
*Default:* macOS: `/private/tmp`, Linux: `/tmp`. *Default:* macOS: `/private/tmp`, Linux: `/tmp`.
- `HOMEBREW_UPDATE_REPORT_ALL_FORMULAE` - `HOMEBREW_UPDATE_REPORT_ALL_FORMULAE`
<br>If set, `brew update` lists updates to all software. <br>If set, `brew update` lists changes to all formulae and cask files rather than only showing when they are installed or outdated.
- `HOMEBREW_UPDATE_REPORT_VERSION_CHANGED_FORMULAE`
<br>If set, `brew update` only lists updates to formulae with differing versions. Note this is slower than the default behaviour.
- `HOMEBREW_UPDATE_TO_TAG` - `HOMEBREW_UPDATE_TO_TAG`
<br>If set, always use the latest stable tag (even if developer commands have been run). <br>If set, always use the latest stable tag (even if developer commands have been run).

View File

@ -1,7 +1,7 @@
.\" generated with Ronn/v0.7.3 .\" generated with Ronn/v0.7.3
.\" http://github.com/rtomayko/ronn/tree/0.7.3 .\" http://github.com/rtomayko/ronn/tree/0.7.3
. .
.TH "BREW" "1" "May 2022" "Homebrew" "brew" .TH "BREW" "1" "June 2022" "Homebrew" "brew"
. .
.SH "NAME" .SH "NAME"
\fBbrew\fR \- The Missing Package Manager for macOS (or Linux) \fBbrew\fR \- The Missing Package Manager for macOS (or Linux)
@ -3186,13 +3186,7 @@ Use this path as the temporary directory for building packages\. Changing this m
\fBHOMEBREW_UPDATE_REPORT_ALL_FORMULAE\fR \fBHOMEBREW_UPDATE_REPORT_ALL_FORMULAE\fR
. .
.br .br
If set, \fBbrew update\fR lists updates to all software\. If set, \fBbrew update\fR lists changes to all formulae and cask files rather than only showing when they are installed or outdated\.
.
.TP
\fBHOMEBREW_UPDATE_REPORT_VERSION_CHANGED_FORMULAE\fR
.
.br
If set, \fBbrew update\fR only lists updates to formulae with differing versions\. Note this is slower than the default behaviour\.
. .
.TP .TP
\fBHOMEBREW_UPDATE_TO_TAG\fR \fBHOMEBREW_UPDATE_TO_TAG\fR