Skip to content

Commit 14a6f0f

Browse files
authored
Merge pull request #1262 from reactjs/create-release-script
Create release script
2 parents 9e8fb5f + 64c6123 commit 14a6f0f

File tree

5 files changed

+389
-1
lines changed

5 files changed

+389
-1
lines changed

Gemfile.lock

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,7 @@ GEM
109109
execjs (2.7.0)
110110
ffi (1.15.5)
111111
formatador (1.1.0)
112+
gem-release (2.2.2)
112113
globalid (1.0.1)
113114
activesupport (>= 5.0)
114115
guard (2.18.0)
@@ -248,6 +249,7 @@ DEPENDENCIES
248249
codeclimate-test-reporter
249250
coffee-rails
250251
es5-shim-rails (>= 2.0.5)
252+
gem-release
251253
guard
252254
guard-minitest
253255
jbuilder

package.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
"build": "cd react_ujs && webpack"
1212
},
1313
"devDependencies": {
14-
"webpack": "^5.74.0"
14+
"webpack": "^5.74.0",
15+
"webpack-cli": "^5.0.1"
1516
}
1617
}

rakelib/create_release.rake

Lines changed: 125 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,125 @@
1+
# frozen_string_literal: true
2+
3+
require 'English'
4+
5+
desc("Releases both the gem and node package using the given version.
6+
IMPORTANT: the gem version must be in valid rubygem format (no dashes).
7+
It will be automatically converted to a valid yarn semver by the rake task
8+
for the node package version. This only makes a difference for pre-release
9+
versions such as `3.0.0.beta.1` (yarn version would be `3.0.0-beta.1`).
10+
This task depends on the gem-release (ruby gem) and release-it (node package)
11+
which are installed via `bundle install` and `yarn global add release-it`
12+
13+
1st argument: The new version in rubygem format (no dashes). Pass no argument to
14+
automatically perform a patch version bump.
15+
2nd argument: Perform a dry run by passing 'true' as a second argument.
16+
17+
Note, accept defaults for npmjs options. Script will pause to get 2FA tokens.
18+
Example: `rake release[2.1.0,false]`")
19+
20+
task :create_release, %i[gem_version dry_run] do |_t, args|
21+
args_hash = args.to_hash
22+
23+
is_dry_run = Release.object_to_boolean(args_hash[:dry_run])
24+
gem_version = args_hash.fetch(:gem_version, '').strip
25+
npm_version = gem_version.empty? ? '' : Release.convert_rubygem_to_npm_version(gem_version)
26+
27+
Release.update_the_local_project
28+
Release.ensure_there_is_nothing_to_commit
29+
30+
# Preparing for release
31+
32+
# Updating the pre-bundled react
33+
puts 'Updating react'
34+
Rake::Task['react:update'].invoke
35+
36+
# Updating ReactRailsUJS
37+
puts 'Updating ujs:update'
38+
Rake::Task['ujs:update'].invoke
39+
40+
release_the_new_npm_version(npm_version, is_dry_run)
41+
release_the_new_gem_version(gem_version, is_dry_run)
42+
43+
Release.push
44+
end
45+
46+
# A collection of helper functions for gem and npm release
47+
module Release
48+
extend FileUtils
49+
class << self
50+
def gem_root
51+
File.expand_path('..', __dir__)
52+
end
53+
54+
# Executes a string or an array of strings in a shell in the given directory in an unbundled environment
55+
def sh_in_dir(dir, *shell_commands)
56+
shell_commands.flatten.each { |shell_command| sh %(cd #{dir} && #{shell_command.strip}) }
57+
end
58+
59+
def ensure_there_is_nothing_to_commit
60+
status = `git status --porcelain`
61+
62+
return if $CHILD_STATUS.success? && status == ''
63+
64+
error = if $CHILD_STATUS.success?
65+
'You have uncommitted code. Please commit or stash your changes before continuing'
66+
else
67+
'You do not have Git installed. Please install Git, and commit your changes before continuing'
68+
end
69+
raise(error)
70+
end
71+
72+
def object_to_boolean(value)
73+
[true, 'true', 'yes', 1, '1', 't'].include?(value.instance_of?(String) ? value.downcase : value)
74+
end
75+
76+
def convert_rubygem_to_npm_version(gem_version)
77+
regex_match = gem_version.match(/(\d+\.\d+\.\d+)[.-]?(.+)?/)
78+
return "#{regex_match[1]}-#{regex_match[2]}" if regex_match[2]
79+
80+
regex_match[1].to_s
81+
end
82+
83+
def update_the_local_project
84+
puts 'Pulling latest commits from remote repository'
85+
86+
sh_in_dir(gem_root, 'git pull --rebase')
87+
raise 'Failed in pulling latest changes from default remore repository.' unless $CHILD_STATUS.success?
88+
rescue Errno::ENOENT
89+
raise 'Ensure you have Git and Bundler installed before continuing.'
90+
end
91+
92+
def release_the_new_gem_version(gem_version, is_dry_run)
93+
puts 'Bumping gem version'
94+
Release.sh_in_dir(
95+
gem_root,
96+
"gem bump --no-commit #{gem_version == '' ? '' : %(--version #{gem_version})}",
97+
'bundle install',
98+
"git commit -am 'Bump version to #{gem_version}'"
99+
)
100+
puts 'ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ'
101+
puts 'Use the OTP for RubyGems!'
102+
puts 'ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ'
103+
104+
sh_in_dir(gem_root, 'gem release --push --tag') unless is_dry_run
105+
end
106+
107+
def release_the_new_npm_version(npm_version, is_dry_run)
108+
puts 'Making npm release'
109+
# Will bump the yarn version, commit, tag the commit, push to repo, and release on yarn
110+
release_it_command = +'release-it'
111+
release_it_command << " #{npm_version}" unless npm_version == ''
112+
release_it_command << ' --npm.publish --no-git.requireCleanWorkingDir'
113+
release_it_command << ' --dry-run --verbose' if is_dry_run
114+
puts 'ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ'
115+
puts 'Use the OTP for NPM!'
116+
puts 'ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ'
117+
118+
system(release_it_command)
119+
end
120+
121+
def push
122+
sh_in_dir(gem_root, 'git push')
123+
end
124+
end
125+
end

react-rails.gemspec

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ Gem::Specification.new do |s|
1919
s.add_development_dependency 'codeclimate-test-reporter'
2020
s.add_development_dependency 'coffee-rails'
2121
s.add_development_dependency 'es5-shim-rails', '>= 2.0.5'
22+
s.add_development_dependency 'gem-release'
2223
s.add_development_dependency 'guard'
2324
s.add_development_dependency 'guard-minitest'
2425
s.add_development_dependency 'jbuilder'

0 commit comments

Comments
 (0)