jabber_admin 2.10.0 → 3.0.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +4 -0
- data/Gemfile +1 -1
- data/README.md +26 -0
- data/UPGRADING.md +276 -0
- data/gemfiles/rails_8.1.gemfile +1 -1
- data/jabber_admin.gemspec +1 -1
- data/lib/jabber_admin/api_call.rb +29 -15
- data/lib/jabber_admin/commands/get_room_affiliations.rb +3 -1
- data/lib/jabber_admin/commands/get_vcard.rb +3 -3
- data/lib/jabber_admin/configuration.rb +19 -0
- data/lib/jabber_admin/errors.rb +1 -1
- data/lib/jabber_admin/version.rb +1 -1
- data/lib/jabber_admin.rb +7 -3
- metadata +9 -8
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 3f2e90026aefdce2606c730204ccb616b9c75caf383bebcd0e1ff61b98ffd56d
|
|
4
|
+
data.tar.gz: 5ff8a175b171834fcd12fd6a41855880007e8fe4cf6c4b782217b8fb4cc45640
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 8d05859217fd8975bec38d07531c54ee56ced4211f93164ef60626e9a0977685aa20a2290660624fdc28d6c7581ee1ed4e663fdca1f7044bd5050c562a8bae96
|
|
7
|
+
data.tar.gz: 1e4b22c10f62b0e6a0cc2bbcec1ed09a407839bc0fe977cfaf418a2b0c15e00dd648c433bdb39e91446435a79c8825e0c01ba284f9e4305e7ecc59ca54348c85
|
data/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,10 @@
|
|
|
2
2
|
|
|
3
3
|
* TODO: Replace this bullet point with an actual description of a change.
|
|
4
4
|
|
|
5
|
+
### 3.0.0 (18 September 2026)
|
|
6
|
+
|
|
7
|
+
* Switched from the rest-client to the http gem ([#34](https://github.com/hausgold/jabber_admin/pull/34))
|
|
8
|
+
|
|
5
9
|
### 2.10.0 (27 August 2026)
|
|
6
10
|
|
|
7
11
|
* Corrected some RuboCop glitches ([#33](https://github.com/hausgold/jabber_admin/pull/33))
|
data/Gemfile
CHANGED
data/README.md
CHANGED
|
@@ -10,6 +10,7 @@ jabber_admin is a small library to easily communicate with the [ejabberd
|
|
|
10
10
|
admin API](https://docs.ejabberd.im/developer/ejabberd-api/admin-api).
|
|
11
11
|
|
|
12
12
|
- [Installation](#installation)
|
|
13
|
+
- [Upgrading](#upgrading)
|
|
13
14
|
- [Configuration](#configuration)
|
|
14
15
|
- [Usage](#usage)
|
|
15
16
|
- [Predefined commands](#predefined-commands)
|
|
@@ -39,6 +40,11 @@ Or install it yourself as:
|
|
|
39
40
|
$ gem install jabber_admin
|
|
40
41
|
```
|
|
41
42
|
|
|
43
|
+
## Upgrading
|
|
44
|
+
|
|
45
|
+
Major releases come with breaking changes. See the [upgrade
|
|
46
|
+
guide](./UPGRADING.md) for the details and the migration steps.
|
|
47
|
+
|
|
42
48
|
## Configuration
|
|
43
49
|
|
|
44
50
|
You can configure the jabber_admin gem in a global initializer way with the
|
|
@@ -55,6 +61,10 @@ JabberAdmin.configure do |config|
|
|
|
55
61
|
config.username = 'admin@jabber.local'
|
|
56
62
|
# The password of the administrator account.
|
|
57
63
|
config.password = 'password'
|
|
64
|
+
# The request timeout in seconds, or a hash with per-operation limits
|
|
65
|
+
# (eg. `{ connect: 5, read: 30, write: 10 }`), or `nil` to disable it.
|
|
66
|
+
# (60 seconds by default)
|
|
67
|
+
config.timeout = 60
|
|
58
68
|
end
|
|
59
69
|
```
|
|
60
70
|
|
|
@@ -162,6 +172,22 @@ command.response.object_id # => 21934400
|
|
|
162
172
|
command.response.object_id # => 21934400
|
|
163
173
|
```
|
|
164
174
|
|
|
175
|
+
The response is an `HTTP::Response` of the
|
|
176
|
+
[http](https://github.com/httprb/http) gem. Its body is already read, so you
|
|
177
|
+
can access the status code and the body string as often as you like.
|
|
178
|
+
|
|
179
|
+
```ruby
|
|
180
|
+
response = JabberAdmin.get_last(check_res_body: false,
|
|
181
|
+
user: 'tom', host: 'ejabberd.local')
|
|
182
|
+
response.code # => 200
|
|
183
|
+
response.body.to_s # => '{"timestamp":"2026-09-17T10:00:00Z","status":"..."}'
|
|
184
|
+
JSON.parse(response.to_s) # => {"timestamp"=>"2026-09-17T10:00:00Z", ...}
|
|
185
|
+
```
|
|
186
|
+
|
|
187
|
+
Connection failures and timeouts raise an `HTTP::Error` (eg.
|
|
188
|
+
`HTTP::ConnectionError` or `HTTP::TimeoutError`), on the bang and non-bang
|
|
189
|
+
variants alike.
|
|
190
|
+
|
|
165
191
|
## Development
|
|
166
192
|
|
|
167
193
|
After checking out the repo, run `make install` to install dependencies. Then,
|
data/UPGRADING.md
ADDED
|
@@ -0,0 +1,276 @@
|
|
|
1
|
+
# Upgrading from jabber_admin 2.x to 3.0
|
|
2
|
+
|
|
3
|
+
This guide covers all breaking changes and required migration steps when
|
|
4
|
+
upgrading from jabber_admin 2.10.x to 3.0.
|
|
5
|
+
|
|
6
|
+
## Table of Contents
|
|
7
|
+
|
|
8
|
+
- [Dependency Changes](#dependency-changes)
|
|
9
|
+
- [Configuration Changes](#configuration-changes)
|
|
10
|
+
- [Request Timeout](#request-timeout)
|
|
11
|
+
- [Response Changes](#response-changes)
|
|
12
|
+
- [Response Class](#response-class)
|
|
13
|
+
- [Response Body](#response-body)
|
|
14
|
+
- [Response Headers](#response-headers)
|
|
15
|
+
- [Request Content-Type](#request-content-type)
|
|
16
|
+
- [Error Handling Changes](#error-handling-changes)
|
|
17
|
+
- [Command Errors](#command-errors)
|
|
18
|
+
- [Connection Failures and Timeouts](#connection-failures-and-timeouts)
|
|
19
|
+
- [Testing Changes](#testing-changes)
|
|
20
|
+
- [Response Doubles](#response-doubles)
|
|
21
|
+
- [Request Stubs](#request-stubs)
|
|
22
|
+
- [VCR Cassettes](#vcr-cassettes)
|
|
23
|
+
- [WebMock Version](#webmock-version)
|
|
24
|
+
- [Behavior Differences at a Glance](#behavior-differences-at-a-glance)
|
|
25
|
+
|
|
26
|
+
---
|
|
27
|
+
|
|
28
|
+
## Dependency Changes
|
|
29
|
+
|
|
30
|
+
The HTTP client library changed from `rest-client` to `http` (http.rb).
|
|
31
|
+
|
|
32
|
+
Dependency | 2.x | 3.0 | Upgrading Guide
|
|
33
|
+
--------------|------------|------------|----------------
|
|
34
|
+
`rest-client` | `~> 2.1` | _removed_ | -
|
|
35
|
+
`http` | _not used_ | `~> 6.0` | [Changelog](https://github.com/httprb/http/blob/main/CHANGELOG.md)
|
|
36
|
+
|
|
37
|
+
**Removed transitive dependencies:**
|
|
38
|
+
|
|
39
|
+
- `http-accept`, `mime-types`, `mime-types-data`, `netrc` — only rest-client
|
|
40
|
+
needed them
|
|
41
|
+
|
|
42
|
+
**New transitive dependencies:**
|
|
43
|
+
|
|
44
|
+
- `llhttp-ffi` — the HTTP parser of http.rb, a native extension loaded via
|
|
45
|
+
`ffi` (make sure your build environment supports it, `ffi` was already
|
|
46
|
+
part of the tree)
|
|
47
|
+
- `http-form_data`, `base64` — pulled in by http.rb
|
|
48
|
+
|
|
49
|
+
The `http-cookie` gem stays in the tree, both clients use it.
|
|
50
|
+
|
|
51
|
+
If your application used rest-client itself and relied on jabber_admin to
|
|
52
|
+
pull it in, add it to your own Gemfile now:
|
|
53
|
+
|
|
54
|
+
```ruby
|
|
55
|
+
gem 'rest-client', '~> 2.1'
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
## Configuration Changes
|
|
59
|
+
|
|
60
|
+
### Request Timeout
|
|
61
|
+
|
|
62
|
+
jabber_admin 3.0 adds the optional `config.timeout` option. It defaults to
|
|
63
|
+
60 seconds, which matches the implicit Net::HTTP defaults (60 seconds to
|
|
64
|
+
connect, 60 seconds to read) of jabber_admin 2.x, so nothing changes unless
|
|
65
|
+
you set it.
|
|
66
|
+
|
|
67
|
+
```ruby
|
|
68
|
+
JabberAdmin.configure do |config|
|
|
69
|
+
config.url = 'http://jabber.local/api'
|
|
70
|
+
config.username = 'admin@jabber.local'
|
|
71
|
+
config.password = 'password'
|
|
72
|
+
|
|
73
|
+
# A single number caps the whole request (connect, write and read
|
|
74
|
+
# together) in seconds. This is the default with 60 seconds.
|
|
75
|
+
config.timeout = 60
|
|
76
|
+
|
|
77
|
+
# A hash sets per-operation limits in seconds instead. The keys are
|
|
78
|
+
# passed to http.rb as they are, unknown keys raise an ArgumentError on
|
|
79
|
+
# the first request.
|
|
80
|
+
config.timeout = { connect: 5, read: 30, write: 10 }
|
|
81
|
+
|
|
82
|
+
# Or disable the client timeout entirely.
|
|
83
|
+
config.timeout = nil
|
|
84
|
+
end
|
|
85
|
+
```
|
|
86
|
+
|
|
87
|
+
See the [http.rb timeout
|
|
88
|
+
documentation](https://github.com/httprb/http/wiki/Timeouts) for the
|
|
89
|
+
details of the hash form.
|
|
90
|
+
|
|
91
|
+
## Response Changes
|
|
92
|
+
|
|
93
|
+
### Response Class
|
|
94
|
+
|
|
95
|
+
Every command, `JabberAdmin::ApiCall#response`, `#perform` and `#perform!`
|
|
96
|
+
now return an `HTTP::Response` instead of a `RestClient::Response`. The
|
|
97
|
+
status code is still an Integer:
|
|
98
|
+
|
|
99
|
+
```ruby
|
|
100
|
+
response = JabberAdmin.get_last(check_res_body: false,
|
|
101
|
+
user: 'tom', host: 'ejabberd.local')
|
|
102
|
+
response.code # => 200
|
|
103
|
+
```
|
|
104
|
+
|
|
105
|
+
### Response Body
|
|
106
|
+
|
|
107
|
+
**This is the change most likely to affect you.** `response.body` is no
|
|
108
|
+
longer a String but an `HTTP::Response::Body` object. Use
|
|
109
|
+
`response.body.to_s` (or the shortcut `response.to_s`) wherever you need
|
|
110
|
+
the String:
|
|
111
|
+
|
|
112
|
+
```diff
|
|
113
|
+
- JSON.parse(response.body)
|
|
114
|
+
+ JSON.parse(response.body.to_s)
|
|
115
|
+
|
|
116
|
+
- response.body == '0'
|
|
117
|
+
+ response.body.to_s == '0'
|
|
118
|
+
|
|
119
|
+
- response.body.include?('error_no_vcard_found')
|
|
120
|
+
+ response.body.to_s.include?('error_no_vcard_found')
|
|
121
|
+
|
|
122
|
+
- /room does not exist/.match?(response.body)
|
|
123
|
+
+ /room does not exist/.match?(response.body.to_s)
|
|
124
|
+
```
|
|
125
|
+
|
|
126
|
+
Beware of `include?` in particular: the body object is enumerable, so
|
|
127
|
+
`response.body.include?(...)` does not raise a `NoMethodError` but tries
|
|
128
|
+
to stream the already consumed body and fails with an
|
|
129
|
+
`HTTP::StateError`.
|
|
130
|
+
|
|
131
|
+
jabber_admin reads the body eagerly while performing the request, so the
|
|
132
|
+
memoized response is complete, the connection is closed, and `to_s`
|
|
133
|
+
returns the cached String as often as you call it.
|
|
134
|
+
|
|
135
|
+
### Response Headers
|
|
136
|
+
|
|
137
|
+
rest-client exposed the headers as a Hash with symbolized, underscored
|
|
138
|
+
keys. http.rb uses the canonical header names:
|
|
139
|
+
|
|
140
|
+
```diff
|
|
141
|
+
- response.headers[:content_type]
|
|
142
|
+
+ response.headers['Content-Type']
|
|
143
|
+
```
|
|
144
|
+
|
|
145
|
+
### Request Content-Type
|
|
146
|
+
|
|
147
|
+
Requests now carry a `Content-Type: application/json; charset=utf-8`
|
|
148
|
+
header. jabber_admin 2.x sent the JSON payload without any content type.
|
|
149
|
+
The payload itself is unchanged.
|
|
150
|
+
|
|
151
|
+
## Error Handling Changes
|
|
152
|
+
|
|
153
|
+
### Command Errors
|
|
154
|
+
|
|
155
|
+
The error classes and their messages are unchanged. The bang variants still
|
|
156
|
+
raise `JabberAdmin::RequestError`, `JabberAdmin::CommandError` and
|
|
157
|
+
`JabberAdmin::UnknownCommandError`, all inheriting from
|
|
158
|
+
`JabberAdmin::Error`, and the message still carries the response body
|
|
159
|
+
(`"Response code was not 200 => {...}"`). Code which matches on
|
|
160
|
+
`error.message` keeps working:
|
|
161
|
+
|
|
162
|
+
```ruby
|
|
163
|
+
begin
|
|
164
|
+
JabberAdmin.register!(user: 'tom@jabber.local', password: 'secret')
|
|
165
|
+
rescue JabberAdmin::RequestError => e
|
|
166
|
+
raise e unless /already registered/.match?(e.message)
|
|
167
|
+
end
|
|
168
|
+
```
|
|
169
|
+
|
|
170
|
+
Only `error.response` changed its class to `HTTP::Response`, so the
|
|
171
|
+
[Response Body](#response-body) rules apply when you read it:
|
|
172
|
+
|
|
173
|
+
```diff
|
|
174
|
+
- e.response.body.include?('already registered')
|
|
175
|
+
+ e.response.body.to_s.include?('already registered')
|
|
176
|
+
```
|
|
177
|
+
|
|
178
|
+
### Connection Failures and Timeouts
|
|
179
|
+
|
|
180
|
+
jabber_admin 2.x rescued every `RestClient::Exception`, including timeouts
|
|
181
|
+
and broken connections, and memoized their (missing) response. The failure
|
|
182
|
+
surfaced later as a `NoMethodError` on `nil`.
|
|
183
|
+
|
|
184
|
+
jabber_admin 3.0 lets these failures raise directly from `#response`,
|
|
185
|
+
`#perform` and `#perform!` as http.rb errors, all inheriting from
|
|
186
|
+
`HTTP::Error`:
|
|
187
|
+
|
|
188
|
+
- `HTTP::ConnectionError` — DNS failures, refused connections, broken
|
|
189
|
+
sockets
|
|
190
|
+
- `HTTP::TimeoutError` — the configured timeout elapsed (see [Request
|
|
191
|
+
Timeout](#request-timeout))
|
|
192
|
+
|
|
193
|
+
Rescue them where you want to handle unreachable ejabberd instances:
|
|
194
|
+
|
|
195
|
+
```diff
|
|
196
|
+
begin
|
|
197
|
+
JabberAdmin.restart!
|
|
198
|
+
- rescue JabberAdmin::Error, NoMethodError => e
|
|
199
|
+
+ rescue JabberAdmin::Error, HTTP::Error => e
|
|
200
|
+
# ...
|
|
201
|
+
end
|
|
202
|
+
```
|
|
203
|
+
|
|
204
|
+
Responses with a 4xx or 5xx status are still delivered as regular responses
|
|
205
|
+
and turned into `JabberAdmin::Error` subclasses by the bang variants, as
|
|
206
|
+
before.
|
|
207
|
+
|
|
208
|
+
## Testing Changes
|
|
209
|
+
|
|
210
|
+
### Response Doubles
|
|
211
|
+
|
|
212
|
+
Replace `RestClient::Response` doubles with real `HTTP::Response` objects.
|
|
213
|
+
They are cheap to build and behave like the responses jabber_admin
|
|
214
|
+
delivers:
|
|
215
|
+
|
|
216
|
+
```diff
|
|
217
|
+
- let(:response) do
|
|
218
|
+
- instance_double(RestClient::Response, code: 200, body: '0')
|
|
219
|
+
- end
|
|
220
|
+
+ let(:response) do
|
|
221
|
+
+ HTTP::Response.new(status: 200, version: '1.1', body: '0')
|
|
222
|
+
+ end
|
|
223
|
+
```
|
|
224
|
+
|
|
225
|
+
### Request Stubs
|
|
226
|
+
|
|
227
|
+
Stubs of `RestClient::Request.execute` no longer intercept anything.
|
|
228
|
+
Stub the wire format with WebMock instead, which also lets you assert on
|
|
229
|
+
the request:
|
|
230
|
+
|
|
231
|
+
```diff
|
|
232
|
+
- allow(RestClient::Request).to receive(:execute).and_return(response)
|
|
233
|
+
+ stub_request(:post, 'http://jabber.local/api/restart').to_return(body: '0')
|
|
234
|
+
|
|
235
|
+
- expect(RestClient::Request).to \
|
|
236
|
+
- receive(:execute).with(a_hash_including(user: 'admin@jabber.local'))
|
|
237
|
+
+ stub = stub_request(:post, 'http://jabber.local/api/restart')
|
|
238
|
+
+ .with(basic_auth: %w[admin@jabber.local password])
|
|
239
|
+
+ # ... perform the command ...
|
|
240
|
+
+ expect(stub).to have_been_requested
|
|
241
|
+
```
|
|
242
|
+
|
|
243
|
+
Stubbing at the jabber_admin level (`allow(JabberAdmin).to
|
|
244
|
+
receive(:restart!)`) keeps working unchanged.
|
|
245
|
+
|
|
246
|
+
### VCR Cassettes
|
|
247
|
+
|
|
248
|
+
Cassettes recorded with jabber_admin 2.x replay without re-recording, as
|
|
249
|
+
long as your VCR configuration uses the default request matchers (method
|
|
250
|
+
and URI). The JSON request body is byte-identical to 2.x. If you match on
|
|
251
|
+
headers, note the new `Content-Type` request header and the changed
|
|
252
|
+
`User-Agent`.
|
|
253
|
+
|
|
254
|
+
### WebMock Version
|
|
255
|
+
|
|
256
|
+
http.rb 6 requires WebMock 3.26 or newer, older adapters build the
|
|
257
|
+
responses with a positional Hash and fail with an `ArgumentError` on
|
|
258
|
+
`HTTP::Response.new`. Update your lock:
|
|
259
|
+
|
|
260
|
+
```shell
|
|
261
|
+
$ bundle update webmock
|
|
262
|
+
```
|
|
263
|
+
|
|
264
|
+
## Behavior Differences at a Glance
|
|
265
|
+
|
|
266
|
+
Aspect | 2.x (rest-client) | 3.0 (http.rb)
|
|
267
|
+
--------------------|-----------------------------------|----------------------------------------
|
|
268
|
+
Response class | `RestClient::Response` | `HTTP::Response`
|
|
269
|
+
`response.code` | Integer | Integer
|
|
270
|
+
`response.body` | String | `HTTP::Response::Body`, use `.to_s`
|
|
271
|
+
`response.headers` | `{ content_type: ... }` | `{ 'Content-Type' => ... }`
|
|
272
|
+
4xx/5xx responses | `JabberAdmin::Error` on bang | unchanged
|
|
273
|
+
Connection failures | swallowed, later `NoMethodError` | `HTTP::ConnectionError`
|
|
274
|
+
Timeouts | implicit 60s connect / 60s read | `config.timeout`, 60s global by default
|
|
275
|
+
Request body | `payload.to_json` | unchanged
|
|
276
|
+
Request headers | no `Content-Type` | `Content-Type: application/json; charset=utf-8`
|
data/gemfiles/rails_8.1.gemfile
CHANGED
|
@@ -15,7 +15,7 @@ gem "rubocop-rails"
|
|
|
15
15
|
gem "rubocop-rspec"
|
|
16
16
|
gem "simplecov", ">= 0.22"
|
|
17
17
|
gem "vcr", "~> 6.0"
|
|
18
|
-
gem "webmock", "~> 3.
|
|
18
|
+
gem "webmock", "~> 3.26"
|
|
19
19
|
gem "yard", ">= 0.9.28"
|
|
20
20
|
gem "yard-activesupport-concern", ">= 0.0.1"
|
|
21
21
|
gem "activesupport", "~> 8.1.0"
|
data/jabber_admin.gemspec
CHANGED
|
@@ -34,7 +34,7 @@ Gem::Specification.new do |spec|
|
|
|
34
34
|
spec.required_ruby_version = '>= 4.0'
|
|
35
35
|
|
|
36
36
|
spec.add_dependency 'activesupport', '>= 8.1'
|
|
37
|
+
spec.add_dependency 'http', '~> 6.0'
|
|
37
38
|
spec.add_dependency 'logger', '~> 1.7'
|
|
38
|
-
spec.add_dependency 'rest-client', '~> 2.1'
|
|
39
39
|
spec.add_dependency 'zeitwerk', '~> 2.6'
|
|
40
40
|
end
|
|
@@ -28,21 +28,31 @@ module JabberAdmin
|
|
|
28
28
|
"#{JabberAdmin.configuration.url.strip.chomp('/')}/#{@command}"
|
|
29
29
|
end
|
|
30
30
|
|
|
31
|
+
# Build a ready to use HTTP client for the API call. It carries the
|
|
32
|
+
# configured administrator credentials as HTTP basic authentication and
|
|
33
|
+
# the configured request timeout, when one is set.
|
|
34
|
+
#
|
|
35
|
+
# @return [HTTP::Session] the prepared HTTP client
|
|
36
|
+
def client
|
|
37
|
+
config = JabberAdmin.configuration
|
|
38
|
+
session = HTTP.basic_auth(user: config.username, pass: config.password)
|
|
39
|
+
session = session.timeout(config.timeout) if config.timeout
|
|
40
|
+
session
|
|
41
|
+
end
|
|
42
|
+
|
|
31
43
|
# This method compose the actual request, performs it and stores the
|
|
32
44
|
# response to the instance. Additional calls to this method will not
|
|
33
45
|
# repeat the request, but will deliver the response directly.
|
|
34
46
|
#
|
|
35
|
-
#
|
|
47
|
+
# The payload is sent as a JSON document. The response body is read
|
|
48
|
+
# right away, so the response is complete and the connection is closed
|
|
49
|
+
# when we hand it out. Any status code is delivered as a regular
|
|
50
|
+
# response, only connection failures and timeouts raise.
|
|
51
|
+
#
|
|
52
|
+
# @return [HTTP::Response] the response of the API call
|
|
53
|
+
# @raise [HTTP::Error] on connection failures or timeouts
|
|
36
54
|
def response
|
|
37
|
-
@response ||=
|
|
38
|
-
method: :post,
|
|
39
|
-
url: url,
|
|
40
|
-
user: JabberAdmin.configuration.username,
|
|
41
|
-
password: JabberAdmin.configuration.password,
|
|
42
|
-
payload: payload.to_json
|
|
43
|
-
)
|
|
44
|
-
rescue RestClient::Exception => e
|
|
45
|
-
@response = e.response
|
|
55
|
+
@response ||= client.post(url, json: payload).flush
|
|
46
56
|
end
|
|
47
57
|
|
|
48
58
|
# Check if the response was successful. Otherwise raise exceptions with
|
|
@@ -77,12 +87,13 @@ module JabberAdmin
|
|
|
77
87
|
# not get any further information here, which makes error debugging a
|
|
78
88
|
# struggle.
|
|
79
89
|
raise CommandError.new('Command was not successful', response) \
|
|
80
|
-
unless response.body == '0'
|
|
90
|
+
unless response.body.to_s == '0'
|
|
81
91
|
end
|
|
82
92
|
|
|
83
93
|
# Just a simple DSL wrapper for the response method.
|
|
84
94
|
#
|
|
85
|
-
# @return [
|
|
95
|
+
# @return [HTTP::Response] the API call response
|
|
96
|
+
# @raise [HTTP::Error] on connection failures or timeouts
|
|
86
97
|
def perform
|
|
87
98
|
response
|
|
88
99
|
end
|
|
@@ -93,7 +104,8 @@ module JabberAdmin
|
|
|
93
104
|
#
|
|
94
105
|
# @raise JabberAdmin::ApiError
|
|
95
106
|
# @raise JabberAdmin::CommandError
|
|
96
|
-
# @
|
|
107
|
+
# @raise [HTTP::Error] on connection failures or timeouts
|
|
108
|
+
# @return [HTTP::Response] the API call response
|
|
97
109
|
def perform!
|
|
98
110
|
check_response
|
|
99
111
|
response
|
|
@@ -105,7 +117,8 @@ module JabberAdmin
|
|
|
105
117
|
#
|
|
106
118
|
# @param args [Array<Mixed>] the initializer arguments
|
|
107
119
|
# @param kwargs [Hash{Symbol => Mixed}] the initializer arguments
|
|
108
|
-
# @return [
|
|
120
|
+
# @return [HTTP::Response] the API call response
|
|
121
|
+
# @raise [HTTP::Error] on connection failures or timeouts
|
|
109
122
|
def self.perform(*, **)
|
|
110
123
|
new(*, **).perform
|
|
111
124
|
end
|
|
@@ -116,10 +129,11 @@ module JabberAdmin
|
|
|
116
129
|
#
|
|
117
130
|
# @param args [Array<Mixed>] the initializer arguments
|
|
118
131
|
# @param kwargs [Hash{Symbol => Mixed}] the initializer arguments
|
|
119
|
-
# @return [
|
|
132
|
+
# @return [HTTP::Response] the API call response
|
|
120
133
|
#
|
|
121
134
|
# @raise JabberAdmin::ApiError
|
|
122
135
|
# @raise JabberAdmin::CommandError
|
|
136
|
+
# @raise [HTTP::Error] on connection failures or timeouts
|
|
123
137
|
def self.perform!(*, **)
|
|
124
138
|
new(*, **).perform!
|
|
125
139
|
end
|
|
@@ -53,13 +53,13 @@ module JabberAdmin
|
|
|
53
53
|
|
|
54
54
|
res = callable.call(meth, check_res_body: false,
|
|
55
55
|
user: uid, host: host, **args)
|
|
56
|
-
body = (200..299).cover?(res.code) ? JSON.parse(res.body) : nil
|
|
56
|
+
body = (200..299).cover?(res.code) ? JSON.parse(res.body.to_s) : nil
|
|
57
57
|
body.is_a?(Hash) ? body['content'] : body
|
|
58
58
|
rescue JabberAdmin::Error => e
|
|
59
59
|
# When ejabberd tells us there was no value, it does this the hard way
|
|
60
|
-
next if e.response.body.include? 'error_no_value_found_in_vcard'
|
|
60
|
+
next if e.response.body.to_s.include? 'error_no_value_found_in_vcard'
|
|
61
61
|
# Same for the case when there is no vCard at all
|
|
62
|
-
next if e.response.body.include? 'error_no_vcard_found'
|
|
62
|
+
next if e.response.body.to_s.include? 'error_no_vcard_found'
|
|
63
63
|
|
|
64
64
|
raise e
|
|
65
65
|
end
|
|
@@ -7,6 +7,25 @@ module JabberAdmin
|
|
|
7
7
|
#
|
|
8
8
|
# See the +JabberAdmin+ documentation for further details.
|
|
9
9
|
class Configuration
|
|
10
|
+
# The ejabberd REST API endpoint and the administrator credentials
|
|
10
11
|
attr_accessor :username, :password, :url
|
|
12
|
+
|
|
13
|
+
# The request timeout, either in seconds as a single number which caps
|
|
14
|
+
# the whole request (connect, write and read together), or a hash with
|
|
15
|
+
# per-operation limits (eg. +{ connect: 5, read: 30, write: 10 }+), or
|
|
16
|
+
# +nil+ to disable the client timeout entirely. The value is passed to
|
|
17
|
+
# the http gem as is, so a malformed hash raises an +ArgumentError+ on
|
|
18
|
+
# the first request.
|
|
19
|
+
#
|
|
20
|
+
# See: https://github.com/httprb/http/wiki/Timeouts
|
|
21
|
+
#
|
|
22
|
+
# @return [Numeric, Hash{Symbol => Numeric}, nil] the request timeout
|
|
23
|
+
attr_accessor :timeout
|
|
24
|
+
|
|
25
|
+
# Setup a new configuration instance with the defaults. The endpoint and
|
|
26
|
+
# the credentials have no defaults, the timeout defaults to 60 seconds.
|
|
27
|
+
def initialize
|
|
28
|
+
@timeout = 60
|
|
29
|
+
end
|
|
11
30
|
end
|
|
12
31
|
end
|
data/lib/jabber_admin/errors.rb
CHANGED
|
@@ -16,7 +16,7 @@ module JabberAdmin
|
|
|
16
16
|
# Create a new exception.
|
|
17
17
|
#
|
|
18
18
|
# @param msg [String] the exception message
|
|
19
|
-
# @param response [
|
|
19
|
+
# @param response [HTTP::Response] the response when available
|
|
20
20
|
def initialize(msg, response = nil)
|
|
21
21
|
@response = response
|
|
22
22
|
msg += " => #{response.body}" if response&.body
|
data/lib/jabber_admin/version.rb
CHANGED
data/lib/jabber_admin.rb
CHANGED
|
@@ -4,7 +4,7 @@ require 'zeitwerk'
|
|
|
4
4
|
require 'logger'
|
|
5
5
|
require 'active_support/inflector'
|
|
6
6
|
require 'json'
|
|
7
|
-
require '
|
|
7
|
+
require 'http'
|
|
8
8
|
|
|
9
9
|
# jabber_admin
|
|
10
10
|
#
|
|
@@ -37,6 +37,10 @@ require 'rest-client'
|
|
|
37
37
|
# config.username = 'admin@jabber.local'
|
|
38
38
|
# # The password of the administrator account.
|
|
39
39
|
# config.password = 'password'
|
|
40
|
+
# # The request timeout in seconds, or a per-operation hash
|
|
41
|
+
# # (eg. +{ connect: 5, read: 30, write: 10 }+), or +nil+ to
|
|
42
|
+
# # disable it. (60 seconds by default)
|
|
43
|
+
# config.timeout = 60
|
|
40
44
|
# end
|
|
41
45
|
#
|
|
42
46
|
# @example Restart the ejabberd service
|
|
@@ -97,7 +101,7 @@ module JabberAdmin
|
|
|
97
101
|
# @param method [Symbol, String, #to_s] the name of the command to run
|
|
98
102
|
# @param args [Array<Mixed>] all additional API call payload
|
|
99
103
|
# @param kwargs [Hash{Symbol => Mixed}] all additional API call payload
|
|
100
|
-
# @return [
|
|
104
|
+
# @return [HTTP::Response] the actual response of the command
|
|
101
105
|
def method_missing(method, *, **)
|
|
102
106
|
predefined_command(method).call(
|
|
103
107
|
predefined_callable(method), *, **
|
|
@@ -144,7 +148,7 @@ module JabberAdmin
|
|
|
144
148
|
get_room_affiliations!(room: room)
|
|
145
149
|
true
|
|
146
150
|
rescue JabberAdmin::CommandError => e
|
|
147
|
-
raise e unless /room does not exist/.match? e.response.body
|
|
151
|
+
raise e unless /room does not exist/.match? e.response.body.to_s
|
|
148
152
|
|
|
149
153
|
false
|
|
150
154
|
end
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: jabber_admin
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version:
|
|
4
|
+
version: 3.0.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Hermann Mayer
|
|
@@ -25,33 +25,33 @@ dependencies:
|
|
|
25
25
|
- !ruby/object:Gem::Version
|
|
26
26
|
version: '8.1'
|
|
27
27
|
- !ruby/object:Gem::Dependency
|
|
28
|
-
name:
|
|
28
|
+
name: http
|
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
|
30
30
|
requirements:
|
|
31
31
|
- - "~>"
|
|
32
32
|
- !ruby/object:Gem::Version
|
|
33
|
-
version: '
|
|
33
|
+
version: '6.0'
|
|
34
34
|
type: :runtime
|
|
35
35
|
prerelease: false
|
|
36
36
|
version_requirements: !ruby/object:Gem::Requirement
|
|
37
37
|
requirements:
|
|
38
38
|
- - "~>"
|
|
39
39
|
- !ruby/object:Gem::Version
|
|
40
|
-
version: '
|
|
40
|
+
version: '6.0'
|
|
41
41
|
- !ruby/object:Gem::Dependency
|
|
42
|
-
name:
|
|
42
|
+
name: logger
|
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
|
44
44
|
requirements:
|
|
45
45
|
- - "~>"
|
|
46
46
|
- !ruby/object:Gem::Version
|
|
47
|
-
version: '
|
|
47
|
+
version: '1.7'
|
|
48
48
|
type: :runtime
|
|
49
49
|
prerelease: false
|
|
50
50
|
version_requirements: !ruby/object:Gem::Requirement
|
|
51
51
|
requirements:
|
|
52
52
|
- - "~>"
|
|
53
53
|
- !ruby/object:Gem::Version
|
|
54
|
-
version: '
|
|
54
|
+
version: '1.7'
|
|
55
55
|
- !ruby/object:Gem::Dependency
|
|
56
56
|
name: zeitwerk
|
|
57
57
|
requirement: !ruby/object:Gem::Requirement
|
|
@@ -93,6 +93,7 @@ files:
|
|
|
93
93
|
- Makefile
|
|
94
94
|
- README.md
|
|
95
95
|
- Rakefile
|
|
96
|
+
- UPGRADING.md
|
|
96
97
|
- bin/config.rb
|
|
97
98
|
- bin/console
|
|
98
99
|
- bin/setup
|
|
@@ -150,7 +151,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
|
150
151
|
- !ruby/object:Gem::Version
|
|
151
152
|
version: '0'
|
|
152
153
|
requirements: []
|
|
153
|
-
rubygems_version: 4.0.
|
|
154
|
+
rubygems_version: 4.0.20
|
|
154
155
|
specification_version: 4
|
|
155
156
|
summary: Library for the ejabberd RESTful admin API
|
|
156
157
|
test_files: []
|