# # Copyright 2012-2014 Chef Software, Inc. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. # module Omnibus class Fetcher include Digestable include Logging include Util extend Util # # The name of the software this fetcher shall fetch # # @return [String] # attr_reader :name # # The source for this fetcher. # # @return [Hash] # attr_reader :source # # The exact upstream version that a fetcher should fetch. # # @return [String] # # For sources that allow aliases (branch name, tags, etc). Users # should use the class method resolve_version to determine this # before constructing a fetcher. attr_reader :resolved_version # # The upstream version as described before resolution. # # @return [String] # # This will usually be the same as +resolved_version+ but may # refer toa remote ref name or tag for a source such as git. attr_reader :described_version # # The path where extracted software should live. # # @return [String] # attr_reader :project_dir attr_reader :build_dir # # Create a new Fetcher object from the given software. # # @param [Software] software # # To preserve the original interface, this still takes a software-like # argument, but to avoid coupling with the software object, we pull out # what we need and don't touch it again. def initialize(manifest_entry, project_dir, build_dir) @name = manifest_entry.name @source = manifest_entry.locked_source @resolved_version = manifest_entry.locked_version @described_version = manifest_entry.described_version @project_dir = project_dir @build_dir = build_dir end # # @!group Abstract methods # # The following methods are all abstract and should be overriden in child # classes. # -------------------------------------------------- # # @abstract # def fetch_required? raise NotImplementedError end # # @abstract # def clean raise NotImplementedError end # # @abstract # def fetch raise NotImplementedError end # # @abstract # def version_guid raise NotImplementedError end # # @abstract # def version_for_cache raise NotImplementedError end # # @!endgroup # -------------------------------------------------- def fetcher self end # # All fetchers should prefer resolved_version to version # this is provided for compatibility. # def version resolved_version end private # # Override the +log_key+ for this fetcher to include the name of the # software during the fetch. # # @return [String] # def log_key @log_key ||= "#{super}: #{name}" end # # Idempotently create the required directories for building/downloading. # Fetchers should call this method before performing any operations that # manipulate the filesystem. # # @return [void] # def create_required_directories [ Config.cache_dir, Config.source_dir, build_dir, project_dir, ].each do |directory| FileUtils.mkdir_p(directory) unless File.directory?(directory) end end # Class Methods def self.resolve_version(version, source) fetcher_class_for_source(source).resolve_version(version, source) end def self.fetcher_class_for_source(source) if source if source[:url] NetFetcher elsif source[:git] GitFetcher elsif source[:path] PathFetcher end else NullFetcher end end end end