toy-executable-hooks 1.6.2.1
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 +7 -0
- data/.gitignore +5 -0
- data/.travis.yml +47 -0
- data/CHANGELOG.md +103 -0
- data/DEVELOPMENT.md +11 -0
- data/Gemfile +5 -0
- data/LICENSE +13 -0
- data/README.md +27 -0
- data/bin/executable-hooks-uninstaller +5 -0
- data/bin/ruby_executable_hooks +23 -0
- data/executable-hooks.gemspec +28 -0
- data/ext/wrapper_installer/extconf.rb +25 -0
- data/lib/executable-hooks/hooks.rb +54 -0
- data/lib/executable-hooks/installer.rb +100 -0
- data/lib/executable-hooks/regenerate_binstubs_command.rb +154 -0
- data/lib/executable-hooks/specification.rb +17 -0
- data/lib/executable-hooks/uninstaller.rb +14 -0
- data/lib/executable-hooks/version.rb +3 -0
- data/lib/executable-hooks/wrapper.rb +85 -0
- data/lib/rubygems_executable_plugin.rb +3 -0
- data/lib/rubygems_plugin.rb +29 -0
- data/test-tf/rubygems_comment_test.sh +15 -0
- data/test-tf-bundle/bundle_comment_test.sh +20 -0
- data/test-tf-truffleruby/truffleruby_comment_test.sh +16 -0
- metadata +85 -0
checksums.yaml
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
---
|
|
2
|
+
SHA256:
|
|
3
|
+
metadata.gz: 4228b8fc482489f26f465e9343a7f4cf8441c1028f8355a9b4eab920a3305bf9
|
|
4
|
+
data.tar.gz: f9724765c712ad7a708e2df328d684277426dc1e597e82ad5eee411f708c0a57
|
|
5
|
+
SHA512:
|
|
6
|
+
metadata.gz: bbb46a195def1f1d8fbb5498d832d00ebc1fbbfd7df426218d267c0485edbe27b70df9b64f7d52e69ae5fd7bc9534a6515c58378e625994dccc55ca6a79dfdcc
|
|
7
|
+
data.tar.gz: 6e089e4c1fca69a9518ab2621cd918e5f57de5d3a102f2d69aea8459c7ab7e4d1da68987ba97def73ece83ff6227d2ca95a2b06050008982064212b6dfa99256
|
data/.travis.yml
ADDED
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
language: ruby
|
|
2
|
+
rvm:
|
|
3
|
+
- jruby
|
|
4
|
+
- jruby-head
|
|
5
|
+
- rbx-3
|
|
6
|
+
before_install:
|
|
7
|
+
- 'rvm @global do gem uninstall -a -x rubygems-bundler executable-hooks || true'
|
|
8
|
+
- 'rm -f $(rvm @global do gem env home)/bin/jruby_executable_hooks'
|
|
9
|
+
- 'rm -rf $rvm_path/gems/*/{bin,gems}/rubygems-bundler-* $rvm_path/gems/*/{bin,gems}/executable-hooks-* $rvm_path/gems/*/bin/ruby_*_{wrapper,hooks}'
|
|
10
|
+
- hash -r
|
|
11
|
+
- 'if [[ -n "${WITH_RUBYGEMS:-}" ]] ; then gem update --system "${WITH_RUBYGEMS}" ; fi'
|
|
12
|
+
- gem build executable-hooks.gemspec
|
|
13
|
+
- gem install executable-hooks-$(awk -F'"' '/VERSION/{print $2}' < lib/executable-hooks/version.rb).gem --development
|
|
14
|
+
before_script:
|
|
15
|
+
- unset BUNDLE_GEMFILE
|
|
16
|
+
script: NOEXEC=0 tf --text test-tf${TEST_SUFFIX:-}/*
|
|
17
|
+
notifications:
|
|
18
|
+
irc:
|
|
19
|
+
channels:
|
|
20
|
+
- "irc.freenode.org#rubygems-bundler"
|
|
21
|
+
email:
|
|
22
|
+
recipients:
|
|
23
|
+
- mpapis@gmail.com
|
|
24
|
+
on_failure: change
|
|
25
|
+
matrix:
|
|
26
|
+
fast_finish: true
|
|
27
|
+
include:
|
|
28
|
+
- rvm: 1.8.7
|
|
29
|
+
env: WITH_RUBYGEMS=1.4.2
|
|
30
|
+
- rvm: 1.8.7
|
|
31
|
+
env: WITH_RUBYGEMS=1.6.2
|
|
32
|
+
- rvm: 2.5
|
|
33
|
+
env: TEST_SUFFIX=-bundle
|
|
34
|
+
- rvm: 2.5
|
|
35
|
+
env: TEST_SUFFIX=-truffleruby
|
|
36
|
+
- rvm: 1.8.7
|
|
37
|
+
- rvm: 1.9.2
|
|
38
|
+
- rvm: 1.9.3
|
|
39
|
+
- rvm: 2.0.0
|
|
40
|
+
- rvm: 2.1
|
|
41
|
+
- rvm: 2.2
|
|
42
|
+
- rvm: 2.3
|
|
43
|
+
- rvm: 2.4
|
|
44
|
+
- rvm: 2.5
|
|
45
|
+
- rvm: ruby-head
|
|
46
|
+
allow_failures:
|
|
47
|
+
- rvm: rbx-3
|
data/CHANGELOG.md
ADDED
|
@@ -0,0 +1,103 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
## 1.6.2
|
|
4
|
+
date: 2021-01-26
|
|
5
|
+
|
|
6
|
+
- Converts end_with? to match for Ruby 1.8.6 compatibility #37
|
|
7
|
+
|
|
8
|
+
## 1.6.1
|
|
9
|
+
date: 2021-01-26
|
|
10
|
+
|
|
11
|
+
- Avoid Ruby 2.7 warning, merge #38
|
|
12
|
+
|
|
13
|
+
## 1.6.0
|
|
14
|
+
date: 2018-10-25
|
|
15
|
+
|
|
16
|
+
- Restore support for ruby-1.8.6, fixes #34
|
|
17
|
+
- Do not force overwrite wrapper, fixes #33
|
|
18
|
+
|
|
19
|
+
## 1.5.0
|
|
20
|
+
date: 2018-06-25
|
|
21
|
+
|
|
22
|
+
- Support truffleruby, fixes rvm/rvm#4408
|
|
23
|
+
|
|
24
|
+
## 1.4.2
|
|
25
|
+
date: 2018-02-14
|
|
26
|
+
|
|
27
|
+
- Support rubygems 1.4.2, fixes #29
|
|
28
|
+
|
|
29
|
+
## 1.4.1
|
|
30
|
+
date: 2018-02-12
|
|
31
|
+
|
|
32
|
+
- Fix bundle install, fixes #28
|
|
33
|
+
|
|
34
|
+
## 1.4.0
|
|
35
|
+
date: 2018-02-08
|
|
36
|
+
|
|
37
|
+
- Add bindir support, fixes #24
|
|
38
|
+
|
|
39
|
+
## 1.3.2
|
|
40
|
+
date: 2014-06-06
|
|
41
|
+
|
|
42
|
+
- make sure executable mode is set on binaries when using fast fix, update wayneeseguin/rvm#2894
|
|
43
|
+
|
|
44
|
+
## 1.3.1
|
|
45
|
+
date: 2014-01-16
|
|
46
|
+
|
|
47
|
+
- do not hardcode env ruby_executable_hooks when using shortcut try_to_fix_binstubs, fix #12
|
|
48
|
+
|
|
49
|
+
## 1.3.0
|
|
50
|
+
date: 2014-01-11
|
|
51
|
+
|
|
52
|
+
- First try to fix binstubs before installing them, fix wayneeseguin/rvm#2536
|
|
53
|
+
|
|
54
|
+
## 1.2.6
|
|
55
|
+
date: 2013-10-21
|
|
56
|
+
|
|
57
|
+
- Remind users about regenerating binstubs "in case of problems", merge #11
|
|
58
|
+
|
|
59
|
+
## 1.2.5
|
|
60
|
+
date: 2013-10-12
|
|
61
|
+
|
|
62
|
+
- first try to create the bin dir then check if it is writable, update #9, update wayneeseguin/rvm#2277
|
|
63
|
+
|
|
64
|
+
## 1.2.4
|
|
65
|
+
date: 2013-10-10
|
|
66
|
+
|
|
67
|
+
- raise exception if can not write to bindir, fix #9
|
|
68
|
+
|
|
69
|
+
## 1.2.3
|
|
70
|
+
date: 2013-09-24
|
|
71
|
+
|
|
72
|
+
- fix detecting program name and system process title, fix #8, update #7, update #5
|
|
73
|
+
|
|
74
|
+
## 1.2.2
|
|
75
|
+
date: 2013-09-23
|
|
76
|
+
|
|
77
|
+
- change process title only when supported by Process, fix #7, update #5
|
|
78
|
+
|
|
79
|
+
## 1.2.1
|
|
80
|
+
date: 2013-09-22
|
|
81
|
+
|
|
82
|
+
- fix installing wrapper when first time installing the gem, fix #6
|
|
83
|
+
|
|
84
|
+
## 1.2.0
|
|
85
|
+
date: 2013-09-17
|
|
86
|
+
|
|
87
|
+
- fix full program name with params, fix #5
|
|
88
|
+
- RG 2.1 introduces find_latest_files
|
|
89
|
+
- add license to gemspec, fix #4
|
|
90
|
+
|
|
91
|
+
## 1.1.0
|
|
92
|
+
date: 2013-07-11
|
|
93
|
+
|
|
94
|
+
- fix hooks for older rubygems versions
|
|
95
|
+
- add regenerating wrappers on gem installation, closes #2
|
|
96
|
+
- fix uninstaller
|
|
97
|
+
- honor the program suffix, fix #3
|
|
98
|
+
- add a warning for custom custom_shebang, fix #1
|
|
99
|
+
|
|
100
|
+
## 1.0.0
|
|
101
|
+
date: 2013-07-10
|
|
102
|
+
|
|
103
|
+
- extracted hooking to rubygems executables from https://github.com/mpapis/rubygems-bundler
|
data/DEVELOPMENT.md
ADDED
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
# Releasing
|
|
2
|
+
|
|
3
|
+
- update `lib/executable-hooks/version.rb` with new version (use semantic versioning)
|
|
4
|
+
- update `CHANGELOG.md` with changes relevant to running hooks
|
|
5
|
+
- git commit changes with version as comment
|
|
6
|
+
- git tag version
|
|
7
|
+
- `git push`
|
|
8
|
+
- `git push --tags`
|
|
9
|
+
- use ruby 1.8.7 for releasing `rvm use 1.8.7 --install`
|
|
10
|
+
- `gem build executable-hooks.gemspec`
|
|
11
|
+
- `gem push executable-hooks-1.6.1.gem` - update version
|
data/Gemfile
ADDED
data/LICENSE
ADDED
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
Copyright (c) 2013-2014 Michal Papis
|
|
2
|
+
|
|
3
|
+
Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
+
you may not use this file except in compliance with the License.
|
|
5
|
+
You may obtain a copy of the License at
|
|
6
|
+
|
|
7
|
+
http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
+
|
|
9
|
+
Unless required by applicable law or agreed to in writing, software
|
|
10
|
+
distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
+
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
+
See the License for the specific language governing permissions and
|
|
13
|
+
limitations under the License.
|
data/README.md
ADDED
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
# Rubygems executable hooks
|
|
2
|
+
|
|
3
|
+
Add next rubygems plugin support for executables.
|
|
4
|
+
|
|
5
|
+
## Usage
|
|
6
|
+
|
|
7
|
+
Install the gem:
|
|
8
|
+
|
|
9
|
+
gem install executable-hooks
|
|
10
|
+
|
|
11
|
+
In gem `lib` dir create `rubygems_executable_plugin.rb`:
|
|
12
|
+
|
|
13
|
+
Gem.execute do |original_file|
|
|
14
|
+
warn("Executing: #{original_file}")
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
Generate and install the new gem with executable hook.
|
|
18
|
+
|
|
19
|
+
Now try it:
|
|
20
|
+
|
|
21
|
+
gem install haml
|
|
22
|
+
haml --version
|
|
23
|
+
|
|
24
|
+
Returns:
|
|
25
|
+
|
|
26
|
+
Executing: /home/mpapis/.rvm/gems/ruby-1.8.7-p374-new1/bin/haml
|
|
27
|
+
Haml 4.0.3
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
|
|
3
|
+
title = "ruby #{ARGV*" "}"
|
|
4
|
+
$0 = ARGV.shift
|
|
5
|
+
Process.setproctitle(title) if Process.methods.include?(:setproctitle)
|
|
6
|
+
|
|
7
|
+
require 'rubygems'
|
|
8
|
+
begin
|
|
9
|
+
require 'executable-hooks/hooks'
|
|
10
|
+
Gem::ExecutableHooks.run($0)
|
|
11
|
+
rescue LoadError
|
|
12
|
+
warn "unable to load executable-hooks/hooks" if ENV.key?('ExecutableHooks_DEBUG')
|
|
13
|
+
end unless $0.match(/\/executable-hooks-uninstaller$/)
|
|
14
|
+
|
|
15
|
+
content = File.read($0)
|
|
16
|
+
|
|
17
|
+
if (index = content.index("\n#!ruby\n")) && index > 0
|
|
18
|
+
skipped_content = content.slice!(0..index)
|
|
19
|
+
start_line = skipped_content.count("\n") + 1
|
|
20
|
+
eval content, binding, $0, start_line
|
|
21
|
+
else
|
|
22
|
+
eval content, binding, $0
|
|
23
|
+
end
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
# -*- encoding: utf-8 -*-
|
|
3
|
+
|
|
4
|
+
Kernel.load(File.expand_path("../lib/executable-hooks/version.rb", __FILE__))
|
|
5
|
+
|
|
6
|
+
Gem::Specification.new do |s|
|
|
7
|
+
s.name = "toy-executable-hooks"
|
|
8
|
+
s.version = ExecutableHooks::VERSION
|
|
9
|
+
s.license = 'Apache 2.0'
|
|
10
|
+
s.authors = ["Michal Papis"]
|
|
11
|
+
s.email = ["mpapis@gmail.com"]
|
|
12
|
+
s.homepage = "https://github.com/rvm/executable-hooks"
|
|
13
|
+
s.summary = %q{
|
|
14
|
+
Hook into rubygems executables allowing extra actions to be taken before executable is run.
|
|
15
|
+
}
|
|
16
|
+
s.post_install_message = <<-MESSAGE
|
|
17
|
+
# In case of problems run the following command to update binstubs:
|
|
18
|
+
gem regenerate_binstubs
|
|
19
|
+
MESSAGE
|
|
20
|
+
|
|
21
|
+
|
|
22
|
+
s.files = `git ls-files`.split("\n")
|
|
23
|
+
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
|
24
|
+
s.extensions = %w( ext/wrapper_installer/extconf.rb )
|
|
25
|
+
s.executables = %w( executable-hooks-uninstaller )
|
|
26
|
+
|
|
27
|
+
s.add_development_dependency "tf", "~>0.4"
|
|
28
|
+
end
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
# Fake building extension
|
|
2
|
+
File.open('Makefile', 'w') { |f| f.write("all:\n\ninstall:\n\n") }
|
|
3
|
+
File.open('make', 'w') do |f|
|
|
4
|
+
f.write('#!/bin/sh')
|
|
5
|
+
f.chmod(f.stat.mode | 0111)
|
|
6
|
+
end
|
|
7
|
+
File.open('wrapper_installer.so', 'w') {}
|
|
8
|
+
File.open('wrapper_installer.dll', 'w') {}
|
|
9
|
+
File.open('nmake.bat', 'w') { |f| }
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
# add the gem to load path
|
|
13
|
+
$: << File.expand_path("../../../lib", __FILE__)
|
|
14
|
+
# load the actions
|
|
15
|
+
require 'executable-hooks/wrapper'
|
|
16
|
+
require 'executable-hooks/regenerate_binstubs_command'
|
|
17
|
+
# call the actions
|
|
18
|
+
options = RegenerateBinstubsCommand.default_install_options
|
|
19
|
+
ExecutableHooks::Wrapper.new(options).install_from(File.expand_path("../../..", __FILE__))
|
|
20
|
+
RegenerateBinstubsCommand.new.execute_no_wrapper
|
|
21
|
+
# unload the path, what was required stays ... but there is that much we can do
|
|
22
|
+
$:.pop
|
|
23
|
+
|
|
24
|
+
# just in case - it worked
|
|
25
|
+
true
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
module Gem
|
|
2
|
+
@executables_hooks ||= []
|
|
3
|
+
|
|
4
|
+
class << self
|
|
5
|
+
unless method_defined?(:execute)
|
|
6
|
+
def execute(&hook)
|
|
7
|
+
@executables_hooks << hook
|
|
8
|
+
end
|
|
9
|
+
|
|
10
|
+
attr_reader :executables_hooks
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
unless method_defined?(:load_executable_plugins)
|
|
14
|
+
def load_executable_plugins
|
|
15
|
+
if ENV['RUBYGEMS_LOAD_ALL_PLUGINS']
|
|
16
|
+
load_plugin_files find_files('rubygems_executable_plugin', false)
|
|
17
|
+
else
|
|
18
|
+
begin
|
|
19
|
+
load_plugin_files find_latest_files('rubygems_executable_plugin', false)
|
|
20
|
+
rescue NoMethodError
|
|
21
|
+
load_plugin_files find_files('rubygems_executable_plugin', false)
|
|
22
|
+
end
|
|
23
|
+
end
|
|
24
|
+
rescue ArgumentError, NoMethodError
|
|
25
|
+
# old rubygems
|
|
26
|
+
plugins = find_files('rubygems_executable_plugin')
|
|
27
|
+
|
|
28
|
+
plugins.each do |plugin|
|
|
29
|
+
|
|
30
|
+
# Skip older versions of the GemCutter plugin: Its commands are in
|
|
31
|
+
# RubyGems proper now.
|
|
32
|
+
|
|
33
|
+
next if plugin =~ /gemcutter-0\.[0-3]/
|
|
34
|
+
|
|
35
|
+
begin
|
|
36
|
+
load plugin
|
|
37
|
+
rescue ::Exception => e
|
|
38
|
+
details = "#{plugin.inspect}: #{e.message} (#{e.class})"
|
|
39
|
+
warn "Error loading RubyGems plugin #{details}"
|
|
40
|
+
end
|
|
41
|
+
end
|
|
42
|
+
end
|
|
43
|
+
end
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
class ExecutableHooks
|
|
47
|
+
def self.run(original_file)
|
|
48
|
+
Gem.load_executable_plugins
|
|
49
|
+
Gem.executables_hooks.each do |hook|
|
|
50
|
+
hook.call(original_file)
|
|
51
|
+
end
|
|
52
|
+
end
|
|
53
|
+
end
|
|
54
|
+
end
|
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
module ExecutableHooksInstaller
|
|
2
|
+
# Iterate through executables and generate wrapper for each one,
|
|
3
|
+
# extract of rubygems code
|
|
4
|
+
def self.bundler_generate_bin(inst)
|
|
5
|
+
return if inst.spec.executables.nil?
|
|
6
|
+
executables = inst.spec.executables.reject{ |name| name == 'executable-hooks-uninstaller' }
|
|
7
|
+
return if executables.empty?
|
|
8
|
+
bindir = inst.bin_dir ? inst.bin_dir : Gem.bindir(inst.gem_home)
|
|
9
|
+
executables.each do |filename|
|
|
10
|
+
filename.untaint
|
|
11
|
+
original = File.join bindir, filename
|
|
12
|
+
if File.exists?( original )
|
|
13
|
+
bin_script_path = File.join bindir, inst.formatted_program_filename(filename)
|
|
14
|
+
FileUtils.rm_f bin_script_path
|
|
15
|
+
File.open bin_script_path, 'wb', 0755 do |file|
|
|
16
|
+
file.print bundler_app_script_text(inst, filename)
|
|
17
|
+
end
|
|
18
|
+
inst.say bin_script_path if Gem.configuration.really_verbose
|
|
19
|
+
else
|
|
20
|
+
inst.say "Can not find #{inst.spec.name} in GEM_PATH"
|
|
21
|
+
break
|
|
22
|
+
end
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
|
|
27
|
+
def self.shebang(inst, bin_file_name)
|
|
28
|
+
# options were defined first in 1.5, we want to support back to 1.3.7
|
|
29
|
+
ruby_name = Gem::ConfigMap[:ruby_install_name] if inst.instance_variable_get(:@env_shebang)
|
|
30
|
+
bindir = inst.bin_dir ? inst.bin_dir : Gem.bindir(inst.gem_home)
|
|
31
|
+
path = File.join bindir, inst.formatted_program_filename(bin_file_name)
|
|
32
|
+
first_line = File.open(path, "rb") {|file| file.gets}
|
|
33
|
+
|
|
34
|
+
if /\A#!/ =~ first_line then
|
|
35
|
+
# Preserve extra words on shebang line, like "-w". Thanks RPA.
|
|
36
|
+
shebang = first_line.sub(/\A\#!.*?ruby\S*((\s+\S+)+)/, "#!#{Gem.ruby}")
|
|
37
|
+
opts = $1
|
|
38
|
+
shebang.strip! # Avoid nasty ^M issues.
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
if which = Gem.configuration[:custom_shebang]
|
|
42
|
+
which = which.gsub(/\$(\w+)/) do
|
|
43
|
+
case $1
|
|
44
|
+
when "env"
|
|
45
|
+
env_path
|
|
46
|
+
when "ruby"
|
|
47
|
+
"#{Gem.ruby}#{opts}"
|
|
48
|
+
when "exec"
|
|
49
|
+
bin_file_name
|
|
50
|
+
when "name"
|
|
51
|
+
inst.spec.name
|
|
52
|
+
end
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
return "#!#{which}"
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
if not ruby_name then
|
|
59
|
+
"#!#{Gem.ruby}#{opts}"
|
|
60
|
+
elsif opts then
|
|
61
|
+
"#!/bin/sh\n'exec' #{ruby_name.dump} '-x' \"$0\" \"$@\"\n#{shebang}"
|
|
62
|
+
else
|
|
63
|
+
"#!#{env_path} #{ruby_name}"
|
|
64
|
+
end
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
def self.env_path
|
|
68
|
+
@env_path ||= Gem::Installer::ENV_PATHS.find {|path| File.executable?(path) }
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
# Return the text for an application file.
|
|
72
|
+
def self.bundler_app_script_text(inst, bin_file_name)
|
|
73
|
+
<<-TEXT
|
|
74
|
+
#{shebang(inst, bin_file_name)}
|
|
75
|
+
#
|
|
76
|
+
# This file was generated by RubyGems.
|
|
77
|
+
#
|
|
78
|
+
# The application '#{inst.spec.name}' is installed as part of a gem, and
|
|
79
|
+
# this file is here to facilitate running it.
|
|
80
|
+
#
|
|
81
|
+
|
|
82
|
+
require 'rubygems'
|
|
83
|
+
|
|
84
|
+
version = "#{Gem::Requirement.default}"
|
|
85
|
+
|
|
86
|
+
if ARGV.first =~ /^_(.*)_$/ and Gem::Version.correct? $1 then
|
|
87
|
+
version = $1
|
|
88
|
+
ARGV.shift
|
|
89
|
+
end
|
|
90
|
+
|
|
91
|
+
gem '#{inst.spec.name}', version
|
|
92
|
+
load Gem.bin_path('#{inst.spec.name}', '#{bin_file_name}', version)
|
|
93
|
+
TEXT
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
end
|
|
97
|
+
|
|
98
|
+
Gem.post_install do |inst|
|
|
99
|
+
ExecutableHooksInstaller.bundler_generate_bin(inst)
|
|
100
|
+
end
|
|
@@ -0,0 +1,154 @@
|
|
|
1
|
+
require 'rubygems/command_manager'
|
|
2
|
+
require 'rubygems/installer'
|
|
3
|
+
require 'rubygems/version'
|
|
4
|
+
require 'executable-hooks/wrapper'
|
|
5
|
+
|
|
6
|
+
class RegenerateBinstubsCommand < Gem::Command
|
|
7
|
+
def self.default_install_options
|
|
8
|
+
require 'rubygems/commands/install_command'
|
|
9
|
+
Gem::Command.extra_args = Gem.configuration[:gem]
|
|
10
|
+
config_args = Gem.configuration[:install]
|
|
11
|
+
config_args =
|
|
12
|
+
case config_args
|
|
13
|
+
when String
|
|
14
|
+
config_args.split ' '
|
|
15
|
+
else
|
|
16
|
+
Array(config_args)
|
|
17
|
+
end
|
|
18
|
+
Gem::Command.add_specific_extra_args 'install', config_args
|
|
19
|
+
ic = Gem::Commands::InstallCommand.new
|
|
20
|
+
ic.handle_options ["install"]
|
|
21
|
+
ic.options
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
def initialize
|
|
25
|
+
super 'regenerate_binstubs', 'Re run generation of executable wrappers for gems.'
|
|
26
|
+
|
|
27
|
+
add_option(:"Install/Update", '-i', '--install-dir DIR',
|
|
28
|
+
'Gem repository directory to get installed',
|
|
29
|
+
'gems') do |value, options|
|
|
30
|
+
options[:install_dir] = File.expand_path(value)
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
add_option(:"Install/Update", '-n', '--bindir DIR',
|
|
34
|
+
'Directory where binary files are',
|
|
35
|
+
'located') do |value, options|
|
|
36
|
+
options[:bin_dir] = File.expand_path(value)
|
|
37
|
+
end
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
def arguments # :nodoc:
|
|
41
|
+
"STRING start of gem name to regenerate binstubs"
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
def usage # :nodoc:
|
|
45
|
+
"#{program_name} [STRING]"
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
def defaults_str # :nodoc:
|
|
49
|
+
""
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
def description # :nodoc:
|
|
53
|
+
'Re run generation of executable wrappers for all gems. '+
|
|
54
|
+
'Wrappers will be compatible with both rubygems and bundler. '+
|
|
55
|
+
'The switcher is BUNDLE_GEMFILE environment variable, '+
|
|
56
|
+
'when set it switches to bundler mode, when not set, '+
|
|
57
|
+
'then the command will work as it was with pure rubygems.'
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
def execute
|
|
61
|
+
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('2.0.0') then
|
|
62
|
+
# https://github.com/rubygems/rubygems/issues/326
|
|
63
|
+
puts "try also: gem pristine --binstubs"
|
|
64
|
+
end
|
|
65
|
+
ExecutableHooks::Wrapper.new(options).install
|
|
66
|
+
execute_no_wrapper
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
def execute_no_wrapper(wrapper_name = ExecutableHooks::Wrapper.expanded_wrapper_name)
|
|
70
|
+
require 'executable-hooks/installer'
|
|
71
|
+
name = get_one_optional_argument || ''
|
|
72
|
+
specs = installed_gems.select{|spec| spec.name =~ /^#{name}/i }
|
|
73
|
+
specs.each do |spec|
|
|
74
|
+
executables = spec.executables.reject{ |name| name == 'executable-hooks-uninstaller' }
|
|
75
|
+
unless executables.empty?
|
|
76
|
+
try_to_fix_binstubs(spec, executables, wrapper_name) or
|
|
77
|
+
try_to_install_binstubs(spec) or
|
|
78
|
+
$stderr.puts "##{spec.name} #{spec.version} not found in GEM_PATH"
|
|
79
|
+
end
|
|
80
|
+
end
|
|
81
|
+
end
|
|
82
|
+
|
|
83
|
+
private
|
|
84
|
+
|
|
85
|
+
def try_to_fix_binstubs(spec, executables, wrapper_name)
|
|
86
|
+
executable_paths =
|
|
87
|
+
executables.map do |executable|
|
|
88
|
+
path = expanded_bin_paths.detect{|bin_path| File.exist?(File.join(bin_path, executable)) }
|
|
89
|
+
File.join(path, executable) if path
|
|
90
|
+
end
|
|
91
|
+
return false if executable_paths.include?(nil) # not found
|
|
92
|
+
executable_shebangs =
|
|
93
|
+
executable_paths.map do |path|
|
|
94
|
+
[path, File.readlines(path).map{|l|l.chomp}]
|
|
95
|
+
end
|
|
96
|
+
return false if executable_shebangs.detect{|path, lines| !(lines[0] =~ /^#!\//) }
|
|
97
|
+
puts "#{spec.name} #{spec.version}"
|
|
98
|
+
executable_mode = 0111
|
|
99
|
+
executable_shebangs.map do |path, lines|
|
|
100
|
+
lines[0] = "#!#{ExecutableHooksInstaller.env_path} #{wrapper_name}"
|
|
101
|
+
File.open(path, "w") do |file|
|
|
102
|
+
file.puts(lines)
|
|
103
|
+
end
|
|
104
|
+
mode = File.stat(path).mode
|
|
105
|
+
File.chmod(mode | executable_mode, path) if mode & executable_mode != executable_mode
|
|
106
|
+
end
|
|
107
|
+
end
|
|
108
|
+
|
|
109
|
+
def expanded_bin_paths
|
|
110
|
+
@expanded_bin_paths ||= begin
|
|
111
|
+
paths = expanded_gem_paths.map{|path| File.join(path, "bin") }
|
|
112
|
+
paths << RbConfig::CONFIG["bindir"]
|
|
113
|
+
# TODO: bindir from options?
|
|
114
|
+
paths
|
|
115
|
+
end
|
|
116
|
+
end
|
|
117
|
+
|
|
118
|
+
def try_to_install_binstubs(spec)
|
|
119
|
+
org_gem_path = options[:install_dir] || existing_gem_path(spec.full_name) || Gem.dir
|
|
120
|
+
cache_gem = File.join(org_gem_path, 'cache', spec.file_name)
|
|
121
|
+
if File.exist? cache_gem
|
|
122
|
+
puts "#{spec.name} #{spec.version}"
|
|
123
|
+
installer_method = Gem::Installer.respond_to?(:at) ? :at : :new
|
|
124
|
+
inst = Gem::Installer.public_send installer_method, Dir[cache_gem].first, :wrappers => true, :force => true, :install_dir => org_gem_path, :bin_dir => options[:bin_dir]
|
|
125
|
+
ExecutableHooksInstaller.bundler_generate_bin(inst)
|
|
126
|
+
else
|
|
127
|
+
false
|
|
128
|
+
end
|
|
129
|
+
end
|
|
130
|
+
|
|
131
|
+
def existing_gem_path(full_name)
|
|
132
|
+
expanded_gem_paths.find{|path| File.exists?(File.join(path, 'gems', full_name))}
|
|
133
|
+
end
|
|
134
|
+
|
|
135
|
+
def expanded_gem_paths
|
|
136
|
+
@expanded_gem_paths ||=
|
|
137
|
+
Gem.path.map do |path|
|
|
138
|
+
paths = [path]
|
|
139
|
+
while File.symlink?(path)
|
|
140
|
+
path = File.readlink(path)
|
|
141
|
+
paths << path
|
|
142
|
+
end
|
|
143
|
+
paths
|
|
144
|
+
end.flatten
|
|
145
|
+
end
|
|
146
|
+
|
|
147
|
+
def installed_gems
|
|
148
|
+
if Gem::VERSION > '1.8' then
|
|
149
|
+
Gem::Specification.to_a
|
|
150
|
+
else
|
|
151
|
+
Gem.source_index.map{|name,spec| spec}
|
|
152
|
+
end
|
|
153
|
+
end
|
|
154
|
+
end
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
module ExecutableHooks
|
|
2
|
+
module Specification
|
|
3
|
+
def self.find
|
|
4
|
+
@executable_hooks_spec ||=
|
|
5
|
+
if Gem::Specification.respond_to?(:find_by_name)
|
|
6
|
+
Gem::Specification.find_by_name("executable-hooks", ">=0", ">=0.alpha")
|
|
7
|
+
else
|
|
8
|
+
Gem.source_index.find_name("executable-hooks").last
|
|
9
|
+
end
|
|
10
|
+
rescue Gem::LoadError
|
|
11
|
+
nil
|
|
12
|
+
end
|
|
13
|
+
def self.version
|
|
14
|
+
find ? find.version.to_s : nil
|
|
15
|
+
end
|
|
16
|
+
end
|
|
17
|
+
end
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
require 'executable-hooks/wrapper'
|
|
2
|
+
require 'executable-hooks/regenerate_binstubs_command'
|
|
3
|
+
require 'rubygems/uninstaller'
|
|
4
|
+
|
|
5
|
+
module ExecutableHooks
|
|
6
|
+
def self.uninstall
|
|
7
|
+
Gem.configuration[:custom_shebang] = "$env #{Gem.default_exec_format % "ruby"}"
|
|
8
|
+
options = RegenerateBinstubsCommand.default_install_options
|
|
9
|
+
RegenerateBinstubsCommand.new.execute_no_wrapper("ruby")
|
|
10
|
+
ExecutableHooks::Wrapper.new(options).uninstall
|
|
11
|
+
options.merge!(:executables => true, :all => true, :ignore => true)
|
|
12
|
+
Gem::Uninstaller.new("executable-hooks", options).uninstall
|
|
13
|
+
end
|
|
14
|
+
end
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
# install / uninstall wrapper
|
|
2
|
+
require 'fileutils'
|
|
3
|
+
require 'rubygems'
|
|
4
|
+
require 'executable-hooks/specification'
|
|
5
|
+
|
|
6
|
+
module ExecutableHooks
|
|
7
|
+
class Wrapper
|
|
8
|
+
def self.wrapper_name
|
|
9
|
+
'ruby_executable_hooks'
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def self.expanded_wrapper_name
|
|
13
|
+
Gem.default_exec_format % self.wrapper_name
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
attr_reader :options
|
|
17
|
+
|
|
18
|
+
def initialize(options)
|
|
19
|
+
@options = options || RegenerateBinstubsCommand.default_install_options
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
def install
|
|
23
|
+
@bindir = options[:bin_dir] if options[:bin_dir]
|
|
24
|
+
ensure_custom_shebang
|
|
25
|
+
|
|
26
|
+
executable_hooks_spec = ExecutableHooks::Specification.find
|
|
27
|
+
|
|
28
|
+
if executable_hooks_spec
|
|
29
|
+
install_from( executable_hooks_spec.full_gem_path )
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
def install_from(full_gem_path)
|
|
34
|
+
wrapper_path = File.expand_path( "bin/#{self.class.wrapper_name}", full_gem_path )
|
|
35
|
+
bindir = calculate_bindir(options)
|
|
36
|
+
destination = calculate_destination(bindir)
|
|
37
|
+
|
|
38
|
+
if File.exist?(wrapper_path) && !same_file(wrapper_path, destination)
|
|
39
|
+
FileUtils.mkdir_p(bindir) unless File.exist?(bindir)
|
|
40
|
+
# exception based on Gem::Installer.generate_bin
|
|
41
|
+
raise Gem::FilePermissionError.new(bindir) unless File.writable?(bindir)
|
|
42
|
+
FileUtils.cp(wrapper_path, destination)
|
|
43
|
+
File.chmod(0775, destination)
|
|
44
|
+
end
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
def same_file(file1, file2)
|
|
48
|
+
File.exist?(file1) && File.exist?(file2) &&
|
|
49
|
+
File.read(file1) == File.read(file2)
|
|
50
|
+
end
|
|
51
|
+
private :same_file
|
|
52
|
+
|
|
53
|
+
def uninstall
|
|
54
|
+
destination = calculate_destination(calculate_bindir(options))
|
|
55
|
+
FileUtils.rm_f(destination) if File.exist?(destination)
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
def calculate_bindir(options)
|
|
59
|
+
return options[:bin_dir] if options[:bin_dir]
|
|
60
|
+
Gem.respond_to?(:bindir,true) ? Gem.send(:bindir) : File.join(Gem.dir, 'bin')
|
|
61
|
+
end
|
|
62
|
+
|
|
63
|
+
def calculate_destination(bindir)
|
|
64
|
+
File.expand_path(self.class.expanded_wrapper_name, bindir)
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
|
|
68
|
+
def ensure_custom_shebang
|
|
69
|
+
expected_shebang = "$env #{self.class.expanded_wrapper_name}"
|
|
70
|
+
|
|
71
|
+
Gem.configuration[:custom_shebang] ||= expected_shebang
|
|
72
|
+
|
|
73
|
+
if Gem.configuration[:custom_shebang] != expected_shebang
|
|
74
|
+
warn("
|
|
75
|
+
Warning:
|
|
76
|
+
Found custom_shebang: '#{Gem.configuration[:custom_shebang]}',
|
|
77
|
+
Expected custom_shebang: '#{expected_shebang}',
|
|
78
|
+
this can potentially break 'executable-hooks' and gem executables overall!
|
|
79
|
+
Check your '~/.gemrc' and '/etc/gemrc' for 'custom_shebang' and remove it.
|
|
80
|
+
")
|
|
81
|
+
end
|
|
82
|
+
end
|
|
83
|
+
|
|
84
|
+
end
|
|
85
|
+
end
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
# Simulate require_relative - it's required as the plugin can be called in wrong version or from bundler.
|
|
2
|
+
require File.expand_path('../executable-hooks/specification.rb', __FILE__)
|
|
3
|
+
|
|
4
|
+
called_path, called_version = __FILE__.match(/^(.*\/executable-hooks-([^\/]+)\/lib).*$/)[1..2]
|
|
5
|
+
|
|
6
|
+
# continue only if loaded and called versions all the same, and not shared gems disabled in bundler
|
|
7
|
+
if
|
|
8
|
+
( $:.include?(called_path) || ExecutableHooks::Specification.version == called_version ) and
|
|
9
|
+
( !defined?(Bundler) || ( defined?(Bundler) && Bundler::SharedHelpers.in_bundle? && !Bundler.settings[:disable_shared_gems]) )
|
|
10
|
+
|
|
11
|
+
require 'rubygems/version'
|
|
12
|
+
require 'executable-hooks/wrapper'
|
|
13
|
+
|
|
14
|
+
# Set the custom_shebang if user did not set one
|
|
15
|
+
Gem.pre_install do |gem_installer|
|
|
16
|
+
options = if gem_installer.methods.map{|m|m.to_s}.include?('options')
|
|
17
|
+
gem_installer.options
|
|
18
|
+
end
|
|
19
|
+
ExecutableHooks::Wrapper.new(options).install
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
if Gem::Version.new(Gem::VERSION) < Gem::Version.new('2.0') then
|
|
23
|
+
# Add custom_shebang support to rubygems
|
|
24
|
+
require 'executable-hooks/installer'
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
require 'executable-hooks/regenerate_binstubs_command'
|
|
28
|
+
Gem::CommandManager.instance.register_command :regenerate_binstubs
|
|
29
|
+
end
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
gem install executable-hooks-$(awk -F'"' '/VERSION/{print $2}' < lib/executable-hooks/version.rb).gem --development
|
|
2
|
+
# match=/installed/
|
|
3
|
+
wrapper_name=$(ruby -I ./lib/ -r executable-hooks/wrapper -e "puts ExecutableHooks::Wrapper.expanded_wrapper_name")
|
|
4
|
+
|
|
5
|
+
gem install haml -v "<5" # match=/installed/
|
|
6
|
+
head -n 1 $(which haml ) # match=/ruby_executable_hooks/
|
|
7
|
+
which ${wrapper_name} # status=0
|
|
8
|
+
|
|
9
|
+
gem list # match=/haml/
|
|
10
|
+
executable-hooks-uninstaller # match=/haml/
|
|
11
|
+
|
|
12
|
+
head -n 1 $(which haml) # match!=/ruby_executable_hooks/
|
|
13
|
+
which ${wrapper_name} # status=1
|
|
14
|
+
|
|
15
|
+
gem uninstall -x haml # match=/Successfully uninstalled/
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
gem install executable-hooks-$(awk -F'"' '/VERSION/{print $2}' < lib/executable-hooks/version.rb).gem --development
|
|
2
|
+
# match=/installed/
|
|
3
|
+
gem install rubygems-bundler bundler
|
|
4
|
+
# match=/installed/
|
|
5
|
+
gem install haml -v "4.0.7" # match=/installed/
|
|
6
|
+
# match=/installed/
|
|
7
|
+
|
|
8
|
+
true TMPDIR:${TMPDIR:=/tmp}:
|
|
9
|
+
d=$TMPDIR/test-bundled
|
|
10
|
+
mkdir $d
|
|
11
|
+
pushd $d
|
|
12
|
+
|
|
13
|
+
NOEXEC=1 haml -v # match=/4.0.7/
|
|
14
|
+
|
|
15
|
+
echo -e 'source "https://rubygems.org"\ngem "haml", "4.0.6"' > Gemfile
|
|
16
|
+
bundle install # match=/haml 4.0.6/
|
|
17
|
+
NOEXEC=1 haml -v # match=/4.0.6/
|
|
18
|
+
|
|
19
|
+
popd
|
|
20
|
+
rm -rf $d
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
gem install executable-hooks-$(awk -F'"' '/VERSION/{print $2}' < lib/executable-hooks/version.rb).gem --development
|
|
2
|
+
# match=/installed/
|
|
3
|
+
|
|
4
|
+
gem install haml -v "4.0.7" # match=/installed/
|
|
5
|
+
haml_bin=$(which haml )
|
|
6
|
+
head -n 1 $haml_bin # match=/ruby_executable_hooks/
|
|
7
|
+
|
|
8
|
+
## simulate truffleruby style binary with shell code mixed in
|
|
9
|
+
## \043 - is a # ... somehow it breaks tf
|
|
10
|
+
( head -n 1 $haml_bin; echo -e 'echo $HOME\n\043!ruby'; tail -n +2 $haml_bin ) > $haml_bin.new
|
|
11
|
+
mv $haml_bin.new $haml_bin
|
|
12
|
+
chmod +x $haml_bin
|
|
13
|
+
|
|
14
|
+
haml _4.0.7_ -v # match=/4.0.7/
|
|
15
|
+
|
|
16
|
+
gem uninstall -x haml -v 4.0.7 # match=/Successfully uninstalled/
|
metadata
ADDED
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
|
2
|
+
name: toy-executable-hooks
|
|
3
|
+
version: !ruby/object:Gem::Version
|
|
4
|
+
version: 1.6.2.1
|
|
5
|
+
platform: ruby
|
|
6
|
+
authors:
|
|
7
|
+
- Michal Papis
|
|
8
|
+
autorequire:
|
|
9
|
+
bindir: bin
|
|
10
|
+
cert_chain: []
|
|
11
|
+
date: 2023-01-22 00:00:00.000000000 Z
|
|
12
|
+
dependencies:
|
|
13
|
+
- !ruby/object:Gem::Dependency
|
|
14
|
+
name: tf
|
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
|
16
|
+
requirements:
|
|
17
|
+
- - "~>"
|
|
18
|
+
- !ruby/object:Gem::Version
|
|
19
|
+
version: '0.4'
|
|
20
|
+
type: :development
|
|
21
|
+
prerelease: false
|
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
23
|
+
requirements:
|
|
24
|
+
- - "~>"
|
|
25
|
+
- !ruby/object:Gem::Version
|
|
26
|
+
version: '0.4'
|
|
27
|
+
description:
|
|
28
|
+
email:
|
|
29
|
+
- mpapis@gmail.com
|
|
30
|
+
executables:
|
|
31
|
+
- executable-hooks-uninstaller
|
|
32
|
+
extensions:
|
|
33
|
+
- ext/wrapper_installer/extconf.rb
|
|
34
|
+
extra_rdoc_files: []
|
|
35
|
+
files:
|
|
36
|
+
- ".gitignore"
|
|
37
|
+
- ".travis.yml"
|
|
38
|
+
- CHANGELOG.md
|
|
39
|
+
- DEVELOPMENT.md
|
|
40
|
+
- Gemfile
|
|
41
|
+
- LICENSE
|
|
42
|
+
- README.md
|
|
43
|
+
- bin/executable-hooks-uninstaller
|
|
44
|
+
- bin/ruby_executable_hooks
|
|
45
|
+
- executable-hooks.gemspec
|
|
46
|
+
- ext/wrapper_installer/extconf.rb
|
|
47
|
+
- lib/executable-hooks/hooks.rb
|
|
48
|
+
- lib/executable-hooks/installer.rb
|
|
49
|
+
- lib/executable-hooks/regenerate_binstubs_command.rb
|
|
50
|
+
- lib/executable-hooks/specification.rb
|
|
51
|
+
- lib/executable-hooks/uninstaller.rb
|
|
52
|
+
- lib/executable-hooks/version.rb
|
|
53
|
+
- lib/executable-hooks/wrapper.rb
|
|
54
|
+
- lib/rubygems_executable_plugin.rb
|
|
55
|
+
- lib/rubygems_plugin.rb
|
|
56
|
+
- test-tf-bundle/bundle_comment_test.sh
|
|
57
|
+
- test-tf-truffleruby/truffleruby_comment_test.sh
|
|
58
|
+
- test-tf/rubygems_comment_test.sh
|
|
59
|
+
homepage: https://github.com/rvm/executable-hooks
|
|
60
|
+
licenses:
|
|
61
|
+
- Apache 2.0
|
|
62
|
+
metadata: {}
|
|
63
|
+
post_install_message: |
|
|
64
|
+
# In case of problems run the following command to update binstubs:
|
|
65
|
+
gem regenerate_binstubs
|
|
66
|
+
rdoc_options: []
|
|
67
|
+
require_paths:
|
|
68
|
+
- lib
|
|
69
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
|
70
|
+
requirements:
|
|
71
|
+
- - ">="
|
|
72
|
+
- !ruby/object:Gem::Version
|
|
73
|
+
version: '0'
|
|
74
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
75
|
+
requirements:
|
|
76
|
+
- - ">="
|
|
77
|
+
- !ruby/object:Gem::Version
|
|
78
|
+
version: '0'
|
|
79
|
+
requirements: []
|
|
80
|
+
rubygems_version: 3.3.26
|
|
81
|
+
signing_key:
|
|
82
|
+
specification_version: 4
|
|
83
|
+
summary: Hook into rubygems executables allowing extra actions to be taken before
|
|
84
|
+
executable is run.
|
|
85
|
+
test_files: []
|