DEV: Improve rake `release_note:generate` date handling (#13726)
* DEV: Improve rake `release_note:generate` date handling A commit-ish value like HEAD@{2021-01-01} is based on the **local state** of HEAD on that date. It does not use dates attached to commits. Instead, the rake task now detects date-like strings and supplies them to `git log` via the `--after` and `--before` flags * Skip printing plugin when there are no changes found A list of skipped plugins is printed on a single line at the end of the output
This commit is contained in:
parent
76fe3a16a9
commit
4ce58fbf0b
|
@ -1,48 +1,26 @@
|
|||
# frozen_string_literal: true
|
||||
|
||||
DATE_REGEX = /\A\d{4}-\d{2}-\d{2}/
|
||||
|
||||
CHANGE_TYPES = [
|
||||
{ pattern: /^FEATURE:/, heading: "New Features" },
|
||||
{ pattern: /^FIX:/, heading: "Bug Fixes" },
|
||||
{ pattern: /^UX:/, heading: "UX Changes" },
|
||||
{ pattern: /^SECURITY:/, heading: "Security Changes" },
|
||||
{ pattern: /^PERF:/, heading: "Performance" },
|
||||
{ pattern: /^A11Y:/, heading: "Accessibility" },
|
||||
]
|
||||
|
||||
desc "generate a release note from the important commits"
|
||||
task "release_note:generate", :from, :to, :repo do |t, args|
|
||||
repo = args[:repo] || "."
|
||||
from = args[:from] || `git -C #{repo} describe --tags --abbrev=0`.strip
|
||||
to = args[:to] || "HEAD"
|
||||
changes = find_changes(repo, args[:from], args[:to])
|
||||
|
||||
bug_fixes = Set.new
|
||||
new_features = Set.new
|
||||
ux_changes = Set.new
|
||||
sec_changes = Set.new
|
||||
perf_changes = Set.new
|
||||
a11y_changes = Set.new
|
||||
|
||||
out = `git -C #{repo} log --pretty="tformat:%s" '#{from}..#{to}'`
|
||||
next "Status #{$?.exitstatus} running git log\n#{out}" if !$?.success?
|
||||
|
||||
out.each_line do |comment|
|
||||
next if comment =~ /^\s*Revert/
|
||||
split_comments(comment).each do |line|
|
||||
if line =~ /^FIX:/
|
||||
bug_fixes << better(line)
|
||||
elsif line =~ /^FEATURE:/
|
||||
new_features << better(line)
|
||||
elsif line =~ /^UX:/
|
||||
ux_changes << better(line)
|
||||
elsif line =~ /^SECURITY:/
|
||||
sec_changes << better(line)
|
||||
elsif line =~ /^PERF:/
|
||||
perf_changes << better(line)
|
||||
elsif line =~ /^A11Y:/
|
||||
a11y_changes << better(line)
|
||||
end
|
||||
end
|
||||
CHANGE_TYPES.each do |ct|
|
||||
print_changes(ct[:heading], changes[ct])
|
||||
end
|
||||
|
||||
print_changes("New Features", new_features)
|
||||
print_changes("Bug Fixes", bug_fixes)
|
||||
print_changes("UX Changes", ux_changes)
|
||||
print_changes("Security Changes", sec_changes)
|
||||
print_changes("Performance", perf_changes)
|
||||
print_changes("Accessibility", a11y_changes)
|
||||
|
||||
if [bug_fixes, new_features, ux_changes, sec_changes, perf_changes, a11y_changes].all?(&:empty?)
|
||||
if changes.values.all?(&:empty?)
|
||||
puts "(no changes)", ""
|
||||
end
|
||||
end
|
||||
|
@ -51,7 +29,7 @@ end
|
|||
# 1. Make sure you have a local, up-to-date clone of https://github.com/discourse/all-the-plugins
|
||||
# 2. In all-the-plugins, `git submodule update --init --recursive --remote`
|
||||
# 3. Change back to your discourse directory
|
||||
# 4. rake "release_note:plugins:generate[ HEAD@{2021-06-01} , HEAD@{now} , /path/to/all-the-plugins/plugins/* , discourse ]"
|
||||
# 4. rake "release_note:plugins:generate[ 2021-06-01 , 2021-07-01 , /path/to/all-the-plugins/plugins/* , discourse ]"
|
||||
desc "generate release notes for all official plugins in a directory"
|
||||
task "release_note:plugins:generate", :from, :to, :plugin_glob, :org do |t, args|
|
||||
from = args[:from]
|
||||
|
@ -65,12 +43,60 @@ task "release_note:plugins:generate", :from, :to, :plugin_glob, :org do |t, args
|
|||
all_repos = all_repos.filter { |dir| `git -C #{dir} remote get-url origin`.match?(/github.com[\/:]#{git_org}\//) }
|
||||
end
|
||||
|
||||
no_changes_repos = []
|
||||
|
||||
all_repos.each do |dir|
|
||||
puts "## #{File.basename(dir)}\n\n"
|
||||
Rake::Task["release_note:generate"].invoke(from, to, dir)
|
||||
Rake::Task["release_note:generate"].reenable
|
||||
name = File.basename(dir)
|
||||
changes = find_changes(dir, from, to)
|
||||
|
||||
if changes.values.all?(&:empty?)
|
||||
no_changes_repos << name
|
||||
next
|
||||
end
|
||||
|
||||
puts "## #{name}\n\n"
|
||||
CHANGE_TYPES.each do |ct|
|
||||
print_changes(ct[:heading], changes[ct])
|
||||
end
|
||||
puts "---", ""
|
||||
end
|
||||
|
||||
puts "(No changes found in #{no_changes_repos.join(", ")})"
|
||||
end
|
||||
|
||||
def find_changes(repo, from, to)
|
||||
dates = from&.match?(DATE_REGEX) || to&.match?(DATE_REGEX)
|
||||
|
||||
if !dates
|
||||
from ||= `git -C #{repo} describe --tags --abbrev=0`.strip
|
||||
to ||= "HEAD"
|
||||
end
|
||||
|
||||
cmd = "git -C #{repo} log --pretty='tformat:%s' "
|
||||
if dates
|
||||
cmd += "--after '#{from}' " if from
|
||||
cmd += "--before '#{to}' " if to
|
||||
else
|
||||
cmd += "#{from}..#{to}"
|
||||
end
|
||||
|
||||
out = `#{cmd}`
|
||||
raise "Status #{$?.exitstatus} running git log\n#{out}" if !$?.success?
|
||||
|
||||
changes = {}
|
||||
CHANGE_TYPES.each do |ct|
|
||||
changes[ct] = Set.new
|
||||
end
|
||||
|
||||
out.each_line do |comment|
|
||||
next if comment =~ /^\s*Revert/
|
||||
split_comments(comment).each do |line|
|
||||
ct = CHANGE_TYPES.find { |t| line =~ t[:pattern] }
|
||||
changes[ct] << better(line) if ct
|
||||
end
|
||||
end
|
||||
|
||||
changes
|
||||
end
|
||||
|
||||
def print_changes(heading, changes)
|
||||
|
|
Loading…
Reference in New Issue