github_api 0.10.1 → 0.10.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (38) hide show
  1. data/README.md +1 -1
  2. data/features/cassettes/ratelimit/get.yml +64 -0
  3. data/features/cassettes/ratelimit/get_remaining.yml +64 -0
  4. data/features/cassettes/repos/contents/create.yml +60 -0
  5. data/features/cassettes/repos/contents/delete.yml +59 -0
  6. data/features/cassettes/repos/contents/update.yml +62 -0
  7. data/features/issues.feature +3 -3
  8. data/features/pagination.feature +12 -12
  9. data/features/rate_limit.feature +16 -0
  10. data/features/repos/contents.feature +39 -0
  11. data/features/support/settings.rb +5 -1
  12. data/features/support/vcr.rb +1 -0
  13. data/lib/github_api/issues.rb +2 -16
  14. data/lib/github_api/jsonable.rb +1 -0
  15. data/lib/github_api/params_hash.rb +13 -0
  16. data/lib/github_api/rate_limit.rb +8 -4
  17. data/lib/github_api/repos.rb +2 -2
  18. data/lib/github_api/repos/contents.rb +110 -0
  19. data/lib/github_api/response/raise_error.rb +2 -2
  20. data/lib/github_api/version.rb +1 -1
  21. data/spec/fixtures/repos/content_created.json +44 -0
  22. data/spec/fixtures/repos/content_deleted.json +30 -0
  23. data/spec/github/api_spec.rb +2 -0
  24. data/spec/github/issues/list_spec.rb +10 -0
  25. data/spec/github/mime_type_spec.rb +2 -0
  26. data/spec/github/normalizer_spec.rb +2 -0
  27. data/spec/github/parameter_filter_spec.rb +2 -0
  28. data/spec/github/params_hash_spec.rb +5 -0
  29. data/spec/github/repos/contents/create_spec.rb +41 -0
  30. data/spec/github/repos/contents/delete_spec.rb +55 -0
  31. data/spec/github/repos/downloads/delete_spec.rb +2 -3
  32. data/spec/github/request/jsonize_spec.rb +2 -0
  33. data/spec/github/request/oauth2_spec.rb +2 -0
  34. data/spec/github/s3_uploader_spec.rb +2 -0
  35. data/spec/github/utils/url_spec.rb +2 -0
  36. data/spec/github/validations_spec.rb +2 -0
  37. data/spec/integration/multiple_invocations_spec.rb +2 -2
  38. metadata +52 -42
@@ -4,4 +4,8 @@ def settings_file
4
4
  Pathname.new(File.expand_path("../../settings.yml", __FILE__))
5
5
  end
6
6
 
7
- SETTINGS = (File.exists?(settings_file) && yaml= YAML.load_file(settings_file)) ? yaml : {'basic_auth' => 'login:password', 'oauth_token' => 'as79asfd79ads', 'user'=> 'octokat', 'repo' => 'dummy', 'email' => 'email@example.com'}
7
+ def live_credentials?
8
+ true
9
+ end
10
+
11
+ SETTINGS = (live_credentials? && File.exists?(settings_file) && yaml= YAML.load_file(settings_file)) ? yaml : {'basic_auth' => 'login:password', 'oauth_token' => 'as79asfd79ads', 'user'=> 'murek', 'repo' => 'dummy', 'email' => 'email@example.com'}
@@ -8,6 +8,7 @@ VCR.configure do |conf|
8
8
  conf.filter_sensitive_data('<TOKEN>') { SETTINGS['oauth_token'] }
9
9
  conf.filter_sensitive_data('<BASIC_AUTH>') { SETTINGS['basic_auth'] }
10
10
  conf.filter_sensitive_data('<USER>') { SETTINGS['user'] }
11
+ conf.debug_logger = File.open('test.log', 'w')
11
12
  end
12
13
 
13
14
  VCR.cucumber_tags do |t|
@@ -126,15 +126,6 @@ module Github
126
126
  # :sort => 'comments',
127
127
  # :direction => 'asc'
128
128
  #
129
- # github = Github.new :user => 'user-name', :repo => 'repo-name'
130
- # github.issues.list_repo :milestone => 1,
131
- # :state => 'open',
132
- # :assignee => '*',
133
- # :mentioned => 'octocat',
134
- # :labels => "bug,ui,bla",
135
- # :sort => 'comments',
136
- # :direction => 'asc'
137
- #
138
129
  def list(*args)
139
130
  params = arguments(args) do
140
131
  assert_values VALID_ISSUE_PARAM_VALUES
@@ -146,7 +137,7 @@ module Github
146
137
  elsif (user_name = params.delete('user')) &&
147
138
  (repo_name = params.delete('repo'))
148
139
 
149
- list_repo user_name, repo_name, params
140
+ list_repo user_name, repo_name
150
141
  elsif args.include? :user
151
142
  get_request("/user/issues", params)
152
143
  else
@@ -160,12 +151,7 @@ module Github
160
151
  # List issues for a repository
161
152
  #
162
153
  # def list_repo(user_name, repo_name, params)
163
- def list_repo(*args)
164
- arguments(args, :required => [:user, :repo]) do
165
- sift VALID_ISSUE_PARAM_NAMES
166
- assert_values VALID_ISSUE_PARAM_VALUES
167
- end
168
-
154
+ def list_repo(user, repo)
169
155
  get_request("/repos/#{user}/#{repo}/issues", arguments.params)
170
156
  end
171
157
  private :list_repo
@@ -7,6 +7,7 @@ module Github
7
7
  extend self
8
8
 
9
9
  def decode(*args)
10
+ return unless args.first
10
11
  if MultiJson.respond_to?(:load)
11
12
  MultiJson.load *args
12
13
  else
@@ -1,6 +1,7 @@
1
1
  # encoding: utf-8
2
2
 
3
3
  require 'delegate'
4
+ require 'base64'
4
5
 
5
6
  module Github
6
7
 
@@ -66,5 +67,17 @@ module Github
66
67
  self
67
68
  end
68
69
 
70
+ # Base64 encode string removing newline characters
71
+ #
72
+ def strict_encode64(key)
73
+ value = self[key]
74
+ encoded = if Base64.respond_to?(:strict_encode64)
75
+ Base64.strict_encode64(value)
76
+ else
77
+ [value].pack("m0")
78
+ end
79
+ self[key] = encoded.delete("\n\r")
80
+ end
81
+
69
82
  end # ParamsHash
70
83
  end # Github
@@ -3,12 +3,16 @@
3
3
  module Github
4
4
  module RateLimit
5
5
 
6
- def ratelimit
7
- get_request("/rate_limit").rate.limit
6
+ def ratelimit(*args)
7
+ arguments(args)
8
+
9
+ get_request("/rate_limit", arguments.params).rate.limit
8
10
  end
9
11
 
10
- def ratelimit_remaining
11
- get_request("/rate_limit").rate.remaining
12
+ def ratelimit_remaining(*args)
13
+ arguments(args)
14
+
15
+ get_request("/rate_limit", arguments.params).rate.remaining
12
16
  end
13
17
 
14
18
  end # RateLimit
@@ -120,8 +120,8 @@ module Github
120
120
  #
121
121
  # = Examples
122
122
  # github = Github.new
123
- # github.repos.list every: true
124
- # github.repos.list every: true { |repo| ... }
123
+ # github.repos.list :every
124
+ # github.repos.list :every { |repo| ... }
125
125
  #
126
126
  # List public repositories for the specified user.
127
127
  #
@@ -6,6 +6,8 @@ module Github
6
6
  # as Base64 encoded content.
7
7
  class Repos::Contents < API
8
8
 
9
+ REQUIRED_CONTENT_OPTIONS = %w[ path message content ]
10
+
9
11
  # Get the README
10
12
  #
11
13
  # This method returns the preferred README for a repository.
@@ -46,6 +48,114 @@ module Github
46
48
  end
47
49
  alias :find :get
48
50
 
51
+ # Create a file
52
+ #
53
+ # This method creates a new file in a repository
54
+ #
55
+ # = Parameters
56
+ # * <tt>:path</tt> - Requried string - The content path
57
+ # * <tt>:message</tt> - Requried string - The commit message
58
+ # * <tt>:content</tt> - Requried string - The new file content,
59
+ # which will be Base64 encoded
60
+ # * <tt>:branch</tt> - Optional string - The branch name. If not provided,
61
+ # uses the repository’s default branch (usually master)
62
+ # = Optional Parameters
63
+ #
64
+ # The <tt>author</tt> section is optional and is filled in with the
65
+ # <tt>committer</tt> information if omitted. If the <tt>committer</tt>
66
+ # information is omitted, the authenticated user’s information is used.
67
+ #
68
+ # You must provide values for both <tt>name</tt> and <tt>email</tt>, whether
69
+ # you choose to use <tt>author</tt> or <tt>committer</tt>. Otherwise, you’ll
70
+ # receive a <tt>500</tt> status code.
71
+ #
72
+ # * <tt>author.name</tt> - string - The name of the author of the commit
73
+ # * <tt>author.email</tt> - string - The email of the author of the commit
74
+ # * <tt>committer.name</tt> - string - The name of the committer of the commit
75
+ # * <tt>committer.email</tt> - string - The email of the committer of the commit
76
+ #
77
+ # = Examples
78
+ # github = Github.new
79
+ # github.repos.contents.create 'user-name', 'repo-name', 'path',
80
+ # path: 'hello.rb',
81
+ # content: "puts 'hello ruby'",
82
+ # message: "my commit message"
83
+ #
84
+ def create(*args)
85
+ arguments(args, :required => [:user, :repo, :path]) do
86
+ assert_required REQUIRED_CONTENT_OPTIONS
87
+ end
88
+ params = arguments.params
89
+ params.strict_encode64('content')
90
+
91
+ put_request("/repos/#{user}/#{repo}/contents/#{path}", params)
92
+ end
93
+
94
+ # Update a file
95
+ #
96
+ # This method updates a file in a repository
97
+ #
98
+ # = Parameters
99
+ # * <tt>:path</tt> - Requried string - The content path
100
+ # * <tt>:message</tt> - Requried string - The commit message
101
+ # * <tt>:content</tt> - Requried string - The new file content,
102
+ # which will be Base64 encoded
103
+ # * <tt>:sha</tt> - Requried string - The blob SHA of the file being replaced.
104
+ # * <tt>:branch</tt> - Optional string - The branch name. If not provided,
105
+ # uses the repository’s default branch (usually master)
106
+ #
107
+ # = Examples
108
+ # github = Github.new
109
+ # github.repos.contents.update 'user-name', 'repo-name', 'path',
110
+ # path: 'hello.rb',
111
+ # content: "puts 'hello ruby again'",
112
+ # message: "my commit message",
113
+ # sha: "25b0bef9e404bd2e3233de26b7ef8cbd86d0e913"
114
+ #
115
+ def update(*args)
116
+ create(*args)
117
+ end
118
+
119
+ # Delete a file
120
+ #
121
+ # This method deletes a file in a repository
122
+ #
123
+ # = Parameters
124
+ # * <tt>:path</tt> - Requried string - The content path
125
+ # * <tt>:message</tt> - Requried string - The commit message
126
+ # * <tt>:sha</tt> - Requried string - The blob SHA of the file being removed.
127
+ # * <tt>:branch</tt> - Optional string - The branch name. If not provided,
128
+ # uses the repository’s default branch (usually master)
129
+ # = Optional Parameters
130
+ #
131
+ # The <tt>author</tt> section is optional and is filled in with the
132
+ # <tt>committer</tt> information if omitted. If the <tt>committer</tt>
133
+ # information is omitted, the authenticated user’s information is used.
134
+ #
135
+ # You must provide values for both <tt>name</tt> and <tt>email</tt>, whether
136
+ # you choose to use <tt>author</tt> or <tt>committer</tt>. Otherwise, you’ll
137
+ # receive a <tt>500</tt> status code.
138
+ #
139
+ # * <tt>author.name</tt> - string - The name of the author of the commit
140
+ # * <tt>author.email</tt> - string - The email of the author of the commit
141
+ # * <tt>committer.name</tt> - string - The name of the committer of the commit
142
+ # * <tt>committer.email</tt> - string - The email of the committer of the commit
143
+ #
144
+ # = Examples
145
+ # github = Github.new
146
+ # github.repos.contents.delete 'user-name', 'repo-name', 'path',
147
+ # path: 'hello.rb',
148
+ # message: "delete hello.rb file",
149
+ # sha: "329688480d39049927147c162b9d2deaf885005f"
150
+ #
151
+ def delete(*args)
152
+ arguments(args, :required => [:user, :repo, :path]) do
153
+ assert_required %w[ path message sha ]
154
+ end
155
+
156
+ delete_request("/repos/#{user}/#{repo}/contents/#{path}", arguments.params)
157
+ end
158
+
49
159
  # Get archive link
50
160
  #
51
161
  # This method will return a 302 to a URL to download a tarball or zipball
@@ -7,10 +7,10 @@ module Github
7
7
  class Response::RaiseError < Faraday::Response::Middleware
8
8
 
9
9
  def on_complete(env)
10
- status_code = env[:status].to_i
10
+ status_code = env[:status].to_i
11
11
  service_error = Github::Error::ServiceError
12
12
  error_class = service_error.errors[status_code]
13
- error_class = service_error if !error_class and (400...600).include? status_code
13
+ error_class = service_error if !error_class and (400...600) === status_code
14
14
  raise error_class.new(env) if error_class
15
15
  end
16
16
 
@@ -4,7 +4,7 @@ module Github
4
4
  module VERSION
5
5
  MAJOR = 0
6
6
  MINOR = 10
7
- PATCH = 1
7
+ PATCH = 2
8
8
  BUILD = nil
9
9
 
10
10
  STRING = [MAJOR, MINOR, PATCH, BUILD].compact.join('.');
@@ -0,0 +1,44 @@
1
+ {
2
+ "content": {
3
+ "name": "hello.txt",
4
+ "path": "notes/hello.txt",
5
+ "sha": "95b966ae1c166bd92f8ae7d1c313e738c731dfc3",
6
+ "size": 9,
7
+ "url": "https://api.github.com/repos/octocat/Hello-World/contents/notes/hello.txt",
8
+ "html_url": "https://github.com/octocat/Hello-World/blob/master/notes/hello.txt",
9
+ "git_url": "https://api.github.com/repos/octocat/Hello-World/git/blobs/95b966ae1c166bd92f8ae7d1c313e738c731dfc3",
10
+ "type": "file",
11
+ "_links": {
12
+ "self": "https://api.github.com/repos/octocat/Hello-World/contents/notes/hello.txt",
13
+ "git": "https://api.github.com/repos/octocat/Hello-World/git/blobs/95b966ae1c166bd92f8ae7d1c313e738c731dfc3",
14
+ "html": "https://github.com/octocat/Hello-World/blob/master/notes/hello.txt"
15
+ }
16
+ },
17
+ "commit": {
18
+ "sha": "7638417db6d59f3c431d3e1f261cc637155684cd",
19
+ "url": "https://api.github.com/repos/octocat/Hello-World/git/commits/7638417db6d59f3c431d3e1f261cc637155684cd",
20
+ "html_url": "https://github.com/octocat/Hello-World/git/commit/7638417db6d59f3c431d3e1f261cc637155684cd",
21
+ "author": {
22
+ "date": "2010-04-10T14:10:01-07:00",
23
+ "name": "Scott Chacon",
24
+ "email": "schacon@gmail.com"
25
+ },
26
+ "committer": {
27
+ "date": "2010-04-10T14:10:01-07:00",
28
+ "name": "Scott Chacon",
29
+ "email": "schacon@gmail.com"
30
+ },
31
+ "message": "my commit message",
32
+ "tree": {
33
+ "url": "https://api.github.com/repos/octocat/Hello-World/git/trees/691272480426f78a0138979dd3ce63b77f706feb",
34
+ "sha": "691272480426f78a0138979dd3ce63b77f706feb"
35
+ },
36
+ "parents": [
37
+ {
38
+ "url": "https://api.github.com/repos/octocat/Hello-World/git/commits/1acc419d4d6a9ce985db7be48c6349a0475975b5",
39
+ "html_url": "https://github.com/octocat/Hello-World/git/commit/1acc419d4d6a9ce985db7be48c6349a0475975b5",
40
+ "sha": "1acc419d4d6a9ce985db7be48c6349a0475975b5"
41
+ }
42
+ ]
43
+ }
44
+ }
@@ -0,0 +1,30 @@
1
+ {
2
+ "content": null,
3
+ "commit": {
4
+ "sha": "7638417db6d59f3c431d3e1f261cc637155684cd",
5
+ "url": "https://api.github.com/repos/octocat/Hello-World/git/commits/7638417db6d59f3c431d3e1f261cc637155684cd",
6
+ "html_url": "https://github.com/octocat/Hello-World/git/commit/7638417db6d59f3c431d3e1f261cc637155684cd",
7
+ "author": {
8
+ "date": "2010-04-10T14:10:01-07:00",
9
+ "name": "Scott Chacon",
10
+ "email": "schacon@gmail.com"
11
+ },
12
+ "committer": {
13
+ "date": "2010-04-10T14:10:01-07:00",
14
+ "name": "Scott Chacon",
15
+ "email": "schacon@gmail.com"
16
+ },
17
+ "message": "my commit message",
18
+ "tree": {
19
+ "url": "https://api.github.com/repos/octocat/Hello-World/git/trees/691272480426f78a0138979dd3ce63b77f706feb",
20
+ "sha": "691272480426f78a0138979dd3ce63b77f706feb"
21
+ },
22
+ "parents": [
23
+ {
24
+ "url": "https://api.github.com/repos/octocat/Hello-World/git/commits/1acc419d4d6a9ce985db7be48c6349a0475975b5",
25
+ "html_url": "https://github.com/octocat/Hello-World/git/commit/1acc419d4d6a9ce985db7be48c6349a0475975b5",
26
+ "sha": "1acc419d4d6a9ce985db7be48c6349a0475975b5"
27
+ }
28
+ ]
29
+ }
30
+ }
@@ -1,3 +1,5 @@
1
+ # encoding: utf-8
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Github::API do
@@ -63,6 +63,11 @@ describe Github::Issues, '#list' do
63
63
  let(:repo) { 'github' }
64
64
  let(:request_path) { "/repos/#{user}/#{repo}/issues" }
65
65
 
66
+ before {
67
+ stub_request(:get, "https://api.github.com/repos/peter-murach/github/issues?param1=foo&param2=bar").
68
+ to_return(:headers => {:content_type => "application/json; charset=utf-8"})
69
+ }
70
+
66
71
  it "should get the resources" do
67
72
  subject.list :user => user, :repo => repo
68
73
  a_get(request_path).should have_been_made
@@ -82,6 +87,11 @@ describe Github::Issues, '#list' do
82
87
  result = subject.list(:user => user, :repo => repo) { |obj| yielded << obj }
83
88
  yielded.should == result
84
89
  end
90
+
91
+ it "should pass parameters" do
92
+ subject.list :user => user, :repo => repo, :param1 => "foo", :param2 => "bar"
93
+ a_get(request_path + "?param1=foo&param2=bar").should have_been_made
94
+ end
85
95
  end
86
96
 
87
97
  it_should_behave_like 'request failure' do
@@ -1,3 +1,5 @@
1
+ # encoding: utf-8
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Github::MimeType do
@@ -1,3 +1,5 @@
1
+ # encoding: utf-8
2
+
1
3
  require 'spec_helper'
2
4
  require 'github_api/core_ext/hash'
3
5
 
@@ -1,3 +1,5 @@
1
+ # encoding: utf-8
2
+
1
3
  require 'spec_helper'
2
4
  require 'github_api/core_ext/hash'
3
5
 
@@ -61,4 +61,9 @@ describe Github::ParamsHash do
61
61
  end
62
62
  end
63
63
 
64
+ context 'strict encode' do
65
+ let(:hash) { { :content => "puts 'hello ruby'"} }
66
+
67
+ it { expect(subject.strict_encode64('content')).to eql('cHV0cyAnaGVsbG8gcnVieSc=') }
68
+ end
64
69
  end
@@ -0,0 +1,41 @@
1
+ # encoding: utf-8
2
+
3
+ require 'spec_helper'
4
+
5
+ describe Github::Repos::Contents, '#create' do
6
+ let(:user) { 'peter-murach' }
7
+ let(:repo) { 'github' }
8
+ let(:path) { 'hello.rb' }
9
+ let(:request_path) { "/repos/#{user}/#{repo}/contents/#{path}" }
10
+
11
+ before {
12
+ stub_put(request_path).to_return(:body => body, :status => status,
13
+ :headers => {:content_type => "application/json; charset=utf-8"})
14
+ }
15
+
16
+ after { reset_authentication_for(subject) }
17
+
18
+ let(:params) {
19
+ {
20
+ "path" => 'hello.rb',
21
+ "content" => "puts 'hello ruby'",
22
+ "message" => "initial commit"
23
+ }
24
+ }
25
+ let(:body) { fixture('repos/content_created.json') }
26
+ let(:status) { 201 }
27
+
28
+ it { expect { subject.create }.to raise_error(ArgumentError)}
29
+
30
+ it { expect { subject.create user, repo, path }.to raise_error(Github::Error::RequiredParams) }
31
+
32
+ it "creates the resource" do
33
+ subject.create user, repo, path, params
34
+ a_put(request_path).should have_been_made
35
+ end
36
+
37
+ it "gets repository contents information" do
38
+ content = subject.create user, repo, path, params
39
+ content.content.name.should == 'hello.txt'
40
+ end
41
+ end