github_changelog_generator 1.15.0.pre.alpha → 1.16.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +5 -5
- data/LICENSE +1 -1
- data/README.md +332 -275
- data/Rakefile +3 -4
- data/bin/git-generate-changelog +1 -1
- data/lib/github_changelog_generator.rb +10 -6
- data/lib/github_changelog_generator/generator/entry.rb +218 -0
- data/lib/github_changelog_generator/generator/generator.rb +126 -104
- data/lib/github_changelog_generator/generator/generator_fetcher.rb +139 -23
- data/lib/github_changelog_generator/generator/generator_processor.rb +59 -27
- data/lib/github_changelog_generator/generator/generator_tags.rb +26 -22
- data/lib/github_changelog_generator/generator/section.rb +124 -0
- data/lib/github_changelog_generator/helper.rb +1 -1
- data/lib/github_changelog_generator/octo_fetcher.rb +261 -130
- data/lib/github_changelog_generator/options.rb +74 -1
- data/lib/github_changelog_generator/parser.rb +120 -176
- data/lib/github_changelog_generator/parser_file.rb +8 -3
- data/lib/github_changelog_generator/reader.rb +2 -2
- data/lib/github_changelog_generator/task.rb +5 -6
- data/lib/github_changelog_generator/version.rb +1 -1
- data/man/git-generate-changelog.1 +144 -45
- data/man/git-generate-changelog.1.html +157 -84
- data/man/git-generate-changelog.html +19 -7
- data/man/git-generate-changelog.md +151 -84
- data/spec/files/github-changelog-generator.md +114 -114
- data/spec/{install-gem-in-bundler.gemfile → install_gem_in_bundler.gemfile} +2 -0
- data/spec/spec_helper.rb +2 -6
- data/spec/unit/generator/entry_spec.rb +766 -0
- data/spec/unit/generator/generator_processor_spec.rb +103 -41
- data/spec/unit/generator/generator_spec.rb +47 -0
- data/spec/unit/generator/generator_tags_spec.rb +56 -24
- data/spec/unit/generator/section_spec.rb +34 -0
- data/spec/unit/octo_fetcher_spec.rb +247 -197
- data/spec/unit/options_spec.rb +28 -4
- data/spec/unit/parse_file_spec.rb +2 -2
- data/spec/unit/parser_spec.rb +0 -79
- data/spec/unit/reader_spec.rb +4 -4
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_commits/when_API_is_valid/returns_commits.json +1 -0
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_commits_before/when_API_is_valid/returns_commits.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_closed_issues_and_pr/when_API_call_is_valid.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_closed_issues_and_pr/when_API_call_is_valid/returns_issue_with_proper_key/values.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_closed_issues_and_pr/when_API_call_is_valid/returns_issues.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_closed_issues_and_pr/when_API_call_is_valid/returns_issues_with_labels.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_closed_issues_and_pr/when_API_call_is_valid/returns_pull_request_with_proper_key/values.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_closed_issues_and_pr/when_API_call_is_valid/returns_pull_requests_with_labels.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_closed_pull_requests/when_API_call_is_valid.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_closed_pull_requests/when_API_call_is_valid/returns_correct_pull_request_keys.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_closed_pull_requests/when_API_call_is_valid/returns_pull_requests.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_commit/when_API_call_is_valid.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_commit/when_API_call_is_valid/returns_commit.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_date_of_tag/when_API_call_is_valid.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_date_of_tag/when_API_call_is_valid/returns_date.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_events_async/when_API_call_is_valid.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_fetch_events_async/when_API_call_is_valid/populates_issues.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_github_fetch_tags/when_API_call_is_valid.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_github_fetch_tags/when_API_call_is_valid/should_return_tags.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_github_fetch_tags/when_API_call_is_valid/should_return_tags_count.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_github_fetch_tags/when_wrong_token_provided.json +1 -1
- data/spec/vcr/GitHubChangelogGenerator_OctoFetcher/_github_fetch_tags/when_wrong_token_provided/should_raise_Unauthorized_error.json +1 -1
- metadata +71 -38
- data/bin/ghclgen +0 -5
- data/lib/github_changelog_generator/generator/generator_generation.rb +0 -180
- data/spec/unit/generator/generator_generation_spec.rb +0 -17
@@ -1,22 +1,35 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
require "delegate"
|
4
|
+
require "github_changelog_generator/helper"
|
5
|
+
|
4
6
|
module GitHubChangelogGenerator
|
7
|
+
# This class wraps Options, and knows a list of known options. Others options
|
8
|
+
# will raise exceptions.
|
5
9
|
class Options < SimpleDelegator
|
10
|
+
# Raised on initializing with unknown keys in the values hash,
|
11
|
+
# and when trying to store a value on an unknown key.
|
6
12
|
UnsupportedOptionError = Class.new(ArgumentError)
|
7
13
|
|
14
|
+
# List of valid option names
|
8
15
|
KNOWN_OPTIONS = %i[
|
9
16
|
add_issues_wo_labels
|
10
17
|
add_pr_wo_labels
|
18
|
+
add_sections
|
11
19
|
author
|
12
20
|
base
|
13
21
|
between_tags
|
22
|
+
breaking_labels
|
23
|
+
breaking_prefix
|
14
24
|
bug_labels
|
15
25
|
bug_prefix
|
16
26
|
cache_file
|
17
27
|
cache_log
|
18
28
|
compare_link
|
29
|
+
configure_sections
|
19
30
|
date_format
|
31
|
+
deprecated_labels
|
32
|
+
deprecated_prefix
|
20
33
|
due_tag
|
21
34
|
enhancement_labels
|
22
35
|
enhancement_prefix
|
@@ -24,16 +37,18 @@ module GitHubChangelogGenerator
|
|
24
37
|
exclude_tags
|
25
38
|
exclude_tags_regex
|
26
39
|
filter_issues_by_milestone
|
40
|
+
issues_of_open_milestones
|
27
41
|
frontmatter
|
28
42
|
future_release
|
29
|
-
git_remote
|
30
43
|
github_endpoint
|
31
44
|
github_site
|
32
45
|
header
|
33
46
|
http_cache
|
34
47
|
include_labels
|
48
|
+
include_tags_regex
|
35
49
|
issue_prefix
|
36
50
|
issue_line_labels
|
51
|
+
issue_line_body
|
37
52
|
issues
|
38
53
|
max_issues
|
39
54
|
merge_prefix
|
@@ -42,9 +57,17 @@ module GitHubChangelogGenerator
|
|
42
57
|
pulls
|
43
58
|
release_branch
|
44
59
|
release_url
|
60
|
+
removed_labels
|
61
|
+
removed_prefix
|
62
|
+
require
|
63
|
+
security_labels
|
64
|
+
security_prefix
|
45
65
|
simple_list
|
46
66
|
since_tag
|
67
|
+
since_commit
|
47
68
|
ssl_ca_file
|
69
|
+
summary_labels
|
70
|
+
summary_prefix
|
48
71
|
token
|
49
72
|
unreleased
|
50
73
|
unreleased_label
|
@@ -54,26 +77,76 @@ module GitHubChangelogGenerator
|
|
54
77
|
verbose
|
55
78
|
]
|
56
79
|
|
80
|
+
# @param values [Hash]
|
81
|
+
#
|
82
|
+
# @raise [UnsupportedOptionError] if given values contain unknown options
|
57
83
|
def initialize(values)
|
58
84
|
super(values)
|
59
85
|
unsupported_options.any? && raise(UnsupportedOptionError, unsupported_options.inspect)
|
60
86
|
end
|
61
87
|
|
88
|
+
# Set option key to val.
|
89
|
+
#
|
90
|
+
# @param key [Symbol]
|
91
|
+
# @param val [Object]
|
92
|
+
#
|
93
|
+
# @raise [UnsupportedOptionError] when trying to set an unknown option
|
62
94
|
def []=(key, val)
|
63
95
|
supported_option?(key) || raise(UnsupportedOptionError, key.inspect)
|
64
96
|
values[key] = val
|
65
97
|
end
|
66
98
|
|
99
|
+
# @return [Hash]
|
67
100
|
def to_hash
|
68
101
|
values
|
69
102
|
end
|
70
103
|
|
104
|
+
# Loads the configured Ruby files from the --require option.
|
105
|
+
def load_custom_ruby_files
|
106
|
+
self[:require].each { |f| require f }
|
107
|
+
end
|
108
|
+
|
109
|
+
# Pretty-prints a censored options hash, if :verbose.
|
110
|
+
def print_options
|
111
|
+
return unless self[:verbose]
|
112
|
+
|
113
|
+
Helper.log.info "Using these options:"
|
114
|
+
# For ruby 2.5.0+
|
115
|
+
censored_values.each do |key, value|
|
116
|
+
print(key.inspect, "=>", value.inspect)
|
117
|
+
puts ""
|
118
|
+
end
|
119
|
+
puts ""
|
120
|
+
end
|
121
|
+
|
122
|
+
# Boolean method for whether the user is using configure_sections
|
123
|
+
def configure_sections?
|
124
|
+
!self[:configure_sections].nil? && !self[:configure_sections].empty?
|
125
|
+
end
|
126
|
+
|
127
|
+
# Boolean method for whether the user is using add_sections
|
128
|
+
def add_sections?
|
129
|
+
!self[:add_sections].nil? && !self[:add_sections].empty?
|
130
|
+
end
|
131
|
+
|
132
|
+
# @return [Boolean] whether write to `:output`
|
133
|
+
def write_to_file?
|
134
|
+
self[:output].present?
|
135
|
+
end
|
136
|
+
|
71
137
|
private
|
72
138
|
|
73
139
|
def values
|
74
140
|
__getobj__
|
75
141
|
end
|
76
142
|
|
143
|
+
# Returns a censored options hash.
|
144
|
+
#
|
145
|
+
# @return [Hash] The GitHub `:token` key is censored in the output.
|
146
|
+
def censored_values
|
147
|
+
values.clone.tap { |opts| opts[:token] = opts[:token].nil? ? "No token used" : "hidden value" }
|
148
|
+
end
|
149
|
+
|
77
150
|
def unsupported_options
|
78
151
|
values.keys - KNOWN_OPTIONS
|
79
152
|
end
|
@@ -2,9 +2,9 @@
|
|
2
2
|
# frozen_string_literal: true
|
3
3
|
|
4
4
|
require "optparse"
|
5
|
-
require "
|
6
|
-
|
7
|
-
|
5
|
+
require "github_changelog_generator/version"
|
6
|
+
require "github_changelog_generator/helper"
|
7
|
+
|
8
8
|
module GitHubChangelogGenerator
|
9
9
|
class Parser
|
10
10
|
# parse options with optparse
|
@@ -19,87 +19,100 @@ module GitHubChangelogGenerator
|
|
19
19
|
abort [e, parser].join("\n")
|
20
20
|
end
|
21
21
|
|
22
|
-
|
23
|
-
|
24
|
-
|
22
|
+
unless options[:user] && options[:project]
|
23
|
+
warn "Configure which user and project to work on."
|
24
|
+
warn "Options --user and --project, or settings to that effect. See --help for more."
|
25
|
+
abort(parser.banner)
|
26
|
+
end
|
25
27
|
|
26
|
-
print_options
|
28
|
+
options.print_options
|
27
29
|
|
28
30
|
options
|
29
31
|
end
|
30
32
|
|
31
|
-
#
|
32
|
-
#
|
33
|
-
# The GitHub `:token` key is censored in the output.
|
33
|
+
# Setup parsing options
|
34
34
|
#
|
35
|
-
# @param options [
|
36
|
-
# @
|
37
|
-
def self.print_options(options)
|
38
|
-
if options[:verbose]
|
39
|
-
Helper.log.info "Performing task with options:"
|
40
|
-
options_to_display = options.clone
|
41
|
-
options_to_display[:token] = options_to_display[:token].nil? ? nil : "hidden value"
|
42
|
-
pp options_to_display
|
43
|
-
puts ""
|
44
|
-
end
|
45
|
-
end
|
46
|
-
|
47
|
-
# setup parsing options
|
35
|
+
# @param options [Options]
|
36
|
+
# @return [OptionParser]
|
48
37
|
def self.setup_parser(options)
|
49
|
-
|
50
|
-
opts.banner = "Usage: github_changelog_generator [options]"
|
51
|
-
opts.on("-u", "--user
|
38
|
+
OptionParser.new do |opts| # rubocop:disable Metrics/BlockLength
|
39
|
+
opts.banner = "Usage: github_changelog_generator --user USER --project PROJECT [options]"
|
40
|
+
opts.on("-u", "--user USER", "Username of the owner of the target GitHub repo OR the namespace of target Github repo if owned by an organization.") do |last|
|
52
41
|
options[:user] = last
|
53
42
|
end
|
54
|
-
opts.on("-p", "--project
|
43
|
+
opts.on("-p", "--project PROJECT", "Name of project on GitHub.") do |last|
|
55
44
|
options[:project] = last
|
56
45
|
end
|
57
46
|
opts.on("-t", "--token [TOKEN]", "To make more than 50 requests per hour your GitHub token is required. You can generate it at: https://github.com/settings/tokens/new") do |last|
|
58
47
|
options[:token] = last
|
59
48
|
end
|
60
|
-
opts.on("-f", "--date-format
|
49
|
+
opts.on("-f", "--date-format FORMAT", "Date format. Default is %Y-%m-%d.") do |last|
|
61
50
|
options[:date_format] = last
|
62
51
|
end
|
63
|
-
opts.on("-o", "--output [NAME]", "Output file. Default is CHANGELOG.md") do |last|
|
52
|
+
opts.on("-o", "--output [NAME]", "Output file. To print to STDOUT instead, use blank as path. Default is CHANGELOG.md") do |last|
|
64
53
|
options[:output] = last
|
65
54
|
end
|
66
55
|
opts.on("-b", "--base [NAME]", "Optional base file to append generated changes to.") do |last|
|
67
56
|
options[:base] = last
|
68
57
|
end
|
69
|
-
opts.on("--
|
70
|
-
options[:
|
58
|
+
opts.on("--summary-label [LABEL]", "Set up custom label for the release summary section. Default is \"\".") do |v|
|
59
|
+
options[:summary_prefix] = v
|
71
60
|
end
|
72
|
-
opts.on("--
|
61
|
+
opts.on("--breaking-label [LABEL]", "Set up custom label for the breaking changes section. Default is \"**Breaking changes:**\".") do |v|
|
62
|
+
options[:breaking_prefix] = v
|
63
|
+
end
|
64
|
+
opts.on("--enhancement-label [LABEL]", "Set up custom label for enhancements section. Default is \"**Implemented enhancements:**\".") do |v|
|
73
65
|
options[:enhancement_prefix] = v
|
74
66
|
end
|
75
|
-
opts.on("--
|
67
|
+
opts.on("--bugs-label [LABEL]", "Set up custom label for bug-fixes section. Default is \"**Fixed bugs:**\".") do |v|
|
68
|
+
options[:bug_prefix] = v
|
69
|
+
end
|
70
|
+
opts.on("--deprecated-label [LABEL]", "Set up custom label for the deprecated changes section. Default is \"**Deprecated:**\".") do |v|
|
71
|
+
options[:deprecated_prefix] = v
|
72
|
+
end
|
73
|
+
opts.on("--removed-label [LABEL]", "Set up custom label for the removed changes section. Default is \"**Removed:**\".") do |v|
|
74
|
+
options[:removed_prefix] = v
|
75
|
+
end
|
76
|
+
opts.on("--security-label [LABEL]", "Set up custom label for the security changes section. Default is \"**Security fixes:**\".") do |v|
|
77
|
+
options[:security_prefix] = v
|
78
|
+
end
|
79
|
+
opts.on("--issues-label [LABEL]", "Set up custom label for closed-issues section. Default is \"**Closed issues:**\".") do |v|
|
76
80
|
options[:issue_prefix] = v
|
77
81
|
end
|
78
|
-
opts.on("--header-label [LABEL]", "
|
82
|
+
opts.on("--header-label [LABEL]", "Set up custom header label. Default is \"# Changelog\".") do |v|
|
79
83
|
options[:header] = v
|
80
84
|
end
|
81
|
-
opts.on("--
|
82
|
-
options[:
|
85
|
+
opts.on("--configure-sections [Hash, String]", "Define your own set of sections which overrides all default sections.") do |v|
|
86
|
+
options[:configure_sections] = v
|
87
|
+
end
|
88
|
+
opts.on("--add-sections [Hash, String]", "Add new sections but keep the default sections.") do |v|
|
89
|
+
options[:add_sections] = v
|
83
90
|
end
|
84
|
-
opts.on("--
|
91
|
+
opts.on("--front-matter [JSON]", "Add YAML front matter. Formatted as JSON because it's easier to add on the command line.") do |v|
|
92
|
+
options[:frontmatter] = "#{JSON.parse(v).to_yaml}---\n"
|
93
|
+
end
|
94
|
+
opts.on("--pr-label [LABEL]", "Set up custom label for pull requests section. Default is \"**Merged pull requests:**\".") do |v|
|
85
95
|
options[:merge_prefix] = v
|
86
96
|
end
|
87
|
-
opts.on("--[no-]issues", "Include closed issues in changelog. Default is true") do |v|
|
97
|
+
opts.on("--[no-]issues", "Include closed issues in changelog. Default is true.") do |v|
|
88
98
|
options[:issues] = v
|
89
99
|
end
|
90
|
-
opts.on("--[no-]issues-wo-labels", "Include closed issues without labels in changelog. Default is true") do |v|
|
100
|
+
opts.on("--[no-]issues-wo-labels", "Include closed issues without labels in changelog. Default is true.") do |v|
|
91
101
|
options[:add_issues_wo_labels] = v
|
92
102
|
end
|
93
|
-
opts.on("--[no-]pr-wo-labels", "Include pull requests without labels in changelog. Default is true") do |v|
|
103
|
+
opts.on("--[no-]pr-wo-labels", "Include pull requests without labels in changelog. Default is true.") do |v|
|
94
104
|
options[:add_pr_wo_labels] = v
|
95
105
|
end
|
96
|
-
opts.on("--[no-]pull-requests", "Include pull-requests in changelog. Default is true") do |v|
|
106
|
+
opts.on("--[no-]pull-requests", "Include pull-requests in changelog. Default is true.") do |v|
|
97
107
|
options[:pulls] = v
|
98
108
|
end
|
99
|
-
opts.on("--[no-]filter-by-milestone", "Use milestone to detect when issue was resolved. Default is true") do |last|
|
109
|
+
opts.on("--[no-]filter-by-milestone", "Use milestone to detect when issue was resolved. Default is true.") do |last|
|
100
110
|
options[:filter_issues_by_milestone] = last
|
101
111
|
end
|
102
|
-
opts.on("--[no-]
|
112
|
+
opts.on("--[no-]issues-of-open-milestones", "Include issues of open milestones. Default is true.") do |v|
|
113
|
+
options[:issues_of_open_milestones] = v
|
114
|
+
end
|
115
|
+
opts.on("--[no-]author", "Add author of pull request at the end. Default is true.") do |author|
|
103
116
|
options[:author] = author
|
104
117
|
end
|
105
118
|
opts.on("--usernames-as-github-logins", "Use GitHub tags instead of Markdown links for the author of an issue or pull-request.") do |v|
|
@@ -108,64 +121,85 @@ module GitHubChangelogGenerator
|
|
108
121
|
opts.on("--unreleased-only", "Generate log from unreleased closed issues only.") do |v|
|
109
122
|
options[:unreleased_only] = v
|
110
123
|
end
|
111
|
-
opts.on("--[no-]unreleased", "Add to log unreleased closed issues. Default is true") do |v|
|
124
|
+
opts.on("--[no-]unreleased", "Add to log unreleased closed issues. Default is true.") do |v|
|
112
125
|
options[:unreleased] = v
|
113
126
|
end
|
114
|
-
opts.on("--unreleased-label [label]", "
|
127
|
+
opts.on("--unreleased-label [label]", "Set up custom label for unreleased closed issues section. Default is \"**Unreleased:**\".") do |v|
|
115
128
|
options[:unreleased_label] = v
|
116
129
|
end
|
117
|
-
opts.on("--[no-]compare-link", "Include compare link (Full Changelog) between older version and newer version. Default is true") do |v|
|
130
|
+
opts.on("--[no-]compare-link", "Include compare link (Full Changelog) between older version and newer version. Default is true.") do |v|
|
118
131
|
options[:compare_link] = v
|
119
132
|
end
|
120
|
-
opts.on("--include-labels x,y,z", Array, "
|
133
|
+
opts.on("--include-labels x,y,z", Array, "Of the labeled issues, only include the ones with the specified labels.") do |list|
|
121
134
|
options[:include_labels] = list
|
122
135
|
end
|
123
|
-
opts.on("--exclude-labels x,y,z", Array,
|
136
|
+
opts.on("--exclude-labels x,y,z", Array, "Issues with the specified labels will be excluded from changelog. Default is 'duplicate,question,invalid,wontfix'.") do |list|
|
124
137
|
options[:exclude_labels] = list
|
125
138
|
end
|
126
|
-
opts.on("--
|
127
|
-
options[:
|
139
|
+
opts.on("--summary-labels x,y,z", Array, 'Issues with these labels will be added to a new section, called "Release Summary". The section display only body of issues. Default is \'release-summary,summary\'.') do |list|
|
140
|
+
options[:summary_labels] = list
|
141
|
+
end
|
142
|
+
opts.on("--breaking-labels x,y,z", Array, 'Issues with these labels will be added to a new section, called "Breaking changes". Default is \'backwards-incompatible,breaking\'.') do |list|
|
143
|
+
options[:breaking_labels] = list
|
128
144
|
end
|
129
|
-
opts.on("--enhancement-labels x,y,z", Array, 'Issues with the specified labels will be
|
145
|
+
opts.on("--enhancement-labels x,y,z", Array, 'Issues with the specified labels will be added to "Implemented enhancements" section. Default is \'enhancement,Enhancement\'.') do |list|
|
130
146
|
options[:enhancement_labels] = list
|
131
147
|
end
|
148
|
+
opts.on("--bug-labels x,y,z", Array, 'Issues with the specified labels will be added to "Fixed bugs" section. Default is \'bug,Bug\'.') do |list|
|
149
|
+
options[:bug_labels] = list
|
150
|
+
end
|
151
|
+
opts.on("--deprecated-labels x,y,z", Array, 'Issues with the specified labels will be added to a section called "Deprecated". Default is \'deprecated,Deprecated\'.') do |list|
|
152
|
+
options[:deprecated_labels] = list
|
153
|
+
end
|
154
|
+
opts.on("--removed-labels x,y,z", Array, 'Issues with the specified labels will be added to a section called "Removed". Default is \'removed,Removed\'.') do |list|
|
155
|
+
options[:removed_labels] = list
|
156
|
+
end
|
157
|
+
opts.on("--security-labels x,y,z", Array, 'Issues with the specified labels will be added to a section called "Security fixes". Default is \'security,Security\'.') do |list|
|
158
|
+
options[:security_labels] = list
|
159
|
+
end
|
132
160
|
opts.on("--issue-line-labels x,y,z", Array, 'The specified labels will be shown in brackets next to each matching issue. Use "ALL" to show all labels. Default is [].') do |list|
|
133
161
|
options[:issue_line_labels] = list
|
134
162
|
end
|
135
|
-
opts.on("--
|
163
|
+
opts.on("--include-tags-regex [REGEX]", "Apply a regular expression on tag names so that they can be included, for example: --include-tags-regex \".*\+\d{1,}\".") do |last|
|
164
|
+
options[:include_tags_regex] = last
|
165
|
+
end
|
166
|
+
opts.on("--exclude-tags x,y,z", Array, "Changelog will exclude specified tags") do |list|
|
136
167
|
options[:exclude_tags] = list
|
137
168
|
end
|
138
|
-
opts.on("--exclude-tags-regex [REGEX]", "Apply a regular expression on tag names so that they can be excluded, for example: --exclude-tags-regex \".*\+\d{1,}\"
|
169
|
+
opts.on("--exclude-tags-regex [REGEX]", "Apply a regular expression on tag names so that they can be excluded, for example: --exclude-tags-regex \".*\+\d{1,}\".") do |last|
|
139
170
|
options[:exclude_tags_regex] = last
|
140
171
|
end
|
141
|
-
opts.on("--since-tag x", "
|
172
|
+
opts.on("--since-tag x", "Changelog will start after specified tag.") do |v|
|
142
173
|
options[:since_tag] = v
|
143
174
|
end
|
144
|
-
opts.on("--due-tag x", "
|
175
|
+
opts.on("--due-tag x", "Changelog will end before specified tag.") do |v|
|
145
176
|
options[:due_tag] = v
|
146
177
|
end
|
147
|
-
opts.on("--
|
178
|
+
opts.on("--since-commit x", "Fetch only commits after this time. eg. \"2017-01-01 10:00:00\"") do |v|
|
179
|
+
options[:since_commit] = v
|
180
|
+
end
|
181
|
+
opts.on("--max-issues [NUMBER]", Integer, "Maximum number of issues to fetch from GitHub. Default is unlimited.") do |max|
|
148
182
|
options[:max_issues] = max
|
149
183
|
end
|
150
184
|
opts.on("--release-url [URL]", "The URL to point to for release links, in printf format (with the tag as variable).") do |url|
|
151
185
|
options[:release_url] = url
|
152
186
|
end
|
153
|
-
opts.on("--github-site [URL]", "The Enterprise
|
187
|
+
opts.on("--github-site [URL]", "The Enterprise GitHub site where your project is hosted.") do |last|
|
154
188
|
options[:github_site] = last
|
155
189
|
end
|
156
|
-
opts.on("--github-api [URL]", "The enterprise endpoint to use for your
|
190
|
+
opts.on("--github-api [URL]", "The enterprise endpoint to use for your GitHub API.") do |last|
|
157
191
|
options[:github_endpoint] = last
|
158
192
|
end
|
159
|
-
opts.on("--simple-list", "Create simple list from issues and pull requests. Default is false.") do |v|
|
193
|
+
opts.on("--simple-list", "Create a simple list from issues and pull requests. Default is false.") do |v|
|
160
194
|
options[:simple_list] = v
|
161
195
|
end
|
162
196
|
opts.on("--future-release [RELEASE-VERSION]", "Put the unreleased changes in the specified release number.") do |future_release|
|
163
197
|
options[:future_release] = future_release
|
164
198
|
end
|
165
|
-
opts.on("--release-branch [RELEASE-BRANCH]", "Limit pull requests to the release branch, such as master or release") do |release_branch|
|
199
|
+
opts.on("--release-branch [RELEASE-BRANCH]", "Limit pull requests to the release branch, such as master or release.") do |release_branch|
|
166
200
|
options[:release_branch] = release_branch
|
167
201
|
end
|
168
|
-
opts.on("--[no-]http-cache", "Use HTTP Cache to cache
|
202
|
+
opts.on("--[no-]http-cache", "Use HTTP Cache to cache GitHub API requests (useful for large repos). Default is true.") do |http_cache|
|
169
203
|
options[:http_cache] = http_cache
|
170
204
|
end
|
171
205
|
opts.on("--cache-file [CACHE-FILE]", "Filename to use for cache. Default is github-changelog-http-cache in a temporary directory.") do |cache_file|
|
@@ -177,22 +211,24 @@ module GitHubChangelogGenerator
|
|
177
211
|
opts.on("--ssl-ca-file [PATH]", "Path to cacert.pem file. Default is a bundled lib/github_changelog_generator/ssl_certs/cacert.pem. Respects SSL_CA_PATH.") do |ssl_ca_file|
|
178
212
|
options[:ssl_ca_file] = ssl_ca_file
|
179
213
|
end
|
180
|
-
opts.on("--
|
214
|
+
opts.on("--require x,y,z", Array, "Path to Ruby file(s) to require before generating changelog.") do |paths|
|
215
|
+
options[:require] = paths
|
216
|
+
end
|
217
|
+
opts.on("--[no-]verbose", "Run verbosely. Default is true.") do |v|
|
181
218
|
options[:verbose] = v
|
182
219
|
end
|
183
|
-
opts.on("-v", "--version", "Print version number") do |_v|
|
220
|
+
opts.on("-v", "--version", "Print version number.") do |_v|
|
184
221
|
puts "Version: #{GitHubChangelogGenerator::VERSION}"
|
185
222
|
exit
|
186
223
|
end
|
187
|
-
opts.on("-h", "--help", "Displays Help") do
|
224
|
+
opts.on("-h", "--help", "Displays Help.") do
|
188
225
|
puts opts
|
189
226
|
exit
|
190
227
|
end
|
191
228
|
end
|
192
|
-
parser
|
193
229
|
end
|
194
230
|
|
195
|
-
# @return [
|
231
|
+
# @return [Options] Default options
|
196
232
|
def self.default_options
|
197
233
|
Options.new(
|
198
234
|
date_format: "%Y-%m-%d",
|
@@ -203,131 +239,39 @@ module GitHubChangelogGenerator
|
|
203
239
|
add_pr_wo_labels: true,
|
204
240
|
pulls: true,
|
205
241
|
filter_issues_by_milestone: true,
|
242
|
+
issues_of_open_milestones: true,
|
206
243
|
author: true,
|
207
244
|
unreleased: true,
|
208
245
|
unreleased_label: "Unreleased",
|
209
246
|
compare_link: true,
|
247
|
+
exclude_labels: ["duplicate", "question", "invalid", "wontfix", "Duplicate", "Question", "Invalid", "Wontfix", "Meta: Exclude From Changelog"],
|
248
|
+
summary_labels: ["Release summary", "release-summary", "Summary", "summary"],
|
249
|
+
breaking_labels: ["backwards-incompatible", "Backwards incompatible", "breaking"],
|
210
250
|
enhancement_labels: ["enhancement", "Enhancement", "Type: Enhancement"],
|
211
251
|
bug_labels: ["bug", "Bug", "Type: Bug"],
|
212
|
-
|
252
|
+
deprecated_labels: ["deprecated", "Deprecated", "Type: Deprecated"],
|
253
|
+
removed_labels: ["removed", "Removed", "Type: Removed"],
|
254
|
+
security_labels: ["security", "Security", "Type: Security"],
|
255
|
+
configure_sections: {},
|
256
|
+
add_sections: {},
|
213
257
|
issue_line_labels: [],
|
214
258
|
max_issues: nil,
|
215
259
|
simple_list: false,
|
216
260
|
ssl_ca_file: nil,
|
217
261
|
verbose: true,
|
218
|
-
header: "#
|
262
|
+
header: "# Changelog",
|
219
263
|
merge_prefix: "**Merged pull requests:**",
|
220
264
|
issue_prefix: "**Closed issues:**",
|
221
|
-
|
265
|
+
summary_prefix: "",
|
266
|
+
breaking_prefix: "**Breaking changes:**",
|
222
267
|
enhancement_prefix: "**Implemented enhancements:**",
|
223
|
-
|
224
|
-
|
268
|
+
bug_prefix: "**Fixed bugs:**",
|
269
|
+
deprecated_prefix: "**Deprecated:**",
|
270
|
+
removed_prefix: "**Removed:**",
|
271
|
+
security_prefix: "**Security fixes:**",
|
272
|
+
http_cache: true,
|
273
|
+
require: []
|
225
274
|
)
|
226
275
|
end
|
227
|
-
|
228
|
-
# If `:user` or `:project` not set in options, try setting them
|
229
|
-
# Valid unnamed parameters:
|
230
|
-
# 1) in 1 param: repo_name/project
|
231
|
-
# 2) in 2 params: repo name project
|
232
|
-
def self.fetch_user_and_project(options)
|
233
|
-
if options[:user].nil? || options[:project].nil?
|
234
|
-
user, project = user_and_project_from_git(options, ARGV[0], ARGV[1])
|
235
|
-
options[:user] ||= user
|
236
|
-
options[:project] ||= project
|
237
|
-
end
|
238
|
-
end
|
239
|
-
|
240
|
-
# Sets `:user` and `:project` in `options` from CLI arguments or `git remote`
|
241
|
-
# @param [String] arg0 first argument in cli
|
242
|
-
# @param [String] arg1 second argument in cli
|
243
|
-
# @return [Array<String>] user and project, or nil if unsuccessful
|
244
|
-
def self.user_and_project_from_git(options, arg0 = nil, arg1 = nil)
|
245
|
-
user, project = user_project_from_option(arg0, arg1, options[:github_site])
|
246
|
-
unless user && project
|
247
|
-
if ENV["RUBYLIB"] =~ /ruby-debug-ide/
|
248
|
-
user = "skywinder"
|
249
|
-
project = "changelog_test"
|
250
|
-
else
|
251
|
-
remote = `git config --get remote.#{options[:git_remote]}.url`
|
252
|
-
user, project = user_project_from_remote(remote)
|
253
|
-
end
|
254
|
-
end
|
255
|
-
|
256
|
-
[user, project]
|
257
|
-
end
|
258
|
-
|
259
|
-
# Returns GitHub username and project from CLI arguments
|
260
|
-
#
|
261
|
-
# @param arg0 [String] This parameter takes two forms: Either a full
|
262
|
-
# GitHub URL, or a 'username/projectname', or
|
263
|
-
# simply a GitHub username
|
264
|
-
# @param arg1 [String] If arg0 is given as a username,
|
265
|
-
# then arg1 can given as a projectname
|
266
|
-
# @param github_site [String] Domain name of GitHub site
|
267
|
-
#
|
268
|
-
# @return [Array, nil] user and project, or nil if unsuccessful
|
269
|
-
def self.user_project_from_option(arg0, arg1, github_site)
|
270
|
-
user = nil
|
271
|
-
project = nil
|
272
|
-
github_site ||= "github.com"
|
273
|
-
if arg0 && !arg1
|
274
|
-
# this match should parse strings such "https://github.com/skywinder/Github-Changelog-Generator" or
|
275
|
-
# "skywinder/Github-Changelog-Generator" to user and name
|
276
|
-
match = /(?:.+#{Regexp.escape(github_site)}\/)?(.+)\/(.+)/.match(arg0)
|
277
|
-
|
278
|
-
begin
|
279
|
-
param = match[2].nil?
|
280
|
-
rescue StandardError
|
281
|
-
puts "Can't detect user and name from first parameter: '#{arg0}' -> exit'"
|
282
|
-
return
|
283
|
-
end
|
284
|
-
if param
|
285
|
-
return
|
286
|
-
else
|
287
|
-
user = match[1]
|
288
|
-
project = match[2]
|
289
|
-
end
|
290
|
-
end
|
291
|
-
[user, project]
|
292
|
-
end
|
293
|
-
|
294
|
-
# These patterns match these formats:
|
295
|
-
#
|
296
|
-
# ```
|
297
|
-
# origin git@github.com:skywinder/Github-Changelog-Generator.git (fetch)
|
298
|
-
# git@github.com:skywinder/Github-Changelog-Generator.git
|
299
|
-
# ```
|
300
|
-
#
|
301
|
-
# and
|
302
|
-
#
|
303
|
-
# ```
|
304
|
-
# origin https://github.com/skywinder/ChangelogMerger (fetch)
|
305
|
-
# https://github.com/skywinder/ChangelogMerger
|
306
|
-
# ```
|
307
|
-
GIT_REMOTE_PATTERNS = [
|
308
|
-
/.*(?:[:\/])(?<user>(?:-|\w|\.)*)\/(?<project>(?:-|\w|\.)*)(?:\.git).*/,
|
309
|
-
/.*\/(?<user>(?:-|\w|\.)*)\/(?<project>(?:-|\w|\.)*).*/
|
310
|
-
]
|
311
|
-
|
312
|
-
# Returns GitHub username and project from git remote output
|
313
|
-
#
|
314
|
-
# @param git_remote_output [String] Output of git remote command
|
315
|
-
#
|
316
|
-
# @return [Array] user and project
|
317
|
-
def self.user_project_from_remote(git_remote_output)
|
318
|
-
user = nil
|
319
|
-
project = nil
|
320
|
-
GIT_REMOTE_PATTERNS.each do |git_remote_pattern|
|
321
|
-
git_remote_pattern =~ git_remote_output
|
322
|
-
|
323
|
-
if Regexp.last_match
|
324
|
-
user = Regexp.last_match(:user)
|
325
|
-
project = Regexp.last_match(:project)
|
326
|
-
break
|
327
|
-
end
|
328
|
-
end
|
329
|
-
|
330
|
-
[user, project]
|
331
|
-
end
|
332
276
|
end
|
333
277
|
end
|