class IssuesDb

Main Program Logic
Main Program Logic

Public Class Methods

new(database_file) click to toggle source
# File bin/issues, line 199
def initialize(database_file)
  @database_file = database_file
  @issues_array = FileTest.exists?(database_file) && YAML.load_file(database_file) || []
end

Public Instance Methods

count_issues(opts) click to toggle source
# File bin/issues, line 352
def count_issues(opts)
  num_issues = select_issues_with_opts(opts).count
  puts "#{num_issues} issues."
end
create_issue(opts) click to toggle source
# File bin/issues, line 266
def create_issue(opts)
  type = determine_issue_type(opts)
  new_issue = Issue.createNewIssue(opts[:title], type)
  new_issue.milestone = opts[:milestone]
  new_issue.estimate = opts[:estimate]
  @issues_array << new_issue
  save_db()  
  puts "Created issue #{new_issue.short_id} #{new_issue.title}"
end
delete_issues(opts) click to toggle source
# File bin/issues, line 400
def delete_issues(opts)
  delete_issues = []

  opts[:issue_ids].each do |issue_id|
    delete_issues << select_issue{|i| i.id.start_with?(issue_id)}
  end
  
  puts "Ok to delete issues: "
  delete_issues.each { |issue| puts "#{issue.short_id} \"#{issue.title}\"" }
  puts "[y/N]"
  
  answer = STDIN.getch
  
  if /y/i =~ answer
    @issues_array -= delete_issues
    save_db()
    
    if delete_issues.count == 1
      puts "Removed issue #{delete_issues[0].short_id} \"#{delete_issues[0].title}\" from database."
    else
      puts "Removed issues "
      delete_issues.each { |issue| puts "#{issue.short_id} \"#{issue.title}\"" }
      puts "from database."
    end
  end

end
determine_issue_type(opts) click to toggle source
# File bin/issues, line 246
def determine_issue_type(opts)
  issue_types = %w{bug improvement task feature}
  issue_type = opts[:type] ? opts[:type].downcase : nil
  
  issue_type && (return issue_type)

  case opts[:title]
  when /\b(improve)/i
    "improvement"
  when /\b(implement)/i
    "feature"
  when /\b(fix|bug|crash)/i
    "bug"
  else
    "task"
  end
end
edit_issue(opts) click to toggle source
# File bin/issues, line 430
def edit_issue(opts)
  issue_id = opts[:issue_id]
  issue = select_issue { |i| i.id.start_with?(issue_id) } 

  did_change_issue = false

  if (opts[:description])
    did_change_issue = issue.edit_description && issue.log("Edited description")
  else
    did_change_issue = issue.edit_all && issue.log("Edited issue")
  end
 
  did_change_issue && save_db()
end
estimate(opts) click to toggle source
# File bin/issues, line 465
def estimate(opts)
  milestone = opts[:milestone]
  total = 0.0
  
  issues_to_estimate = @issues_array.select { |i| select_issue_for_estimate?(i, milestone) }
  issues_without_estimates = @issues_array.select { |i| select_issue_for_estimate?(i, milestone) && !i.estimate }

  if issues_to_estimate.empty? 
    puts "No open issues found for milestone " << milestone << "!"
    exit
  end

  if issues_without_estimates.count > 0 
    puts PrettyComment.h3("Warning: Found issues without estimates")
    issues_without_estimates.each {|i| puts i.format_list(opts)}
    puts PrettyComment.separator("-")
    puts
  end
  
  issues_to_estimate.each { |i| (i.estimate && total += i.estimate) }
  
  milestones = get_milestones_for_pattern(milestone)

  result_str = "Milestone" << (milestones.length > 1 ? "s" : "")

  puts result_str << " #{milestones.join(", ")} will take #{total} man-hours to complete."
  puts
end
get_milestones_for_pattern(pattern) click to toggle source
# File bin/issues, line 457
def get_milestones_for_pattern(pattern)
  result_hash = {}    
  issues_array.each { |i| select_issue_for_estimate?(i, pattern) && result_hash[i.milestone] = true }
  result_hash.keys.sort
end
has_issue(issue_id) click to toggle source
# File bin/issues, line 233
def has_issue(issue_id)
  @issues_array.any? { |issue| issue.id.start_with?(issue_id) }
end
has_open_issues_with_estimate?() click to toggle source
# File bin/issues, line 303
def has_open_issues_with_estimate?
  @issues_array.any? { |issue| issue.status == "open" && issue.estimate != nil }
end
has_open_issues_with_milestone?() click to toggle source
# File bin/issues, line 297
def has_open_issues_with_milestone?
  @issues_array.any? { |issue| issue.status == "open" && issue.milestone != nil }
end
list_issue(opts) click to toggle source
# File bin/issues, line 344
def list_issue(opts)
  issue_id = opts[:issue_id]
  issue = select_issue {|i| i.id.start_with?(issue_id) }
  puts issue.format_verbose(opts)
end
list_issues(opts) click to toggle source
# File bin/issues, line 330
def list_issues(opts)
  if opts[:issue_id]
    list_issue(opts)
    sort_proc = "sort_milestone"
  else
    list_proc = opts[:verbose] ? "format_verbose" : "format_list"
    select_issues_with_opts(opts).\
      sort {|a,b| sort_milestone(a,b)}.\
      each {|issue| puts issue.method(list_proc).call(opts)}
  end
end
milestone_column_width(array = @issues_array) click to toggle source
# File bin/issues, line 309
def milestone_column_width(array = @issues_array)
  result = 0

  array.each { |issue| issue.milestone != nil && result = max(issue.milestone.length, result) }

  result
end
resolve_issues(opts) click to toggle source
# File bin/issues, line 359
def resolve_issues(opts)
  issue_id = opts[:issue_id]
  resolved_issue = select_issue{|i| i.id.start_with?(issue_id) && i.status == "open"}

  duplicate_of_id = opts[:cmd] == "duplicate" && select_issue {|i| i.id.start_with?(opts[:duplicate_of_id]) }.id

  status, message = 
  case opts[:cmd]
  when "resolve"
    ["resolved", "Resolved"]
  when "wontfix"
    ["wontfix", "Won't fix"]
  when "cantreproduce"
    ["cantreproduce", "Can't reproduce"]
  when "duplicate"
    ["duplicate(#{duplicate_of_id})", "Duplicate"]
  end

  resolved_issue.status = status
  resolved_issue.log "Changed status to #{status}"
  
  message = "#{message} issue #{resolved_issue.short_id}: #{resolved_issue.title}"
  puts message
  
  save_db()

  if opts[:commit]
    system "git add .issues"
    system "git commit -m \"#{message}\""
  end
  
  if opts[:close_branch] == true
    issue_branch = git_get_current_branch()
    system "git checkout dev"
    system "git merge #{issue_branch}"
    system "git branch -d #{issue_branch}"
  end
end
save_db() click to toggle source
# File bin/issues, line 239
def save_db()
  FileTest.exists?('.issues') || Dir.mkdir('.issues')
  File.open(@database_file, 'w' ) { |out| YAML.dump(@issues_array, out) }
end
select_issue(&select_proc) click to toggle source
# File bin/issues, line 212
def select_issue(&select_proc)
  result = select_issues(&select_proc)
  
  if result.count == 1
    return result[0]

  elsif result.count > 1
    puts "Found more than one issue that match this query:"
    result.each{|i| puts("#{i.id} #{i.title}")}
    exit
  
  else
    puts "Error: No issue found for query."
    exit
  end

  nil
end
select_issue_for_estimate?(issue, milestone) click to toggle source
# File bin/issues, line 447
def select_issue_for_estimate?(issue, milestone)
  issue.milestone != nil \
  && issue.status == "open" \
  && (issue.milestone == milestone \
     || milestone.start_with?(".") && issue.milestone.end_with?(milestone) \
     || milestone.end_with?(".") && issue.milestone.start_with?(milestone) )
end
select_issues(&select_proc) click to toggle source
# File bin/issues, line 206
def select_issues(&select_proc)
  return @issues_array.select(&select_proc)
end
select_issues_with_opts(opts) click to toggle source
# File bin/issues, line 278
def select_issues_with_opts(opts)
  did_select_issue_types = opts[:type]       
  status_regex = opts[:all] ? /^(open|resolved|duplicate|wontfix)/ : /^open$/
  did_select_milestone = opts[:milestone] != nil
  milestone = opts[:milestone]
                
  return @issues_array.select do |issue| 
    (status_regex =~ issue.status) \
      && (issue.type == opts[:type] || !did_select_issue_types) \
      && (issue.milestone == opts[:milestone] \
          || !did_select_milestone \
          || milestone.end_with?(".") && issue.milestone.start_with?(milestone)\
          || milestone.start_with?(".") && issue.milestone.end_with?(milestone)) \
      && (issue.milestone == nil || opts["no-milestone"] == false)
  end
end
sort_milestone(a, b) click to toggle source
# File bin/issues, line 324
def sort_milestone(a, b)
  return a.milestone <=> b.milestone
end
sort_none(a, b) click to toggle source
# File bin/issues, line 319
def sort_none(a, b)
  return 0
end
start_branch(opts) click to toggle source
# File bin/issues, line 544
def start_branch(opts)
  git_get_current_branch() == "dev" || Trollop::die("Must be on dev branch to start new issue branch.")
  
  issue_id = opts[:issue_id]
  issue = select_issue{|i| i.id.start_with?(issue_id) && i.status == "open"}

  system("git checkout -b #{issue.type}/#{issue.short_id}")
end
update(opts) click to toggle source
# File bin/issues, line 496
def update(opts)
  new_type = opts[:type]
  new_milestone = opts[:milestone]
  new_estimate = opts[:estimate]
  
  opts[:issue_ids].each do |issue_id|
    did_update = false
    issue = select_issue { |i| i.id.start_with?(issue_id) }

    if new_type 
      if issue.type != new_type
        issue.type = new_type
        issue.log("Changed type to #{issue.type}")
        did_update = true
      else
        puts "Issue #{issue.short_id} already of type #{issue.type}."
      end
    end

    if new_milestone
      if issue.milestone != new_milestone
        issue.milestone = new_milestone
        issue.log("Changed milestone to #{issue.milestone}")
        did_update = true
      else
        puts "Issue #{issue.short_id} already in milestone #{issue.milestone}."
      end
    end

    if new_estimate
      if issue.estimate != new_estimate
        issue.estimate = new_estimate
        issue.log("Changed estimate to #{issue.estimate}")
        did_update = true
      else
        puts "Issue #{issue.short_id} already has estimate #{issue.estimate}h."
      end
    end

    if did_update == true
      puts issue.format_list(opts)
      save_db()
    end
  end
end