codefumes 0.1.10 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (68) hide show
  1. data/Gemfile +19 -0
  2. data/Gemfile.lock +135 -0
  3. data/History.txt +12 -0
  4. data/LICENSE +20 -0
  5. data/Manifest.txt +40 -19
  6. data/README.txt +11 -29
  7. data/Rakefile +15 -10
  8. data/bin/fumes +214 -0
  9. data/config/website.yml +2 -0
  10. data/cucumber.yml +2 -0
  11. data/features/claiming_a_project.feature +46 -0
  12. data/features/deleting_a_project.feature +32 -0
  13. data/features/releasing_a_project.feature +50 -0
  14. data/features/step_definitions/cli_steps.rb +98 -0
  15. data/features/step_definitions/common_steps.rb +168 -0
  16. data/features/step_definitions/filesystem_steps.rb +19 -0
  17. data/features/storing_user_api_key.feature +41 -0
  18. data/features/support/common.rb +29 -0
  19. data/features/support/env.rb +24 -0
  20. data/features/support/matchers.rb +11 -0
  21. data/features/synchronizing_repository_with_project.feature +33 -0
  22. data/lib/codefumes.rb +10 -8
  23. data/lib/codefumes/api.rb +20 -11
  24. data/lib/codefumes/api/build.rb +139 -0
  25. data/lib/codefumes/api/claim.rb +74 -0
  26. data/lib/codefumes/api/commit.rb +150 -0
  27. data/lib/codefumes/api/payload.rb +93 -0
  28. data/lib/codefumes/api/project.rb +158 -0
  29. data/lib/codefumes/cli_helpers.rb +54 -0
  30. data/lib/codefumes/config_file.rb +3 -2
  31. data/lib/codefumes/errors.rb +21 -0
  32. data/lib/codefumes/exit_codes.rb +10 -0
  33. data/lib/codefumes/harvester.rb +113 -0
  34. data/lib/codefumes/quick_build.rb +43 -0
  35. data/lib/codefumes/quick_metric.rb +20 -0
  36. data/lib/codefumes/source_control.rb +137 -0
  37. data/lib/integrity_notifier/codefumes.haml +11 -0
  38. data/lib/integrity_notifier/codefumes.rb +62 -0
  39. data/spec/codefumes/{build_spec.rb → api/build_spec.rb} +14 -24
  40. data/spec/codefumes/{claim_spec.rb → api/claim_spec.rb} +42 -3
  41. data/spec/codefumes/{commit_spec.rb → api/commit_spec.rb} +34 -24
  42. data/spec/codefumes/api/payload_spec.rb +148 -0
  43. data/spec/codefumes/api/project_spec.rb +286 -0
  44. data/spec/codefumes/api_spec.rb +38 -15
  45. data/spec/codefumes/config_file_spec.rb +69 -13
  46. data/spec/codefumes/harvester_spec.rb +118 -0
  47. data/spec/codefumes/source_control_spec.rb +199 -0
  48. data/spec/codefumes_service_helpers.rb +23 -19
  49. data/spec/fixtures/sample_project_dirs/no_scm/description +4 -0
  50. data/spec/spec_helper.rb +1 -0
  51. data/tasks/cucumber.rake +11 -0
  52. metadata +145 -60
  53. data/bin/cf_claim_project +0 -9
  54. data/bin/cf_release_project +0 -10
  55. data/bin/cf_store_credentials +0 -10
  56. data/lib/cf_claim_project/cli.rb +0 -95
  57. data/lib/cf_release_project/cli.rb +0 -76
  58. data/lib/cf_store_credentials/cli.rb +0 -50
  59. data/lib/codefumes/build.rb +0 -131
  60. data/lib/codefumes/claim.rb +0 -57
  61. data/lib/codefumes/commit.rb +0 -144
  62. data/lib/codefumes/payload.rb +0 -103
  63. data/lib/codefumes/project.rb +0 -129
  64. data/spec/cf_claim_project/cli_spec.rb +0 -17
  65. data/spec/cf_release_project/cli_spec.rb +0 -41
  66. data/spec/cf_store_credentials/cli_spec.rb +0 -28
  67. data/spec/codefumes/payload_spec.rb +0 -155
  68. data/spec/codefumes/project_spec.rb +0 -274
@@ -0,0 +1,43 @@
1
+ module CodeFumes
2
+ class QuickBuild
3
+ # Creates a new build for the CodeFumes project linked
4
+ # at the specified repository path and associates
5
+ # it with the current local commit identifier
6
+ #
7
+ # Returns +true+ if the request succeeded.
8
+ #
9
+ # Returns +false+ if the request failed.
10
+ def self.start(build_name, options = {})
11
+ repo = SourceControl.new(options[:repository_path] || './')
12
+
13
+ commit_identifier = options[:commit_identifier] || repo.local_commit_identifier
14
+ public_key = options[:public_key] || repo.public_key
15
+ private_key = options[:private_key] || repo.private_key
16
+ started_at = options[:started_at] || Time.now
17
+
18
+ project = Project.new(public_key, :private_key => private_key)
19
+ commit = Commit.new(project, commit_identifier)
20
+ timestamps = {:started_at => started_at, :ended_at => ""}
21
+ build = Build.new(commit, build_name, :running, timestamps)
22
+ build.save
23
+ end
24
+
25
+ def self.finish(build_name, success_or_failure, options = {})
26
+ repo = SourceControl.new(options[:repository_path] || './')
27
+
28
+ commit_identifier = options[:commit_identifier] || repo.local_commit_identifier
29
+ public_key = options[:public_key] || repo.public_key
30
+ private_key = options[:private_key] || repo.private_key
31
+ ended_at = options[:ended_at] || Time.now
32
+
33
+ project = Project.new(public_key, :private_key => private_key)
34
+ commit = Commit.new(project, commit_identifier)
35
+
36
+ build = Build.find(commit, build_name)
37
+ return false if build.nil?
38
+ build.state = success_or_failure.to_s
39
+ build.ended_at = ended_at
40
+ build.save
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,20 @@
1
+ module CodeFumes
2
+ class QuickMetric
3
+ # Associates a Hash of +custom_attributes+ with the current commit
4
+ # identifier of the repository located at +repository_path+.
5
+ #
6
+ # Returns +true+ if the request succeeded.
7
+ #
8
+ # Returns +false+ if the request failed.
9
+ def self.save(custom_attributes, repository_path = './')
10
+ repo = SourceControl.new(repository_path)
11
+ commit = {:identifier => repo.local_commit_identifier,
12
+ :custom_attributes => custom_attributes
13
+ }
14
+ content = {:content => {:commits => [commit]}}
15
+ project = Project.new(repo.public_key, :private_key => repo.private_key)
16
+ payload_set = Payload.prepare(project, content)
17
+ payload_set.reject {|payload| payload.save}.empty?
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,137 @@
1
+ module CodeFumes
2
+ # Defines the contract between CodeFumes and any local source control
3
+ # management system (SCM).
4
+ #
5
+ # *NOTE:* Git is currently the only supported SCM. We look
6
+ # forward to changing this soon.
7
+ class SourceControl
8
+ SUPPORTED_SCMS_AND_DETECTORS = {:git => '.git'} #:nodoc:
9
+
10
+ # Sets up a SourceControl object to read content from the repository
11
+ # located at +path+.
12
+ def initialize(path)
13
+ begin
14
+ @repository = Grit::Repo.new(path)
15
+ rescue Grit::InvalidGitRepositoryError
16
+ raise Errors::UnsupportedScmToolError
17
+ end
18
+ end
19
+
20
+ # Returns a serialized Hash containing a single +:commits+ key
21
+ # associated with an Array of serialized commit information, ready
22
+ # to be sent to the CodeFumes service.
23
+ def payload_between(from = initial_commit_identifier, to = "HEAD")
24
+ start_commit = from || initial_commit_identifier
25
+ end_commit = to || "HEAD"
26
+ new_commits = commits_between(start_commit, end_commit)
27
+ new_commits.empty? ? {} : {:commits => new_commits}
28
+ end
29
+ alias :payload :payload_between
30
+
31
+ # Returns the first commit identifier of a repository's history.
32
+ def initial_commit_identifier
33
+ initial_commit.sha
34
+ end
35
+
36
+ # Returns an array of 'symbolized' executable names for all
37
+ # supported SCMs.
38
+ #
39
+ # The names are returned as symbols.
40
+ def self.supported_systems
41
+ SUPPORTED_SCMS_AND_DETECTORS.keys
42
+ end
43
+
44
+ # Accepts command-line executable name of SCM and returns whether it
45
+ # is a supported SCM or not. +tool_cli_name+ should be the
46
+ # name of the executable, not the 'full name' of the application
47
+ # (ex: 'svn' not 'subversion').
48
+ #
49
+ # Returns +true+ if the SCM is supported
50
+ #
51
+ # Returns +false+ if the SCM is not supported.
52
+ def self.supported_system?(tool_cli_name)
53
+ SUPPORTED_SCMS_AND_DETECTORS.keys.include?(tool_cli_name.to_sym)
54
+ end
55
+
56
+ # Stores the public_key of the project associated with the
57
+ # underlying local repository. This will not be necessary
58
+ # with all SCMs.
59
+ #
60
+ # For example, in a git repository, this method will store a
61
+ # +codefumes+ key in the +.git/config+ file. This value can be used
62
+ # as a lookup key for other tools to use in conjunction with the
63
+ # CodeFumes config file (see +ConfigFile+) to interact with a
64
+ # CodeFumes project.
65
+ def store_public_key(public_key)
66
+ @repository.config["codefumes.public-key"] = public_key
67
+ end
68
+
69
+ # Removes any association to the CodeFumes service which would have
70
+ # been added using the +store_public_key+ method.
71
+ #
72
+ # This method does not remove anything from the user's global
73
+ # CodeFumes config file.
74
+ def unlink_from_codefumes!
75
+ @repository.git.config({}, "--remove-section", "codefumes")
76
+ end
77
+
78
+ # Returns the public key of the project associated with this
79
+ # repository.
80
+ def public_key
81
+ @repository.config["codefumes.public-key"]
82
+ end
83
+
84
+ # Returns the private key of the project assciated with this
85
+ # repository.
86
+ def private_key
87
+ ConfigFile.options_for_project(public_key)[:private_key]
88
+ end
89
+
90
+ # Returns the current commit identifier of the underlying
91
+ # repository ('HEAD' of the supplied branch in git parlance).
92
+ def local_commit_identifier(branch_name = "master")
93
+ raise ArgumentError, "nil branch name supplied" if branch_name.nil?
94
+ @repository.get_head(branch_name).commit.sha
95
+ end
96
+
97
+ # Returns the full path of the underlying repository.
98
+ def path
99
+ @repository.path
100
+ end
101
+
102
+ private
103
+ def initial_commit
104
+ @repository.log.last
105
+ end
106
+
107
+ # Returns Array of serialized commit data. Each item in the Array
108
+ # contains attributes of a single commit.
109
+ def commits_between(from, to, including_from_commit = false)
110
+ commit_list = @repository.commits_between(from,to)
111
+
112
+ if including_from_commit == true || from == initial_commit_identifier
113
+ commit_list = [initial_commit] + commit_list
114
+ end
115
+
116
+ commit_list.map do |commit|
117
+ commit_stats = commit.stats
118
+ {
119
+ :identifier => commit.sha,
120
+ :author_name => commit.author.name,
121
+ :author_email => commit.author.email,
122
+ :committer_name => commit.committer.name,
123
+ :committer_email => commit.committer.email,
124
+ :authored_at => commit.authored_date,
125
+ :committed_at => commit.committed_date,
126
+ :message => commit.message,
127
+ :short_message => commit.short_message,
128
+ :parent_identifiers => commit.parents.map(&:sha).join(','),
129
+ :line_additions => commit_stats.additions,
130
+ :line_deletions => commit_stats.deletions,
131
+ :line_total => commit_stats.deletions,
132
+ :affected_file_count => commit_stats.files.count
133
+ }
134
+ end.reverse
135
+ end
136
+ end
137
+ end
@@ -0,0 +1,11 @@
1
+ %p.normal
2
+ %label{ :for => "cf_build_name" } Build name
3
+ %input.text#cf_build_name{ :name => "notifiers[CodeFumes][build_name]", :type => "text", :value => config["build_name"] }
4
+
5
+ %p.normal
6
+ %label{ :for => "cf_public_key" } Public key
7
+ %input.text#cf_public_key{ :name => "notifiers[CodeFumes][public_key]", :type => "text", :value => config["public_key"] }
8
+
9
+ %p.normal
10
+ %label{ :for => "cf_private_key" } Private key
11
+ %input.text#cf_private_key{ :name => "notifiers[CodeFumes][private_key]", :type => "text", :value => config["private_key"] }
@@ -0,0 +1,62 @@
1
+ begin
2
+ require 'codefumes_harvester'
3
+ rescue LoadError
4
+ abort "Install codefumes_harvester to use the CodeFumes notifier"
5
+ end
6
+
7
+ module CodeFumesHarvester
8
+ class IntegrityNotifier
9
+ class CodeFumes < ::Integrity::Notifier::Base
10
+ attr_reader :private_key, :public_key
11
+
12
+ def self.to_haml
13
+ @haml ||= File.read(File.dirname(__FILE__) + "/codefumes.haml")
14
+ end
15
+
16
+ def initialize(build, config={})
17
+ @public_key = config["public_key"]
18
+ @private_key = config["private_key"]
19
+ @build_name = config["build_name"]
20
+ @repo_path = Integrity::Repository.new(
21
+ build.id, build.project.uri, build.project.branch, build.commit.identifier
22
+ ).directory
23
+ super(build, config)
24
+ end
25
+
26
+ def deliver!
27
+ Integrity.log "Updating build '#{@build_name}' for '#{@public_key}' (state: #{build_state})"
28
+ qb_options = {:public_key => @public_key,
29
+ :private_key => @private_key,
30
+ :ended_at => @build.completed_at,
31
+ :repository_path => @repo_path}
32
+
33
+ CodeFumesHarvester::QuickBuild.finish(@build_name, build_state, qb_options)
34
+ end
35
+
36
+ def deliver_started_notification!
37
+ Integrity.log "Adding build '#{@build_name}' for '#{@public_key}' (state: #{build_state})"
38
+ qb_options = {:public_key => @public_key,
39
+ :private_key => @private_key,
40
+ :started_at => @build.started_at,
41
+ :repository_path => @repo_path}
42
+
43
+ CodeFumesHarvester::QuickBuild.start(@build_name, qb_options)
44
+ end
45
+
46
+ private
47
+ def build_state
48
+ case @build.status
49
+ when :success then :successful
50
+ when :failed then :failed
51
+ when :building then :running
52
+ end
53
+ end
54
+ end
55
+ end
56
+ end
57
+
58
+ module Integrity
59
+ class Notifier
60
+ register CodeFumesHarvester::IntegrityNotifier::CodeFumes
61
+ end
62
+ end
@@ -1,7 +1,7 @@
1
- require File.dirname(__FILE__) + '/../spec_helper.rb'
1
+ require File.dirname(__FILE__) + '/../../spec_helper.rb'
2
2
 
3
- describe "Build" do
4
- include CodeFumesServiceHelpers::Build
3
+ describe "API::Build" do
4
+ include CodeFumesServiceHelpers::BuildHelpers
5
5
 
6
6
  after(:all) do
7
7
  FakeWeb.allow_net_connect = false
@@ -11,11 +11,7 @@ describe "Build" do
11
11
  before(:each) do
12
12
  setup_fixture_base
13
13
  setup_build_fixtures
14
- @build_params = { :public_key => @pub_key, :private_key => @priv_key,
15
- :name => @build_name, :commit_identifier => @commit_identifier,
16
- :started_at => @started_at, :state => @state}
17
-
18
- @build = Build.new(@build_params)
14
+ @build = Build.new(@commit, @build_name, @state, {:started_at => @started_at})
19
15
  end
20
16
 
21
17
  describe "save" do
@@ -23,10 +19,10 @@ describe "Build" do
23
19
  @build.stub!(:exists?).and_return(false)
24
20
  register_create_uri(["401", "Unauthorized"], "")
25
21
 
26
- basic_auth_params = {:username => @pub_key, :password => @priv_key}
22
+ basic_auth_params = {:username => @project.public_key, :password => @project.private_key}
27
23
 
28
24
  build_query = {:build => {:name => @build_name, :ended_at => nil, :started_at => @started_at, :state => @state}}
29
- Build.should_receive(:post).with("/projects/#{@project.public_key}/commits/#{@commit_identifier}/builds", :query => build_query, :basic_auth => basic_auth_params).and_return(mock("response", :code => 401))
25
+ API.should_receive(:post).with("/projects/#{@project.public_key}/commits/#{@commit_identifier}/builds", :query => build_query, :basic_auth => basic_auth_params).and_return(mock("response", :code => 401))
30
26
  @build.save
31
27
  end
32
28
 
@@ -63,16 +59,13 @@ describe "Build" do
63
59
  end
64
60
 
65
61
  context "when the build already exists on the server" do
66
- before(:each) do
67
- register_update_uri(["200", "OK"])
68
- @build = Build.new(@build_params.merge(:identifier => @build_identifier))
69
- Build.stub!(:find).and_return(@build)
70
- end
71
-
72
62
  it "updates the existing build" do
63
+ register_update_uri(["200", "OK"])
64
+ build = Build.new(@commit, @build_name, @state, {:identifier => @build_identifier})
65
+ Build.stub!(:find).and_return(build)
73
66
  mock_response = mock("Response", :code => 200).as_null_object
74
- @build.should_receive(:update).and_return(mock_response)
75
- @build.save
67
+ build.should_receive(:update).and_return(mock_response)
68
+ build.save
76
69
  end
77
70
  end
78
71
  end
@@ -81,21 +74,18 @@ describe "Build" do
81
74
  before(:each) do
82
75
  setup_fixture_base
83
76
  setup_build_fixtures
84
- @find_params = {:public_key => @pub_key,
85
- :commit_identifier => @commit_identifier,
86
- :identifier => @build_identifier}
87
77
  end
88
78
 
89
79
  it "returns an instance of Build when found" do
90
80
  register_show_uri(["200", "OK"])
91
- returned_object = Build.find(@find_params)
81
+ returned_object = Build.find(@commit, @build_name)
92
82
  returned_object.should be_instance_of(Build)
93
83
  returned_object.state.should_not be_nil
94
84
  end
95
85
 
96
86
  it "returns nil when not found" do
97
87
  register_show_uri(["404", "Not found"])
98
- Build.find(@find_params).should be_nil
88
+ Build.find(@commit, @build_name).should be_nil
99
89
  end
100
90
  end
101
91
 
@@ -103,7 +93,7 @@ describe "Build" do
103
93
  before(:each) do
104
94
  setup_fixture_base
105
95
  setup_build_fixtures
106
- @build = Build.new(@build_params.merge(:identifier => @build_identifier))
96
+ @build = Build.new(@commit, @build_name, @state)
107
97
  end
108
98
 
109
99
  it "returns true when the request returns a status of '200 Ok'" do
@@ -1,7 +1,7 @@
1
- require File.dirname(__FILE__) + '/../spec_helper.rb'
1
+ require File.dirname(__FILE__) + '/../../spec_helper.rb'
2
2
 
3
- describe Claim do
4
- include CodeFumesServiceHelpers::Claim
3
+ describe "API::Claim" do
4
+ include CodeFumesServiceHelpers::ClaimHelpers
5
5
 
6
6
  after(:all) do
7
7
  FakeWeb.allow_net_connect = false
@@ -47,6 +47,32 @@ describe Claim do
47
47
  }.should raise_error(ArgumentError)
48
48
  end
49
49
  end
50
+
51
+ context "a nil value is passed in for the api_key" do
52
+ it "should not hit the CodeFumes API" do
53
+ API.should_not_receive(:put)
54
+ lambda {Claim.create(@project, nil)}
55
+ end
56
+
57
+ it "raises a NoUserApiKeyError" do
58
+ lambda {
59
+ Claim.create(@project, nil)
60
+ }.should raise_error(Errors::NoUserApiKeyError)
61
+ end
62
+ end
63
+
64
+ context "an empty string is passed in for the api_key" do
65
+ it "should not hit the CodeFumes API" do
66
+ API.should_not_receive(:put)
67
+ lambda {Claim.create(@project, '')}
68
+ end
69
+
70
+ it "raises a NoUserApiKeyError" do
71
+ lambda {
72
+ Claim.create(@project, '')
73
+ }.should raise_error(Errors::NoUserApiKeyError)
74
+ end
75
+ end
50
76
  end
51
77
 
52
78
  describe "destroy" do
@@ -63,5 +89,18 @@ describe Claim do
63
89
  Claim.destroy(@project, @api_key).should be_false
64
90
  end
65
91
  end
92
+
93
+ context "a nil value is passed in for the api_key" do
94
+ it "should not hit the CodeFumes API" do
95
+ API.should_not_receive(:delete)
96
+ lambda {Claim.destroy(@project, nil)}
97
+ end
98
+
99
+ it "raises a NoUserApiKeyError" do
100
+ lambda {
101
+ Claim.destroy(@project, nil)
102
+ }.should raise_error(Errors::NoUserApiKeyError)
103
+ end
104
+ end
66
105
  end
67
106
  end
@@ -1,7 +1,7 @@
1
- require File.dirname(__FILE__) + '/../spec_helper.rb'
1
+ require File.dirname(__FILE__) + '/../../spec_helper.rb'
2
2
 
3
- describe "Commit" do
4
- include CodeFumesServiceHelpers::Commit
3
+ describe "API::Commit" do
4
+ include CodeFumesServiceHelpers::CommitHelpers
5
5
 
6
6
  before(:all) do
7
7
  FakeWeb.allow_net_connect = false
@@ -11,9 +11,7 @@ describe "Commit" do
11
11
  @priv_key = 'private_key_value'
12
12
  @anonymous_base_uri = "http://codefumes.com/api/v1/xml"
13
13
  @authenticated_base_uri = "http://#{@pub_key}:#{@priv_key}@codefumes.com/api/v1/xml/projects"
14
- @project = Project.new(:public_key => @pub_key,
15
- :private_key => @priv_key,
16
- :name => @project_name)
14
+ @project = Project.new(@pub_key, :private_key => @priv_key, :name => @project_name)
17
15
  @authd_project_api_uri = "#{@authenticated_base_uri}/projects/#{@pub_key}"
18
16
  @anon_project_api_uri = "#{@anonymous_base_uri}/projects/#{@pub_key}"
19
17
  @basic_auth_params = {:username => @pub_key, :password => @priv_key}
@@ -24,11 +22,23 @@ describe "Commit" do
24
22
  FakeWeb.clean_registry
25
23
  end
26
24
 
27
- describe "find" do
25
+ describe "#id" do
26
+ it "returns the value of #identifier" do
27
+ Commit.new(@project, @identifier).id.should == @identifier
28
+ end
29
+ end
30
+
31
+ describe "#sha" do
32
+ it "returns the value of #identifier" do
33
+ Commit.new(@project, @identifier).sha.should == @identifier
34
+ end
35
+ end
36
+
37
+ describe "#find" do
28
38
  context "with a valid commit identifier" do
29
39
  before(:each) do
30
40
  register_find_uri
31
- @commit = Commit.find(@identifier)
41
+ @commit = Commit.find(@project, @identifier)
32
42
  end
33
43
 
34
44
  [:identifier,
@@ -60,40 +70,40 @@ describe "Commit" do
60
70
  end
61
71
 
62
72
  it "returns nil" do
63
- Commit.find(@identifier).should == nil
73
+ Commit.find(@project, @identifier).should == nil
64
74
  end
65
75
  end
66
76
  end
67
77
 
68
- describe "calling 'latest'" do
78
+ describe "#latest" do
69
79
  context "with valid parameters" do
70
80
  it "returns a commit object for the latest commit" do
71
81
  register_latest_uri
72
- Commit.latest(@pub_key).identifier.should == @identifier
82
+ Commit.latest(@project).identifier.should == @identifier
73
83
  end
74
84
  end
75
85
 
76
86
  context "with invalid parameters" do
77
87
  it "returns nil" do
78
88
  register_latest_uri(["404", "Not Found"], "")
79
- Commit.latest(@pub_key).should == nil
89
+ Commit.latest(@project).should == nil
80
90
  end
81
91
  end
82
92
  end
83
93
 
84
- describe "calling 'latest_identifier'" do
94
+ describe "#latest_identifier" do
85
95
  context "with valid parameters" do
86
96
  context "when the specified project has commits stored" do
87
97
  it "returns the commit identifier of the latest commit" do
88
98
  register_latest_uri
89
- Commit.latest_identifier(@pub_key).should == @identifier
99
+ Commit.latest_identifier(@project).should == @identifier
90
100
  end
91
101
  end
92
102
 
93
103
  context "when the specified project does not have any commits stored" do
94
104
  it "returns nil" do
95
105
  register_latest_uri(["404", "Not Found"], "")
96
- Commit.latest_identifier(@pub_key).should == nil
106
+ Commit.latest_identifier(@project).should == nil
97
107
  end
98
108
  end
99
109
  end
@@ -101,23 +111,23 @@ describe "Commit" do
101
111
  context "with invalid parameters" do
102
112
  it "returns nil" do
103
113
  register_latest_uri(["404", "Not Found"], "")
104
- Commit.latest(@pub_key).should == nil
114
+ Commit.latest(@project).should == nil
105
115
  end
106
116
  end
107
117
  end
108
118
 
109
- describe "calling 'all'" do
119
+ describe "#all" do
110
120
  context "with valid parameters" do
111
121
  it "returns an array of commits" do
112
122
  register_index_uri
113
- Commit.all(@pub_key).should have(3).items
123
+ Commit.all(@project).should have(3).items
114
124
  end
115
125
  end
116
126
 
117
127
  context "with invalid parameters" do
118
128
  it "returns nil" do
119
129
  register_index_uri(["404", "Not Found"], "")
120
- Commit.all(@pub_key).should == nil
130
+ Commit.all(@project).should == nil
121
131
  end
122
132
  end
123
133
  end
@@ -127,17 +137,17 @@ describe "Commit" do
127
137
  register_find_uri
128
138
  @email = "jdoe@example.com"
129
139
  @name = "John Doe"
130
- @commit = Commit.find(@identifier)
140
+ @commit = Commit.find(@project, @identifier)
131
141
  end
132
142
 
133
- describe "author" do
143
+ describe "#author" do
134
144
  it "returns a concatenated string containing the author's name & email" do
135
145
  @commit.author.should =~ /#{@name}/
136
146
  @commit.author.should =~ /#{@email}/
137
147
  end
138
148
  end
139
149
 
140
- describe "committer" do
150
+ describe "#committer" do
141
151
  it "returns a concatenated string containing the author's name & email" do
142
152
  @commit.committer.should =~ /#{@name}/
143
153
  @commit.committer.should =~ /#{@email}/
@@ -152,14 +162,14 @@ describe "Commit" do
152
162
  end
153
163
 
154
164
  it "returns an empty Hash" do
155
- Commit.latest(@pub_key).custom_attributes.should == {}
165
+ Commit.latest(@project).custom_attributes.should == {}
156
166
  end
157
167
  end
158
168
 
159
169
  context "when the commit has defined custom attributes" do
160
170
  before(:each) do
161
171
  register_latest_uri(["200", "Ok"], fixtures[:commit_with_custom_attrs])
162
- @commit = Commit.latest(@pub_key)
172
+ @commit = Commit.latest(@project)
163
173
  end
164
174
 
165
175
  it "returns a Hash of key-value pairs (attribute_name -> attribute_value)" do