Class: Gem::Commands::UnpackCommand
- Inherits:
-
Gem::Command
- Object
- Gem::Command
- Gem::Commands::UnpackCommand
- Includes:
- VersionOption
- Defined in:
- lib/rubygems/commands/unpack_command.rb
Instance Attribute Summary
Attributes inherited from Gem::Command
#command, #defaults, #options, #program_name, #summary
Instance Method Summary collapse
-
#arguments ⇒ Object
:nodoc:.
-
#defaults_str ⇒ Object
:nodoc:.
- #description ⇒ Object
-
#execute ⇒ Object
– TODO: allow, e.g., ‘gem unpack rake-0.3.1’.
-
#find_in_cache(filename) ⇒ Object
Find cached filename in Gem.path.
-
#get_metadata(path) ⇒ Object
Extracts the Gem::Specification and raw metadata from the .gem file at
path
. -
#get_path(dependency) ⇒ Object
Return the full path to the cached gem file matching the given name and version requirement.
-
#initialize ⇒ UnpackCommand
constructor
A new instance of UnpackCommand.
-
#usage ⇒ Object
:nodoc:.
Methods included from VersionOption
#add_platform_option, #add_prerelease_option, #add_version_option
Methods inherited from Gem::Command
add_common_option, #add_extra_args, #add_option, add_specific_extra_args, #begins?, build_args, build_args=, common_options, extra_args, extra_args=, #get_all_gem_names, #get_all_gem_names_and_versions, #get_one_gem_name, #get_one_optional_argument, #handle_options, #handles?, #invoke, #invoke_with_build_args, #merge_options, #remove_option, #show_help, #show_lookup_failure, specific_extra_args, specific_extra_args_hash, #when_invoked
Methods included from UserInteraction
#alert, #alert_error, #alert_warning, #ask, #ask_for_password, #ask_yes_no, #choose_from_list, #say, #terminate_interaction, #verbose
Methods included from DefaultUserInteraction
ui, #ui, ui=, #ui=, use_ui, #use_ui
Constructor Details
#initialize ⇒ UnpackCommand
Returns a new instance of UnpackCommand.
11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
# File 'lib/rubygems/commands/unpack_command.rb', line 11 def initialize require 'fileutils' super 'unpack', 'Unpack an installed gem to the current directory', :version => Gem::Requirement.default, :target => Dir.pwd add_option('--target=DIR', 'target directory for unpacking') do |value, | [:target] = value end add_option('--spec', 'unpack the gem specification') do |value, | [:spec] = true end add_version_option end |
Instance Method Details
#arguments ⇒ Object
:nodoc:
30 31 32 |
# File 'lib/rubygems/commands/unpack_command.rb', line 30 def arguments # :nodoc: "GEMNAME name of gem to unpack" end |
#defaults_str ⇒ Object
:nodoc:
34 35 36 |
# File 'lib/rubygems/commands/unpack_command.rb', line 34 def defaults_str # :nodoc: "--version '#{Gem::Requirement.default}'" end |
#description ⇒ Object
38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 |
# File 'lib/rubygems/commands/unpack_command.rb', line 38 def description "The unpack command allows you to examine the contents of a gem or modify\nthem to help diagnose a bug.\n\nYou can add the contents of the unpacked gem to the load path using the\nRUBYLIB environment variable or -I:\n\n$ gem unpack my_gem\nUnpacked gem: '.../my_gem-1.0'\n[edit my_gem-1.0/lib/my_gem.rb]\n$ ruby -Imy_gem-1.0/lib -S other_program\n\nYou can repackage an unpacked gem using the build command. See the build\ncommand help for an example.\n EOF\nend\n" |
#execute ⇒ Object
– TODO: allow, e.g., ‘gem unpack rake-0.3.1’. Find a general solution for this, so that it works for uninstall as well. (And check other commands at the same time.)
65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 |
# File 'lib/rubygems/commands/unpack_command.rb', line 65 def execute get_all_gem_names.each do |name| dependency = Gem::Dependency.new name, [:version] path = get_path dependency unless path then alert_error "Gem '#{name}' not installed nor fetchable." next end if [:spec] then spec, = path if .nil? then alert_error "--spec is unsupported on '#{name}' (old format gem)" next end spec_file = File.basename spec.spec_file open spec_file, 'w' do |io| io.write end else basename = File.basename path, '.gem' target_dir = File. basename, [:target] package = Gem::Package.new path package.extract_files target_dir say "Unpacked gem: '#{target_dir}'" end end end |
#find_in_cache(filename) ⇒ Object
Find cached filename in Gem.path. Returns nil if the file cannot be found.
– TODO: see comments in get_path() about general service.
107 108 109 110 111 112 113 114 |
# File 'lib/rubygems/commands/unpack_command.rb', line 107 def find_in_cache(filename) Gem.path.each do |path| this_path = File.join(path, "cache", filename) return this_path if File.exist? this_path end return nil end |
#get_metadata(path) ⇒ Object
Extracts the Gem::Specification and raw metadata from the .gem file at path
. – TODO move to Gem::Package as #raw_spec or something
161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 |
# File 'lib/rubygems/commands/unpack_command.rb', line 161 def path format = Gem::Package.new path spec = format.spec = nil open path, Gem.binary_mode do |io| tar = Gem::Package::TarReader.new io tar.each_entry do |entry| case entry.full_name when 'metadata' then = entry.read when 'metadata.gz' then = Gem.gunzip entry.read end end end return spec, end |
#get_path(dependency) ⇒ Object
Return the full path to the cached gem file matching the given name and version requirement. Returns ‘nil’ if no match.
Example:
get_path 'rake', '> 0.4' # "/usr/lib/ruby/gems/1.8/cache/rake-0.4.2.gem"
get_path 'rake', '< 0.1' # nil
get_path 'rak' # nil (exact name required)
– TODO: This should be refactored so that it’s a general service. I don’t think any of our existing classes are the right place though. Just maybe ‘Cache’?
TODO: It just uses Gem.dir for now. What’s an easy way to get the list of source directories?
133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 |
# File 'lib/rubygems/commands/unpack_command.rb', line 133 def get_path dependency return dependency.name if dependency.name =~ /\.gem$/i specs = dependency.matching_specs selected = specs.max_by { |s| s.version } return Gem::RemoteFetcher.fetcher.download_to_cache(dependency) unless selected return unless dependency.name =~ /^#{selected.name}$/i # We expect to find (basename).gem in the 'cache' directory. Furthermore, # the name match must be exact (ignoring case). path = find_in_cache File.basename selected.cache_file return Gem::RemoteFetcher.fetcher.download_to_cache(dependency) unless path path end |
#usage ⇒ Object
:nodoc:
56 57 58 |
# File 'lib/rubygems/commands/unpack_command.rb', line 56 def usage # :nodoc: "#{program_name} GEMNAME" end |