class Ninny::Git

rubocop:disable Metrics/ClassLength

Constants

CheckoutFailed

Exceptions

DEFAULT_DIRTY_MESSAGE
DEPLOYABLE_PREFIX

branch prefixes

DIRTY_CONFIRM_MESSAGE
DirtyIndex
NO_BRANCH
NoBranchOfType
NotOnBranch
QAREADY_PREFIX
STAGING_PREFIX

Attributes

git[R]

Public Class Methods

new() click to toggle source
# File lib/ninny/git.rb, line 21
def initialize
  @git = ::Git.open(Dir.pwd)
end

Public Instance Methods

alert_dirty_index(message) click to toggle source

Public: Display the message and show the git status

# File lib/ninny/git.rb, line 162
def alert_dirty_index(message)
  prompt.say ' '
  prompt.say message
  prompt.say ' '
  prompt.say command('status')
  raise DirtyIndex
end
branches_for(prefix) click to toggle source

Public: List of branches starting with the given string

prefix - String to match branch names against

Returns an Array of Branches containing the branch name

# File lib/ninny/git.rb, line 129
def branches_for(prefix)
  remote_branches.select do |branch|
    branch.name =~ /^#{prefix}/
  end
end
check_out(branch, do_after_pull = true) click to toggle source

Public: Check out the given branch name

branch_name - The name of the branch to check out do_after_pull - Should a pull be done after checkout?

# File lib/ninny/git.rb, line 67
def check_out(branch, do_after_pull = true)
  git.fetch('-p')
  git.checkout(branch)
  pull if do_after_pull
  raise CheckoutFailed, "Failed to check out '#{branch}'" unless current_branch.name == branch.name
end
clean?() click to toggle source

Public: Whether the Git index is clean (has no uncommited changes)

Returns a Boolean

# File lib/ninny/git.rb, line 147
def clean?
  command('status', '--short').empty?
end
command(*args) click to toggle source
# File lib/ninny/git.rb, line 25
def command(*args)
  git.lib.send(:command, *args)
end
current_branch() click to toggle source
# File lib/ninny/git.rb, line 29
def current_branch
  git.branch(current_branch_name)
end
current_branch_name() click to toggle source
# File lib/ninny/git.rb, line 33
def current_branch_name
  raise NotOnBranch, 'Not currently checked out to a particular branch' if git.current_branch == NO_BRANCH

  git.current_branch
end
delete_branch(branch_name) click to toggle source

Public: Delete the given branch

branch_name - The name of the branch to delete

# File lib/ninny/git.rb, line 106
def delete_branch(branch_name)
  branch = branch_name.is_a?(::Git::Branch) ? branch_name : git.branch(branch_name)
  git.push('origin', ":#{branch}")
  branch.delete
rescue ::Git::GitExecuteError => e
  if e.message.include?(':error: branch') && e.message.include?(' not found.')
    puts 'Could not delete local branch, but the remote branch was deleted.'
  end
end
if_clean(message = DEFAULT_DIRTY_MESSAGE) { || ... } click to toggle source

Public: Perform the block if the Git index is clean

# File lib/ninny/git.rb, line 152
def if_clean(message = DEFAULT_DIRTY_MESSAGE)
  if clean? || prompt.yes?(DIRTY_CONFIRM_MESSAGE)
    yield
  else
    alert_dirty_index message
    exit 1
  end
end
latest_branch_for(prefix) click to toggle source

Public: Most recent branch starting with the given string

prefix - String to match branch names against

Returns an Array of Branches containing the branch name

# File lib/ninny/git.rb, line 140
def latest_branch_for(prefix)
  branches_for(prefix).last || raise(NoBranchOfType, "No #{prefix} branch")
end
merge(branch_name) click to toggle source
# File lib/ninny/git.rb, line 39
def merge(branch_name)
  if_clean do
    git.fetch('-p')
    command 'merge', ['--no-ff', "origin/#{branch_name}"]
    raise MergeFailed unless clean?

    push
  end
end
new_branch(new_branch_name, source_branch_name) click to toggle source

Public: Create a new branch from the given source

new_branch_name - The name of the branch to create source_branch_name - The name of the branch to branch from

# File lib/ninny/git.rb, line 86
def new_branch(new_branch_name, source_branch_name)
  git.fetch('-p')
  remote_branches = command('branch', ['--remote'])

  if remote_branches.include?("origin/#{new_branch_name}")
    ask_to_recreate_branch(new_branch_name, source_branch_name)
  else
    create_branch(new_branch_name, source_branch_name)
  end
rescue ::Git::GitExecuteError => e
  if e.message.include?(':fatal: A branch named') && e.message.include?(' already exists')
    puts "The local branch #{new_branch_name} already exists." \
         ' Please delete it manually and then run this command again.'
    exit 1
  end
end
prompt(**options) click to toggle source
# File lib/ninny/git.rb, line 170
def prompt(**options)
  require 'tty-prompt'
  TTY::Prompt.new(*options)
end
pull() click to toggle source

Public: Pull the latest changes for the checked-out branch

# File lib/ninny/git.rb, line 57
def pull
  if_clean do
    command('pull')
  end
end
push() click to toggle source

Public: Push the current branch to GitHub

# File lib/ninny/git.rb, line 50
def push
  if_clean do
    git.push('origin', current_branch_name)
  end
end
remote_branches() click to toggle source

Public: The list of branches on GitHub

Returns an Array of Strings containing the branch names

# File lib/ninny/git.rb, line 119
def remote_branches
  git.fetch('-p')
  git.branches.remote.map { |branch| git.branch(branch.name) }.sort_by(&:name)
end
track_current_branch(do_after_pull = true) click to toggle source

Public: Track remote branch matching current branch

do_after_pull - Should a pull be done after tracking?

# File lib/ninny/git.rb, line 77
def track_current_branch(do_after_pull = true)
  command('branch', ['-u', "origin/#{current_branch_name}"])
  pull if do_after_pull
end

Private Instance Methods

ask_to_recreate_branch(new_branch_name, source_branch_name) click to toggle source

Private: Ask the user if they wish to delete and recreate a branch

new_branch_name: the name of the branch in question source_branch_name: the name of the branch the new branch is supposed to be based off of

# File lib/ninny/git.rb, line 179
        def ask_to_recreate_branch(new_branch_name, source_branch_name)
  if prompt.yes?("The branch #{new_branch_name} already exists. Do you wish to delete and recreate?")
    delete_branch(new_branch_name)
    new_branch(new_branch_name, source_branch_name)
  else
    exit 1
  end
end
create_branch(new_branch_name, source_branch_name) click to toggle source

Private: Create a branch

new_branch_name: the name of the branch in question source_branch_name: the name of the branch the new branch is supposed to be based off of

# File lib/ninny/git.rb, line 192
        def create_branch(new_branch_name, source_branch_name)
  command('branch', ['--no-track', new_branch_name, "origin/#{source_branch_name}"])
  new_branch = branch(new_branch_name)
  new_branch.checkout
  command('push', ['-u', 'origin', new_branch_name])
end