Class: Gem::Source
- Inherits:
-
Object
- Object
- Gem::Source
- Includes:
- Comparable
- Defined in:
- lib/rubygems/source.rb
Overview
A Source knows how to list and fetch gems from a RubyGems marshal index.
There are other Source subclasses for installed gems, local gems, the bundler dependency API and so-forth.
Direct Known Subclasses
Defined Under Namespace
Classes: Git, Installed, Local, Lock, SpecificFile, Vendor
Constant Summary collapse
- FILES =
:nodoc:
{ # :nodoc: :released => 'specs', :latest => 'latest_specs', :prerelease => 'prerelease_specs', }
Instance Attribute Summary collapse
-
#uri ⇒ Object
readonly
The URI this source will fetch gems from.
Instance Method Summary collapse
-
#<=>(other) ⇒ Object
Sources are ordered by installation preference.
-
#==(other) ⇒ Object
(also: #eql?)
:nodoc:.
-
#api_uri ⇒ Object
Use an SRV record on the host to look up the true endpoint for the index.
-
#cache_dir(uri) ⇒ Object
Returns the local directory to write
uri
to. -
#dependency_resolver_set ⇒ Object
Returns a Set that can fetch specifications from this source.
-
#download(spec, dir = Dir.pwd) ⇒ Object
Downloads
spec
and writes it todir
. -
#fetch_spec(name_tuple) ⇒ Object
Fetches a specification for the given
name_tuple
. -
#hash ⇒ Object
:nodoc:.
-
#initialize(uri) ⇒ Source
constructor
Creates a new Source which will use the index located at
uri
. -
#load_specs(type) ⇒ Object
Loads
type
kind of specs fetching from @uri if the on-disk cache is out of date. -
#pretty_print(q) ⇒ Object
:nodoc:.
-
#update_cache? ⇒ Boolean
Returns true when it is possible and safe to update the cache directory.
Constructor Details
#initialize(uri) ⇒ Source
Creates a new Source which will use the index located at uri
.
29 30 31 32 33 34 35 36 37 38 39 40 |
# File 'lib/rubygems/source.rb', line 29 def initialize(uri) begin unless uri.kind_of? URI uri = URI.parse(uri.to_s) end rescue URI::InvalidURIError raise if Gem::Source == self.class end @uri = uri @api_uri = nil end |
Instance Attribute Details
#uri ⇒ Object (readonly)
The URI this source will fetch gems from.
24 25 26 |
# File 'lib/rubygems/source.rb', line 24 def uri @uri end |
Instance Method Details
#<=>(other) ⇒ Object
Sources are ordered by installation preference.
53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 |
# File 'lib/rubygems/source.rb', line 53 def <=>(other) case other when Gem::Source::Installed, Gem::Source::Local, Gem::Source::Lock, Gem::Source::SpecificFile, Gem::Source::Git, Gem::Source::Vendor then -1 when Gem::Source then if !@uri return 0 unless other.uri return 1 end return -1 if !other.uri @uri.to_s <=> other.uri.to_s else nil end end |
#==(other) ⇒ Object Also known as: eql?
:nodoc:
76 77 78 |
# File 'lib/rubygems/source.rb', line 76 def == other # :nodoc: self.class === other and @uri == other.uri end |
#api_uri ⇒ Object
Use an SRV record on the host to look up the true endpoint for the index.
45 46 47 48 |
# File 'lib/rubygems/source.rb', line 45 def api_uri # :nodoc: require 'rubygems/remote_fetcher' @api_uri ||= Gem::RemoteFetcher.fetcher.api_endpoint uri end |
#cache_dir(uri) ⇒ Object
Returns the local directory to write uri
to.
111 112 113 114 115 116 117 |
# File 'lib/rubygems/source.rb', line 111 def cache_dir(uri) # Correct for windows paths escaped_path = uri.path.sub(/^\/([a-z]):\//i, '/\\1-/') escaped_path.untaint File.join Gem.spec_cache_dir, "#{uri.host}%#{uri.port}", File.dirname(escaped_path) end |
#dependency_resolver_set ⇒ Object
Returns a Set that can fetch specifications from this source.
85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 |
# File 'lib/rubygems/source.rb', line 85 def dependency_resolver_set # :nodoc: return Gem::Resolver::IndexSet.new self if 'file' == api_uri.scheme bundler_api_uri = api_uri + './api/v1/dependencies' begin fetcher = Gem::RemoteFetcher.fetcher response = fetcher.fetch_path bundler_api_uri, nil, true rescue Gem::RemoteFetcher::FetchError Gem::Resolver::IndexSet.new self else if response.respond_to? :uri then Gem::Resolver::APISet.new response.uri else Gem::Resolver::APISet.new bundler_api_uri end end end |
#download(spec, dir = Dir.pwd) ⇒ Object
Downloads spec
and writes it to dir
. See also Gem::RemoteFetcher#download.
209 210 211 212 |
# File 'lib/rubygems/source.rb', line 209 def download(spec, dir=Dir.pwd) fetcher = Gem::RemoteFetcher.fetcher fetcher.download spec, api_uri.to_s, dir end |
#fetch_spec(name_tuple) ⇒ Object
Fetches a specification for the given name_tuple
.
134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 |
# File 'lib/rubygems/source.rb', line 134 def fetch_spec name_tuple fetcher = Gem::RemoteFetcher.fetcher spec_file_name = name_tuple.spec_name uri = api_uri + "#{Gem::MARSHAL_SPEC_DIR}#{spec_file_name}" cache_dir = cache_dir uri local_spec = File.join cache_dir, spec_file_name if File.exist? local_spec then spec = Gem.read_binary local_spec spec = Marshal.load(spec) rescue nil return spec if spec end uri.path << '.rz' spec = fetcher.fetch_path uri spec = Gem.inflate spec if update_cache? then FileUtils.mkdir_p cache_dir open local_spec, 'wb' do |io| io.write spec end end # TODO: Investigate setting Gem::Specification#loaded_from to a URI Marshal.load spec end |
#hash ⇒ Object
:nodoc:
104 105 106 |
# File 'lib/rubygems/source.rb', line 104 def hash # :nodoc: @uri.hash end |
#load_specs(type) ⇒ Object
Loads type
kind of specs fetching from @uri if the on-disk cache is out of date.
type
is one of the following:
:released => Return the list of all released specs :latest => Return the list of only the highest version of each gem :prerelease => Return the list of all prerelease only specs
179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 |
# File 'lib/rubygems/source.rb', line 179 def load_specs(type) file = FILES[type] fetcher = Gem::RemoteFetcher.fetcher file_name = "#{file}.#{Gem.marshal_version}" spec_path = api_uri + "#{file_name}.gz" cache_dir = cache_dir spec_path local_file = File.join(cache_dir, file_name) retried = false FileUtils.mkdir_p cache_dir if update_cache? spec_dump = fetcher.cache_update_path spec_path, local_file, update_cache? begin Gem::NameTuple.from_list Marshal.load(spec_dump) rescue ArgumentError if update_cache? && !retried FileUtils.rm local_file retried = true retry else raise Gem::Exception.new("Invalid spec cache file in #{local_file}") end end end |
#pretty_print(q) ⇒ Object
:nodoc:
214 215 216 217 218 219 220 221 222 223 224 225 |
# File 'lib/rubygems/source.rb', line 214 def pretty_print q # :nodoc: q.group 2, '[Remote:', ']' do q.breakable q.text @uri.to_s if api = api_uri q.breakable q.text 'API URI: ' q.text api.to_s end end end |