octocat_herder 0.0.2 → 0.1.0
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.
- data/.document +2 -1
- data/.travis.yml +3 -0
- data/CONTRIBUTING.markdown +93 -0
- data/Gemfile +8 -6
- data/Gemfile.lock +5 -1
- data/{LICENSE.txt → LICENSE} +0 -0
- data/README.markdown +46 -0
- data/Rakefile +2 -9
- data/VERSION +1 -1
- data/lib/octocat_herder/base.rb +53 -44
- data/lib/octocat_herder/connection.rb +145 -6
- data/lib/octocat_herder/pull_request/repo.rb +38 -4
- data/lib/octocat_herder/pull_request.rb +186 -24
- data/lib/octocat_herder/repository.rb +128 -11
- data/lib/octocat_herder/user.rb +107 -8
- data/lib/octocat_herder.rb +22 -1
- data/octocat_herder.gemspec +17 -9
- data/spec/octocat_herder/connection_spec.rb +4 -4
- metadata +48 -14
- data/README.rdoc +0 -19
@@ -6,13 +6,27 @@ require 'octocat_herder/user'
|
|
6
6
|
require 'octocat_herder/pull_request/repo'
|
7
7
|
|
8
8
|
class OctocatHerder
|
9
|
-
|
9
|
+
# Interface to the GitHub v3 API for interacting with pull requests.
|
10
|
+
#
|
11
|
+
# Currently, this only supports retrieval of information about the
|
12
|
+
# pull request itself, not the comments, or any updating/creation.
|
13
|
+
class PullRequest
|
14
|
+
include OctocatHerder::Base
|
15
|
+
|
16
|
+
# Query either the open or closed pull requests for a given
|
17
|
+
# repository.
|
18
|
+
#
|
19
|
+
# @since 0.0.1
|
20
|
+
# @param [String] owner_login The login name of the repository owner.
|
21
|
+
# @param [String] repository_name The name of the repository itself.
|
22
|
+
# @param ['open', 'closed'] status Defaults to querying open pull requests.
|
23
|
+
# @param [OctocatHerder::Connection] conn Defaults to unauthenticated requests.
|
24
|
+
# @return [Array<OctocatHerder::PullRequest>] An array of found pull requests.
|
10
25
|
def self.find_for_repository(owner_login, repository_name, status = 'open', conn = OctocatHerder::Connection.new)
|
11
26
|
raise ArgumentError.new("Unknown PullRequest status '#{status}'. Must be one of ['open', 'closed'].") unless
|
12
27
|
['open', 'closed'].include? status
|
13
28
|
|
14
|
-
pull_requests =
|
15
|
-
conn,
|
29
|
+
pull_requests = conn.get(
|
16
30
|
"/repos/#{CGI.escape(owner_login.to_s)}/#{CGI.escape(repository_name.to_s)}/pulls",
|
17
31
|
:paginated => true,
|
18
32
|
:params => { :state => status },
|
@@ -24,17 +38,38 @@ class OctocatHerder
|
|
24
38
|
end
|
25
39
|
end
|
26
40
|
|
41
|
+
# Query the open pull requests for a given repository.
|
42
|
+
#
|
43
|
+
# @since 0.0.1
|
44
|
+
# @param [String] owner_login The login name of the repository owner.
|
45
|
+
# @param [String] repository_name The name of the repository itself.
|
46
|
+
# @param [OctocatHerder::Connection] conn Defaults to unauthenticated requests.
|
47
|
+
# @return [Array<OctocatHerder::PullRequest>] An array of found pull requests.
|
27
48
|
def self.find_open_for_repository(owner_login, repository_name, conn = OctocatHerder::Connection.new)
|
28
49
|
OctocatHerder::PullRequest.find_for_repository(owner_login, repository_name, 'open', conn)
|
29
50
|
end
|
30
51
|
|
52
|
+
# Query the closed pull requests for a given repository.
|
53
|
+
#
|
54
|
+
# @since 0.0.1
|
55
|
+
# @param [String] owner_login The login name of the repository owner.
|
56
|
+
# @param [String] repository_name The name of the repository itself.
|
57
|
+
# @param [OctocatHerder::Connection] conn Defaults to unauthenticated requests.
|
58
|
+
# @return [Array<OctocatHerder::PullRequest>] An array of found pull requests.
|
31
59
|
def self.find_closed_for_repository(owner_login, repository_name, conn = OctocatHerder::Connection.new)
|
32
60
|
OctocatHerder::PullRequest.find_for_repository(owner_login, repository_name, 'closed', conn)
|
33
61
|
end
|
34
62
|
|
63
|
+
# Query information about a specific pull request.
|
64
|
+
#
|
65
|
+
# @since 0.0.1
|
66
|
+
# @param [String] owner_login The login name of the repository owner.
|
67
|
+
# @param [String] repository_name The name of the repository itself.
|
68
|
+
# @param [String, Integer] pull_request_number The pull request to retrieve.
|
69
|
+
# @param [OctocatHerder::Connection] conn Defaults to unauthenticated requests.
|
70
|
+
# @return [OctocatHerder::PullRequest]
|
35
71
|
def self.fetch(owner_login, repository_name, pull_request_number, conn = OctocatHerder::Connection.new)
|
36
|
-
request =
|
37
|
-
conn,
|
72
|
+
request = conn.get(
|
38
73
|
"/repos/#{CGI.escape(owner_login.to_s)}/#{CGI.escape(repository_name.to_s)}/pulls/#{CGI.escape(pull_request_number.to_s)}",
|
39
74
|
:headers => { 'Accept' => 'application/vnd.github-pull.full+json' }
|
40
75
|
)
|
@@ -42,15 +77,29 @@ class OctocatHerder
|
|
42
77
|
new(nil, request, conn)
|
43
78
|
end
|
44
79
|
|
80
|
+
# @api private
|
81
|
+
# @since 0.0.1
|
82
|
+
# @param [Hash] raw_hash The 'overview' information retrieved from the pull request listing API.
|
83
|
+
# @param [Hash] raw_detail_hash The full information available by querying information about a specific pull request.
|
84
|
+
# @param [OctocatHerder::Connection] conn Defaults to unauthenticated requests.
|
45
85
|
def initialize(raw_hash, raw_detail_hash = nil, conn = OctocatHerder::Connection.new)
|
46
86
|
super raw_hash, conn
|
47
87
|
@raw_detail_hash = raw_detail_hash
|
48
88
|
end
|
49
89
|
|
90
|
+
# Get the full pull request details. When retrieved from
|
91
|
+
# .find_for_repository, .find_open_for_repository, or
|
92
|
+
# .find_closed_for_repository not all of the details of the pull
|
93
|
+
# request are available since GitHub doesn't return them in the
|
94
|
+
# listing. This will query information about the specific pull
|
95
|
+
# request, which will get us all of the available details.
|
96
|
+
#
|
97
|
+
# @since 0.0.1
|
98
|
+
# @return [self]
|
50
99
|
def get_detail
|
51
100
|
return if @raw_detail_hash
|
52
101
|
|
53
|
-
@raw_detail_hash =
|
102
|
+
@raw_detail_hash = connection.get(
|
54
103
|
url,
|
55
104
|
:headers => { 'Accept' => 'application/vnd.github-pull.full+json' }
|
56
105
|
)
|
@@ -58,6 +107,12 @@ class OctocatHerder
|
|
58
107
|
self
|
59
108
|
end
|
60
109
|
|
110
|
+
# Check the "normal" place first for the information returned by
|
111
|
+
# the GitHub API, then check +@raw_detail_hash+ (populating it if
|
112
|
+
# needed).
|
113
|
+
#
|
114
|
+
# @since 0.0.1
|
115
|
+
# @return [String]
|
61
116
|
def method_missing(id, *args)
|
62
117
|
super
|
63
118
|
rescue NoMethodError => e
|
@@ -67,105 +122,212 @@ class OctocatHerder
|
|
67
122
|
raise e
|
68
123
|
end
|
69
124
|
|
70
|
-
#
|
125
|
+
# The URL to the avatar image of the person that opened the pull request.
|
126
|
+
#
|
127
|
+
# @note Since this is returned by the pull request API itself, this can be used without making an additional API request.
|
128
|
+
#
|
129
|
+
# @since 0.0.1
|
130
|
+
# @return [String] Avatar URL
|
71
131
|
def user_avatar_url
|
72
132
|
return @raw['user']['avatar_url'] if @raw
|
73
133
|
@raw_detail_hash['user']['avatar_url']
|
74
134
|
end
|
75
135
|
|
136
|
+
# The URL of the person that opened the pull request.
|
137
|
+
#
|
138
|
+
# @note Since this is returned by the pull request API itself, this can be used without making an additional API request.
|
139
|
+
#
|
140
|
+
# @since 0.0.1
|
141
|
+
# @return [String] User URL
|
76
142
|
def user_url
|
77
143
|
return @raw['user']['url'] if @raw
|
78
144
|
@raw_detail_hash['user']['url']
|
79
145
|
end
|
80
146
|
|
147
|
+
# The ID number of the person that opened the pull request.
|
148
|
+
#
|
149
|
+
# @note Since this is returned by the pull request API itself, this can be used without making an additional API request.
|
150
|
+
#
|
151
|
+
# @since 0.0.1
|
152
|
+
# @return [Integer] User ID
|
81
153
|
def user_id
|
82
154
|
return @raw['user']['id'] if @raw
|
83
155
|
@raw_detail_hash['user']['id']
|
84
156
|
end
|
85
157
|
|
158
|
+
# The login name of the person that opened the pull request.
|
159
|
+
#
|
160
|
+
# @note Since this is returned by the pull request API itself, this can be used without making an additional API request.
|
161
|
+
#
|
162
|
+
# @since 0.0.1
|
163
|
+
# @return [String] User login name
|
86
164
|
def user_login
|
87
165
|
return @raw['user']['login'] if @raw
|
88
166
|
@raw_detail_hash['user']['login']
|
89
167
|
end
|
90
168
|
|
91
|
-
#
|
169
|
+
# The user that opened the pull request.
|
170
|
+
#
|
171
|
+
# @note This is cached locally to the individual pull request, but will make an additional API request to populate it initially.
|
172
|
+
#
|
173
|
+
# @since 0.0.1
|
174
|
+
# @return [OctocatHerder::User]
|
92
175
|
def user
|
93
176
|
@user ||= OctocatHerder::User.fetch(user_login, connection)
|
94
177
|
end
|
95
178
|
|
96
|
-
#
|
179
|
+
# The login name of the person that merged the pull request, or
|
180
|
+
# +nil+ if it has not been merged yet.
|
181
|
+
#
|
182
|
+
# @since 0.0.1
|
183
|
+
# @return [String, nil]
|
97
184
|
def merged_by_login
|
98
|
-
|
185
|
+
return nil unless merged
|
99
186
|
|
187
|
+
get_detail
|
100
188
|
@raw_detail_hash['merged_by']['login']
|
101
189
|
end
|
102
190
|
|
191
|
+
# The ID number of the person that merged the pull request, or
|
192
|
+
# +nil+ if it has not been merged yet.
|
193
|
+
#
|
194
|
+
# @since 0.0.1
|
195
|
+
# @return [String, nil]
|
103
196
|
def merged_by_id
|
104
|
-
|
197
|
+
return nil unless merged
|
105
198
|
|
199
|
+
get_detail
|
106
200
|
@raw_detail_hash['merged_by']['id']
|
107
201
|
end
|
108
202
|
|
203
|
+
# The URL to the avatar image of the person that merged the pull
|
204
|
+
# request, or +nil+ if it has not been merged yet.
|
205
|
+
#
|
206
|
+
# @since 0.0.1
|
207
|
+
# @return [String, nil]
|
109
208
|
def merged_by_avatar_url
|
110
|
-
|
209
|
+
return nil unless merged
|
111
210
|
|
211
|
+
get_detail
|
112
212
|
@raw_detail_hash['merged_by']['avatar_url']
|
113
213
|
end
|
114
214
|
|
215
|
+
# The URL of the person that merged the pull request, or +nil+ if
|
216
|
+
# it has not been merged yet.
|
217
|
+
#
|
218
|
+
# @since 0.0.1
|
219
|
+
# @return [String, nil]
|
115
220
|
def merged_by_url
|
116
|
-
|
221
|
+
return nil unless merged
|
117
222
|
|
223
|
+
get_detail
|
118
224
|
@raw_detail_hash['merged_by']['url']
|
119
225
|
end
|
120
226
|
|
121
|
-
#
|
227
|
+
# The user that merged the pull request, or +nil+ if it has not
|
228
|
+
# been merged yet.
|
229
|
+
#
|
230
|
+
# @note This is cached locally to the individual pull request, but will make an additional API request to populate it initially.
|
231
|
+
#
|
232
|
+
# @since 0.0.1
|
233
|
+
# @return [OctocatHerder::User, nil]
|
122
234
|
def merged_by
|
123
|
-
|
235
|
+
return nil unless merged
|
124
236
|
|
125
237
|
@merged_by ||= OctocatHerder::User.fetch(merged_by_login, connection)
|
126
238
|
end
|
127
239
|
|
128
|
-
#
|
240
|
+
# When the pull request was first created.
|
241
|
+
#
|
242
|
+
# @since 0.0.1
|
243
|
+
# @return [Time]
|
129
244
|
def created_at
|
130
245
|
parse_date_time(@raw_detail_hash['created_at'])
|
131
246
|
end
|
132
247
|
|
248
|
+
# When the pull request was last updated.
|
249
|
+
#
|
250
|
+
# @since 0.0.1
|
251
|
+
# @return [Time]
|
133
252
|
def updated_at
|
134
253
|
parse_date_time(@raw_detail_hash['updated_at'])
|
135
254
|
end
|
136
255
|
|
256
|
+
# When the pull request was closed, or +nil+ if it is still open.
|
257
|
+
#
|
258
|
+
# @since 0.0.1
|
259
|
+
# @return [Time, nil]
|
137
260
|
def closed_at
|
138
261
|
parse_date_time(@raw_detail_hash['closed_at'])
|
139
262
|
end
|
140
263
|
|
264
|
+
# When the pull request was merged, or +nil+ if it hasn't been merged.
|
265
|
+
#
|
266
|
+
# @since 0.0.1
|
267
|
+
# @return [Time, nil]
|
141
268
|
def merged_at
|
142
269
|
parse_date_time(@raw_detail_hash['merged_at'])
|
143
270
|
end
|
144
271
|
|
272
|
+
# Information about what is being asked to be merged in the pull
|
273
|
+
# request.
|
274
|
+
#
|
275
|
+
# @since 0.0.1
|
276
|
+
# @return [OctocatHerder::PullRequest::Repo]
|
145
277
|
def head
|
146
278
|
get_detail
|
147
279
|
|
148
280
|
@head_repo ||= OctocatHerder::PullRequest::Repo.new(@raw_detail_hash['head'], connection)
|
149
281
|
end
|
150
282
|
|
283
|
+
# Information about what the pull request was based on in the pull
|
284
|
+
# request.
|
285
|
+
#
|
286
|
+
# @since 0.0.1
|
287
|
+
# @return [OctocatHerder::PullRequest::Repo]
|
151
288
|
def base
|
152
289
|
get_detail
|
153
290
|
|
154
291
|
@base_repo ||= OctocatHerder::PullRequest::Repo.new(@raw_detail_hash['base'], connection)
|
155
292
|
end
|
156
293
|
|
157
|
-
|
158
|
-
|
159
|
-
|
160
|
-
|
161
|
-
|
162
|
-
end
|
163
|
-
|
294
|
+
# A Hash representation of the pull request. Combines +@raw+, and
|
295
|
+
# +@raw_detail_hash+ into a single hash.
|
296
|
+
#
|
297
|
+
# @since 0.0.2
|
298
|
+
# @return [Hash]
|
164
299
|
def to_hash
|
165
300
|
raw = @raw || {}
|
166
301
|
detail = @raw_detail_hash || {}
|
167
302
|
|
168
|
-
raw.merge(detail)
|
303
|
+
ret = raw.merge(detail)
|
304
|
+
ret['patch_text'] = patch_text
|
305
|
+
ret['diff_text'] = diff_text
|
306
|
+
|
307
|
+
ret
|
308
|
+
end
|
309
|
+
|
310
|
+
def patch_text
|
311
|
+
@patch_text ||= connection.raw_get(patch_url).body
|
312
|
+
end
|
313
|
+
|
314
|
+
def diff_text
|
315
|
+
@diff_text ||= connection.raw_get(diff_url).body
|
316
|
+
end
|
317
|
+
|
318
|
+
private
|
319
|
+
|
320
|
+
# Give a full listing of the available information, since we
|
321
|
+
# define some of our own methods, and don't have everything in
|
322
|
+
# +@raw+.
|
323
|
+
#
|
324
|
+
# @api private
|
325
|
+
# @since 0.0.1
|
326
|
+
def additional_attributes
|
327
|
+
attrs = ['user_avatar_url', 'user_url', 'user_id', 'user_login', 'patch_text', 'diff_text']
|
328
|
+
|
329
|
+
attrs += @raw_detail_hash.keys if @raw_detail_hash
|
330
|
+
attrs += ['merged_by_login', 'merged_by_id', 'merged_by_avatar_url', 'merged_by_url']
|
169
331
|
end
|
170
332
|
end
|
171
333
|
end
|
@@ -5,11 +5,42 @@ require 'octocat_herder/connection'
|
|
5
5
|
require 'octocat_herder/user'
|
6
6
|
|
7
7
|
class OctocatHerder
|
8
|
-
|
8
|
+
# Interface to the GitHub v3 API for interacting with repositories.
|
9
|
+
#
|
10
|
+
# Currently, this only supports retrieval of information about the
|
11
|
+
# repository itself, not any updating/creation.
|
12
|
+
class Repository
|
13
|
+
include OctocatHerder::Base
|
14
|
+
|
15
|
+
# @overload list_all(login_name, account_type, conn = OctocatHerder::Connection.new)
|
16
|
+
# @overload list_private(login_name, account_type, conn)
|
17
|
+
# @overload list_public(login_name, account_type, conn = OctocatHerder::Connection.new)
|
18
|
+
# @overload list_member(login_name, account_type, conn = OctocatHerder::Connection.new)
|
19
|
+
#
|
20
|
+
# Fetch all, private, public, or member repositories for the specified user.
|
21
|
+
#
|
22
|
+
# @since 0.0.1
|
23
|
+
#
|
24
|
+
# @raise [ArgumentError] If no conn is not provided when listing
|
25
|
+
# private repositories.
|
26
|
+
#
|
27
|
+
# @param [String] login_name The login name of the user.
|
28
|
+
#
|
29
|
+
# @param ['User', 'Organization'] Whether login_name is for a user
|
30
|
+
# or organization.
|
31
|
+
#
|
32
|
+
# @param [OctocatHerder::Connection] conn Defaults to
|
33
|
+
# unauthenticated requests.
|
34
|
+
#
|
35
|
+
# @return [Array<OctocatHerder::Repository>]
|
9
36
|
def self.method_missing(id, *args)
|
10
37
|
if id.id2name =~ /list_(.+)/
|
11
38
|
repository_type = Regexp.last_match(1)
|
12
39
|
if ['all', 'private', 'public', 'member'].include? repository_type
|
40
|
+
if repository_type == 'private' and args[2].nil?
|
41
|
+
raise ArgumentError.new("Must specify a connection when listing private repositories.")
|
42
|
+
end
|
43
|
+
|
13
44
|
arguments = [args[0], args[1], repository_type]
|
14
45
|
arguments << args[2] unless args[2].nil?
|
15
46
|
|
@@ -20,42 +51,108 @@ class OctocatHerder
|
|
20
51
|
raise NoMethodError.new("undefined method #{id.id2name} for #{self}:#{self.class}")
|
21
52
|
end
|
22
53
|
|
54
|
+
# The login name of the owner of the repository.
|
55
|
+
#
|
56
|
+
# @since 0.0.1
|
57
|
+
# @return [String]
|
23
58
|
def owner_login
|
24
59
|
@raw['owner']['login']
|
25
60
|
end
|
26
61
|
|
62
|
+
# The ID number of the owner of the repository.
|
63
|
+
#
|
64
|
+
# @since 0.0.1
|
65
|
+
# @return [Integer]
|
27
66
|
def owner_id
|
28
67
|
@raw['owner']['id']
|
29
68
|
end
|
30
69
|
|
70
|
+
# The URL to the avatar image of the owner of the repository.
|
71
|
+
#
|
72
|
+
# @since 0.0.1
|
73
|
+
# @return [String]
|
31
74
|
def owner_avatar_url
|
32
75
|
@raw['owner']['avatar_url']
|
33
76
|
end
|
34
77
|
|
78
|
+
# The URL of the owner of the repository.
|
79
|
+
#
|
80
|
+
# @since 0.0.1
|
81
|
+
# @return [String]
|
35
82
|
def owner_url
|
36
83
|
@raw['owner']['url']
|
37
84
|
end
|
38
85
|
|
86
|
+
# The owner of the repository.
|
87
|
+
#
|
88
|
+
# @note This is cached locally to the instance of
|
89
|
+
# {OctocatHerder::Repository}, but will make an additional API
|
90
|
+
# request to populate it initially.
|
91
|
+
#
|
92
|
+
# @since 0.0.1
|
93
|
+
# @return [OctocatHerder::User]
|
39
94
|
def owner
|
40
|
-
OctocatHerder::User.fetch(owner_login, connection)
|
95
|
+
@owner ||= OctocatHerder::User.fetch(owner_login, connection)
|
41
96
|
end
|
42
97
|
|
98
|
+
# The open pull requests for the repository.
|
99
|
+
#
|
100
|
+
# @note This is _not_ cached, and will make at least one API
|
101
|
+
# request every time it is called.
|
102
|
+
#
|
103
|
+
# @since 0.0.1
|
104
|
+
# @return [Array<OctocatHerder::PullRequest>]
|
43
105
|
def open_pull_requests
|
44
|
-
OctocatHerder::PullRequest.
|
106
|
+
OctocatHerder::PullRequest.find_open_for_repository(owner_login, name, connection)
|
45
107
|
end
|
46
108
|
|
109
|
+
# The closed pull requests for the repository.
|
110
|
+
#
|
111
|
+
# @note This is _not_ cached, and will make at least one API
|
112
|
+
# request every time it is called.
|
113
|
+
#
|
114
|
+
# @since 0.0.1
|
115
|
+
# @return [Array<OctocatHerder::PullRequest>]
|
47
116
|
def closed_pull_requests
|
48
|
-
OctocatHerder::PullRequest.
|
117
|
+
OctocatHerder::PullRequest.find_closed_for_repository(owner_login, name, connection)
|
49
118
|
end
|
50
119
|
|
120
|
+
# The source repository that this one was forked from, or +nil+ if
|
121
|
+
# this repository is not a fork.
|
122
|
+
#
|
123
|
+
# @since 0.0.1
|
124
|
+
# @return [OctocatHerder::Repository, nil]
|
51
125
|
def source
|
52
|
-
return unless @raw['source']
|
126
|
+
return nil unless @raw['source']
|
53
127
|
|
54
128
|
OctocatHerder::Repository.new(@raw['source'], connection)
|
55
129
|
end
|
56
130
|
|
57
|
-
|
58
|
-
|
131
|
+
# Fetch repositories of the specified type, owned by the given login
|
132
|
+
#
|
133
|
+
# @since 0.0.1
|
134
|
+
#
|
135
|
+
# @raise [ArgumentError] If provided an unauthenticated
|
136
|
+
# OctocatHerder::Connection and repository_type is 'private'.
|
137
|
+
#
|
138
|
+
# @raise [ArgumentError] If account_type is not one of the strings
|
139
|
+
# 'User', or 'Organization'.
|
140
|
+
#
|
141
|
+
# @raise [ArgumentError] If repository_type is not one of the
|
142
|
+
# strings 'all', 'private', 'public', or 'member'.
|
143
|
+
#
|
144
|
+
# @param [String] login Login name of the account.
|
145
|
+
#
|
146
|
+
# @param ['User', 'Organization'] account_type Type of the
|
147
|
+
# specified login.
|
148
|
+
#
|
149
|
+
# @param ['all', 'private', 'public', 'member'] repository_type
|
150
|
+
# Which set of repositories to list.
|
151
|
+
#
|
152
|
+
# @param [OctocatHerder::Connection] conn Default to
|
153
|
+
# unauthenticated requests.
|
154
|
+
#
|
155
|
+
# @return [Array<OctocatHerder::Repository>]
|
59
156
|
def self.list(login, account_type, repository_type, conn = OctocatHerder::Connection.new)
|
60
157
|
url_base = case account_type
|
61
158
|
when "User" then "users"
|
@@ -64,8 +161,15 @@ class OctocatHerder
|
|
64
161
|
raise ArgumentError.new("Unknown account type: #{account_type}")
|
65
162
|
end
|
66
163
|
|
67
|
-
|
68
|
-
|
164
|
+
raise ArgumentError.new(
|
165
|
+
"Unknown repository type: #{repository_type}"
|
166
|
+
) unless ['all', 'private', 'public', 'member'].include?(repository_type)
|
167
|
+
|
168
|
+
raise ArgumentError.new(
|
169
|
+
"Must provide an authenticated OctocatHerder::Connection when listing private repositories."
|
170
|
+
) if !conn.authenticated_requests? && repository_type == 'private'
|
171
|
+
|
172
|
+
repositories = conn.get(
|
69
173
|
"/#{url_base}/#{CGI.escape(login)}/repos",
|
70
174
|
:paginated => true,
|
71
175
|
:params => { :type => repository_type }
|
@@ -76,15 +180,28 @@ class OctocatHerder
|
|
76
180
|
end
|
77
181
|
end
|
78
182
|
|
183
|
+
# Fetch a single repository.
|
184
|
+
#
|
185
|
+
# @since 0.0.1
|
186
|
+
#
|
187
|
+
# @param [String] login Login name of the account.
|
188
|
+
#
|
189
|
+
# @param [String] repository_name Name of the repository.
|
190
|
+
#
|
191
|
+
# @param [OctocatHerder::Connection] Default to unauthenticated
|
192
|
+
# requests.
|
193
|
+
#
|
194
|
+
# @return [OctocatHerder::Repository]
|
79
195
|
def self.fetch(login, repository_name, conn = OctocatHerder::Connection.new)
|
80
|
-
repo_data =
|
81
|
-
conn,
|
196
|
+
repo_data = conn.get(
|
82
197
|
"/repos/#{CGI.escape(login)}/#{CGI.escape(repository_name)}"
|
83
198
|
)
|
84
199
|
|
85
200
|
new(repo_data, conn)
|
86
201
|
end
|
87
202
|
|
203
|
+
private
|
204
|
+
|
88
205
|
def additional_attributes
|
89
206
|
['owner_login', 'owner_id', 'owner_avatar_url', 'owner_url']
|
90
207
|
end
|
data/lib/octocat_herder/user.rb
CHANGED
@@ -1,34 +1,133 @@
|
|
1
|
+
require 'cgi'
|
2
|
+
|
1
3
|
require 'octocat_herder/base'
|
2
4
|
require 'octocat_herder/connection'
|
3
5
|
require 'octocat_herder/repository'
|
4
6
|
|
5
7
|
class OctocatHerder
|
6
|
-
|
8
|
+
# Interface to the GitHub v3 API for interacting with users.
|
9
|
+
#
|
10
|
+
# Currently, this only supports retrieval of information about the
|
11
|
+
# requested user.
|
12
|
+
class User
|
13
|
+
include OctocatHerder::Base
|
14
|
+
|
15
|
+
# Find a user by login name
|
16
|
+
#
|
17
|
+
# @since 0.0.1
|
18
|
+
# @param [String] user_name The login name of the desired user.
|
19
|
+
#
|
20
|
+
# @param [OctocatHerder::Connection] conn Defaults to
|
21
|
+
# unauthenticated requests.
|
22
|
+
#
|
23
|
+
# @return [OctocatHerder::User]
|
7
24
|
def self.fetch(user_name, conn = OctocatHerder::Connection.new)
|
8
|
-
user =
|
25
|
+
user = conn.get("/users/#{CGI.escape(user_name)}")
|
9
26
|
|
10
|
-
|
27
|
+
new(user, conn)
|
11
28
|
end
|
12
29
|
|
30
|
+
# All repositories owned by the user.
|
31
|
+
#
|
32
|
+
# @note This is cached locally to the {OctocatHerder::User}
|
33
|
+
# instance, but at least one API request will be made to
|
34
|
+
# populate it initially.
|
35
|
+
#
|
36
|
+
# @since 0.0.1
|
37
|
+
# @return [Array<OctocatHerder::Repository>]
|
13
38
|
def repositories
|
14
39
|
@repositories ||= OctocatHerder::Repository.list_all(login, user_type, connection)
|
15
40
|
end
|
16
41
|
|
17
|
-
# The
|
18
|
-
#
|
42
|
+
# The ID number of the user.
|
43
|
+
#
|
44
|
+
# @since 0.0.1
|
45
|
+
# @return [Integer]
|
19
46
|
def user_id
|
47
|
+
# The user id can't be handled by the method_missing magic from
|
48
|
+
# OctocatHerder::Base, since the id method returns the object
|
49
|
+
# id.
|
20
50
|
@raw['id']
|
21
51
|
end
|
22
52
|
|
23
|
-
# The
|
24
|
-
#
|
25
|
-
#
|
53
|
+
# The type of account. Typically one of +'User'+, or
|
54
|
+
# +'Organization'+.
|
55
|
+
#
|
56
|
+
# @since 0.0.1
|
57
|
+
# @return [String]
|
26
58
|
def user_type
|
59
|
+
# The user type can't be handled by the method_missing magic
|
60
|
+
# from OctocatHerder::Base, since 'type' is the deprecated form
|
61
|
+
# of the method 'class'.
|
27
62
|
@raw['type']
|
28
63
|
end
|
29
64
|
|
65
|
+
# List of users following this user.
|
66
|
+
#
|
67
|
+
# @since development
|
68
|
+
# @return [Array<OctocatHerder::User>]
|
69
|
+
def followers
|
70
|
+
result = connection.get(
|
71
|
+
"/users/#{CGI.escape(login)}/followers"
|
72
|
+
)
|
73
|
+
|
74
|
+
result.map do |follower|
|
75
|
+
self.class.new(follower, connection)
|
76
|
+
end
|
77
|
+
end
|
78
|
+
|
79
|
+
# List of users this user is following.
|
80
|
+
#
|
81
|
+
# @since development
|
82
|
+
# @return [Array<OctocatHerder::User>]
|
83
|
+
def following
|
84
|
+
users = connection.get(
|
85
|
+
"/users/#{CGI.escape(login)}/following"
|
86
|
+
)
|
87
|
+
|
88
|
+
users.map do |stalkee|
|
89
|
+
self.class.new(stalkee, connection)
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
# Check if the user authenticated by the provided
|
94
|
+
# {OctocatHerder::Connection} is following the specified user.
|
95
|
+
#
|
96
|
+
# @since development
|
97
|
+
#
|
98
|
+
# @raise [ArgumentError] If user is not a String or an
|
99
|
+
# OctocatHerder::User
|
100
|
+
#
|
101
|
+
# @raise [ArgumentError] If the connection will not make
|
102
|
+
# authenticated requests.
|
103
|
+
#
|
104
|
+
# @param [String, OctocatHerder::User] user
|
105
|
+
#
|
106
|
+
# @param [OctocatHerder::Connection] connection An authenticated connection
|
107
|
+
#
|
108
|
+
# @return [true, false]
|
109
|
+
def self.following?(user, connection)
|
110
|
+
raise ArgumentError.new(
|
111
|
+
"Provided user must be a String, or an OctocatHerder::User."
|
112
|
+
) unless user.is_a?(String) or user.is_a?(OctocatHerder::User)
|
113
|
+
|
114
|
+
raise ArgumentError.new(
|
115
|
+
"Provided connection must make authenticated requests."
|
116
|
+
) unless connection.authenticated_requests?
|
117
|
+
|
118
|
+
user_name = user.is_a?(OctocatHerder::User) ? user.login : user
|
119
|
+
|
120
|
+
result = connection.raw_get("/user/following/#{CGI.escape(user_name)}")
|
121
|
+
|
122
|
+
# The GitHub API gives us back a "204 No Content" if we are
|
123
|
+
# following the user.
|
124
|
+
result.response.code == "204"
|
125
|
+
end
|
126
|
+
|
30
127
|
private
|
31
128
|
|
129
|
+
# @api private
|
130
|
+
# @since 0.0.1
|
32
131
|
def additional_attributes
|
33
132
|
['user_id', 'user_type']
|
34
133
|
end
|