matrix_sdk 0.0.4 → 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.
- checksums.yaml +4 -4
- data/.rubocop.yml +7 -0
- data/CHANGELOG.md +11 -0
- data/README.md +2 -0
- data/examples/simple_client.rb +6 -3
- data/lib/matrix_sdk.rb +13 -2
- data/lib/matrix_sdk/api.rb +70 -720
- data/lib/matrix_sdk/application_service.rb +210 -0
- data/lib/matrix_sdk/client.rb +69 -44
- data/lib/matrix_sdk/extensions.rb +22 -10
- data/lib/matrix_sdk/protocols/as.rb +5 -0
- data/lib/matrix_sdk/protocols/cs.rb +799 -0
- data/lib/matrix_sdk/protocols/is.rb +33 -0
- data/lib/matrix_sdk/protocols/ss.rb +12 -0
- data/lib/matrix_sdk/room.rb +15 -38
- data/lib/matrix_sdk/user.rb +6 -4
- data/lib/matrix_sdk/version.rb +1 -1
- data/matrix-sdk.gemspec +4 -3
- metadata +25 -7
@@ -0,0 +1,210 @@
|
|
1
|
+
require 'matrix_sdk'
|
2
|
+
|
3
|
+
module MatrixSdk
|
4
|
+
class ApplicationService
|
5
|
+
include MatrixSdk::Logging
|
6
|
+
attr_reader :api, :port
|
7
|
+
|
8
|
+
def_delegators :@api,
|
9
|
+
:access_token, :access_token=, :device_id, :device_id=, :homeserver, :homeserver=,
|
10
|
+
:validate_certificate, :validate_certificate=
|
11
|
+
|
12
|
+
def initialize(hs_url, as_token:, hs_token:, default_routes: true, **params)
|
13
|
+
logger.warning 'This abstraction is still under HEAVY development, expect errors'
|
14
|
+
|
15
|
+
params = { protocols: %i[AS CS] }.merge(params).merge(access_token: as_token)
|
16
|
+
if hs_url.is_a? Api
|
17
|
+
@api = hs_url
|
18
|
+
params.each do |k, v|
|
19
|
+
api.instance_variable_set("@#{k}", v) if api.instance_variable_defined? "@#{k}"
|
20
|
+
end
|
21
|
+
else
|
22
|
+
@api = Api.new hs_url, params
|
23
|
+
end
|
24
|
+
|
25
|
+
@id = params.fetch(:id, MatrixSdk::Api::USER_AGENT)
|
26
|
+
@port = params.fetch(:port, 8888)
|
27
|
+
@url = params.fetch(:url, URI("http://localhost:#{@port}"))
|
28
|
+
@as_token = as_token
|
29
|
+
@hs_token = hs_token
|
30
|
+
|
31
|
+
@method_map = {}
|
32
|
+
|
33
|
+
if default_routes
|
34
|
+
add_method(:GET, '/_matrix/app/v1/users/', %r{^/_matrix/app/v1/users/(?<user>[^/]+)$}, :do_get_user)
|
35
|
+
add_method(:GET, '/_matrix/app/v1/rooms/', %r{^/_matrix/app/v1/rooms/(?<room>[^/]+)$}, :do_get_room)
|
36
|
+
|
37
|
+
add_method(:GET, '/_matrix/app/v1/thirdparty/protocol/', %r{^/_matrix/app/v1/thirdparty/protocol/(?<protocol>[^/]+)$}, :do_get_3p_protocol_p)
|
38
|
+
add_method(:GET, '/_matrix/app/v1/thirdparty/user/', %r{^/_matrix/app/v1/thirdparty/user/(?<protocol>[^/]+)$}, :do_get_3p_user_p)
|
39
|
+
add_method(:GET, '/_matrix/app/v1/thirdparty/location/', %r{^/_matrix/app/v1/thirdparty/location/(?<protocol>[^/]+)$}, :do_get_3p_location_p)
|
40
|
+
add_method(:GET, '/_matrix/app/v1/thirdparty/user', %r{^/_matrix/app/v1/thirdparty/user$}, :do_get_3p_user)
|
41
|
+
add_method(:GET, '/_matrix/app/v1/thirdparty/location', %r{^/_matrix/app/v1/thirdparty/location$}, :do_get_3p_location)
|
42
|
+
|
43
|
+
add_method(:PUT, '/_matrix/app/v1/transactions/', %r{^/_matrix/app/v1/transactions/(?<txn_id>[^/]+)$}, :do_put_transaction)
|
44
|
+
|
45
|
+
if params.fetch(:legacy_routes, false)
|
46
|
+
add_method(:GET, '/users/', %r{^/users/(?<user>[^/]+)$}, :do_get_user)
|
47
|
+
add_method(:GET, '/rooms/', %r{^/rooms/(?<room>[^/]+)$}, :do_get_room)
|
48
|
+
|
49
|
+
add_method(:GET, '/_matrix/app/unstable/thirdparty/protocol/', %r{^/_matrix/app/unstable/thirdparty/protocol/(?<protocol>[^/]+)$}, :do_get_3p_protocol_p)
|
50
|
+
add_method(:GET, '/_matrix/app/unstable/thirdparty/user/', %r{^/_matrix/app/unstable/thirdparty/user/(?<protocol>[^/]+)$}, :do_get_3p_user_p)
|
51
|
+
add_method(:GET, '/_matrix/app/unstable/thirdparty/location/', %r{^/_matrix/app/unstable/thirdparty/location/(?<protocol>[^/]+)$}, :do_get_3p_location_p)
|
52
|
+
add_method(:GET, '/_matrix/app/unstable/thirdparty/user', %r{^/_matrix/app/unstable/thirdparty/user$}, :do_get_3p_user)
|
53
|
+
add_method(:GET, '/_matrix/app/unstable/thirdparty/location', %r{^/_matrix/app/unstable/thirdparty/location$}, :do_get_3p_location)
|
54
|
+
|
55
|
+
add_method(:PUT, '/transactions/', %r{^/transactions/(?<txn_id>[^/]+)$}, :do_put_transaction)
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
start_server
|
60
|
+
end
|
61
|
+
|
62
|
+
def registration
|
63
|
+
{
|
64
|
+
id: @id,
|
65
|
+
url: @url,
|
66
|
+
as_token: @as_token,
|
67
|
+
hs_token: @hs_token,
|
68
|
+
sender_localpart: '',
|
69
|
+
namespaces: {
|
70
|
+
users: [],
|
71
|
+
aliases: [],
|
72
|
+
rooms: []
|
73
|
+
},
|
74
|
+
rate_limited: false,
|
75
|
+
protocols: []
|
76
|
+
}
|
77
|
+
end
|
78
|
+
|
79
|
+
def port=(port)
|
80
|
+
raise ArgumentError, 'Port must be a number' unless port.is_a? Numeric
|
81
|
+
|
82
|
+
raise NotImplementedError, "Can't change port of a running server" if server.status != :Stop
|
83
|
+
|
84
|
+
@port = port
|
85
|
+
end
|
86
|
+
|
87
|
+
protected
|
88
|
+
|
89
|
+
def add_method(verb, prefix, regex, proc = nil, &block)
|
90
|
+
proc ||= block
|
91
|
+
raise ArgumentError, 'No method specified' if proc.nil?
|
92
|
+
|
93
|
+
method_entry = (@method_map[verb] ||= {})[regex] = {
|
94
|
+
verb: verb,
|
95
|
+
prefix: prefix,
|
96
|
+
proc: proc
|
97
|
+
}
|
98
|
+
return true unless @server
|
99
|
+
|
100
|
+
server.mount_proc(method.prefix) { |req, res| _handle_proc(verb, method_entry, req, res) }
|
101
|
+
end
|
102
|
+
|
103
|
+
def do_get_user(user:, **params)
|
104
|
+
[user, params]
|
105
|
+
raise NotImplementedError
|
106
|
+
end
|
107
|
+
|
108
|
+
def do_get_room(room:, **params)
|
109
|
+
[room, params]
|
110
|
+
raise NotImplementedError
|
111
|
+
end
|
112
|
+
|
113
|
+
def do_get_3p_protocol_p(protocol:, **params)
|
114
|
+
[protocol, params]
|
115
|
+
raise NotImplementedError
|
116
|
+
end
|
117
|
+
|
118
|
+
def do_get_3p_user_p(protocol:, **params)
|
119
|
+
[protocol, params]
|
120
|
+
raise NotImplementedError
|
121
|
+
end
|
122
|
+
|
123
|
+
def do_get_3p_location_p(protocol:, **params)
|
124
|
+
[protocol, params]
|
125
|
+
raise NotImplementedError
|
126
|
+
end
|
127
|
+
|
128
|
+
def do_get_3p_location(**params)
|
129
|
+
[protocol, params]
|
130
|
+
raise NotImplementedError
|
131
|
+
end
|
132
|
+
|
133
|
+
def do_get_3p_user(**params)
|
134
|
+
[protocol, params]
|
135
|
+
raise NotImplementedError
|
136
|
+
end
|
137
|
+
|
138
|
+
def do_put_transaction(txn_id:, **params)
|
139
|
+
[txn_id, params]
|
140
|
+
raise NotImplementedError
|
141
|
+
end
|
142
|
+
|
143
|
+
def start_server
|
144
|
+
server.start
|
145
|
+
|
146
|
+
@method_map.each do |verb, method_entry|
|
147
|
+
# break if verb != method_entry[:verb]
|
148
|
+
|
149
|
+
method = method_entry[:proc]
|
150
|
+
server.mount_proc(method.prefix) { |req, res| _handle_proc(verb, method_entry, req, res) }
|
151
|
+
end
|
152
|
+
|
153
|
+
logger.info "Application Service is now running on port #{port}"
|
154
|
+
end
|
155
|
+
|
156
|
+
def stop_server
|
157
|
+
@server.shutdown if @server
|
158
|
+
@server = nil
|
159
|
+
end
|
160
|
+
|
161
|
+
private
|
162
|
+
|
163
|
+
def _handle_proc(verb, method_entry, req, res)
|
164
|
+
logger.debug "Received request for #{verb} #{method_entry}"
|
165
|
+
match = regex.match(req.request_uri.path)
|
166
|
+
match_hash = Hash[match.names.zip(match.captures)].merge(
|
167
|
+
request: req,
|
168
|
+
response: res
|
169
|
+
)
|
170
|
+
|
171
|
+
if method.is_a? Symbol
|
172
|
+
send method, match_hash
|
173
|
+
else
|
174
|
+
method.call match_hash
|
175
|
+
end
|
176
|
+
end
|
177
|
+
|
178
|
+
def server
|
179
|
+
@server ||= WEBrick::HTTPServer.new(Port: port, ServerSoftware: "#{MatrixSdk::Api::USER_AGENT} (Ruby #{RUBY_VERSION})").tap do |server|
|
180
|
+
server.mount_proc '/', &:handle_request
|
181
|
+
end
|
182
|
+
end
|
183
|
+
|
184
|
+
def handle_request(request, response)
|
185
|
+
logger.debug "Received request #{request.inspect}"
|
186
|
+
|
187
|
+
req_method = request.request_method.to_s.to_sym
|
188
|
+
req_uri = request.request_uri
|
189
|
+
|
190
|
+
map = @method_map[req_method]
|
191
|
+
raise WEBrick::HTTPStatus[405], { message: 'Unsupported verb' }.to_json if map.nil?
|
192
|
+
|
193
|
+
discovered = map.find { |k, _v| k =~ req_uri.path }
|
194
|
+
raise WEBrick::HTTPStatus[404], { message: 'Unknown request' }.to_json if discovered.nil?
|
195
|
+
|
196
|
+
method = discovered.last
|
197
|
+
match = Regexp.last_match
|
198
|
+
match_hash = Hash[match.names.zip(match.captures)].merge(
|
199
|
+
request: request,
|
200
|
+
response: response
|
201
|
+
)
|
202
|
+
|
203
|
+
if method.is_a? Symbol
|
204
|
+
send method, match_hash
|
205
|
+
else
|
206
|
+
method.call match_hash
|
207
|
+
end
|
208
|
+
end
|
209
|
+
end
|
210
|
+
end
|
data/lib/matrix_sdk/client.rb
CHANGED
@@ -4,19 +4,28 @@ require 'forwardable'
|
|
4
4
|
|
5
5
|
module MatrixSdk
|
6
6
|
class Client
|
7
|
+
include MatrixSdk::Logging
|
7
8
|
extend Forwardable
|
8
9
|
|
9
10
|
attr_reader :api
|
10
11
|
attr_accessor :cache, :sync_filter
|
11
12
|
|
12
|
-
events :event, :presence_event, :invite_event, :
|
13
|
+
events :event, :presence_event, :invite_event, :leave_event, :ephemeral_event
|
13
14
|
ignore_inspect :api,
|
14
|
-
:on_event, :on_presence_event, :on_invite_event, :
|
15
|
+
:on_event, :on_presence_event, :on_invite_event, :on_leave_event, :on_ephemeral_event
|
15
16
|
|
16
17
|
def_delegators :@api,
|
17
18
|
:access_token, :access_token=, :device_id, :device_id=, :homeserver, :homeserver=,
|
18
19
|
:validate_certificate, :validate_certificate=
|
19
20
|
|
21
|
+
def self.new_for_domain(domain, **params)
|
22
|
+
api = MatrixSdk::Api.new_for_domain(domain, keep_wellknown: true)
|
23
|
+
return new(api, params) unless api.well_known.key? 'm.identity_server'
|
24
|
+
|
25
|
+
identity_server = MatrixSdk::Api.new(api.well_known['m.identity_server']['base_url'], protocols: %i[IS])
|
26
|
+
new(api, params.merge(identity_server: identity_server))
|
27
|
+
end
|
28
|
+
|
20
29
|
# @param hs_url [String,URI,Api] The URL to the Matrix homeserver, without the /_matrix/ part, or an existing Api instance
|
21
30
|
# @param client_cache [:all,:some,:none] (:all) How much data should be cached in the client
|
22
31
|
# @param params [Hash] Additional parameters on creation
|
@@ -40,10 +49,11 @@ module MatrixSdk
|
|
40
49
|
@rooms = {}
|
41
50
|
@users = {}
|
42
51
|
@cache = client_cache
|
52
|
+
@identity_server = params.fetch(:identity_server, nil)
|
43
53
|
|
44
54
|
@sync_token = nil
|
45
55
|
@sync_thread = nil
|
46
|
-
@sync_filter = { room: { timeline: { limit: params.fetch(:sync_filter_limit, 20) } } }
|
56
|
+
@sync_filter = { room: { timeline: { limit: params.fetch(:sync_filter_limit, 20) }, state: { lazy_load_members: true } } }
|
47
57
|
|
48
58
|
@should_listen = false
|
49
59
|
@next_batch = nil
|
@@ -61,10 +71,6 @@ module MatrixSdk
|
|
61
71
|
@mxid = params[:user_id]
|
62
72
|
end
|
63
73
|
|
64
|
-
def logger
|
65
|
-
@logger ||= Logging.logger[self]
|
66
|
-
end
|
67
|
-
|
68
74
|
def mxid
|
69
75
|
@mxid ||= begin
|
70
76
|
api.whoami?[:user_id] if api && api.access_token
|
@@ -154,8 +160,15 @@ module MatrixSdk
|
|
154
160
|
ensure_room(data.fetch(:room_id, room_id_or_alias))
|
155
161
|
end
|
156
162
|
|
157
|
-
def find_room(room_id_or_alias)
|
158
|
-
|
163
|
+
def find_room(room_id_or_alias, only_canonical: false)
|
164
|
+
room_id_or_alias = MXID.new(room_id_or_alias.to_s) unless room_id_or_alias.is_a? MXID
|
165
|
+
raise ArgumentError, 'Must be a room id or alias' unless %i[room_id room_alias].include? room_id_or_alias.type
|
166
|
+
|
167
|
+
return @rooms.fetch(room_id_or_alias, nil) if room_id_or_alias.room_id?
|
168
|
+
|
169
|
+
return @rooms.values.find { |r| r.canonical_alias == room_id_or_alias.to_s } if only_canonical
|
170
|
+
|
171
|
+
@rooms.values.find { |r| r.aliases.include? room_id_or_alias.to_s }
|
159
172
|
end
|
160
173
|
|
161
174
|
def get_user(user_id)
|
@@ -177,10 +190,6 @@ module MatrixSdk
|
|
177
190
|
raise MatrixUnexpectedResponseError, 'Upload succeeded, but no media URI returned'
|
178
191
|
end
|
179
192
|
|
180
|
-
def listen_for_events(timeout: 30, **arguments)
|
181
|
-
sync(arguments.merge(timeout: timeout))
|
182
|
-
end
|
183
|
-
|
184
193
|
def start_listener_thread(params = {})
|
185
194
|
@should_listen = true
|
186
195
|
thread = Thread.new { listen_forever(params) }
|
@@ -196,19 +205,44 @@ module MatrixSdk
|
|
196
205
|
@sync_thread = nil
|
197
206
|
end
|
198
207
|
|
208
|
+
def sync(skip_store_batch: false, **params)
|
209
|
+
extra_params = {
|
210
|
+
filter: sync_filter,
|
211
|
+
timeout: 30
|
212
|
+
}
|
213
|
+
extra_params[:since] = @next_batch unless @next_batch.nil?
|
214
|
+
extra_params.merge!(params)
|
215
|
+
extra_params[:filter] = extra_params[:filter].to_json unless extra_params[:filter].is_a? String
|
216
|
+
|
217
|
+
attempts = 0
|
218
|
+
data = loop do
|
219
|
+
begin
|
220
|
+
break api.sync extra_params
|
221
|
+
rescue MatrixSdk::MatrixTimeoutError => e
|
222
|
+
raise e if (attempts += 1) >= params.fetch(:allow_sync_retry, 0)
|
223
|
+
end
|
224
|
+
end
|
225
|
+
|
226
|
+
@next_batch = data[:next_batch] unless skip_store_batch
|
227
|
+
|
228
|
+
handle_sync_response(data)
|
229
|
+
end
|
230
|
+
|
231
|
+
alias listen_for_events sync
|
232
|
+
|
199
233
|
private
|
200
234
|
|
201
235
|
def listen_forever(timeout: 30, bad_sync_timeout: 5, sync_interval: 30, **params)
|
202
|
-
orig_bad_sync_timeout = bad_sync_timeout
|
236
|
+
orig_bad_sync_timeout = bad_sync_timeout + 0
|
203
237
|
while @should_listen
|
204
238
|
begin
|
205
239
|
sync(params.merge(timeout: timeout))
|
206
240
|
|
207
241
|
bad_sync_timeout = orig_bad_sync_timeout
|
208
242
|
sleep(sync_interval) if sync_interval > 0
|
209
|
-
rescue MatrixRequestError =>
|
210
|
-
logger.warn("A #{
|
211
|
-
if
|
243
|
+
rescue MatrixRequestError => e
|
244
|
+
logger.warn("A #{e.class} occurred during sync")
|
245
|
+
if e.httpstatus >= 500
|
212
246
|
logger.warn("Serverside error, retrying in #{bad_sync_timeout} seconds...")
|
213
247
|
sleep params[:bad_sync_timeout]
|
214
248
|
bad_sync_timeout = [bad_sync_timeout * 2, @bad_sync_timeout_limit].min
|
@@ -227,7 +261,11 @@ module MatrixSdk
|
|
227
261
|
|
228
262
|
def ensure_room(room_id)
|
229
263
|
room_id = room_id.to_s unless room_id.is_a? String
|
230
|
-
@rooms.fetch(room_id)
|
264
|
+
@rooms.fetch(room_id) do
|
265
|
+
room = Room.new(self, room_id)
|
266
|
+
@rooms[room_id] = room unless cache == :none
|
267
|
+
room
|
268
|
+
end
|
231
269
|
end
|
232
270
|
|
233
271
|
def handle_state(room_id, state_event)
|
@@ -240,6 +278,8 @@ module MatrixSdk
|
|
240
278
|
room.instance_variable_set '@name', content[:name]
|
241
279
|
when 'm.room.canonical_alias'
|
242
280
|
room.instance_variable_set '@canonical_alias', content[:alias]
|
281
|
+
# Also add as a regular alias
|
282
|
+
room.instance_variable_get('@aliases').concat [content[:alias]]
|
243
283
|
when 'm.room.topic'
|
244
284
|
room.instance_variable_set '@topic', content[:topic]
|
245
285
|
when 'm.room.aliases'
|
@@ -252,63 +292,48 @@ module MatrixSdk
|
|
252
292
|
return unless cache == :all
|
253
293
|
|
254
294
|
if content[:membership] == 'join'
|
255
|
-
room.send
|
295
|
+
room.send(:ensure_member, get_user(state_event[:state_key]).dup.tap do |u|
|
296
|
+
u.instance_variable_set :@display_name, content[:displayname]
|
297
|
+
end)
|
256
298
|
elsif %w[leave kick invite].include? content[:membership]
|
257
299
|
room.members.delete_if { |m| m.id == state_event[:state_key] }
|
258
300
|
end
|
259
301
|
end
|
260
302
|
end
|
261
303
|
|
262
|
-
def sync(skip_store_batch: false, **params)
|
263
|
-
extra_params = {
|
264
|
-
filter: sync_filter.to_json
|
265
|
-
}
|
266
|
-
extra_params[:since] = @next_batch unless @next_batch.nil?
|
267
|
-
|
268
|
-
attempts = 0
|
269
|
-
data = loop do
|
270
|
-
begin
|
271
|
-
break api.sync extra_params.merge(params)
|
272
|
-
rescue MatrixTimeoutError => ex
|
273
|
-
raise ex if (attempts += 1) > params.fetch(:allow_sync_retry, 0)
|
274
|
-
end
|
275
|
-
end
|
276
|
-
|
277
|
-
@next_batch = data[:next_batch] unless skip_store_batch
|
278
|
-
|
279
|
-
handle_sync_response(data)
|
280
|
-
end
|
281
|
-
|
282
304
|
def handle_sync_response(data)
|
283
305
|
data[:presence][:events].each do |presence_update|
|
284
306
|
fire_presence_event(MatrixEvent.new(self, presence_update))
|
285
307
|
end
|
286
308
|
|
287
309
|
data[:rooms][:invite].each do |room_id, invite|
|
288
|
-
fire_invite_event(MatrixEvent.new(self, invite), room_id)
|
310
|
+
fire_invite_event(MatrixEvent.new(self, invite), room_id.to_s)
|
289
311
|
end
|
290
312
|
|
291
313
|
data[:rooms][:leave].each do |room_id, left|
|
292
|
-
fire_leave_event(MatrixEvent.new(self, left), room_id)
|
314
|
+
fire_leave_event(MatrixEvent.new(self, left), room_id.to_s)
|
293
315
|
end
|
294
316
|
|
295
317
|
data[:rooms][:join].each do |room_id, join|
|
296
318
|
room = ensure_room(room_id)
|
297
319
|
room.instance_variable_set '@prev_batch', join[:timeline][:prev_batch]
|
320
|
+
room.instance_variable_set :@members_loaded, true unless sync_filter.fetch(:room, {}).fetch(:state, {}).fetch(:lazy_load_members, false)
|
321
|
+
|
298
322
|
join[:state][:events].each do |event|
|
299
|
-
event[:room_id] = room_id
|
323
|
+
event[:room_id] = room_id.to_s
|
300
324
|
handle_state(room_id, event)
|
301
325
|
end
|
302
326
|
|
303
327
|
join[:timeline][:events].each do |event|
|
304
|
-
event[:room_id] = room_id
|
328
|
+
event[:room_id] = room_id.to_s
|
329
|
+
handle_state(room_id, event) unless event[:type] == 'm.room.message'
|
305
330
|
room.send :put_event, event
|
306
331
|
|
307
332
|
fire_event(MatrixEvent.new(self, event), event[:type])
|
308
333
|
end
|
309
334
|
|
310
335
|
join[:ephemeral][:events].each do |event|
|
311
|
-
event[:room_id] = room_id
|
336
|
+
event[:room_id] = room_id.to_s
|
312
337
|
room.send :put_ephemeral_event, event
|
313
338
|
|
314
339
|
fire_ephemeral_event(MatrixEvent.new(self, event), event[:type])
|
@@ -10,6 +10,14 @@ module URI
|
|
10
10
|
@@schemes['MXC'] = MATRIX
|
11
11
|
end
|
12
12
|
|
13
|
+
unless Object.respond_to? :yield_self
|
14
|
+
class Object
|
15
|
+
def yield_self
|
16
|
+
yield(self)
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
13
21
|
def events(*symbols)
|
14
22
|
module_name = "#{name}Events"
|
15
23
|
|
@@ -52,15 +60,23 @@ end
|
|
52
60
|
def ignore_inspect(*symbols)
|
53
61
|
class_eval %*
|
54
62
|
def inspect
|
63
|
+
reentrant = caller_locations.any? { |l| l.absolute_path == __FILE__ && l.label == 'inspect' }
|
55
64
|
"\#{to_s[0..-2]} \#{instance_variables
|
56
65
|
.reject { |f| %i[#{symbols.map { |s| "@#{s}" }.join ' '}].include? f }
|
57
|
-
.map { |f| "\#{f}=\#{instance_variable_get(f).inspect}" }.join " " }}>"
|
66
|
+
.map { |f| "\#{f}=\#{reentrant ? instance_variable_get(f) : instance_variable_get(f).inspect}" }.join " " }}>"
|
58
67
|
end
|
59
|
-
*, __FILE__, __LINE__ -
|
68
|
+
*, __FILE__, __LINE__ - 7
|
60
69
|
end
|
61
70
|
|
62
71
|
module MatrixSdk
|
72
|
+
module Logging
|
73
|
+
def logger
|
74
|
+
@logger ||= ::Logging.logger[self]
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
63
78
|
class EventHandlerArray < Hash
|
79
|
+
include MatrixSdk::Logging
|
64
80
|
attr_accessor :reraise_exceptions
|
65
81
|
|
66
82
|
def initialize(*args)
|
@@ -82,17 +98,13 @@ module MatrixSdk
|
|
82
98
|
reverse_each do |_k, h|
|
83
99
|
begin
|
84
100
|
h[:block].call(event) if event.matches?(h[:filter], filter)
|
85
|
-
rescue StandardError =>
|
86
|
-
logger.error "#{
|
101
|
+
rescue StandardError => e
|
102
|
+
logger.error "#{e.class.name} occurred when firing event (#{event})\n#{e}"
|
87
103
|
|
88
|
-
raise
|
104
|
+
raise e if @reraise_exceptions
|
89
105
|
end
|
90
106
|
end
|
91
107
|
end
|
92
|
-
|
93
|
-
def logger
|
94
|
-
@logger ||= Logging.logger[self]
|
95
|
-
end
|
96
108
|
end
|
97
109
|
|
98
110
|
class Event
|
@@ -150,7 +162,7 @@ module MatrixSdk
|
|
150
162
|
super
|
151
163
|
end
|
152
164
|
|
153
|
-
def respond_to_missing?(method)
|
165
|
+
def respond_to_missing?(method, *)
|
154
166
|
event.key? method
|
155
167
|
end
|
156
168
|
end
|