require 'repertoire/media' require 'repertoire/repository' module Repertoire class Repository # Path to the directory attr_reader :path # Media type of the directory attr_reader :media # # Creates a new Repository object. # # @param [String] path # The path of the repository. # # @param [Media::Type, nil] media # The media type of the repository. # # @yield [repo] # If a block is given, it will be passed the newly created # repository. # # @yieldparam [Repository] repo # The newly created repository. # # @example # Repository.new('path/to/repo',Media::SVN) # # @example # Repository.new('path/to/svn_repo',Media::SVN) do |repo| # puts repo['**/'] # end # def initialize(path,media=nil,&block) @path = File.expand_path(path) begin @media = (media || Media.guess_from_path(@path)) rescue Media::UnknownMedia @media = nil end block.call(self) if block end # # Infers the repository name from a given URI. # # @param [String, URI::HTTP] uri # The URI to inerfer the repository name from. # # @return [String] # The basename of the specified URI. If the basename is +trunk+, then # the basename of the parent directory within the URI is returned. # # @example # Repertoire.name('http://www.today.com/is/now') # # => "now" # # @example # Repertoire.name('svn://svn.repo.com/var/svn/awesome/trunk') # # => "awesome" # def Repository.name(uri) names = uri.to_s.split(/[:\/@]+/) name = nil names.reverse_each do |part| unless (part == 'trunk' || part == '.' || part == '..') name = part break end end if name if name =~ /\.git$/ name.gsub!(/\.git$/,'') end end return name end # # The name of the media used for the repository. # # @return [Symbol, nil] # The name of the media, or +nil+ if the media could not be detected. # def media_name return @media.name if @media return nil end # # Update the repository. # # @param [String, URI::HTTP] uri # The URI to update from. # # @return [Boolean] # Specifies whether the update was a success or not. # def update(uri=nil) if @media @media.update(@path,uri) return true end return false end # # Delete the repository. # def delete Repertoire.delete(@path) end # # Similar to +Dir.glob+, except the media's directory is omitted # from the returned results. # # @param [String] pattern # The pattern to match file-names with. # # @param [Integer] flags # +Dir.glob+ flags. # # @yield [path] # If a block is given, it will be passed each globbed path. # # @yieldparam [String] path # A path that matches the glob pattern. # # @return [Array] # The paths that match the given pattern. # # @example # repo = Repository.new('path/to/my_svn') # repo.glob('sub_path/.svn/*') # => [] # repo.glob('sub_path/**/') # => [...] # # @see http://www.ruby-doc.org/core/classes/Dir.html#M002322 # def glob(pattern,flags=0,&block) pattern = File.expand_path(File.join(@path,pattern)) paths = filter(Dir.glob(pattern,flags)) paths.each(&block) if block return paths end # # Determines whether the repository contains a specific sub-path. # # @param [String] sub_path # The sub-path to search for. # # @return [Boolean] # Specifies whether the directory contains the specified sub-path. # def has_path?(sub_path) !(glob(sub_path).empty?) end # # Finds files within the repository. # # @param [String] sub_path # The glob pattern to match paths with. # # @return [Array] # The files within the repository that match the given pattern. # def files(sub_path='*') glob(sub_path).select { |path| File.file?(path) } end # # Determines if the repository has a given sub-path. # # @param [String] sub_path # The sbu-path to search for. # # @return [Boolean] # Specifies whether there is a file with the matching sub-path # within the repository. # def has_file?(sub_path) !(files(sub_path).empty?) end # # Finds directories within the repository. # # @param [String] sub_path # The glob pattern to match paths with. # # @return [Array] # The directories within the repository that match the given pattern. # def directories(sub_path='*') glob(sub_path).select { |path| File.directory?(path) } end # # Determines if the repository contains a directory matching a given # sub-path. # # @param [String] sub_path # The sub-path to search for. # # @return [Boolean] # Specifies whether there is a directory with the matching sub-path # within the repository. # def has_directory?(sub_path) !(directories(sub_path).empty?) end alias [] glob # # Converts the repository to a String. # # @return [String] # The path of the repository. # def to_s @path.to_s end protected # # Filter the given paths, removing any path that containing directoires # used by the media. # # @param [Array] paths # The paths to filter. # # @return [Array] # The filtered paths. # def filter(paths) return paths unless @media return paths.reject do |path| path.split(File::SEPARATOR).include?(@media.directory) end end end end