From f9109d366f8125612b0bba02b11880a1388f26db Mon Sep 17 00:00:00 2001 From: Nathan Broadbent Date: Sat, 13 Aug 2011 03:48:37 +0800 Subject: [PATCH] Finished #59 - Refactored Issue Trackers. Remember to run "rake db:migrate". --- app/controllers/apps_controller.rb | 23 ++++++++++++++++++++++- app/helpers/application_helper.rb | 11 ----------- app/models/app.rb | 6 +++--- app/models/issue_tracker.rb | 163 ++++++++++--------------------------------------------------------------------------------------------------------------------------------------------------------- app/models/issue_trackers/fogbugz_tracker.rb | 29 +++++++++++++++++++++++++++++ app/models/issue_trackers/lighthouse_tracker.rb | 30 ++++++++++++++++++++++++++++++ app/models/issue_trackers/mingle_tracker.rb | 41 +++++++++++++++++++++++++++++++++++++++++ app/models/issue_trackers/pivotal_labs_tracker.rb | 22 ++++++++++++++++++++++ app/models/issue_trackers/redmine_tracker.rb | 28 ++++++++++++++++++++++++++++ app/views/apps/_fields.html.haml | 36 ++++++++++++++++++------------------ app/views/errs/fogbugz_body.txt.erb | 31 ------------------------------- app/views/errs/lighthouseapp_body.txt.erb | 34 ---------------------------------- app/views/errs/pivotal_body.txt.erb | 16 ---------------- app/views/errs/redmine_body.txt.erb | 44 -------------------------------------------- app/views/errs/show.html.haml | 4 ++-- app/views/issue_trackers/fogbugz_body.txt.erb | 31 +++++++++++++++++++++++++++++++ app/views/issue_trackers/lighthouseapp_body.txt.erb | 34 ++++++++++++++++++++++++++++++++++ app/views/issue_trackers/pivotal_body.txt.erb | 16 ++++++++++++++++ app/views/issue_trackers/redmine_body.txt.erb | 44 ++++++++++++++++++++++++++++++++++++++++++++ config/application.rb | 3 ++- config/initializers/issue_tracker_apis.rb | 3 +++ config/initializers/issue_trackers.rb | 2 -- db/migrate/20110812135951_move_issue_trackers_to_sti.rb | 30 ++++++++++++++++++++++++++++++ lib/issue_tracker_apis/mingle.rb | 14 ++++++++++++++ lib/issue_trackers/mingle.rb | 14 -------------- public/javascripts/form.js | 4 ++-- spec/controllers/apps_controller_spec.rb | 46 +++++++++++++++++++++++----------------------- spec/controllers/errs_controller_spec.rb | 12 ++++++------ spec/factories/issue_tracker_factories.rb | 26 ++++++++++---------------- spec/views/errs/show.html.haml_spec.rb | 2 +- 30 files changed, 421 insertions(+), 378 deletions(-) create mode 100644 app/models/issue_trackers/fogbugz_tracker.rb create mode 100644 app/models/issue_trackers/lighthouse_tracker.rb create mode 100644 app/models/issue_trackers/mingle_tracker.rb create mode 100644 app/models/issue_trackers/pivotal_labs_tracker.rb create mode 100644 app/models/issue_trackers/redmine_tracker.rb delete mode 100644 app/views/errs/fogbugz_body.txt.erb delete mode 100644 app/views/errs/lighthouseapp_body.txt.erb delete mode 100644 app/views/errs/pivotal_body.txt.erb delete mode 100644 app/views/errs/redmine_body.txt.erb create mode 100644 app/views/issue_trackers/fogbugz_body.txt.erb create mode 100644 app/views/issue_trackers/lighthouseapp_body.txt.erb create mode 100644 app/views/issue_trackers/pivotal_body.txt.erb create mode 100644 app/views/issue_trackers/redmine_body.txt.erb create mode 100644 config/initializers/issue_tracker_apis.rb delete mode 100644 config/initializers/issue_trackers.rb create mode 100644 db/migrate/20110812135951_move_issue_trackers_to_sti.rb create mode 100644 lib/issue_tracker_apis/mingle.rb delete mode 100644 lib/issue_trackers/mingle.rb diff --git a/app/controllers/apps_controller.rb b/app/controllers/apps_controller.rb index 18782f3..0f8fa1c 100644 --- a/app/controllers/apps_controller.rb +++ b/app/controllers/apps_controller.rb @@ -24,6 +24,18 @@ class AppsController < InheritedResources::Base end end + def create + @app = App.new(params[:app]) + initialize_subclassed_issue_tracker + create! + end + + def update + @app = resource + initialize_subclassed_issue_tracker + update! + end + def new plug_params build_resource new! @@ -34,7 +46,16 @@ class AppsController < InheritedResources::Base edit! end + protected + def initialize_subclassed_issue_tracker + if params[:app][:issue_tracker_attributes] && tracker_type = params[:app][:issue_tracker_attributes][:type] + if IssueTracker.subclasses.map(&:to_s).include?(tracker_type.to_s) + @app.issue_tracker = tracker_type.constantize.new(params[:app][:issue_tracker_attributes]) + end + end + end + def begin_of_association_chain current_user unless current_user.admin? end @@ -45,7 +66,7 @@ class AppsController < InheritedResources::Base def plug_params app app.watchers.build if app.watchers.none? - app.issue_tracker = IssueTracker.new if app.issue_tracker.nil? + app.issue_tracker = IssueTracker.new unless app.issue_tracker_configured? end # email_at_notices is edited as a string, and stored as an array. diff --git a/app/helpers/application_helper.rb b/app/helpers/application_helper.rb index 5866fd8..03ffd12 100644 --- a/app/helpers/application_helper.rb +++ b/app/helpers/application_helper.rb @@ -29,16 +29,5 @@ module ApplicationHelper tallies.values.inject(0) {|sum, n| sum + n} end private :total_from_tallies - - def no_tracker? object - object.issue_tracker_type == "none" - end - - %w(lighthouseapp redmine pivotal fogbugz mingle).each do |tracker| - define_method("#{tracker}_tracker?".to_sym) do |object| - object.issue_tracker_type == tracker - end - end - end diff --git a/app/models/app.rb b/app/models/app.rb index c054dde..fb2caee 100644 --- a/app/models/app.rb +++ b/app/models/app.rb @@ -11,7 +11,7 @@ class App field :notify_on_deploys, :type => Boolean, :default => true field :email_at_notices, :type => Array, :default => Errbit::Config.email_at_notices - # Some legacy apps may have sting as key instead of BSON::ObjectID + # Some legacy apps may have string as key instead of BSON::ObjectID identity :type => String # There seems to be a Mongoid bug making it impossible to use String identity with references_many feature: # https://github.com/mongoid/mongoid/issues/703 @@ -37,7 +37,7 @@ class App accepts_nested_attributes_for :watchers, :allow_destroy => true, :reject_if => proc { |attrs| attrs[:user_id].blank? && attrs[:email].blank? } accepts_nested_attributes_for :issue_tracker, :allow_destroy => true, - :reject_if => proc { |attrs| !%w(none lighthouseapp redmine pivotal fogbugz mingle).include?(attrs[:issue_tracker_type]) } + :reject_if => proc { |attrs| !IssueTracker.subclasses.map(&:to_s).include?(attrs[:type].to_s) } def self.find_by_id!(app_id) find app_id @@ -71,7 +71,7 @@ class App end def issue_tracker_configured? - issue_tracker && issue_tracker.issue_tracker_type != "none" && !issue_tracker.project_id.blank? + !!(issue_tracker && issue_tracker.class < IssueTracker && issue_tracker.project_id.present?) end def notification_recipients diff --git a/app/models/issue_tracker.rb b/app/models/issue_tracker.rb index 7b2047c..da576c2 100644 --- a/app/models/issue_tracker.rb +++ b/app/models/issue_tracker.rb @@ -5,171 +5,28 @@ class IssueTracker include Rails.application.routes.url_helpers default_url_options[:host] = Errbit::Application.config.action_mailer.default_url_options[:host] - validate :check_params - embedded_in :app, :inverse_of => :issue_tracker - field :account, :type => String - field :api_token, :type => String field :project_id, :type => String - field :ticket_properties, :type => String + field :api_token, :type => String + field :account, :type => String field :username, :type => String field :password, :type => String - field :issue_tracker_type, :type => String, :default => 'none' - - def create_issue err - case issue_tracker_type - when 'lighthouseapp' - create_lighthouseapp_issue err - when 'redmine' - create_redmine_issue err - when 'pivotal' - create_pivotal_issue err - when 'fogbugz' - create_fogbugz_issue err - when 'mingle' - create_mingle_issue err - end - end - - def ticket_properties_hash - # Parses 'key=value, key2=value2' from user input into a ruby hash. - self.ticket_properties.split(",").inject({}) do |hash, pair| - key, value = pair.split("=").map(&:strip) - hash[key] = value - hash - end - end - - protected - def create_redmine_issue err - token = api_token - acc = account - RedmineClient::Base.configure do - self.token = token - self.site = acc - end - issue = RedmineClient::Issue.new(:project_id => project_id) - issue.subject = issue_title err - issue.description = self.class.redmine_body_template.result(binding) - issue.save! - err.update_attribute :issue_link, "#{RedmineClient::Issue.site.to_s.sub(/#{RedmineClient::Issue.site.path}$/, '')}#{RedmineClient::Issue.element_path(issue.id, :project_id => project_id)}".sub(/\.xml\?project_id=#{project_id}$/, "\?project_id=#{project_id}") - end - - def create_pivotal_issue err - PivotalTracker::Client.token = api_token - PivotalTracker::Client.use_ssl = true - project = PivotalTracker::Project.find project_id.to_i - story = project.stories.create :name => issue_title(err), :story_type => 'bug', :description => self.class.pivotal_body_template.result(binding) - err.update_attribute :issue_link, "https://www.pivotaltracker.com/story/show/#{story.id}" - end - - def create_lighthouseapp_issue err - Lighthouse.account = account - Lighthouse.token = api_token - - # updating lighthouse account - Lighthouse::Ticket.site - - ticket = Lighthouse::Ticket.new(:project_id => project_id) - ticket.title = issue_title err - - ticket.body = self.class.lighthouseapp_body_template.result(binding) - - ticket.tags << "errbit" - ticket.save! - err.update_attribute :issue_link, "#{Lighthouse::Ticket.site.to_s.sub(/#{Lighthouse::Ticket.site.path}$/, '')}#{Lighthouse::Ticket.element_path(ticket.id, :project_id => project_id)}".sub(/\.xml$/, '') - end - - def create_fogbugz_issue err - fogbugz = Fogbugz::Interface.new(:email => username, :password => password, :uri => "https://#{account}.fogbugz.com") - fogbugz.authenticate - - issue = {} - issue['sTitle'] = issue_title err - issue['sArea'] = project_id - issue['sEvent'] = self.class.fogbugz_body_template.result(binding) - issue['sTags'] = ['errbit'].join(',') - issue['cols'] = ['ixBug'].join(',') - - fb_resp = fogbugz.command(:new, issue) - err.update_attribute :issue_link, "https://#{account}.fogbugz.com/default.asp?#{fb_resp['case']['ixBug']}" - end - - def create_mingle_issue err - properties = ticket_properties_hash - basic_auth = account.gsub(/https?:\/\//, "https://#{username}:#{password}@") - Mingle.set_site "#{basic_auth}/api/v1/projects/#{project_id}/" + field :ticket_properties, :type => String - card = Mingle::Card.new - card.card_type_name = properties.delete("card_type") - card.name = issue_title(err) - card.description = self.class.mingle_body_template.result(binding) - properties.each do |property, value| - card.send("cp_#{property}=", value) - end + validate :check_params - card.save! - err.update_attribute :issue_link, URI.parse("#{account}/projects/#{project_id}/cards/#{card.id}").to_s - end + # Subclasses are responsible for overwriting this method. + def check_params; end def issue_title err "[#{ err.environment }][#{ err.where }] #{err.message.to_s.truncate(100)}" end - def check_params - blank_flag_fields = %w(project_id) - if %w(fogbugz mingle).include?(issue_tracker_type) - blank_flag_fields += %w(username password) - else - blank_flag_fields << 'api_token' - end - blank_flag_fields << 'account' if(%w(fogbugz lighthouseapp redmine mingle).include?(issue_tracker_type)) - blank_flags = blank_flag_fields.map {|m| self[m].blank? } - - if issue_tracker_type == "mingle" - # Check that mingle was given a 'card_type' in the ticket_properties - blank_flags << "card_type" unless ticket_properties_hash["card_type"] - end - - if blank_flags.any? && !blank_flags.all? - message = case issue_tracker_type - when 'lighthouseapp' - 'You must specify your Lighthouseapp account, API token and Project ID' - when 'redmine' - 'You must specify your Redmine URL, API token and Project ID' - when 'pivotal' - 'You must specify your Pivotal Tracker API token and Project ID' - when 'fogbugz' - 'You must specify your FogBugz Area Name, Username, and Password' - when 'mingle' - 'You must specify your Mingle URL, Project ID, Card Type (in default card properties), Sign-in name, and Password' - end - errors.add(:base, message) - end - end - - class << self - def lighthouseapp_body_template - @@lighthouseapp_body_template ||= ERB.new(File.read(Rails.root + "app/views/errs/lighthouseapp_body.txt.erb").gsub(/^\s*/, '')) - end + # Allows us to set the issue tracker class from a single form. + def type; self._type; end + def type=(t); self._type=t; end - def redmine_body_template - @@redmine_body_template ||= ERB.new(File.read(Rails.root + "app/views/errs/redmine_body.txt.erb")) - end - - def pivotal_body_template - @@pivotal_body_template ||= ERB.new(File.read(Rails.root + "app/views/errs/pivotal_body.txt.erb")) - end - - def fogbugz_body_template - @@fogbugz_body_template ||= ERB.new(File.read(Rails.root + "app/views/errs/fogbugz_body.txt.erb")) - end - - def mingle_body_template - # Mingle also uses textile markup, so the redmine template is perfect. - redmine_body_template - end - end + def self.label; "(none)"; end end diff --git a/app/models/issue_trackers/fogbugz_tracker.rb b/app/models/issue_trackers/fogbugz_tracker.rb new file mode 100644 index 0000000..58947c9 --- /dev/null +++ b/app/models/issue_trackers/fogbugz_tracker.rb @@ -0,0 +1,29 @@ +class FogbugzTracker < IssueTracker + def self.label; "fogbugz"; end + + def check_params + if %w(project_id account username password).detect {|f| self[f].blank? } + errors.add :base, 'You must specify your FogBugz Area Name, FogBugz URL, Username, and Password' + end + end + + def create_issue(err) + fogbugz = Fogbugz::Interface.new(:email => username, :password => password, :uri => "https://#{account}.fogbugz.com") + fogbugz.authenticate + + issue = {} + issue['sTitle'] = issue_title err + issue['sArea'] = project_id + issue['sEvent'] = body_template.result(binding) + issue['sTags'] = ['errbit'].join(',') + issue['cols'] = ['ixBug'].join(',') + + fb_resp = fogbugz.command(:new, issue) + err.update_attribute :issue_link, "https://#{account}.fogbugz.com/default.asp?#{fb_resp['case']['ixBug']}" + end + + def body_template + @@body_template ||= ERB.new(File.read(Rails.root + "app/views/issue_trackers/fogbugz_body.txt.erb")) + end +end + diff --git a/app/models/issue_trackers/lighthouse_tracker.rb b/app/models/issue_trackers/lighthouse_tracker.rb new file mode 100644 index 0000000..f6044b9 --- /dev/null +++ b/app/models/issue_trackers/lighthouse_tracker.rb @@ -0,0 +1,30 @@ +class LighthouseTracker < IssueTracker + def self.label; "lighthouseapp"; end + + def check_params + if %w(account api_token project_id).detect {|f| self[f].blank? } + errors.add :base, 'You must specify your Lighthouseapp account, API token and Project ID' + end + end + + def create_issue(err) + Lighthouse.account = account + Lighthouse.token = api_token + # updating lighthouse account + Lighthouse::Ticket.site + + ticket = Lighthouse::Ticket.new(:project_id => project_id) + ticket.title = issue_title err + + ticket.body = body_template.result(binding) + + ticket.tags << "errbit" + ticket.save! + err.update_attribute :issue_link, "#{Lighthouse::Ticket.site.to_s.sub(/#{Lighthouse::Ticket.site.path}$/, '')}#{Lighthouse::Ticket.element_path(ticket.id, :project_id => project_id)}".sub(/\.xml$/, '') + end + + def body_template + @@body_template ||= ERB.new(File.read(Rails.root + "app/views/issue_trackers/lighthouseapp_body.txt.erb").gsub(/^\s*/, '')) + end +end + diff --git a/app/models/issue_trackers/mingle_tracker.rb b/app/models/issue_trackers/mingle_tracker.rb new file mode 100644 index 0000000..b6d45ae --- /dev/null +++ b/app/models/issue_trackers/mingle_tracker.rb @@ -0,0 +1,41 @@ +class MingleTracker < IssueTracker + def self.label; "mingle"; end + + def check_params + if %w(account project_id username password).detect {|f| self[f].blank? } or !ticket_properties_hash["card_type"] + errors.add :base, 'You must specify your Mingle URL, Project ID, Card Type (in default card properties), Sign-in name, and Password' + end + end + + def create_issue(err) + properties = ticket_properties_hash + basic_auth = account.gsub(/https?:\/\//, "https://#{username}:#{password}@") + Mingle.set_site "#{basic_auth}/api/v1/projects/#{project_id}/" + + card = Mingle::Card.new + card.card_type_name = properties.delete("card_type") + card.name = issue_title(err) + card.description = body_template.result(binding) + properties.each do |property, value| + card.send("cp_#{property}=", value) + end + + card.save! + err.update_attribute :issue_link, URI.parse("#{account}/projects/#{project_id}/cards/#{card.id}").to_s + end + + def body_template + # Mingle also uses textile markup, so the redmine template is perfect. + @@body_template ||= ERB.new(File.read(Rails.root + "app/views/issue_trackers/redmine_body.txt.erb")) + end + + def ticket_properties_hash + # Parses 'key=value, key2=value2' from ticket_properties into a ruby hash. + self.ticket_properties.split(",").inject({}) do |hash, pair| + key, value = pair.split("=").map(&:strip) + hash[key] = value + hash + end + end +end + diff --git a/app/models/issue_trackers/pivotal_labs_tracker.rb b/app/models/issue_trackers/pivotal_labs_tracker.rb new file mode 100644 index 0000000..1b378c4 --- /dev/null +++ b/app/models/issue_trackers/pivotal_labs_tracker.rb @@ -0,0 +1,22 @@ +class PivotalLabsTracker < IssueTracker + def self.label; "pivotal"; end + + def check_params + if %w(api_token project_id).detect {|f| self[f].blank? } + errors.add :base, 'You must specify your Pivotal Tracker API token and Project ID' + end + end + + def create_issue(err) + PivotalTracker::Client.token = api_token + PivotalTracker::Client.use_ssl = true + project = PivotalTracker::Project.find project_id.to_i + story = project.stories.create :name => issue_title(err), :story_type => 'bug', :description => body_template.result(binding) + err.update_attribute :issue_link, "https://www.pivotaltracker.com/story/show/#{story.id}" + end + + def body_template + @@body_template ||= ERB.new(File.read(Rails.root + "app/views/issue_trackers/pivotal_body.txt.erb")) + end +end + diff --git a/app/models/issue_trackers/redmine_tracker.rb b/app/models/issue_trackers/redmine_tracker.rb new file mode 100644 index 0000000..1f0b28c --- /dev/null +++ b/app/models/issue_trackers/redmine_tracker.rb @@ -0,0 +1,28 @@ +class RedmineTracker < IssueTracker + def self.label; "redmine"; end + + def check_params + if %w(account api_token project_id).detect {|f| self[f].blank? } + errors.add :base, 'You must specify your Redmine URL, API token and Project ID' + end + end + + def create_issue(err) + token = api_token + acc = account + RedmineClient::Base.configure do + self.token = token + self.site = acc + end + issue = RedmineClient::Issue.new(:project_id => project_id) + issue.subject = issue_title err + issue.description = body_template.result(binding) + issue.save! + err.update_attribute :issue_link, "#{RedmineClient::Issue.site.to_s.sub(/#{RedmineClient::Issue.site.path}$/, '')}#{RedmineClient::Issue.element_path(issue.id, :project_id => project_id)}".sub(/\.xml\?project_id=#{project_id}$/, "\?project_id=#{project_id}") + end + + def body_template + @@body_template ||= ERB.new(File.read(Rails.root + "app/views/issue_trackers/redmine_body.txt.erb")) + end +end + diff --git a/app/views/apps/_fields.html.haml b/app/views/apps/_fields.html.haml index 9ea0c80..6d6b152 100644 --- a/app/views/apps/_fields.html.haml +++ b/app/views/apps/_fields.html.haml @@ -50,40 +50,40 @@ = f.fields_for :issue_tracker do |w| %div.issue_tracker.nested %div.choose - = w.radio_button :issue_tracker_type, :none - = label_tag :issue_tracker_type_none, '(None)', :for => label_for_attr(w, 'issue_tracker_type_none') - = w.radio_button :issue_tracker_type, :lighthouseapp - = label_tag :issue_tracker_type_lighthouseapp, 'Lighthouse', :for => label_for_attr(w, 'issue_tracker_type_lighthouseapp') - = w.radio_button :issue_tracker_type, :redmine - = label_tag :issue_tracker_type_redmine, 'Redmine', :for => label_for_attr(w, 'issue_tracker_type_redmine') - = w.radio_button :issue_tracker_type, :pivotal - = label_tag :issue_tracker_type_pivotal, 'Pivotal Tracker', :for => label_for_attr(w, 'issue_tracker_type_pivotal') - = w.radio_button :issue_tracker_type, :fogbugz - = label_tag :issue_tracker_type_fogbugz, 'FogBugz', :for => label_for_attr(w, 'issue_tracker_type_fogbugz') - = w.radio_button :issue_tracker_type, :mingle - = label_tag :issue_tracker_type_fogbugz, 'Mingle', :for => label_for_attr(w, 'issue_tracker_type_mingle') - %div.tracker_params.none{:class => no_tracker?(w.object) ? 'chosen' : nil} + = w.radio_button :type, "IssueTracker", 'data-section' => 'none' + = label_tag :type_none, '(None)', :for => label_for_attr(w, 'type_none') + = w.radio_button :type, "LighthouseTracker", 'data-section' => 'lighthouse' + = label_tag :type_lighthouseapp, 'Lighthouse', :for => label_for_attr(w, 'type_lighthouseapp') + = w.radio_button :type, "RedmineTracker", 'data-section' => 'redmine' + = label_tag :type_redmine, 'Redmine', :for => label_for_attr(w, 'type_redmine') + = w.radio_button :type, "PivotalTracker", 'data-section' => 'pivotal' + = label_tag :type_pivotal, 'Pivotal Tracker', :for => label_for_attr(w, 'type_pivotal') + = w.radio_button :type, "FogbugzTracker", 'data-section' => 'fogbugz' + = label_tag :type_fogbugz, 'FogBugz', :for => label_for_attr(w, 'type_fogbugz') + = w.radio_button :type, "MingleTracker", 'data-section' => 'mingle' + = label_tag :type_fogbugz, 'Mingle', :for => label_for_attr(w, 'type_mingle') + %div.tracker_params.none{:class => (w.object && !(w.object.class < IssueTracker)) ? 'chosen' : nil} %p When no issue tracker has been configured, you will be able to leave comments on errors. - %div.tracker_params.lighthouseapp{:class => lighthouseapp_tracker?(w.object) ? 'chosen' : nil} + %div.tracker_params.lighthouse{:class => w.object.is_a?(LighthouseTracker) ? 'chosen' : nil} = w.label :account, "Account" = w.text_field :account, :placeholder => "abc from abc.lighthouseapp.com" = w.label :api_token, "API token" = w.text_field :api_token, :placeholder => "API Token for your account" = w.label :project_id, "Project ID" = w.text_field :project_id - %div.tracker_params.redmine{:class => redmine_tracker?(w.object) ? 'chosen' : nil} + %div.tracker_params.redmine{:class => w.object.is_a?(RedmineTracker) ? 'chosen' : nil} = w.label :account, "Redmine URL" = w.text_field :account, :placeholder => "like http://www.redmine.org/" = w.label :api_token, "API token" = w.text_field :api_token, :placeholder => "API Token for your account" = w.label :project_id, "Project ID" = w.text_field :project_id - %div.tracker_params.pivotal{:class => pivotal_tracker?(w.object) ? 'chosen' : nil} + %div.tracker_params.pivotal{:class => w.object.is_a?(PivotalLabsTracker) ? 'chosen' : nil} = w.label :project_id, "Project ID" = w.text_field :project_id = w.label :api_token, "API token" = w.text_field :api_token, :placeholder => "API Token for your account" - %div.tracker_params.fogbugz{:class => fogbugz_tracker?(w.object) ? 'chosen' : nil} + %div.tracker_params.fogbugz{:class => w.object.is_a?(FogbugzTracker) ? 'chosen' : nil} = w.label :project_id, "Area Name" = w.text_field :project_id = w.label :account, "FogBugz URL" @@ -92,7 +92,7 @@ = w.text_field :username, :placeholder => 'Username/Email for your account' = w.label :password, 'Password' = w.password_field :password, :placeholder => 'Password for your account' - %div.tracker_params.mingle{:class => mingle_tracker?(w.object) ? 'chosen' : nil} + %div.tracker_params.mingle{:class => w.object.is_a?(MingleTracker) ? 'chosen' : nil} = w.label :account, "Mingle URL" = w.text_field :account, :placeholder => "http://mingle.yoursite.com/" = w.label :project_id, "Project ID" diff --git a/app/views/errs/fogbugz_body.txt.erb b/app/views/errs/fogbugz_body.txt.erb deleted file mode 100644 index 38f0546..0000000 --- a/app/views/errs/fogbugz_body.txt.erb +++ /dev/null @@ -1,31 +0,0 @@ -"See this exception on Errbit": <%= app_err_url(err.app, err) %> -<% if notice = err.notices.first %> - <%= notice.message %> - - Summary - - Where - <%= notice.err.where %> - - - Occured - <%= notice.created_at.to_s(:micro) %> - - - Similar - <%= (notice.err.notices_count - 1).to_s %> - - Params - <%= pretty_hash(notice.params) %> - - Session - <%= pretty_hash(notice.session) %> - - Backtrace - <% for line in notice.backtrace %> - <%= line['number'] %>: <%= line['file'].sub(/^\[PROJECT_ROOT\]/, '') %> - <% end %> - - Environment - <% for key, val in notice.env_vars %> - <%= key %>: <%= val %> - <% end %> -<% end %> - diff --git a/app/views/errs/lighthouseapp_body.txt.erb b/app/views/errs/lighthouseapp_body.txt.erb deleted file mode 100644 index 709d194..0000000 --- a/app/views/errs/lighthouseapp_body.txt.erb +++ /dev/null @@ -1,34 +0,0 @@ -[See this exception on Errbit](<%= app_err_url err.app, err %> "See this exception on Errbit") -<% if notice = err.notices.first %> - # <%= notice.message %> # - ## Summary ## - <% if notice.request['url'].present? %> - ### URL ### - [<%= notice.request['url'] %>](<%= notice.request['url'] %>)" - <% end %> - ### Where ### - <%= notice.err.where %> - - ### Occured ### - <%= notice.created_at.to_s(:micro) %> - - ### Similar ### - <%= (notice.err.notices_count - 1).to_s %> - - ## Params ## - <%= pretty_hash(notice.params) %> - - ## Session ## - <%= pretty_hash(notice.session) %> - - ## Backtrace ## - - <% for line in notice.backtrace %><%= line['number'] %>: <%= line['file'].sub(/^\[PROJECT_ROOT\]/, '') %> -> **<%= line['method'] %>** - <% end %> - - - ## Environment ## - <% for key, val in notice.env_vars %> - <%= key %>: <%= val %> - <% end %> -<% end %> diff --git a/app/views/errs/pivotal_body.txt.erb b/app/views/errs/pivotal_body.txt.erb deleted file mode 100644 index 7a5362d..0000000 --- a/app/views/errs/pivotal_body.txt.erb +++ /dev/null @@ -1,16 +0,0 @@ -See this exception on Errbit: <%= app_err_url err.app, err %> -<% if notice = err.notices.first %> - <% if notice.request['url'].present? %>URL: <%= notice.request['url'] %><% end %> - Where: <%= notice.err.where %> - Occurred: <%= notice.created_at.to_s :micro %> - Similar: <%= (notice.err.notices.count - 1).to_s %> - - Params: - <%= pretty_hash notice.params %> - - Session: - <%= pretty_hash notice.session %> - - Backtrace: - <%= notice.backtrace[0..4].map { |line| "#{line['number']}: #{line['file'].sub(/^\[PROJECT_ROOT\]/, '')} -> *#{line['method']}*" }.join "\n" %> -<% end %> diff --git a/app/views/errs/redmine_body.txt.erb b/app/views/errs/redmine_body.txt.erb deleted file mode 100644 index e1a6642..0000000 --- a/app/views/errs/redmine_body.txt.erb +++ /dev/null @@ -1,44 +0,0 @@ -<% if notice = err.notices.first %> -h1. <%= notice.message %> - -h3. "See this exception on Errbit":<%= app_err_url err.app, err %> - -h2. Summary -<% if notice.request['url'].present? %> -h3. URL - -"<%= notice.request['url'] %>":<%= notice.request['url'] %> -<% end %> -h3. Where - -<%= notice.err.where %> - -h3. Occured - -<%= notice.created_at.to_s(:micro) %> - -h3. Similar - -<%= (notice.err.notices_count - 1).to_s %> - -h2. Params - -
<%= pretty_hash(notice.params) %>
- -h2. Session - -
<%= pretty_hash(notice.session) %>
- -h2. Backtrace - -| Line | File | Method | -<% for line in notice.backtrace %>| <%= line['number'] %> | <%= line['file'].sub(/^\[PROJECT_ROOT\]/, '') %> | *<%= line['method'] %>* | -<% end %> - -h2. Environment - -<% for key, val in notice.env_vars %>| <%= key %> | <%= val %> | -<% end %> - -<% end %> - diff --git a/app/views/errs/show.html.haml b/app/views/errs/show.html.haml index 9eb7643..33ced76 100644 --- a/app/views/errs/show.html.haml +++ b/app/views/errs/show.html.haml @@ -13,9 +13,9 @@ - content_for :action_bar do - if @err.app.issue_tracker_configured? - if @err.issue_link.blank? - %span= link_to 'create issue', create_issue_app_err_path(@app, @err), :method => :post, :class => "#{@app.issue_tracker.issue_tracker_type}_create create-issue" + %span= link_to 'create issue', create_issue_app_err_path(@app, @err), :method => :post, :class => "#{@app.issue_tracker.class.label}_create create-issue" - else - %span= link_to 'go to issue', @err.issue_link, :class => "#{@app.issue_tracker.issue_tracker_type}_goto goto-issue" + %span= link_to 'go to issue', @err.issue_link, :class => "#{@app.issue_tracker.class.label}_goto goto-issue" = link_to 'unlink issue', unlink_issue_app_err_path(@app, @err), :method => :delete, :confirm => "Unlink err issues?", :class => "unlink-issue" - if @err.unresolved? %span= link_to 'resolve', resolve_app_err_path(@app, @err), :method => :put, :confirm => err_confirm, :class => 'resolve' diff --git a/app/views/issue_trackers/fogbugz_body.txt.erb b/app/views/issue_trackers/fogbugz_body.txt.erb new file mode 100644 index 0000000..38f0546 --- /dev/null +++ b/app/views/issue_trackers/fogbugz_body.txt.erb @@ -0,0 +1,31 @@ +"See this exception on Errbit": <%= app_err_url(err.app, err) %> +<% if notice = err.notices.first %> + <%= notice.message %> + + Summary + - Where + <%= notice.err.where %> + + - Occured + <%= notice.created_at.to_s(:micro) %> + + - Similar + <%= (notice.err.notices_count - 1).to_s %> + + Params + <%= pretty_hash(notice.params) %> + + Session + <%= pretty_hash(notice.session) %> + + Backtrace + <% for line in notice.backtrace %> + <%= line['number'] %>: <%= line['file'].sub(/^\[PROJECT_ROOT\]/, '') %> + <% end %> + + Environment + <% for key, val in notice.env_vars %> + <%= key %>: <%= val %> + <% end %> +<% end %> + diff --git a/app/views/issue_trackers/lighthouseapp_body.txt.erb b/app/views/issue_trackers/lighthouseapp_body.txt.erb new file mode 100644 index 0000000..709d194 --- /dev/null +++ b/app/views/issue_trackers/lighthouseapp_body.txt.erb @@ -0,0 +1,34 @@ +[See this exception on Errbit](<%= app_err_url err.app, err %> "See this exception on Errbit") +<% if notice = err.notices.first %> + # <%= notice.message %> # + ## Summary ## + <% if notice.request['url'].present? %> + ### URL ### + [<%= notice.request['url'] %>](<%= notice.request['url'] %>)" + <% end %> + ### Where ### + <%= notice.err.where %> + + ### Occured ### + <%= notice.created_at.to_s(:micro) %> + + ### Similar ### + <%= (notice.err.notices_count - 1).to_s %> + + ## Params ## + <%= pretty_hash(notice.params) %> + + ## Session ## + <%= pretty_hash(notice.session) %> + + ## Backtrace ## + + <% for line in notice.backtrace %><%= line['number'] %>: <%= line['file'].sub(/^\[PROJECT_ROOT\]/, '') %> -> **<%= line['method'] %>** + <% end %> + + + ## Environment ## + <% for key, val in notice.env_vars %> + <%= key %>: <%= val %> + <% end %> +<% end %> diff --git a/app/views/issue_trackers/pivotal_body.txt.erb b/app/views/issue_trackers/pivotal_body.txt.erb new file mode 100644 index 0000000..7a5362d --- /dev/null +++ b/app/views/issue_trackers/pivotal_body.txt.erb @@ -0,0 +1,16 @@ +See this exception on Errbit: <%= app_err_url err.app, err %> +<% if notice = err.notices.first %> + <% if notice.request['url'].present? %>URL: <%= notice.request['url'] %><% end %> + Where: <%= notice.err.where %> + Occurred: <%= notice.created_at.to_s :micro %> + Similar: <%= (notice.err.notices.count - 1).to_s %> + + Params: + <%= pretty_hash notice.params %> + + Session: + <%= pretty_hash notice.session %> + + Backtrace: + <%= notice.backtrace[0..4].map { |line| "#{line['number']}: #{line['file'].sub(/^\[PROJECT_ROOT\]/, '')} -> *#{line['method']}*" }.join "\n" %> +<% end %> diff --git a/app/views/issue_trackers/redmine_body.txt.erb b/app/views/issue_trackers/redmine_body.txt.erb new file mode 100644 index 0000000..e1a6642 --- /dev/null +++ b/app/views/issue_trackers/redmine_body.txt.erb @@ -0,0 +1,44 @@ +<% if notice = err.notices.first %> +h1. <%= notice.message %> + +h3. "See this exception on Errbit":<%= app_err_url err.app, err %> + +h2. Summary +<% if notice.request['url'].present? %> +h3. URL + +"<%= notice.request['url'] %>":<%= notice.request['url'] %> +<% end %> +h3. Where + +<%= notice.err.where %> + +h3. Occured + +<%= notice.created_at.to_s(:micro) %> + +h3. Similar + +<%= (notice.err.notices_count - 1).to_s %> + +h2. Params + +
<%= pretty_hash(notice.params) %>
+ +h2. Session + +
<%= pretty_hash(notice.session) %>
+ +h2. Backtrace + +| Line | File | Method | +<% for line in notice.backtrace %>| <%= line['number'] %> | <%= line['file'].sub(/^\[PROJECT_ROOT\]/, '') %> | *<%= line['method'] %>* | +<% end %> + +h2. Environment + +<% for key, val in notice.env_vars %>| <%= key %> | <%= val %> | +<% end %> + +<% end %> + diff --git a/config/application.rb b/config/application.rb index 69ae1e3..86c1d1c 100644 --- a/config/application.rb +++ b/config/application.rb @@ -19,7 +19,7 @@ module Errbit # -- all .rb files in that directory are automatically loaded. # Custom directories with classes and modules you want to be autoloadable. - # config.autoload_paths += %W(#{config.root}/extras) + config.autoload_paths += %W(app/models/issue_trackers) # Only load the plugins named here, in the order given (default is alphabetical). # :all can be used as a placeholder for all plugins not explicitly named. @@ -53,3 +53,4 @@ module Errbit config.filter_parameters += [:password] end end + diff --git a/config/initializers/issue_tracker_apis.rb b/config/initializers/issue_tracker_apis.rb new file mode 100644 index 0000000..e68683d --- /dev/null +++ b/config/initializers/issue_tracker_apis.rb @@ -0,0 +1,3 @@ +# Require all issue tracker apis in lib/issue_tracker_apis +Dir.glob(Rails.root.join('lib/issue_tracker_apis/*.rb')).each {|t| require t } + diff --git a/config/initializers/issue_trackers.rb b/config/initializers/issue_trackers.rb deleted file mode 100644 index 11e5dd1..0000000 --- a/config/initializers/issue_trackers.rb +++ /dev/null @@ -1,2 +0,0 @@ -require Rails.root.join('lib/issue_trackers/mingle.rb') - diff --git a/db/migrate/20110812135951_move_issue_trackers_to_sti.rb b/db/migrate/20110812135951_move_issue_trackers_to_sti.rb new file mode 100644 index 0000000..26a5d4d --- /dev/null +++ b/db/migrate/20110812135951_move_issue_trackers_to_sti.rb @@ -0,0 +1,30 @@ +class MoveIssueTrackersToSti < Mongoid::Migration + def self.up + App.all.each do |app| + # Update all embedded issue trackers to use STI patterns. + # All issue trackers now subclass the IssueTracker model, + # and their class is stored in the '_type' field, which is + # also aliased to 'type'. + if app.issue_tracker && app.issue_tracker.attributes["issue_tracker_type"] + app.issue_tracker._type = case app.issue_tracker.issue_tracker_type + when 'lighthouseapp'; "LighthouseTracker" + when 'redmine'; "RedmineTracker" + when 'pivotal'; "PivotalLabsTracker" + when 'fogbugz'; "FogbugzTracker" + when 'mingle'; "MingleTracker" + else; nil + end + if app.issue_tracker.issue_tracker_type == "none" + app.issue_tracker = nil + else + app.issue_tracker.issue_tracker_type = nil + end + app.save + end + end + end + + def self.down + end +end + diff --git a/lib/issue_tracker_apis/mingle.rb b/lib/issue_tracker_apis/mingle.rb new file mode 100644 index 0000000..319c3c8 --- /dev/null +++ b/lib/issue_tracker_apis/mingle.rb @@ -0,0 +1,14 @@ +module Mingle + class Card < ActiveResource::Base + # site template ~> "https://username:password@mingle.example.com/api/v1/projects/:project_id/" + end + def self.set_site(site) + # ActiveResource seems to clone and freeze the @site variable + # after the first use. It seems that the only way to change @site + # is to drop the subclass, and then reload it. + Mingle.send(:remove_const, :Card) + load File.join(Rails.root,'lib','issue_tracker_apis','mingle.rb') + Mingle::Card.site = site + end +end + diff --git a/lib/issue_trackers/mingle.rb b/lib/issue_trackers/mingle.rb deleted file mode 100644 index 30e3390..0000000 --- a/lib/issue_trackers/mingle.rb +++ /dev/null @@ -1,14 +0,0 @@ -module Mingle - class Card < ActiveResource::Base - # site template ~> "https://username:password@mingle.example.com/api/v1/projects/:project_id/" - end - def self.set_site(site) - # ActiveResource seems to clone and freeze the @site variable - # after the first use. It seems that the only way to change @site - # is to drop the subclass, and then reload it. - Mingle.send(:remove_const, :Card) - load File.join(Rails.root,'lib','issue_trackers','mingle.rb') - Mingle::Card.site = site - end -end - diff --git a/public/javascripts/form.js b/public/javascripts/form.js index 383cf04..7287c2b 100644 --- a/public/javascripts/form.js +++ b/public/javascripts/form.js @@ -71,8 +71,8 @@ function activateTypeSelector(field_class, section_class) { $('div.'+field_class+' > div.'+section_class).not('.chosen').find('input') .attr('disabled','disabled').val(''); - $('div.'+field_class+' input[name*='+field_class+'_type]').live('click', function(){ - var chosen = $(this).val(); + $('div.'+field_class+' input[name*=type]').live('click', function(){ + var chosen = $(this).data("section"); var wrapper = $(this).closest('.nested'); wrapper.find('div.chosen.'+section_class).removeClass('chosen').find('input').attr('disabled','disabled'); wrapper.find('div.'+section_class+'.'+chosen).addClass('chosen').find('input').removeAttr('disabled'); diff --git a/spec/controllers/apps_controller_spec.rb b/spec/controllers/apps_controller_spec.rb index 25dc2a6..161dfdf 100644 --- a/spec/controllers/apps_controller_spec.rb +++ b/spec/controllers/apps_controller_spec.rb @@ -263,25 +263,25 @@ describe AppsController do context "unknown tracker type" do before(:each) do put :update, :id => @app.id, :app => { :issue_tracker_attributes => { - :issue_tracker_type => 'unknown', :project_id => '1234', :api_token => '123123', :account => 'myapp' + :type => 'unknown', :project_id => '1234', :api_token => '123123', :account => 'myapp' } } @app.reload end it "should not create issue tracker" do - @app.issue_tracker.should be_nil + @app.issue_tracker_configured?.should == false end end context "lighthouseapp" do it "should save tracker params" do put :update, :id => @app.id, :app => { :issue_tracker_attributes => { - :issue_tracker_type => 'lighthouseapp', :project_id => '1234', :api_token => '123123', :account => 'myapp' + :type => 'LighthouseTracker', :project_id => '1234', :api_token => '123123', :account => 'myapp' } } @app.reload tracker = @app.issue_tracker - tracker.issue_tracker_type.should == 'lighthouseapp' + tracker.should be_a(LighthouseTracker) tracker.project_id.should == '1234' tracker.api_token.should == '123123' tracker.account.should == 'myapp' @@ -289,11 +289,11 @@ describe AppsController do it "should show validation notice when sufficient params are not present" do put :update, :id => @app.id, :app => { :issue_tracker_attributes => { - :issue_tracker_type => 'lighthouseapp', :project_id => '1234', :api_token => '123123' + :type => 'LighthouseTracker', :project_id => '1234', :api_token => '123123' } } @app.reload - @app.issue_tracker.should be_nil + @app.issue_tracker_configured?.should == false response.body.should match(/You must specify your Lighthouseapp account, API token and Project ID/) end end @@ -301,12 +301,12 @@ describe AppsController do context "redmine" do it "should save tracker params" do put :update, :id => @app.id, :app => { :issue_tracker_attributes => { - :issue_tracker_type => 'redmine', :project_id => '1234', :api_token => '123123', :account => 'http://myapp.com' + :type => 'RedmineTracker', :project_id => '1234', :api_token => '123123', :account => 'http://myapp.com' } } @app.reload tracker = @app.issue_tracker - tracker.issue_tracker_type.should == 'redmine' + tracker.should be_a(RedmineTracker) tracker.project_id.should == '1234' tracker.api_token.should == '123123' tracker.account.should == 'http://myapp.com' @@ -314,11 +314,11 @@ describe AppsController do it "should show validation notice when sufficient params are not present" do put :update, :id => @app.id, :app => { :issue_tracker_attributes => { - :issue_tracker_type => 'redmine', :project_id => '1234', :api_token => '123123' + :type => 'RedmineTracker', :project_id => '1234', :api_token => '123123' } } @app.reload - @app.issue_tracker.should be_nil + @app.issue_tracker_configured?.should == false response.body.should match(/You must specify your Redmine URL, API token and Project ID/) end end @@ -326,21 +326,21 @@ describe AppsController do context "pivotal" do it "should save tracker params" do put :update, :id => @app.id, :app => { :issue_tracker_attributes => { - :issue_tracker_type => 'pivotal', :project_id => '1234', :api_token => '123123' } } + :type => 'PivotalLabsTracker', :project_id => '1234', :api_token => '123123' } } @app.reload tracker = @app.issue_tracker - tracker.issue_tracker_type.should == 'pivotal' + tracker.should be_a(PivotalLabsTracker) tracker.project_id.should == '1234' tracker.api_token.should == '123123' end it "should show validation notice when sufficient params are not present" do put :update, :id => @app.id, :app => { :issue_tracker_attributes => { - :issue_tracker_type => 'pivotal', :project_id => '1234' } } + :type => 'PivotalLabsTracker', :project_id => '1234' } } @app.reload - @app.issue_tracker.should be_nil + @app.issue_tracker_configured?.should == false response.body.should match(/You must specify your Pivotal Tracker API token and Project ID/) end end @@ -349,12 +349,12 @@ describe AppsController do context 'with correct params' do before do put :update, :id => @app.id, :app => { :issue_tracker_attributes => { - :issue_tracker_type => 'fogbugz', :account => 'abc', :project_id => 'Service - Peon', :username => '1234', :password => '123123' } } + :type => 'FogbugzTracker', :account => 'abc', :project_id => 'Service - Peon', :username => '1234', :password => '123123' } } @app.reload end subject {@app.issue_tracker} - its(:issue_tracker_type) {should == 'fogbugz'} + its(:type) {should == "FogbugzTracker"} its(:account) {should == 'abc'} its(:project_id) {should == 'Service - Peon'} its(:username) {should == '1234'} @@ -364,11 +364,11 @@ describe AppsController do context 'insufficient params' do it 'shows validation notice' do put :update, :id => @app.id, :app => { :issue_tracker_attributes => { - :issue_tracker_type => 'fogbugz', :project_id => '1234' } } + :type => 'FogbugzTracker', :project_id => '1234' } } @app.reload - @app.issue_tracker.should be_nil - response.body.should match(/You must specify your FogBugz Area Name, Username, and Password/) + @app.issue_tracker_configured?.should == false + response.body.should match(/You must specify your FogBugz Area Name, FogBugz URL, Username, and Password/) end end end @@ -377,14 +377,14 @@ describe AppsController do context 'with correct params' do before do put :update, :id => @app.id, :app => { :issue_tracker_attributes => { - :issue_tracker_type => 'mingle', :project_id => 'test', :account => 'http://mingle.example.com', + :type => 'MingleTracker', :project_id => 'test', :account => 'http://mingle.example.com', :username => '1234', :password => '123123', :ticket_properties => "card_type = Defect" } } @app.reload end subject {@app.issue_tracker} - its(:issue_tracker_type) {should == 'mingle'} + its(:type) {should == "MingleTracker"} its(:project_id) {should == 'test'} its(:username) {should == '1234'} its(:password) {should == '123123'} @@ -392,12 +392,12 @@ describe AppsController do it "should show validation notice when sufficient params are not present" do put :update, :id => @app.id, :app => { :issue_tracker_attributes => { - :issue_tracker_type => 'mingle', :project_id => 'test', :account => 'http://mingle.example.com', + :type => 'MingleTracker', :project_id => 'test', :account => 'http://mingle.example.com', :username => '1234', :password => '1234', :ticket_properties => "cards_type = Defect" } } @app.reload - @app.issue_tracker.should be_nil + @app.issue_tracker_configured?.should == false response.body.should match(/You must specify your Mingle URL, Project ID, Card Type \(in default card properties\), Sign-in name, and Password/) end end diff --git a/spec/controllers/errs_controller_spec.rb b/spec/controllers/errs_controller_spec.rb index efcdc4c..e6bcbf8 100644 --- a/spec/controllers/errs_controller_spec.rb +++ b/spec/controllers/errs_controller_spec.rb @@ -173,7 +173,7 @@ describe ErrsController do end it "should exist for err's app with issue tracker" do - tracker = Factory(:lighthouseapp_tracker) + tracker = Factory(:lighthouse_tracker) err = Factory(:err, :app => tracker.app) get :show, :app_id => err.app.id, :id => err.id @@ -181,7 +181,7 @@ describe ErrsController do end it "should not exist for err with issue_link" do - tracker = Factory(:lighthouseapp_tracker) + tracker = Factory(:lighthouse_tracker) err = Factory(:err, :app => tracker.app, :issue_link => "http://some.host") get :show, :app_id => err.app.id, :id => err.id @@ -262,7 +262,7 @@ describe ErrsController do context "successful issue creation" do context "lighthouseapp tracker" do let(:notice) { Factory :notice } - let(:tracker) { Factory :lighthouseapp_tracker, :app => notice.err.app } + let(:tracker) { Factory :lighthouse_tracker, :app => notice.err.app } let(:err) { notice.err } before(:each) do @@ -326,7 +326,7 @@ describe ErrsController do context "pivotal tracker" do let(:notice) { Factory :notice } - let(:tracker) { Factory :pivotal_tracker, :app => notice.err.app, :project_id => 10 } + let(:tracker) { Factory :pivotal_labs_tracker, :app => notice.err.app, :project_id => 10 } let(:err) { notice.err } before(:each) do @@ -370,7 +370,7 @@ describe ErrsController do before(:each) do number = 5 @issue_link = "#{tracker.account}/projects/#{tracker.project_id}/cards/#{number}.xml" - @basic_auth = tracker.account.gsub("https://", "https://#{tracker.username}:#{tracker.password}@") + @basic_auth = tracker.account.gsub("://", "://#{tracker.username}:#{tracker.password}@") body = "#{number}" stub_request(:post, "#{@basic_auth}/api/v1/projects/#{tracker.project_id}/cards.xml"). to_return(:status => 201, :headers => {'Location' => @issue_link}, :body => body ) @@ -415,7 +415,7 @@ describe ErrsController do context "error during request to a tracker" do context "lighthouseapp tracker" do - let(:tracker) { Factory :lighthouseapp_tracker } + let(:tracker) { Factory :lighthouse_tracker } let(:err) { Factory :err, :app => tracker.app } before(:each) do diff --git a/spec/factories/issue_tracker_factories.rb b/spec/factories/issue_tracker_factories.rb index 677c9e2..68eb7e8 100644 --- a/spec/factories/issue_tracker_factories.rb +++ b/spec/factories/issue_tracker_factories.rb @@ -1,28 +1,22 @@ -Factory.define :generic_tracker, :class => IssueTracker do |e| +Factory.define :issue_tracker do |e| e.api_token { Factory.next :word } e.project_id { Factory.next :word } e.association :app, :factory => :app -end - -Factory.define :lighthouseapp_tracker, :parent => :generic_tracker do |e| - e.issue_tracker_type 'lighthouseapp' e.account { Factory.next :word } + e.username { Factory.next :word } + e.password { Factory.next :word } end -Factory.define :redmine_tracker, :parent => :generic_tracker do |e| - e.issue_tracker_type 'redmine' - e.account { "http://#{Factory.next(:word)}.com" } +%w(lighthouse pivotal_labs fogbugz).each do |t| + Factory.define "#{t}_tracker".to_sym, :parent => :issue_tracker, :class => "#{t}_tracker".to_sym do |e|; end end -Factory.define :pivotal_tracker, :parent => :generic_tracker do |e| - e.issue_tracker_type 'pivotal' +Factory.define :redmine_tracker, :parent => :issue_tracker, :class => :redmine_tracker do |e| + e.account 'http://redmine.example.com' end -Factory.define :mingle_tracker, :parent => :generic_tracker do |t| - t.issue_tracker_type 'mingle' - t.account "https://mingle.example.com" - t.ticket_properties 'card_type = Defect, defect_status = open, priority = essential' - t.username "test_user" - t.password "test_password" +Factory.define :mingle_tracker, :parent => :issue_tracker, :class => :mingle_tracker do |e| + e.account 'https://mingle.example.com' + e.ticket_properties 'card_type = Defect, defect_status = open, priority = essential' end diff --git a/spec/views/errs/show.html.haml_spec.rb b/spec/views/errs/show.html.haml_spec.rb index 90d0f72..58f46a0 100644 --- a/spec/views/errs/show.html.haml_spec.rb +++ b/spec/views/errs/show.html.haml_spec.rb @@ -51,7 +51,7 @@ describe "errs/show.html.erb" do context "with issue tracker" do def with_issue_tracker(err) - err.app.issue_tracker = IssueTracker.new :issue_tracker_type => "lighthouseapp", :project_id => "1234" + err.app.issue_tracker = PivotalLabsTracker.new :api_token => "token token token", :project_id => "1234" assign :err, err assign :app, err.app end -- libgit2 0.21.2