ruby-gem-release 0.1.0 → 0.2.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 +4 -4
- data/CHANGELOG.md +5 -0
- data/README.md +4 -2
- data/lib/ruby-gem-release/changelog/base.rb +6 -2
- data/lib/ruby-gem-release/changelog/intridea.rb +13 -8
- data/lib/ruby-gem-release/changelog/keep_a_changelog.rb +6 -5
- data/lib/ruby-gem-release/tasks.rb +1 -0
- data/lib/ruby-gem-release/version.rb +1 -1
- data/lib/ruby-gem-release/workflow/context.rb +9 -2
- metadata +1 -1
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 46ed1a62b715dde573b31f304d33aae0df5eb2a574e42bfb69935a0600c6e43b
|
|
4
|
+
data.tar.gz: 55f8f60509b26d6f7dac36d02e7d8300c1ab6d87701b6b2b28070cca0fb9a4fe
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: dcb52020ceab4b9902377d975765adcd67c2ec3de35fb2c4e1d8c6b6af7c37c0d0ec32e188793686b38af00405e110f1d7318988952583ff58675858957eb220
|
|
7
|
+
data.tar.gz: cd7c6b2e4d8a503c4fb5ef333a9b8ed59ff97788b9a94669ef113ce0333af789d11edb59a84ab84a1b3927bea091b37421150c0959d124c33b5da019e4193c42
|
data/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,10 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 0.2.0 (2026/11/07)
|
|
4
|
+
|
|
5
|
+
- [#15](https://github.com/dblock/ruby-gem-release/pull/15): Add a Marketplace-ready composite action sharing Ruby release tasks, document action setup and publication, and pin workflow examples to `v0.2.0` - [@dblock](https://github.com/dblock).
|
|
6
|
+
- [#16](https://github.com/dblock/ruby-gem-release/pull/16): Preserve release heading depths from `#` through `######` in both changelog formats, without reformatting consumer files - [@dblock](https://github.com/dblock).
|
|
7
|
+
|
|
3
8
|
## 0.1.0 (2026/11/07)
|
|
4
9
|
|
|
5
10
|
- [#2](https://github.com/dblock/ruby-gem-release/pull/2): Add reusable gem release workflow and version management Rake tasks - [@dblock](https://github.com/dblock).
|
data/README.md
CHANGED
|
@@ -18,7 +18,7 @@ Requires Ruby 3.3+, GitHub Actions, and RubyGems Trusted Publishing.
|
|
|
18
18
|
|
|
19
19
|
### 1. Configure Your Gem
|
|
20
20
|
|
|
21
|
-
Add `ruby-gem-release` to the development dependencies and install the standard workflow in your Rakefile. Choose your version file and changelog format explicitly:
|
|
21
|
+
Add `ruby-gem-release` (`~> 0.2.0`) to the development dependencies and install the standard workflow in your Rakefile. Choose your version file and changelog format explicitly:
|
|
22
22
|
|
|
23
23
|
```ruby
|
|
24
24
|
require 'ruby-gem-release/workflow/ruby_gem'
|
|
@@ -53,7 +53,7 @@ permissions:
|
|
|
53
53
|
|
|
54
54
|
jobs:
|
|
55
55
|
release:
|
|
56
|
-
uses: dblock/ruby-gem-release/.github/workflows/release.yml@
|
|
56
|
+
uses: dblock/ruby-gem-release/.github/workflows/release.yml@v0.2.0
|
|
57
57
|
with:
|
|
58
58
|
ruby-version: '3.3'
|
|
59
59
|
rubygems-owner: ${{ inputs.rubygems-owner }}
|
|
@@ -91,6 +91,8 @@ gh workflow run release.yml
|
|
|
91
91
|
|
|
92
92
|
See [Detailed Usage](docs/usage.md#configuration) for workflow customization, callbacks, and available classes, and the [Actions Reference](docs/actions/release.md) for inputs and defaults.
|
|
93
93
|
|
|
94
|
+
For step-based integration, see the [Composite Action](docs/actions/action.md).
|
|
95
|
+
|
|
94
96
|
## Contributing
|
|
95
97
|
|
|
96
98
|
See [CONTRIBUTING.md](CONTRIBUTING.md), [DESIGN.md](DESIGN.md), [CHANGELOG.md](CHANGELOG.md), and [RELEASING.md](RELEASING.md).
|
|
@@ -27,12 +27,12 @@ module RubyGemRelease
|
|
|
27
27
|
matches.first
|
|
28
28
|
end
|
|
29
29
|
|
|
30
|
-
def heading_positions(content, pattern)
|
|
30
|
+
def heading_positions(content, pattern, max_level: 6)
|
|
31
31
|
lines = content.lines
|
|
32
32
|
offsets = line_offsets(lines)
|
|
33
33
|
matches = []
|
|
34
34
|
document(content).each do |node|
|
|
35
|
-
next unless node.type == :heading && node.header_level
|
|
35
|
+
next unless node.type == :heading && node.header_level <= max_level
|
|
36
36
|
|
|
37
37
|
index = node.source_position[:start_line] - 1
|
|
38
38
|
matches << offsets[index] if pattern.match?(lines[index].chomp)
|
|
@@ -40,6 +40,10 @@ module RubyGemRelease
|
|
|
40
40
|
matches
|
|
41
41
|
end
|
|
42
42
|
|
|
43
|
+
def heading_prefix(content, position)
|
|
44
|
+
content[position, 6][/\A#+/]
|
|
45
|
+
end
|
|
46
|
+
|
|
43
47
|
def editable_lines(content)
|
|
44
48
|
excluded = excluded_lines(content)
|
|
45
49
|
offset = 0
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
module RubyGemRelease
|
|
4
4
|
module Changelog
|
|
5
5
|
class Intridea < Base
|
|
6
|
-
UNRELEASED = /\A
|
|
6
|
+
UNRELEASED = /\A\#{1,6} \d+\.\d+\.\d+ \(Next\)\z/
|
|
7
7
|
PLACEHOLDER = '- Your contribution here.'
|
|
8
8
|
|
|
9
9
|
def initialize(path: 'CHANGELOG.md', placeholder: PLACEHOLDER)
|
|
@@ -20,11 +20,11 @@ module RubyGemRelease
|
|
|
20
20
|
content = File.read(@path)
|
|
21
21
|
separator = newline(content)
|
|
22
22
|
position = heading(content, UNRELEASED)
|
|
23
|
+
prefix = heading_prefix(content, position)
|
|
23
24
|
check_release_absent(content, version)
|
|
24
|
-
|
|
25
|
-
section_end =
|
|
26
|
-
|
|
27
|
-
remove_placeholder(content[line_end...section_end])
|
|
25
|
+
section_end = section_end_position(content, position, prefix.length)
|
|
26
|
+
content[position...section_end] = "#{prefix} #{version} (#{date.strftime('%Y/%m/%d')})" +
|
|
27
|
+
remove_placeholder(content[line_end(content, position, separator)...section_end])
|
|
28
28
|
File.write(@path, content)
|
|
29
29
|
end
|
|
30
30
|
|
|
@@ -33,21 +33,26 @@ module RubyGemRelease
|
|
|
33
33
|
validate_version(released_version)
|
|
34
34
|
content = File.read(@path)
|
|
35
35
|
separator = newline(content)
|
|
36
|
-
pattern = %r{\A
|
|
36
|
+
pattern = %r{\A\#{1,6} #{Regexp.escape(released_version)} \(\d{4}/\d{2}/\d{2}\)\z}
|
|
37
37
|
position = heading(content, pattern)
|
|
38
|
+
prefix = heading_prefix(content, position)
|
|
38
39
|
check_absent(content, UNRELEASED, 'unreleased heading already exists')
|
|
39
40
|
|
|
40
|
-
File.write(@path, content.insert(position, ["
|
|
41
|
+
File.write(@path, content.insert(position, ["#{prefix} #{version} (Next)", '', @placeholder, '', ''].join(separator)))
|
|
41
42
|
end
|
|
42
43
|
|
|
43
44
|
def check_release_absent(content, version)
|
|
44
|
-
check_absent(content, %r{\A
|
|
45
|
+
check_absent(content, %r{\A\#{1,6} #{Regexp.escape(version)} \(\d{4}/\d{2}/\d{2}\)\z}, 'release heading already exists')
|
|
45
46
|
end
|
|
46
47
|
|
|
47
48
|
def line_end(content, position, separator)
|
|
48
49
|
content.index(separator, position) || raise(ArgumentError, "heading must end with a newline in #{@path}")
|
|
49
50
|
end
|
|
50
51
|
|
|
52
|
+
def section_end_position(content, position, level)
|
|
53
|
+
heading_positions(content, /\A\#{1,6} /, max_level: level).find { |offset| offset > position } || content.length
|
|
54
|
+
end
|
|
55
|
+
|
|
51
56
|
def remove_placeholder(section)
|
|
52
57
|
positions = []
|
|
53
58
|
editable_lines(section) { |line, offset| positions << offset if line.chomp == @placeholder }
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
module RubyGemRelease
|
|
4
4
|
module Changelog
|
|
5
5
|
class KeepAChangelog < Base
|
|
6
|
-
UNRELEASED = /\A
|
|
6
|
+
UNRELEASED = /\A\#{1,6} \[Unreleased\]\z/
|
|
7
7
|
|
|
8
8
|
private
|
|
9
9
|
|
|
@@ -12,11 +12,11 @@ module RubyGemRelease
|
|
|
12
12
|
content = File.read(@path)
|
|
13
13
|
separator = newline(content)
|
|
14
14
|
position = heading(content, UNRELEASED)
|
|
15
|
-
check_absent(content, /\A
|
|
15
|
+
check_absent(content, /\A\#{1,6} \[#{Regexp.escape(version)}\] - \d{4}-\d{2}-\d{2}\z/, 'release heading already exists')
|
|
16
16
|
line_end = content.index(separator, position)
|
|
17
17
|
raise ArgumentError, "heading must end with a newline in #{@path}" unless line_end
|
|
18
18
|
|
|
19
|
-
content[position...line_end] = "
|
|
19
|
+
content[position...line_end] = "#{heading_prefix(content, position)} [#{version}] - #{date.strftime('%Y-%m-%d')}"
|
|
20
20
|
release_references(content, version, separator)
|
|
21
21
|
File.write(@path, content)
|
|
22
22
|
end
|
|
@@ -26,12 +26,13 @@ module RubyGemRelease
|
|
|
26
26
|
validate_version(released_version)
|
|
27
27
|
content = File.read(@path)
|
|
28
28
|
separator = newline(content)
|
|
29
|
-
pattern = /\A
|
|
29
|
+
pattern = /\A\#{1,6} \[#{Regexp.escape(released_version)}\] - \d{4}-\d{2}-\d{2}\z/
|
|
30
30
|
position = heading(content, pattern)
|
|
31
|
+
prefix = heading_prefix(content, position)
|
|
31
32
|
check_absent(content, UNRELEASED, 'unreleased heading already exists')
|
|
32
33
|
check_next_reference(content, released_version)
|
|
33
34
|
|
|
34
|
-
File.write(@path, content.insert(position, [
|
|
35
|
+
File.write(@path, content.insert(position, ["#{prefix} [Unreleased]", '', ''].join(separator)))
|
|
35
36
|
end
|
|
36
37
|
|
|
37
38
|
def references(content, label)
|
|
@@ -49,6 +49,7 @@ module RubyGemRelease
|
|
|
49
49
|
|
|
50
50
|
def install_workflow_tasks
|
|
51
51
|
namespace :workflow do
|
|
52
|
+
task(:configure) { Workflow::Context.new.configure! }
|
|
52
53
|
task(:capture) { Workflow::Context.new.capture! }
|
|
53
54
|
task(:resolve) { Workflow::Context.new.resolve! }
|
|
54
55
|
task(:credentials) { Workflow::RubyGemsCredentials.new(owner: ENV.fetch('RUBYGEMS_OWNER')).configure! }
|
|
@@ -8,6 +8,13 @@ require_relative '../version/ruby_constant'
|
|
|
8
8
|
module RubyGemRelease
|
|
9
9
|
module Workflow
|
|
10
10
|
class Context
|
|
11
|
+
def configure!
|
|
12
|
+
raise ArgumentError, 'dry-run must be true or false' unless %w[true false].include?(ENV.fetch('DRY_RUN'))
|
|
13
|
+
|
|
14
|
+
names = %w[INPUT_VERSION INPUT_GEMSPEC DEFAULT_BRANCH DRY_RUN GIT_USER_NAME GIT_USER_EMAIL RUBYGEMS_OWNER]
|
|
15
|
+
export(names.to_h { |name| [name, ENV.fetch(name)] })
|
|
16
|
+
end
|
|
17
|
+
|
|
11
18
|
def capture!
|
|
12
19
|
dry_run = ENV.fetch('DRY_RUN', 'false') == 'true'
|
|
13
20
|
check_branch(dry_run)
|
|
@@ -57,10 +64,10 @@ module RubyGemRelease
|
|
|
57
64
|
end
|
|
58
65
|
|
|
59
66
|
def export(values)
|
|
67
|
+
raise ArgumentError, 'Workflow values cannot contain line breaks' if values.values.any? { |value| value.match?(/[\r\n]/) }
|
|
68
|
+
|
|
60
69
|
File.open(ENV.fetch('GITHUB_ENV'), 'a') do |file|
|
|
61
70
|
values.each do |key, value|
|
|
62
|
-
raise ArgumentError, 'Workflow values cannot contain line breaks' if value.match?(/[\r\n]/)
|
|
63
|
-
|
|
64
71
|
file.puts "#{key}=#{value}"
|
|
65
72
|
end
|
|
66
73
|
end
|