module Hoe::Mercurial

Hoe plugin module

Constants

COMMIT_MSG_FILE

The name of the file to edit for the commit message

VERSION

Attributes

check_history_on_release[RW]
hg_release_tag_prefix[RW]
hg_sign_tags[RW]

Public Instance Methods

define_mercurial_tasks() click to toggle source

Hoe hook – Define Rake tasks when the plugin is loaded.

# File lib/hoe/mercurial.rb, line 487
def define_mercurial_tasks
        return unless File.exist?( ".hg" ) &&
                !Rake::Task.task_defined?( 'hg:checkin' )

        file COMMIT_MSG_FILE do |task|
                edit_commit_log( task.name )
        end

        namespace :hg do

                desc "Prepare for a new release"
                task :prep_release do
                        uncommitted_files = get_uncommitted_files()
                        unless uncommitted_files.empty?
                                log "Uncommitted files:\n",
                                        *uncommitted_files.map {|fn| "   #{fn}\n" }
                                ask_for_confirmation( "\nRelease anyway?", true ) do
                                        log "Okay, releasing with uncommitted versions."
                                end
                        end

                        tags = get_tags()
                        rev = get_current_rev()
                        pkg_version_tag = "#{hg_release_tag_prefix}#{version}"

                        # Look for a tag for the current release version, and if it exists abort
                        if tags.include?( pkg_version_tag )
                                error "Version #{version} already has a tag."
                                fail
                        end

                        # Ensure that the History file contains an entry for every release
                        Rake::Task[ 'check_history' ].invoke if self.check_history_on_release

                        # Sign the current rev
                        if self.hg_sign_tags
                                log "Signing rev #{rev}"
                                run 'hg', 'sign'
                        end

                        # Tag the current rev
                        log "Tagging rev #{rev} as #{pkg_version_tag}"
                        run 'hg', 'tag', pkg_version_tag

                        # Offer to push
                        Rake::Task['hg:push'].invoke
                end


                desc "Check for new files and offer to add/ignore/delete them."
                task :newfiles do
                        log "Checking for new files..."

                        entries = get_unknown_files()

                        unless entries.empty?
                                files_to_add = []
                                files_to_ignore = []
                                files_to_delete = []

                                entries.each do |entry|
                                        action = prompt_with_default( "   #{entry}: (a)dd, (i)gnore, (s)kip (d)elete", 's' )
                                        case action
                                        when 'a'
                                                files_to_add << entry
                                        when 'i'
                                                files_to_ignore << entry
                                        when 'd'
                                                files_to_delete << entry
                                        end
                                end

                                unless files_to_add.empty?
                                        run 'hg', 'add', *files_to_add
                                end

                                unless files_to_ignore.empty?
                                        hg_ignore_files( *files_to_ignore )
                                end

                                unless files_to_delete.empty?
                                        delete_extra_files( files_to_delete )
                                end
                        end
                end
                task :add => :newfiles


                desc "Pull and update from the default repo"
                task :pull do
                        paths = get_repo_paths()
                        if origin_url = paths['default']
                                ask_for_confirmation( "Pull and update from '#{origin_url}'?", false ) do
                                        Rake::Task['hg:pull_without_confirmation'].invoke
                                end
                        else
                                trace "Skipping pull: No 'default' path."
                        end
                end


                desc "Pull and update without confirmation"
                task :pull_without_confirmation do
                        run 'hg', 'pull', '-u'
                end


                desc "Update to tip"
                task :update do
                        run 'hg', 'update'
                end


                desc "Clobber all changes (hg up -C)"
                task :update_and_clobber do
                        run 'hg', 'update', '-C'
                end


                task :precheckin do
                        trace "Pre-checkin hooks"
                end


                desc "Check the current code in if tests pass"
                task :checkin => [:pull, :newfiles, :precheckin, COMMIT_MSG_FILE] do
                        targets = get_target_args()
                        $stderr.puts '---', File.read( COMMIT_MSG_FILE ), '---'
                        ask_for_confirmation( "Continue with checkin?" ) do
                                run 'hg', 'ci', '-l', COMMIT_MSG_FILE, targets
                                rm_f COMMIT_MSG_FILE
                        end
                        Rake::Task['hg:push'].invoke
                end
                task :commit => :checkin
                task :ci => :checkin

                CLEAN.include( COMMIT_MSG_FILE )

                desc "Push to the default origin repo (if there is one)"
                task :push do
                        paths = get_repo_paths()
                        if origin_url = paths['default']
                                ask_for_confirmation( "Push to '#{origin_url}'?", false ) do
                                        Rake::Task['hg:push_without_confirmation'].invoke
                                end
                        else
                                trace "Skipping push: No 'default' path."
                        end
                end

                desc "Push to the default repo without confirmation"
                task :push_without_confirmation do
                        run 'hg', 'push'
                end
        end

        # Add a top-level 'ci' task for checkin
        desc "Check in your changes"
        task :ci => 'hg:checkin'

        # Hook the release task and prep the repo first
        task :prerelease => 'hg:prep_release'

        desc "Check the history file to ensure it contains an entry for each release tag"
        task :check_history do
                log "Checking history..."
                missing_tags = get_unhistoried_version_tags()

                unless missing_tags.empty?
                        abort "%s needs updating; missing entries for tags: %p" %
                                [ self.history_file, missing_tags ]
                end
        end

rescue ::Exception => err
        $stderr.puts "%s while defining Mercurial tasks: %s" % [ err.class.name, err.message ]
        raise
end
get_unhistoried_version_tags( include_pkg_version=true ) click to toggle source

Read the list of tags and return any that don't have a corresponding section in the history file.

# File lib/hoe/mercurial.rb, line 466
def get_unhistoried_version_tags( include_pkg_version=true )
        prefix = self.hg_release_tag_prefix
        tag_pattern = /#{prefix}\d+(\.\d+)+/
        release_tags = get_tags().grep( /^#{tag_pattern}$/ )

        release_tags.unshift( "#{prefix}#{version}" ) if include_pkg_version

        IO.readlines( self.history_file ).each do |line|
                if line =~ /^(?:h\d\.|#+|=+)\s+(#{tag_pattern})\s+/
                        trace "  found an entry for tag %p: %p" % [ $1, line ]
                        release_tags.delete( $1 )
                else
                        trace "  no tag on line %p" % [ line ]
                end
        end

        return release_tags
end
initialize_mercurial() click to toggle source

Set up defaults

# File lib/hoe/mercurial.rb, line 452
def initialize_mercurial
        # Follow semantic versioning tagging specification (http://semver.org/)
        self.hg_release_tag_prefix    = "v"
        self.hg_sign_tags             = false
        self.check_history_on_release = false

        minor_version = VERSION[ /^\d+\.\d+/ ]
        self.extra_dev_deps << ['hoe-mercurial', "~> #{minor_version}"] unless
                self.name == 'hoe-mercurial'
end