mediawiki-butt 1.2.0 → 1.3.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 6ac2473bbed75da107401d8c5dceeca3e2ed6b3c
4
- data.tar.gz: 36463ff0c4f70d87ce6d6f62994d7ff03cf4b47a
3
+ metadata.gz: 3d0b018bfc1617afe7610706ea9347c71ad79a57
4
+ data.tar.gz: 5c356aeacdbcd8697eed165665335c48afb38fdd
5
5
  SHA512:
6
- metadata.gz: 208c930ffa7dc8913b4c2b51bc6a82a46f1f55319d2ba92bf33eb139579dfbb8dff5b17327636df5235e651f63381ae4c808f84263868ca931a0cf1c9232035e
7
- data.tar.gz: ef133085ca55bd92f603d43430c4c100d17011c0d64427950463c4e18856da642c2f2270df33e722c1efda9b971484d5a6e416767ed2b487e719ee444001acfc
6
+ metadata.gz: abff053b2c91f898e7d97996c2c866b1269b1461e9d8bf50c7670aaeabd60994d8248fc79b494d6600b9da947722d31a50d0f282223cb468ab16a0a4dffd9dbf
7
+ data.tar.gz: 3357c256bbfe5b77270e014011a36e45a3ae74bac3f432c5585a555c1e0a1f6ad6d267d202ba63161bcf986a946cacb2f372012e23bd9351bb103b81b7fed43b
@@ -1,5 +1,15 @@
1
1
  # Changelog
2
2
  ## Version 1
3
+ ### Version 1.3.0
4
+ **Security update!**
5
+ * Add support for the Assert API (PR #51).
6
+ * New `:assertion` option in initialize opts. It takes either `:user` or `:bot`.
7
+ * New `override_assertion` parameter in `post` to prevent assertion errors being thrown.
8
+ * **Note**: Assertions will only happen if `post`'s `autoparse` parameter is true.
9
+ * New NotLoggedInError and NotBotError for the according assertions.
10
+ * `Butt#user_bot?` no longer has a parameter. It now queries with an assertion rather than checking the user's groups.
11
+ * New method `Butt#logged_in?` to check if the current instance is logged in.
12
+
3
13
  ### Version 1.2.0
4
14
  * Add support for the Purge API (#48)
5
15
 
@@ -22,7 +22,7 @@ module MediaWiki
22
22
  header = {}
23
23
  header['Set-Cookie'] = @cookie if @cookie
24
24
 
25
- response = post(params, true, header)
25
+ response = post(params, true, header, true)
26
26
  result = response['login']['result']
27
27
 
28
28
  if result == 'NeedToken'
@@ -50,7 +50,7 @@ module MediaWiki
50
50
  action: 'logout'
51
51
  }
52
52
 
53
- post(params)
53
+ post(params, true, nil, true)
54
54
  @logged_in = false
55
55
 
56
56
  true
@@ -25,6 +25,7 @@ module MediaWiki
25
25
 
26
26
  attr_accessor :query_limit_default
27
27
  attr_accessor :use_continuation
28
+ attr_accessor :assertion
28
29
 
29
30
  # Creates a new instance of MediaWiki::Butt.
30
31
  # @param url [String] The FULL wiki URL. api.php can be omitted, but it will make harsh assumptions about
@@ -36,6 +37,10 @@ module MediaWiki
36
37
  # use that, otherwise, it will use this. Defaults to 500. It can be set to 'max' to use MW's default max for
37
38
  # each API.
38
39
  # @option opts [Boolean] :use_continuation Whether to use the continuation API on queries.
40
+ # @option opts [Symbol] :assertion If set to :user or :bot, will use the assert parameter in all requests.
41
+ # Setting this will open up the possibility for NotLoggedInErrors and NotBotErrors. It is important to keep in
42
+ # mind that methods that check if the user is logged in do not use the API, but check if the user has *ever*
43
+ # logged in as this Butt instance. In other words, it is a safety check for performance and not a valid API check.
39
44
  def initialize(url, opts = {})
40
45
  @url = url =~ /api.php$/ ? url : "#{url}/api.php"
41
46
  @query_limit_default = opts[:query_limit_default] || 500
@@ -44,6 +49,9 @@ module MediaWiki
44
49
  @logged_in = false
45
50
  @custom_agent = opts[:custom_agent]
46
51
  @use_continuation = opts[:use_continuation]
52
+
53
+ assertion = opts[:assertion]
54
+ @assertion = assertion == :user || assertion == :bot ? assertion : nil
47
55
  end
48
56
 
49
57
  # Performs a generic HTTP POST request and provides the response. This method generally should not be used by the
@@ -52,11 +60,14 @@ module MediaWiki
52
60
  # information.
53
61
  # @param autoparse [Boolean] Whether or not to provide a parsed version of the response's JSON.
54
62
  # @param header [Hash] The header hash. Optional.
63
+ # @param override_assertion [Boolean] Whether to override the @assertion check. This is used in #login because
64
+ # that can never be done while already logged in.
55
65
  # @since 0.1.0
56
66
  # @return [Hash] Parsed JSON if autoparse is true.
57
67
  # @return [HTTPMessage] Raw HTTP response if autoparse is not true.
58
- def post(params, autoparse = true, header = nil)
68
+ def post(params, autoparse = true, header = nil, override_assertion = false)
59
69
  params[:format] = 'json'
70
+ params[:assert] = @assertion.to_s if @assertion && !override_assertion && !params.key?(:assert)
60
71
  header = {} if header.nil?
61
72
 
62
73
  header['User-Agent'] = @logged_in ? "#{@name}/MediaWiki::Butt" : 'NotLoggedIn/MediaWiki::Butt'
@@ -64,7 +75,15 @@ module MediaWiki
64
75
 
65
76
  res = @client.post(@uri, params, header)
66
77
 
67
- autoparse ? JSON.parse(res.body) : res
78
+ return res unless autoparse
79
+ parsed = JSON.parse(res.body)
80
+
81
+ if !override_assertion || @assertion
82
+ code = parsed.dig('error', 'code')
83
+ fail MediaWiki::Butt::NotLoggedInError.new(parsed['error']['info']) if code == 'assertuserfailed'
84
+ fail MediaWiki::Butt::NotBotError.new(parsed['error']['info']) if code == 'assertbotfailed'
85
+ end
86
+ parsed
68
87
  end
69
88
 
70
89
  # Performs a Mediawiki API query and provides the response, dealing with continuation as necessary.
@@ -92,28 +111,49 @@ module MediaWiki
92
111
  base_return
93
112
  end
94
113
 
114
+ # Helper method for query methods that return a two-dimensional hashes in which the keys are not relevant to the
115
+ # returning value. In most cases this key is a redundant page or revision ID that is also available in the object.
116
+ # @param (see #query_ary)
117
+ def query_ary_irrelevant_keys(params, base_response_key, property_key)
118
+ query(params) do |return_val, query|
119
+ return_val.concat(query[base_response_key].values.collect { |obj| obj[property_key] })
120
+ end
121
+ end
122
+
95
123
  # Helper method for query methods that return an array built from the query objects.
96
124
  # @param params [Hash] A hash containing MediaWiki API parameters.
97
- # @param
125
+ # @param base_response_key [String] The key inside the "query" object to collect.
126
+ # @param property_key [String] The key inside the object (under the base_response_key) to collect.
98
127
  def query_ary(params, base_response_key, property_key)
99
128
  query(params) do |return_val, query|
100
- query[base_response_key].each { |obj| return_val << obj[property_key] }
129
+ return_val.concat(query[base_response_key].collect { |obj| obj[property_key] })
101
130
  end
102
131
  end
103
132
 
104
133
  # Gets whether the currently logged in user is a bot.
105
- # @param username [String] The username to check. Optional. Defaults to
106
- # the currently logged in user if nil.
107
134
  # @return [Boolean] true if logged in as a bot, false if not logged in or
108
135
  # logged in as a non-bot
109
136
  # @since 0.1.0 as is_current_user_bot
110
137
  # @since 0.3.0 as is_user_bot?
111
138
  # @since 0.4.1 as user_bot?
112
- def user_bot?(username = nil)
113
- groups = false
114
- name = username || @name
115
- groups = get_usergroups(name) if name
116
- groups && groups.include?('bot')
139
+ def user_bot?
140
+ begin
141
+ post({ action: 'query', assert: 'bot' })
142
+ true
143
+ rescue MediaWiki::Butt::NotBotError
144
+ false
145
+ end
146
+ end
147
+
148
+ # Checks whether this instance is logged in.
149
+ # @return [Boolean] true if logged in, false if not.
150
+ def logged_in?
151
+ begin
152
+ post({ action: 'query', assert: 'user' })
153
+ true
154
+ rescue MediaWiki::Butt::NotLoggedInError
155
+ false
156
+ end
117
157
  end
118
158
 
119
159
  protected
@@ -219,5 +219,9 @@ module MediaWiki
219
219
  # Extension:Flow
220
220
  'FLW_TOPIC'.freeze => 2600
221
221
  }.freeze
222
+
223
+ # @return [Proc] A proc that returns the missing page ID, -1. This is useful for using methods like Enumerable#find
224
+ # and not creating a new Proc object for every call.
225
+ MISSING_PAGEID_PROC = Proc.new { '-1' }
222
226
  end
223
227
  end
@@ -3,5 +3,7 @@ module MediaWiki
3
3
  class AuthenticationError < StandardError; end
4
4
  class EditError < StandardError; end
5
5
  class BlockError < StandardError; end
6
+ class NotLoggedInError < StandardError; end
7
+ class NotBotError < StandardError; end
6
8
  end
7
9
  end
@@ -41,17 +41,12 @@ module MediaWiki
41
41
  params[:action] = 'purge'
42
42
  params[:titles] = titles.join('|')
43
43
 
44
- response = post(params)
45
-
46
- ret = {}
47
-
48
- response['purge'].each do |hash|
44
+ post(params)['purge'].inject({}) do |result, hash|
49
45
  title = hash['title']
50
- ret[title] = hash.key?('purged') && !hash.key?('missing')
46
+ result[title] = hash.key?('purged') && !hash.key?('missing')
51
47
  warn "Invalid purge (#{title}) #{hash['invalidreason']}" if hash.key?('invalid')
48
+ result
52
49
  end
53
-
54
- ret
55
50
  end
56
51
  end
57
52
  end
@@ -184,7 +184,7 @@ module MediaWiki
184
184
  }
185
185
 
186
186
  query(params) do |return_val, query|
187
- query['querypage']['results'].each { |result| return_val << result['title'] }
187
+ return_val.concat(query['querypage']['results'].collect { |result| result['title'] })
188
188
  end
189
189
  end
190
190
  end
@@ -34,9 +34,7 @@ module MediaWiki
34
34
  params[:rcstart] = start.xmlschema unless start.nil?
35
35
  params[:rcend] = stop.xmlschema unless stop.nil?
36
36
 
37
- response = post(params)
38
- ret = []
39
- response['query']['recentchanges'].each do |change|
37
+ post(params)['query']['recentchanges'].collect do |change|
40
38
  old_length = change['oldlen']
41
39
  new_length = change['newlen']
42
40
  diff_length = new_length - old_length
@@ -68,10 +66,8 @@ module MediaWiki
68
66
  hash[:logid] = change['logid']
69
67
  end
70
68
 
71
- ret << hash
69
+ hash
72
70
  end
73
-
74
- ret
75
71
  end
76
72
 
77
73
  # Gets the recent deleted revisions.
@@ -90,9 +86,7 @@ module MediaWiki
90
86
  params[:drstart] = start.xmlschema unless start.nil?
91
87
  params[:drend] = stop.xmlschema unless stop.nil?
92
88
 
93
- response = post(params)
94
- ret = []
95
- response['query']['deletedrevs'].each do |rev|
89
+ post(params)['query']['deletedrevs'].collect do |rev|
96
90
  r = rev['revisions'][0]
97
91
  hash = {
98
92
  timestamp: DateTime.xmlschema(r['timestamp']),
@@ -100,10 +94,9 @@ module MediaWiki
100
94
  comment: r['comment'],
101
95
  title: rev['title']
102
96
  }
103
- ret << hash
104
- end
105
97
 
106
- ret
98
+ hash
99
+ end
107
100
  end
108
101
  end
109
102
  end
@@ -36,19 +36,13 @@ module MediaWiki
36
36
  # @return [Array<String>] All of the user's groups.
37
37
  # @return [Boolean] False if username is nil and not logged in.
38
38
  def get_usergroups(username = nil)
39
- ret = []
40
39
  if username.nil?
41
40
  return false unless @logged_in
42
- info = get_userlists('groups')
43
- info['query']['userinfo']['groups'].each { |i| ret << i }
41
+ get_userlists('groups')['query']['userinfo']['groups']
44
42
  else
45
43
  info = get_userlists('groups', username)
46
- info['query']['users'].each do |i|
47
- i['groups'].each { |g| ret << g }
48
- end
44
+ info['query']['users'].collect { |i| i['groups'] }.flatten
49
45
  end
50
-
51
- ret
52
46
  end
53
47
 
54
48
  # Gets the user rights for the user.
@@ -58,21 +52,14 @@ module MediaWiki
58
52
  # @return [Array<String>] All of the user's groups.
59
53
  # @return [Boolean] False if username is nil and not logged in.
60
54
  def get_userrights(username = nil)
61
- ret = []
62
55
  if username.nil?
63
56
  return false unless @logged_in
64
57
  info = get_userlists('rights')
65
- info['query']['userinfo']['rights'].each { |i| ret << i }
58
+ info['query']['userinfo']['rights']
66
59
  else
67
60
  info = get_userlists('rights', username)
68
- info['query']['users'].each do |i|
69
- i['rights'].each do |g|
70
- ret << g
71
- end
72
- end
61
+ info['query']['users'].find { |hash| hash['name'] == username }['rights']
73
62
  end
74
-
75
- ret
76
63
  end
77
64
 
78
65
  # Gets contribution count for the user.
@@ -83,17 +70,14 @@ module MediaWiki
83
70
  # @return [Boolean] False if username is nil and not logged in.
84
71
  # @return [Fixnum] The number of contributions the user has made.
85
72
  def get_contrib_count(username = nil)
86
- count = nil
87
73
  if username.nil?
88
74
  return false unless @logged_in
89
75
  info = get_userlists('editcount')
90
- count = info['query']['userinfo']['editcount']
76
+ info['query']['userinfo']['editcount']
91
77
  else
92
78
  info = get_userlists('editcount', username)
93
- info['query']['users'].each { |i| count = i['editcount'] }
79
+ info['query']['users'].find { |hash| hash['name'] == username }['editcount']
94
80
  end
95
-
96
- count
97
81
  end
98
82
 
99
83
  # Gets when the user registered.
@@ -104,7 +88,6 @@ module MediaWiki
104
88
  # @return [DateTime] The registration date and time as a DateTime object.
105
89
  # @return [Boolean] False when no username is provided and not logged in, or the user doesn't exist.
106
90
  def get_registration_time(username = nil)
107
- time = nil
108
91
  # Do note that in Userinfo, registration is called registrationdate.
109
92
  if username.nil?
110
93
  return false unless @logged_in
@@ -112,7 +95,7 @@ module MediaWiki
112
95
  time = info['query']['userinfo']['registrationdate']
113
96
  else
114
97
  info = get_userlists('registration', username)
115
- info['query']['users'].each { |i| time = i['registration'] }
98
+ time = info['query']['users'].find { |hash| hash['name'] == username }['registration']
116
99
  end
117
100
 
118
101
  return false if time.nil?
@@ -126,11 +109,8 @@ module MediaWiki
126
109
  # @since 0.4.0
127
110
  # @return [String] The gender. 'male', 'female', or 'unknown'.
128
111
  def get_user_gender(username)
129
- gender = nil
130
112
  info = get_userlists('gender', username)
131
- info['query']['users'].each { |i| gender = i['gender'] }
132
-
133
- gender
113
+ info['query']['users'].find { |hash| hash['name'] == username }['gender']
134
114
  end
135
115
 
136
116
  # Gets the latest contributions by the user until the limit.
@@ -41,26 +41,14 @@ module MediaWiki
41
41
  # @since 0.7.0
42
42
  # @return [Array<String>] All repository names that are marked as local.
43
43
  def get_local_filerepos
44
- response = get_filerepoinfo('name|local')
45
- ret = []
46
- response['query']['repos'].each do |h|
47
- ret << h['name'] if h.key?('local')
48
- end
49
-
50
- ret
44
+ get_filerepoinfo('name|local')['query']['repos'].select { |h| h.key?('local') }.collect { |h| h['name'] }
51
45
  end
52
46
 
53
47
  # Gets an array containing all repositories that aren't local.
54
48
  # @since 0.7.0
55
49
  # @return [Array<String>] All repositories that are not marked as local.
56
50
  def get_nonlocal_filerepos
57
- response = get_filerepoinfo('name|local')
58
- ret = []
59
- response['query']['repos'].each do |h|
60
- ret << h['name'] unless h.key?('local')
61
- end
62
-
63
- ret
51
+ get_filerepoinfo('name|local')['query']['repos'].reject { |h| h.key?('local') }.collect { |h| h['name'] }
64
52
  end
65
53
 
66
54
  # Gets the repository names and their according URLs.
@@ -41,10 +41,7 @@ module MediaWiki
41
41
  # @since 0.6.0
42
42
  # @return [Array<String>] All extension names.
43
43
  def get_extensions
44
- response = get_siteinfo('extensions')
45
- ret = []
46
- response['query']['extensions'].each { |e| ret << e['name'] }
47
- ret
44
+ get_siteinfo('extensions')['query']['extensions'].collect { |e| e['name'] }
48
45
  end
49
46
 
50
47
  # Gets all languages and their codes.
@@ -123,12 +120,7 @@ module MediaWiki
123
120
  # @since 0.6.0
124
121
  # @return [Array<String>] All file extensions.
125
122
  def get_allowed_file_extensions
126
- response = get_siteinfo('fileextensions')
127
- ret = []
128
- response['query']['fileextensions'].each do |e|
129
- ret << e['ext']
130
- end
131
- ret
123
+ get_siteinfo('fileextensions')['query']['fileextensions'].collect { |e| e['ext'] }
132
124
  end
133
125
 
134
126
  # Gets the response for the restrictions siteinfo API. Not really for use by users, mostly for the other two
@@ -136,28 +128,21 @@ module MediaWiki
136
128
  # @since 0.6.0
137
129
  # @return [Hash<String, Array<String>>] All restriction data. See the other restriction methods.
138
130
  def get_restrictions_data
139
- response = get_siteinfo('restrictions')
140
- response['query']['restrictions']
131
+ get_siteinfo('restrictions')['query']['restrictions']
141
132
  end
142
133
 
143
134
  # Gets all restriction/protection types.
144
135
  # @since 0.6.0
145
136
  # @return [Array<String>] All protection types.
146
137
  def get_restriction_types
147
- restrictions = get_restrictions_data
148
- ret = []
149
- restrictions['types'].each { |t| ret << t }
150
- ret
138
+ get_restrictions_data['types']
151
139
  end
152
140
 
153
141
  # Gets all restriction/protection levels.
154
142
  # @since 0.6.0
155
143
  # @return [Array<String>] All protection levels.
156
144
  def get_restriction_levels
157
- restrictions = get_restrictions_data
158
- ret = []
159
- restrictions['levels'].each { |l| ret << l }
160
- ret
145
+ get_restrictions_data['levels']
161
146
  end
162
147
 
163
148
  # Gets all skins and their codes.
@@ -176,36 +161,21 @@ module MediaWiki
176
161
  # @since 0.6.0
177
162
  # @return [Array<String>] All extension tags.
178
163
  def get_extension_tags
179
- response = get_siteinfo('extensiontags')
180
- ret = []
181
- response['query']['extensiontags'].each do |t|
182
- ret << t
183
- end
184
- ret
164
+ get_siteinfo('extensiontags')['query']['extensiontags']
185
165
  end
186
166
 
187
167
  # Gets all function hooks.
188
168
  # @since 0.6.0
189
169
  # @return [Array<String>] All function hooks.
190
170
  def get_function_hooks
191
- response = get_siteinfo('functionhooks')
192
- ret = []
193
- response['query']['functionhooks'].each do |h|
194
- ret << h
195
- end
196
- ret
171
+ get_siteinfo('functionhooks')['query']['functionhooks']
197
172
  end
198
173
 
199
174
  # Gets all variables that are usable on the wiki, such as NUMBEROFPAGES.
200
175
  # @since 0.6.0
201
176
  # @return [Array<String>] All variable string values.
202
177
  def get_variables
203
- response = get_siteinfo('variables')
204
- ret = []
205
- response['query']['variables'].each do |v|
206
- ret << v
207
- end
208
- ret
178
+ get_siteinfo('variables')['query']['variables']
209
179
  end
210
180
  end
211
181
  end
@@ -45,27 +45,19 @@ module MediaWiki
45
45
  # Gets a hash-of-arrays containing all the groups the user can add and remove people from.
46
46
  # @since 0.7.0
47
47
  # @return [Boolean] False if get_current_user_meta is false
48
- # @return [Hash<String, Array<String>>] All the groups that the user can add, remove, add-self, and remove-self.
48
+ # @return [Hash<String, Array<String>>] All the groups that the user can :add, :remove, :addself, and
49
+ # :remove-self.
49
50
  def get_changeable_groups
50
51
  response = get_current_user_meta('changeablegroups')
51
52
  return false unless response
52
53
 
53
- ret = {}
54
- add = []
55
- remove = []
56
- addself = []
57
- removeself = []
58
54
  changeablegroups = response['query']['userinfo']['changeablegroups']
59
- changeablegroups['add'].each { |g| add.push(g) }
60
- changeablegroups['remove'].each { |g| remove.push(g) }
61
- changeablegroups['add-self'].each { |g| addself.push(g) }
62
- changeablegroups['remove-self'].each { |g| removeself.push(g) }
63
- ret['add'] = add
64
- ret['remove'] = remove
65
- ret['addself'] = addself
66
- ret['removeself'] = removeself
67
-
68
- ret
55
+ {
56
+ :add => changeablegroups['add'],
57
+ :remove => changeablegroups['remove'],
58
+ :addself => changeablegroups['add-self'],
59
+ :removeself => changeablegroups['add-self']
60
+ }
69
61
  end
70
62
 
71
63
  # Gets the currently logged in user's real name.
@@ -1,4 +1,5 @@
1
1
  require_relative '../query'
2
+ require_relative '../../constants'
2
3
 
3
4
  module MediaWiki
4
5
  module Query
@@ -28,8 +29,7 @@ module MediaWiki
28
29
  # @return [Array<String>] All usernames for the contributors.
29
30
  def get_logged_in_contributors(title, limit = @query_limit_default)
30
31
  get_contributors_response(title, limit) do |return_val, query|
31
- pageid = nil
32
- query['pages'].each { |r, _| pageid = r }
32
+ pageid = query['pages'].keys.find(MediaWiki::Constants::MISSING_PAGEID_PROC) { |id| id != '-1' }
33
33
  return if query['pages'][pageid].key?('missing')
34
34
  query['pages'][pageid]['contributors'].each { |c| return_val << c['name'] }
35
35
  end
@@ -62,8 +62,7 @@ module MediaWiki
62
62
  ret = 0
63
63
 
64
64
  get_contributors_response(title, limit) do |_, query|
65
- pageid = nil
66
- query['pages'].each { |r, __| pageid = r }
65
+ pageid = query['pages'].keys.find(MediaWiki::Constants::MISSING_PAGEID_PROC) { |id| id != '-1' }
67
66
  return if query['pages'][pageid].key?('missing')
68
67
  ret += query['pages'][pageid]['anoncontributors'].to_i
69
68
  end
@@ -1,4 +1,5 @@
1
1
  require_relative '../query'
2
+ require_relative '../../constants'
2
3
 
3
4
  module MediaWiki
4
5
  module Query
@@ -37,7 +38,7 @@ module MediaWiki
37
38
  dflimit: get_limited(limit)
38
39
  }
39
40
 
40
- query_ary(params, 'pages', 'title')
41
+ query_ary_irrelevant_keys(params, 'pages', 'title')
41
42
  end
42
43
 
43
44
  # Gets the size of an image in bytes.
@@ -82,14 +83,9 @@ module MediaWiki
82
83
  }
83
84
 
84
85
  response = post(params)
85
- pageid = nil
86
- response['query']['pages'].each { |r, _| pageid = r }
86
+ pageid = response['query']['pages'].keys.find(MediaWiki::Constants::MISSING_PAGEID_PROC) { |id| id != '-1'}
87
87
  return nil if pageid == '-1'
88
- ret = {}
89
- response['query']['pages'][pageid]['imageinfo'].each do |i|
90
- i.each { |k, v| ret[k] = v }
91
- end
92
- ret
88
+ response['query']['pages'][pageid]['imageinfo'].reduce({}, :merge)
93
89
  end
94
90
  end
95
91
  end
@@ -1,4 +1,5 @@
1
1
  require_relative '../query'
2
+ require_relative '../../constants'
2
3
 
3
4
  module MediaWiki
4
5
  module Query
@@ -17,14 +18,9 @@ module MediaWiki
17
18
  }
18
19
 
19
20
  query(params) do |return_val, query|
20
- pageid = nil
21
- query['pages'].each do |r, _|
22
- pageid = r
23
- break
24
- end
25
-
21
+ pageid = query['pages'].keys.find(MediaWiki::Constants::MISSING_PAGEID_PROC) { |id| id != '-1' }
26
22
  return if query['pages'][pageid].key?('missing')
27
- query['pages'][pageid].fetch('categories', []).each { |c| return_val << c['title'] }
23
+ return_val.concat(query['pages'][pageid].fetch('categories', []).collect { |c| c['title'] })
28
24
  end
29
25
  end
30
26
 
@@ -44,11 +40,8 @@ module MediaWiki
44
40
  }
45
41
 
46
42
  response = post(params)
47
- revid = nil
48
- response['query']['pages'].each { |r, _| revid = r }
49
-
43
+ revid = response['query']['pages'].keys.find(MediaWiki::Constants::MISSING_PAGEID_PROC) { |id| id != '-1' }
50
44
  revision = response['query']['pages'][revid]
51
-
52
45
  revision['missing'] == '' ? nil : revision['revisions'][0]['*']
53
46
  end
54
47
 
@@ -66,10 +59,7 @@ module MediaWiki
66
59
  titles: title
67
60
  }
68
61
 
69
- response = post(params)
70
- response['query']['pages'].each do |revid, _|
71
- return revid == '-1' ? nil : revid.to_i
72
- end
62
+ post(params)['query']['pages'].keys.find { |id| id != '-1' }&.to_i
73
63
  end
74
64
 
75
65
  # Gets all the external links on a given page.
@@ -88,10 +78,9 @@ module MediaWiki
88
78
  }
89
79
 
90
80
  query(params) do |return_val, query|
91
- query['pages'].each do |revid, _|
92
- return if revid == '-1'
93
- query['pages'][revid]['extlinks'].each { |l| return_val << l['*'] }
94
- end
81
+ pageid = query['pages'].keys.find { |id| id != '-1' }
82
+ return unless pageid
83
+ return_val.concat(query['pages'][pageid]['extlinks'].collect { |l| l['*'] })
95
84
  end
96
85
  end
97
86
 
@@ -104,17 +93,7 @@ module MediaWiki
104
93
  # @return [Nil] If the page does not exist.
105
94
  def do_i_watch?(title)
106
95
  return false unless @logged_in
107
- params = {
108
- action: 'query',
109
- titles: title,
110
- prop: 'info',
111
- inprop: 'watched'
112
- }
113
-
114
- response = post(params)
115
- response['query']['pages'].each do |revid, _|
116
- return revid == '-1' ? nil : response['query']['pages'][revid].key?('watched')
117
- end
96
+ page_info_contains_key(title, 'watched', 'watched')
118
97
  end
119
98
 
120
99
  # Gets whether the current user (can be anonymous) can read the page.
@@ -124,17 +103,7 @@ module MediaWiki
124
103
  # @return [Boolean] Whether the user can read the page.
125
104
  # @return [Nil] If the page does not exist.
126
105
  def can_i_read?(title)
127
- params = {
128
- action: 'query',
129
- titles: title,
130
- prop: 'info',
131
- inprop: 'readable'
132
- }
133
-
134
- response = post(params)
135
- response['query']['pages'].each do |revid, _|
136
- return revid == '-1' ? nil : response['query']['pages'][revid].key?('readable')
137
- end
106
+ page_info_contains_key(title, 'readable', 'readable')
138
107
  end
139
108
 
140
109
  # Gets whether the given page is a redirect.
@@ -144,16 +113,7 @@ module MediaWiki
144
113
  # @return [Boolean] Whether the page is a redirect.
145
114
  # @return [Nil] If the page does not exist.
146
115
  def page_redirect?(title)
147
- params = {
148
- action: 'query',
149
- titles: title,
150
- prop: 'info'
151
- }
152
-
153
- response = post(params)
154
- response['query']['pages'].each do |revid, _|
155
- return revid == '-1' ? nil : response['query']['pages'][revid].key?('redirect')
156
- end
116
+ page_info_contains_key(title, 'redirect')
157
117
  end
158
118
 
159
119
  # Gets whether the given page only has one edit.
@@ -163,16 +123,7 @@ module MediaWiki
163
123
  # @return [Boolean] Whether the page only has one edit.
164
124
  # @return [Nil] If the page does not exist.
165
125
  def page_new?(title)
166
- params = {
167
- action: 'query',
168
- titles: title,
169
- prop: 'info'
170
- }
171
-
172
- response = post(params)
173
- response['query']['pages'].each do |revid, _|
174
- return revid == '-1' ? nil : response['query']['pages'][revid].key?('new')
175
- end
126
+ page_info_contains_key(title, 'new')
176
127
  end
177
128
 
178
129
  # Gets the number of users that watch the given page.
@@ -182,17 +133,7 @@ module MediaWiki
182
133
  # @return [Fixnum] The number of watchers.
183
134
  # @return [Nil] If the page does not exist.
184
135
  def get_number_of_watchers(title)
185
- params = {
186
- action: 'query',
187
- titles: title,
188
- prop: 'info',
189
- inprop: 'watchers'
190
- }
191
-
192
- response = post(params)
193
- response['query']['pages'].each do |revid, _|
194
- return revid == '-1' ? nil : response['query']['pages'][revid]['watchers']
195
- end
136
+ page_info_get_val(title, 'watchers', 'watchers')
196
137
  end
197
138
 
198
139
  # Gets the way the title is actually displayed, after any in-page changes to its display, e.g., using a
@@ -203,17 +144,7 @@ module MediaWiki
203
144
  # @return [String] The page's display title.
204
145
  # @return [Nil] If the page does not exist.
205
146
  def get_display_title(title)
206
- params = {
207
- action: 'query',
208
- titles: title,
209
- prop: 'info',
210
- inprop: 'displaytitle'
211
- }
212
-
213
- response = post(params)
214
- response['query']['pages'].each do |revid, _|
215
- return revid == '-1' ? nil : response['query']['pages'][revid]['displaytitle']
216
- end
147
+ page_info_get_val(title, 'displaytitle', 'displaytitle')
217
148
  end
218
149
 
219
150
  # Gets the levels of protection on the page.
@@ -234,14 +165,15 @@ module MediaWiki
234
165
  }
235
166
 
236
167
  response = post(params)
237
- response['query']['pages'].each do |revid, _|
238
- return if revid == '-1'
239
- protection = response['query']['pages'][revid]['protection']
240
- protection.each do |p|
241
- p.keys.each { |k| p[k.to_sym] = p.delete(k) }
242
- end
243
- return protection
168
+
169
+ pageid = response['query']['pages'].keys.find { |id| id != '-1' }
170
+ return unless pageid
171
+ protection = response['query']['pages'][pageid]['protection']
172
+ protection.each do |p|
173
+ p.keys.each { |k| p[k.to_sym] = p.delete(k) }
244
174
  end
175
+
176
+ protection
245
177
  end
246
178
 
247
179
  # Gets the size, in bytes, of the page.
@@ -251,16 +183,7 @@ module MediaWiki
251
183
  # @return [Fixnum] The number of bytes.
252
184
  # @return [Nil] If the page does not exist.
253
185
  def get_page_size(title)
254
- params = {
255
- action: 'query',
256
- titles: title,
257
- prop: 'info'
258
- }
259
-
260
- response = post(params)
261
- response['query']['pages'].each do |revid, _|
262
- return revid == '-1' ? nil : response['query']['pages'][revid]['length']
263
- end
186
+ page_info_get_val(title, 'length')
264
187
  end
265
188
 
266
189
  # Gets all of the images in the given page.
@@ -277,10 +200,9 @@ module MediaWiki
277
200
  }
278
201
 
279
202
  query(params) do |return_val, query|
280
- query['pages'].each do |revid, _|
281
- return if revid == '-1'
282
- query['pages'][revid]['images'].each { |img| return_val << img['title'] }
283
- end
203
+ pageid = query['pages'].keys.find { |id| id != '-1' }
204
+ return unless pageid
205
+ return_val.concat(query['pages'][pageid]['images'].collect { |img| img['title'] })
284
206
  end
285
207
  end
286
208
 
@@ -298,10 +220,9 @@ module MediaWiki
298
220
  }
299
221
 
300
222
  query(params) do |return_val, query|
301
- query['pages'].each do |revid, _|
302
- return if revid == '-1'
303
- query['pages'][revid]['templates'].each { |template| return_val << template['title'] }
304
- end
223
+ pageid = query['pages'].keys.find { |id| id != '-1' }
224
+ return unless pageid
225
+ return_val.concat(query['pages'][pageid]['templates'].collect { |template| template['title'] })
305
226
  end
306
227
  end
307
228
 
@@ -319,12 +240,10 @@ module MediaWiki
319
240
  }
320
241
 
321
242
  query(params) do |return_val, query|
322
- query['pages'].each do |revid, _|
323
- return if revid == '-1'
324
- query['pages'][revid].fetch('iwlinks', []).each do |l|
325
- return_val << { prefix: l['prefix'], title: l['*'] }
326
- end
327
- end
243
+ pageid = query['pages'].keys.find { |id| id != '-1' }
244
+ return unless pageid
245
+ iwlinks = query['pages'][pageid].fetch('iwlinks', [])
246
+ return_val.concat(iwlinks.collect { |l| { prefix: l['prefix'], title: l['*']} })
328
247
  end
329
248
  end
330
249
 
@@ -344,16 +263,15 @@ module MediaWiki
344
263
  }
345
264
 
346
265
  query(params) do |return_val, query|
347
- query['pages'].each do |revid, _|
348
- return if revid == '-1'
349
- query['pages'][revid]['langlinks'].each do |l|
350
- return_val[l['lang'].to_sym] = {
351
- url: l['url'],
352
- langname: l['langname'],
353
- autonym: l['autonym'],
354
- title: l['*']
355
- }
356
- end
266
+ pageid = query['pages'].keys.find { |id| id != '-1' }
267
+ return unless pageid
268
+ query['pages'][pageid]['langlinks'].each do |l|
269
+ return_val[l['lang'].to_sym] = {
270
+ url: l['url'],
271
+ langname: l['langname'],
272
+ autonym: l['autonym'],
273
+ title: l['*']
274
+ }
357
275
  end
358
276
  end
359
277
  end
@@ -372,12 +290,54 @@ module MediaWiki
372
290
  }
373
291
 
374
292
  query(params) do |return_val, query|
375
- query['pages'].each do |revid, _|
376
- return if revid == '-1'
377
- query['pages'][revid]['links'].each { |l| return_val << l['title'] }
378
- end
293
+ pageid = query['pages'].keys.find { |id| id != '-1' }
294
+ return unless pageid
295
+ return_val.concat(query['pages'][pageid]['links'].collect { |l| l['title'] })
379
296
  end
380
297
  end
298
+
299
+ private
300
+
301
+ # Performs a query for the page info with the provided property.
302
+ # @param title [String] The page name
303
+ # @param inprop [String] The inprop to use. See the MediaWiki API documentation.
304
+ # @return (see #post)
305
+ def get_basic_page_info(title, inprop = nil)
306
+ params = {
307
+ action: 'query',
308
+ titles: title,
309
+ prop: 'info'
310
+ }
311
+ params[:inprop] = inprop if inprop
312
+
313
+ post(params)
314
+ end
315
+
316
+ # Performs a query for the page info with the provided property. Checks if the first non-missing page returned
317
+ # contains the provided key.
318
+ # @param title [String] The page name
319
+ # @param key [String] The key to check for
320
+ # @param inprop [String] The inprop to use. See the MediaWiki API documentation.
321
+ # @return [Nil] If the page is not found.
322
+ # @return [Boolean] If the page object contains the provided key.
323
+ def page_info_contains_key(title, key, inprop = nil)
324
+ response = get_basic_page_info(title, inprop)
325
+ pageid = response['query']['pages'].keys.find { |id| id != '-1' }
326
+ return unless pageid
327
+ response['query']['pages'][pageid].key?(key)
328
+ end
329
+
330
+ # Performs a query for the page info with the provided property, and returns a value by the provided key in
331
+ # the page's returned object.
332
+ # @param (see #page_info_contains_key)
333
+ # @return [Nil] If the page is not found.
334
+ # @return [Any] The returned value for the key.
335
+ def page_info_get_val(title, key, inprop = nil)
336
+ response = get_basic_page_info(title, inprop)
337
+ pageid = response['query']['pages'].keys.find { |id| id != '-1' }
338
+ return unless pageid
339
+ response['query']['pages'][pageid][key]
340
+ end
381
341
  end
382
342
  end
383
343
  end
@@ -36,17 +36,16 @@ module MediaWiki
36
36
  success_key = 'unwatched'
37
37
  end
38
38
 
39
- response = post(params)
40
- ret = {}
41
- response['watch'].each do |entry|
39
+ post(params)['watch'].inject({}) do |result, entry|
42
40
  title = entry['title']
43
41
  if entry.key?(success_key)
44
- ret[title] = entry.key?('missing') ? nil : true
42
+ result[title] = entry.key?('missing') ? nil : true
45
43
  else
46
- ret[title] = false
44
+ result[title] = false
47
45
  end
46
+
47
+ result
48
48
  end
49
- ret
50
49
  end
51
50
  end
52
51
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: mediawiki-butt
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.2.0
4
+ version: 1.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Eli Foster
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2016-09-10 00:00:00.000000000 Z
12
+ date: 2016-10-18 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: httpclient