rubygems-update 3.5.6 → 3.5.8
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 +54 -0
- data/Manifest.txt +7 -4
- data/bundler/CHANGELOG.md +30 -0
- data/bundler/lib/bundler/build_metadata.rb +2 -2
- data/bundler/lib/bundler/cli/binstubs.rb +1 -1
- data/bundler/lib/bundler/cli/plugin.rb +3 -2
- data/bundler/lib/bundler/cli.rb +1 -1
- data/bundler/lib/bundler/dsl.rb +16 -1
- data/bundler/lib/bundler/gem_version_promoter.rb +42 -38
- data/bundler/lib/bundler/man/bundle-add.1 +1 -1
- data/bundler/lib/bundler/man/bundle-binstubs.1 +1 -1
- data/bundler/lib/bundler/man/bundle-cache.1 +1 -1
- data/bundler/lib/bundler/man/bundle-check.1 +1 -1
- data/bundler/lib/bundler/man/bundle-clean.1 +1 -1
- data/bundler/lib/bundler/man/bundle-config.1 +1 -1
- data/bundler/lib/bundler/man/bundle-console.1 +1 -1
- data/bundler/lib/bundler/man/bundle-doctor.1 +1 -1
- data/bundler/lib/bundler/man/bundle-exec.1 +1 -1
- data/bundler/lib/bundler/man/bundle-gem.1 +1 -1
- data/bundler/lib/bundler/man/bundle-help.1 +1 -1
- data/bundler/lib/bundler/man/bundle-info.1 +1 -1
- data/bundler/lib/bundler/man/bundle-init.1 +1 -1
- data/bundler/lib/bundler/man/bundle-inject.1 +1 -1
- data/bundler/lib/bundler/man/bundle-install.1 +3 -3
- data/bundler/lib/bundler/man/bundle-install.1.ronn +2 -2
- data/bundler/lib/bundler/man/bundle-list.1 +1 -1
- data/bundler/lib/bundler/man/bundle-lock.1 +1 -1
- data/bundler/lib/bundler/man/bundle-open.1 +1 -1
- data/bundler/lib/bundler/man/bundle-outdated.1 +1 -1
- data/bundler/lib/bundler/man/bundle-platform.1 +1 -1
- data/bundler/lib/bundler/man/bundle-plugin.1 +7 -4
- data/bundler/lib/bundler/man/bundle-plugin.1.ronn +7 -3
- data/bundler/lib/bundler/man/bundle-pristine.1 +1 -1
- data/bundler/lib/bundler/man/bundle-remove.1 +1 -1
- data/bundler/lib/bundler/man/bundle-show.1 +1 -1
- data/bundler/lib/bundler/man/bundle-update.1 +1 -1
- data/bundler/lib/bundler/man/bundle-version.1 +1 -1
- data/bundler/lib/bundler/man/bundle-viz.1 +1 -1
- data/bundler/lib/bundler/man/bundle.1 +1 -1
- data/bundler/lib/bundler/man/gemfile.5 +3 -3
- data/bundler/lib/bundler/man/gemfile.5.ronn +2 -2
- data/bundler/lib/bundler/plugin/installer/path.rb +18 -0
- data/bundler/lib/bundler/plugin/installer.rb +36 -16
- data/bundler/lib/bundler/plugin/source_list.rb +4 -4
- data/bundler/lib/bundler/resolver/candidate.rb +1 -1
- data/bundler/lib/bundler/resolver.rb +54 -24
- data/bundler/lib/bundler/self_manager.rb +1 -1
- data/bundler/lib/bundler/settings.rb +10 -7
- data/bundler/lib/bundler/source/rubygems.rb +2 -2
- data/bundler/lib/bundler/source_list.rb +2 -2
- data/bundler/lib/bundler/templates/newgem/newgem.gemspec.tt +4 -3
- data/bundler/lib/bundler/templates/newgem/rubocop.yml.tt +0 -5
- data/bundler/lib/bundler/vendor/pub_grub/lib/pub_grub/static_package_source.rb +1 -0
- data/bundler/lib/bundler/vendored_net_http.rb +7 -3
- data/bundler/lib/bundler/vendored_timeout.rb +7 -3
- data/bundler/lib/bundler/version.rb +1 -1
- data/lib/rubygems/command.rb +1 -1
- data/lib/rubygems/command_manager.rb +2 -1
- data/lib/rubygems/commands/build_command.rb +2 -11
- data/lib/rubygems/commands/help_command.rb +2 -2
- data/lib/rubygems/commands/rdoc_command.rb +1 -8
- data/lib/rubygems/commands/rebuild_command.rb +264 -0
- data/lib/rubygems/config_file.rb +20 -8
- data/lib/rubygems/defaults.rb +4 -4
- data/lib/rubygems/dependency.rb +2 -2
- data/lib/rubygems/dependency_list.rb +1 -1
- data/lib/rubygems/ext/cargo_builder.rb +1 -1
- data/lib/rubygems/gemcutter_utilities.rb +1 -1
- data/lib/rubygems/gemspec_helpers.rb +19 -0
- data/lib/rubygems/package.rb +2 -2
- data/lib/rubygems/remote_fetcher.rb +1 -1
- data/lib/rubygems/request.rb +1 -1
- data/lib/rubygems/request_set.rb +1 -1
- data/lib/rubygems/resolver/spec_specification.rb +7 -0
- data/lib/rubygems/s3_uri_signer.rb +1 -1
- data/lib/rubygems/safe_yaml.rb +10 -1
- data/lib/rubygems/security.rb +1 -1
- data/lib/rubygems/specification.rb +1 -1
- data/lib/rubygems/specification_policy.rb +9 -1
- data/lib/rubygems/util/licenses.rb +43 -0
- data/lib/rubygems/vendor/molinillo/lib/molinillo/dependency_graph.rb +1 -1
- data/lib/rubygems/vendored_net_http.rb +5 -0
- data/lib/rubygems/vendored_timeout.rb +5 -0
- data/lib/rubygems.rb +2 -2
- data/rubygems-update.gemspec +1 -1
- metadata +10 -7
- data/lib/rubygems/net/http.rb +0 -3
- data/lib/rubygems/timeout.rb +0 -3
- /data/lib/rubygems/{optparse.rb → vendored_optparse.rb} +0 -0
- /data/lib/rubygems/{tsort.rb → vendored_tsort.rb} +0 -0
@@ -0,0 +1,264 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "date"
|
4
|
+
require "digest"
|
5
|
+
require "fileutils"
|
6
|
+
require "tmpdir"
|
7
|
+
require_relative "../gemspec_helpers"
|
8
|
+
require_relative "../package"
|
9
|
+
|
10
|
+
class Gem::Commands::RebuildCommand < Gem::Command
|
11
|
+
include Gem::GemspecHelpers
|
12
|
+
|
13
|
+
DATE_FORMAT = "%Y-%m-%d %H:%M:%S.%N Z"
|
14
|
+
|
15
|
+
def initialize
|
16
|
+
super "rebuild", "Attempt to reproduce a build of a gem."
|
17
|
+
|
18
|
+
add_option "--diff", "If the files don't match, compare them using diffoscope." do |_value, options|
|
19
|
+
options[:diff] = true
|
20
|
+
end
|
21
|
+
|
22
|
+
add_option "--force", "Skip validation of the spec." do |_value, options|
|
23
|
+
options[:force] = true
|
24
|
+
end
|
25
|
+
|
26
|
+
add_option "--strict", "Consider warnings as errors when validating the spec." do |_value, options|
|
27
|
+
options[:strict] = true
|
28
|
+
end
|
29
|
+
|
30
|
+
add_option "--source GEM_SOURCE", "Specify the source to download the gem from." do |value, options|
|
31
|
+
options[:source] = value
|
32
|
+
end
|
33
|
+
|
34
|
+
add_option "--original GEM_FILE", "Specify a local file to compare against (instead of downloading it)." do |value, options|
|
35
|
+
options[:original_gem_file] = value
|
36
|
+
end
|
37
|
+
|
38
|
+
add_option "--gemspec GEMSPEC_FILE", "Specify the name of the gemspec file." do |value, options|
|
39
|
+
options[:gemspec_file] = value
|
40
|
+
end
|
41
|
+
|
42
|
+
add_option "-C PATH", "Run as if gem build was started in <PATH> instead of the current working directory." do |value, options|
|
43
|
+
options[:build_path] = value
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
def arguments # :nodoc:
|
48
|
+
"GEM_NAME gem name on gem server\n" \
|
49
|
+
"GEM_VERSION gem version you are attempting to rebuild"
|
50
|
+
end
|
51
|
+
|
52
|
+
def description # :nodoc:
|
53
|
+
<<-EOF
|
54
|
+
The rebuild command allows you to (attempt to) reproduce a build of a gem
|
55
|
+
from a ruby gemspec.
|
56
|
+
|
57
|
+
This command assumes the gemspec can be built with the `gem build` command.
|
58
|
+
If you use any of `gem build`, `rake build`, or`rake release` in the
|
59
|
+
build/release process for a gem, it is a potential candidate.
|
60
|
+
|
61
|
+
You will need to match the RubyGems version used, since this is included in
|
62
|
+
the Gem metadata.
|
63
|
+
|
64
|
+
If the gem includes lockfiles (e.g. Gemfile.lock) and similar, it will
|
65
|
+
require more effort to reproduce a build. For example, it might require
|
66
|
+
more precisely matched versions of Ruby and/or Bundler to be used.
|
67
|
+
EOF
|
68
|
+
end
|
69
|
+
|
70
|
+
def usage # :nodoc:
|
71
|
+
"#{program_name} GEM_NAME GEM_VERSION"
|
72
|
+
end
|
73
|
+
|
74
|
+
def execute
|
75
|
+
gem_name, gem_version = get_gem_name_and_version
|
76
|
+
|
77
|
+
old_dir, new_dir = prep_dirs
|
78
|
+
|
79
|
+
gem_filename = "#{gem_name}-#{gem_version}.gem"
|
80
|
+
old_file = File.join(old_dir, gem_filename)
|
81
|
+
new_file = File.join(new_dir, gem_filename)
|
82
|
+
|
83
|
+
if options[:original_gem_file]
|
84
|
+
FileUtils.copy_file(options[:original_gem_file], old_file)
|
85
|
+
else
|
86
|
+
download_gem(gem_name, gem_version, old_file)
|
87
|
+
end
|
88
|
+
|
89
|
+
rg_version = rubygems_version(old_file)
|
90
|
+
unless rg_version == Gem::VERSION
|
91
|
+
alert_error <<-EOF
|
92
|
+
You need to use the same RubyGems version #{gem_name} v#{gem_version} was built with.
|
93
|
+
|
94
|
+
#{gem_name} v#{gem_version} was built using RubyGems v#{rg_version}.
|
95
|
+
Gem files include the version of RubyGems used to build them.
|
96
|
+
This means in order to reproduce #{gem_filename}, you must also use RubyGems v#{rg_version}.
|
97
|
+
|
98
|
+
You're using RubyGems v#{Gem::VERSION}.
|
99
|
+
|
100
|
+
Please install RubyGems v#{rg_version} and try again.
|
101
|
+
EOF
|
102
|
+
terminate_interaction 1
|
103
|
+
end
|
104
|
+
|
105
|
+
source_date_epoch = get_timestamp(old_file).to_s
|
106
|
+
|
107
|
+
if build_path = options[:build_path]
|
108
|
+
Dir.chdir(build_path) { build_gem(gem_name, source_date_epoch, new_file) }
|
109
|
+
else
|
110
|
+
build_gem(gem_name, source_date_epoch, new_file)
|
111
|
+
end
|
112
|
+
|
113
|
+
compare(source_date_epoch, old_file, new_file)
|
114
|
+
end
|
115
|
+
|
116
|
+
private
|
117
|
+
|
118
|
+
def sha256(file)
|
119
|
+
Digest::SHA256.hexdigest(Gem.read_binary(file))
|
120
|
+
end
|
121
|
+
|
122
|
+
def get_timestamp(file)
|
123
|
+
mtime = nil
|
124
|
+
File.open(file, Gem.binary_mode) do |f|
|
125
|
+
Gem::Package::TarReader.new(f) do |tar|
|
126
|
+
mtime = tar.seek("metadata.gz") {|tf| tf.header.mtime }
|
127
|
+
end
|
128
|
+
end
|
129
|
+
|
130
|
+
mtime
|
131
|
+
end
|
132
|
+
|
133
|
+
def compare(source_date_epoch, old_file, new_file)
|
134
|
+
date = Time.at(source_date_epoch.to_i).strftime("%F %T %Z")
|
135
|
+
|
136
|
+
old_hash = sha256(old_file)
|
137
|
+
new_hash = sha256(new_file)
|
138
|
+
|
139
|
+
say
|
140
|
+
say "Built at: #{date} (#{source_date_epoch})"
|
141
|
+
say "Original build saved to: #{old_file}"
|
142
|
+
say "Reproduced build saved to: #{new_file}"
|
143
|
+
say "Working directory: #{options[:build_path] || Dir.pwd}"
|
144
|
+
say
|
145
|
+
say "Hash comparison:"
|
146
|
+
say " #{old_hash}\t#{old_file}"
|
147
|
+
say " #{new_hash}\t#{new_file}"
|
148
|
+
say
|
149
|
+
|
150
|
+
if old_hash == new_hash
|
151
|
+
say "SUCCESS - original and rebuild hashes matched"
|
152
|
+
else
|
153
|
+
say "FAILURE - original and rebuild hashes did not match"
|
154
|
+
say
|
155
|
+
|
156
|
+
if options[:diff]
|
157
|
+
if system("diffoscope", old_file, new_file).nil?
|
158
|
+
alert_error "error: could not find `diffoscope` executable"
|
159
|
+
end
|
160
|
+
else
|
161
|
+
say "Pass --diff for more details (requires diffoscope to be installed)."
|
162
|
+
end
|
163
|
+
|
164
|
+
terminate_interaction 1
|
165
|
+
end
|
166
|
+
end
|
167
|
+
|
168
|
+
def prep_dirs
|
169
|
+
rebuild_dir = Dir.mktmpdir("gem_rebuild")
|
170
|
+
old_dir = File.join(rebuild_dir, "old")
|
171
|
+
new_dir = File.join(rebuild_dir, "new")
|
172
|
+
|
173
|
+
FileUtils.mkdir_p(old_dir)
|
174
|
+
FileUtils.mkdir_p(new_dir)
|
175
|
+
|
176
|
+
[old_dir, new_dir]
|
177
|
+
end
|
178
|
+
|
179
|
+
def get_gem_name_and_version
|
180
|
+
args = options[:args] || []
|
181
|
+
if args.length == 2
|
182
|
+
gem_name, gem_version = args
|
183
|
+
elsif args.length > 2
|
184
|
+
raise Gem::CommandLineError, "Too many arguments"
|
185
|
+
else
|
186
|
+
raise Gem::CommandLineError, "Expected GEM_NAME and GEM_VERSION arguments (gem rebuild GEM_NAME GEM_VERSION)"
|
187
|
+
end
|
188
|
+
|
189
|
+
[gem_name, gem_version]
|
190
|
+
end
|
191
|
+
|
192
|
+
def build_gem(gem_name, source_date_epoch, output_file)
|
193
|
+
gemspec = options[:gemspec_file] || find_gemspec("#{gem_name}.gemspec")
|
194
|
+
|
195
|
+
if gemspec
|
196
|
+
build_package(gemspec, source_date_epoch, output_file)
|
197
|
+
else
|
198
|
+
alert_error error_message(gem_name)
|
199
|
+
terminate_interaction(1)
|
200
|
+
end
|
201
|
+
end
|
202
|
+
|
203
|
+
def build_package(gemspec, source_date_epoch, output_file)
|
204
|
+
with_source_date_epoch(source_date_epoch) do
|
205
|
+
spec = Gem::Specification.load(gemspec)
|
206
|
+
if spec
|
207
|
+
Gem::Package.build(
|
208
|
+
spec,
|
209
|
+
options[:force],
|
210
|
+
options[:strict],
|
211
|
+
output_file
|
212
|
+
)
|
213
|
+
else
|
214
|
+
alert_error "Error loading gemspec. Aborting."
|
215
|
+
terminate_interaction 1
|
216
|
+
end
|
217
|
+
end
|
218
|
+
end
|
219
|
+
|
220
|
+
def with_source_date_epoch(source_date_epoch)
|
221
|
+
old_sde = ENV["SOURCE_DATE_EPOCH"]
|
222
|
+
ENV["SOURCE_DATE_EPOCH"] = source_date_epoch.to_s
|
223
|
+
|
224
|
+
yield
|
225
|
+
ensure
|
226
|
+
ENV["SOURCE_DATE_EPOCH"] = old_sde
|
227
|
+
end
|
228
|
+
|
229
|
+
def error_message(gem_name)
|
230
|
+
if gem_name
|
231
|
+
"Couldn't find a gemspec file matching '#{gem_name}' in #{Dir.pwd}"
|
232
|
+
else
|
233
|
+
"Couldn't find a gemspec file in #{Dir.pwd}"
|
234
|
+
end
|
235
|
+
end
|
236
|
+
|
237
|
+
def download_gem(gem_name, gem_version, old_file)
|
238
|
+
# This code was based loosely off the `gem fetch` command.
|
239
|
+
version = "= #{gem_version}"
|
240
|
+
dep = Gem::Dependency.new gem_name, version
|
241
|
+
|
242
|
+
specs_and_sources, errors =
|
243
|
+
Gem::SpecFetcher.fetcher.spec_for_dependency dep
|
244
|
+
|
245
|
+
# There should never be more than one item in specs_and_sources,
|
246
|
+
# since we search for an exact version.
|
247
|
+
spec, source = specs_and_sources[0]
|
248
|
+
|
249
|
+
if spec.nil?
|
250
|
+
show_lookup_failure gem_name, version, errors, options[:domain]
|
251
|
+
terminate_interaction 1
|
252
|
+
end
|
253
|
+
|
254
|
+
download_path = source.download spec
|
255
|
+
|
256
|
+
FileUtils.move(download_path, old_file)
|
257
|
+
|
258
|
+
say "Downloaded #{gem_name} version #{gem_version} as #{old_file}."
|
259
|
+
end
|
260
|
+
|
261
|
+
def rubygems_version(gem_file)
|
262
|
+
Gem::Package.new(gem_file).spec.rubygems_version
|
263
|
+
end
|
264
|
+
end
|
data/lib/rubygems/config_file.rb
CHANGED
@@ -202,21 +202,33 @@ class Gem::ConfigFile
|
|
202
202
|
@hash = @hash.merge environment_config
|
203
203
|
end
|
204
204
|
|
205
|
+
@hash.transform_keys! do |k|
|
206
|
+
# gemhome and gempath are not working with symbol keys
|
207
|
+
if %w[backtrace bulk_threshold verbose update_sources cert_expiration_length_days
|
208
|
+
install_extension_in_lib ipv4_fallback_enabled sources disable_default_gem_server
|
209
|
+
ssl_verify_mode ssl_ca_cert ssl_client_cert].include?(k)
|
210
|
+
k.to_sym
|
211
|
+
else
|
212
|
+
k
|
213
|
+
end
|
214
|
+
end
|
215
|
+
|
205
216
|
# HACK: these override command-line args, which is bad
|
206
217
|
@backtrace = @hash[:backtrace] if @hash.key? :backtrace
|
207
218
|
@bulk_threshold = @hash[:bulk_threshold] if @hash.key? :bulk_threshold
|
208
|
-
@home = @hash[:gemhome] if @hash.key? :gemhome
|
209
|
-
@path = @hash[:gempath] if @hash.key? :gempath
|
210
|
-
@update_sources = @hash[:update_sources] if @hash.key? :update_sources
|
211
219
|
@verbose = @hash[:verbose] if @hash.key? :verbose
|
212
|
-
@
|
213
|
-
|
220
|
+
@update_sources = @hash[:update_sources] if @hash.key? :update_sources
|
221
|
+
# TODO: We should handle concurrent_downloads same as other options
|
214
222
|
@cert_expiration_length_days = @hash[:cert_expiration_length_days] if @hash.key? :cert_expiration_length_days
|
215
223
|
@ipv4_fallback_enabled = @hash[:ipv4_fallback_enabled] if @hash.key? :ipv4_fallback_enabled
|
216
224
|
|
217
|
-
@
|
218
|
-
@
|
219
|
-
@
|
225
|
+
@home = @hash[:gemhome] if @hash.key? :gemhome
|
226
|
+
@path = @hash[:gempath] if @hash.key? :gempath
|
227
|
+
@sources = @hash[:sources] if @hash.key? :sources
|
228
|
+
@disable_default_gem_server = @hash[:disable_default_gem_server] if @hash.key? :disable_default_gem_server
|
229
|
+
@ssl_verify_mode = @hash[:ssl_verify_mode] if @hash.key? :ssl_verify_mode
|
230
|
+
@ssl_ca_cert = @hash[:ssl_ca_cert] if @hash.key? :ssl_ca_cert
|
231
|
+
@ssl_client_cert = @hash[:ssl_client_cert] if @hash.key? :ssl_client_cert
|
220
232
|
|
221
233
|
@api_keys = nil
|
222
234
|
@rubygems_api_key = nil
|
data/lib/rubygems/defaults.rb
CHANGED
@@ -112,7 +112,7 @@ module Gem
|
|
112
112
|
# The path to standard location of the user's configuration directory.
|
113
113
|
|
114
114
|
def self.config_home
|
115
|
-
@config_home ||=
|
115
|
+
@config_home ||= ENV["XDG_CONFIG_HOME"] || File.join(Gem.user_home, ".config")
|
116
116
|
end
|
117
117
|
|
118
118
|
##
|
@@ -145,21 +145,21 @@ module Gem
|
|
145
145
|
# The path to standard location of the user's cache directory.
|
146
146
|
|
147
147
|
def self.cache_home
|
148
|
-
@cache_home ||=
|
148
|
+
@cache_home ||= ENV["XDG_CACHE_HOME"] || File.join(Gem.user_home, ".cache")
|
149
149
|
end
|
150
150
|
|
151
151
|
##
|
152
152
|
# The path to standard location of the user's data directory.
|
153
153
|
|
154
154
|
def self.data_home
|
155
|
-
@data_home ||=
|
155
|
+
@data_home ||= ENV["XDG_DATA_HOME"] || File.join(Gem.user_home, ".local", "share")
|
156
156
|
end
|
157
157
|
|
158
158
|
##
|
159
159
|
# The path to standard location of the user's state directory.
|
160
160
|
|
161
161
|
def self.state_home
|
162
|
-
@state_home ||=
|
162
|
+
@state_home ||= ENV["XDG_STATE_HOME"] || File.join(Gem.user_home, ".local", "state")
|
163
163
|
end
|
164
164
|
|
165
165
|
##
|
data/lib/rubygems/dependency.rb
CHANGED
@@ -328,9 +328,9 @@ class Gem::Dependency
|
|
328
328
|
return active if active
|
329
329
|
|
330
330
|
unless prerelease?
|
331
|
-
#
|
331
|
+
# Consider prereleases only as a fallback
|
332
332
|
pre, matches = matches.partition {|spec| spec.version.prerelease? }
|
333
|
-
matches
|
333
|
+
matches = pre if matches.empty?
|
334
334
|
end
|
335
335
|
|
336
336
|
matches.first
|
@@ -293,7 +293,7 @@ EOF
|
|
293
293
|
|
294
294
|
case var_name
|
295
295
|
# On windows, it is assumed that mkmf has setup an exports file for the
|
296
|
-
# extension, so we have to
|
296
|
+
# extension, so we have to create one ourselves.
|
297
297
|
when "DEFFILE"
|
298
298
|
write_deffile(dest_dir, crate_name)
|
299
299
|
else
|
@@ -85,7 +85,7 @@ module Gem::GemcutterUtilities
|
|
85
85
|
# If +allowed_push_host+ metadata is present, then it will only allow that host.
|
86
86
|
|
87
87
|
def rubygems_api_request(method, path, host = nil, allowed_push_host = nil, scope: nil, credentials: {}, &block)
|
88
|
-
require_relative "
|
88
|
+
require_relative "vendored_net_http"
|
89
89
|
|
90
90
|
self.host = host if host
|
91
91
|
unless self.host
|
@@ -0,0 +1,19 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require_relative "../rubygems"
|
4
|
+
|
5
|
+
##
|
6
|
+
# Mixin methods for commands that work with gemspecs.
|
7
|
+
|
8
|
+
module Gem::GemspecHelpers
|
9
|
+
def find_gemspec(glob = "*.gemspec")
|
10
|
+
gemspecs = Dir.glob(glob).sort
|
11
|
+
|
12
|
+
if gemspecs.size > 1
|
13
|
+
alert_error "Multiple gemspecs found: #{gemspecs}, please specify one"
|
14
|
+
terminate_interaction(1)
|
15
|
+
end
|
16
|
+
|
17
|
+
gemspecs.first
|
18
|
+
end
|
19
|
+
end
|
data/lib/rubygems/package.rb
CHANGED
@@ -59,7 +59,7 @@ class Gem::Package
|
|
59
59
|
|
60
60
|
def initialize(message, source = nil)
|
61
61
|
if source
|
62
|
-
@path = source.path
|
62
|
+
@path = source.is_a?(String) ? source : source.path
|
63
63
|
|
64
64
|
message += " in #{path}" if path
|
65
65
|
end
|
@@ -454,7 +454,7 @@ EOM
|
|
454
454
|
|
455
455
|
if entry.file?
|
456
456
|
File.open(destination, "wb") {|out| copy_stream(entry, out) }
|
457
|
-
FileUtils.chmod file_mode(entry.header.mode), destination
|
457
|
+
FileUtils.chmod file_mode(entry.header.mode) & ~File.umask, destination
|
458
458
|
end
|
459
459
|
|
460
460
|
verbose destination
|
@@ -74,7 +74,7 @@ class Gem::RemoteFetcher
|
|
74
74
|
|
75
75
|
def initialize(proxy=nil, dns=nil, headers={})
|
76
76
|
require_relative "core_ext/tcpsocket_init" if Gem.configuration.ipv4_fallback_enabled
|
77
|
-
require_relative "
|
77
|
+
require_relative "vendored_net_http"
|
78
78
|
require "stringio"
|
79
79
|
require_relative "vendor/uri/lib/uri"
|
80
80
|
|
data/lib/rubygems/request.rb
CHANGED
data/lib/rubygems/request_set.rb
CHANGED
data/lib/rubygems/safe_yaml.rb
CHANGED
@@ -25,8 +25,17 @@ module Gem
|
|
25
25
|
runtime
|
26
26
|
].freeze
|
27
27
|
|
28
|
+
@aliases_enabled = true
|
29
|
+
def self.aliases_enabled=(value) # :nodoc:
|
30
|
+
@aliases_enabled = !!value
|
31
|
+
end
|
32
|
+
|
33
|
+
def self.aliases_enabled? # :nodoc:
|
34
|
+
@aliases_enabled
|
35
|
+
end
|
36
|
+
|
28
37
|
def self.safe_load(input)
|
29
|
-
::Psych.safe_load(input, permitted_classes: PERMITTED_CLASSES, permitted_symbols: PERMITTED_SYMBOLS, aliases:
|
38
|
+
::Psych.safe_load(input, permitted_classes: PERMITTED_CLASSES, permitted_symbols: PERMITTED_SYMBOLS, aliases: @aliases_enabled)
|
30
39
|
end
|
31
40
|
|
32
41
|
def self.load(input)
|
data/lib/rubygems/security.rb
CHANGED
@@ -341,7 +341,7 @@ class Gem::Specification < Gem::BasicSpecification
|
|
341
341
|
# https://opensource.org/licenses/ approved.
|
342
342
|
#
|
343
343
|
# The most commonly used OSI-approved licenses are MIT and Apache-2.0.
|
344
|
-
# GitHub also provides a license picker at
|
344
|
+
# GitHub also provides a license picker at https://choosealicense.com/.
|
345
345
|
#
|
346
346
|
# You can also use a custom license file along with your gemspec and specify
|
347
347
|
# a LicenseRef-<idstring>, where idstring is the name of the file containing
|
@@ -7,7 +7,7 @@ class Gem::SpecificationPolicy
|
|
7
7
|
|
8
8
|
VALID_NAME_PATTERN = /\A[a-zA-Z0-9\.\-\_]+\z/ # :nodoc:
|
9
9
|
|
10
|
-
SPECIAL_CHARACTERS = /\A[#{Regexp.escape(
|
10
|
+
SPECIAL_CHARACTERS = /\A[#{Regexp.escape(".-_")}]+/ # :nodoc:
|
11
11
|
|
12
12
|
VALID_URI_PATTERN = %r{\Ahttps?:\/\/([^\s:@]+:[^\s:@]*@)?[A-Za-z\d\-]+(\.[A-Za-z\d\-]+)+\.?(:\d{1,5})?([\/?]\S*)?\z} # :nodoc:
|
13
13
|
|
@@ -103,6 +103,8 @@ class Gem::SpecificationPolicy
|
|
103
103
|
|
104
104
|
validate_dependencies
|
105
105
|
|
106
|
+
validate_required_ruby_version
|
107
|
+
|
106
108
|
validate_extensions
|
107
109
|
|
108
110
|
validate_removed_attributes
|
@@ -227,6 +229,12 @@ duplicate dependency on #{dep}, (#{prev.requirement}) use:
|
|
227
229
|
end
|
228
230
|
end
|
229
231
|
|
232
|
+
def validate_required_ruby_version
|
233
|
+
if @specification.required_ruby_version.requirements == [Gem::Requirement::DefaultRequirement]
|
234
|
+
warning "make sure you specify the oldest ruby version constraint (like \">= 3.0\") that you want your gem to support by setting the `required_ruby_version` gemspec attribute"
|
235
|
+
end
|
236
|
+
end
|
237
|
+
|
230
238
|
##
|
231
239
|
# Issues a warning for each file to be packaged which is world-readable.
|
232
240
|
#
|