riemann-client 1.0.1 → 1.1.0

Sign up to get free protection for your applications and to get access to all the features.
data/spec/client.rb DELETED
@@ -1,384 +0,0 @@
1
- #!/usr/bin/env ruby
2
- # frozen_string_literal: true
3
-
4
- # How to run the bacon tests:
5
- # 1. Start Riemann using the config from riemann.config
6
- # 2. $ bundle exec bacon spec/client.rb
7
-
8
- require File.expand_path(File.join(File.dirname(__FILE__), '..', 'lib', 'riemann'))
9
- require 'riemann/client'
10
- require 'bacon'
11
- require 'set'
12
- require 'timecop'
13
-
14
- Bacon.summary_on_exit
15
-
16
- include Riemann # rubocop:disable Style/MixinUsage
17
-
18
- INACTIVITY_TIME = 5
19
-
20
- def wait_for(&block)
21
- tries = 0
22
- while tries < 30
23
- tries += 1
24
- begin
25
- res = block.call
26
- return res if res
27
- rescue NoMethodError
28
- # If a query returns no result (#query retruns nil or #[] returns []),
29
- # calling #first on it will raise a NoMethodError. We can ignore it for
30
- # these tests.
31
- end
32
- sleep(0.1)
33
- end
34
-
35
- raise 'wait_for condition never realized'
36
- end
37
-
38
- def roundtrip_metric(metric)
39
- @client_with_transport << {
40
- service: 'metric-test',
41
- metric: metric
42
- }
43
-
44
- wait_for { @client["service = \"metric-test\" and metric = #{metric}"].first }
45
- .metric.should.equal metric
46
- end
47
-
48
- def truthy
49
- ->(obj) { !(obj.nil? || obj == false) }
50
- end
51
-
52
- def falsey
53
- ->(obj) { obj.nil? || obj == false }
54
- end
55
-
56
- shared 'a riemann client' do
57
- should 'yield itself to given block' do
58
- client = nil
59
- Client.new(host: 'localhost', port: 5555) do |c|
60
- client = c
61
- end
62
- client.should.be.is_a?(Client)
63
- client.should.not.be.connected
64
- end
65
-
66
- should 'close sockets if given a block that raises' do
67
- client = nil
68
- begin
69
- Client.new(host: 'localhost', port: 5555) do |c|
70
- client = c
71
- raise 'The Boom'
72
- end
73
- rescue StandardError
74
- # swallow the exception
75
- end
76
- client.should.be.is_a?(Client)
77
- client.should.not.be.connected
78
- end
79
-
80
- should 'be connected after sending' do
81
- @client_with_transport.connected?.should.be falsey
82
- @client.connected?.should.be falsey
83
- @client_with_transport << { state: 'ok', service: 'connected check' }
84
- @client_with_transport.connected?.should.be truthy
85
- # NOTE: only single transport connected at this point, @client.connected? is still false until all transports used
86
- end
87
-
88
- should 'send longs' do
89
- roundtrip_metric(0)
90
- roundtrip_metric(-3)
91
- roundtrip_metric(5)
92
- roundtrip_metric(-(2**63))
93
- roundtrip_metric(2**63 - 1)
94
- end
95
-
96
- should 'send doubles' do
97
- roundtrip_metric 0.0
98
- roundtrip_metric 12.0
99
- roundtrip_metric 1.2300000190734863
100
- end
101
-
102
- should 'send custom attributes' do
103
- event = Event.new(
104
- service: 'custom',
105
- state: 'ok',
106
- cats: 'meow',
107
- env: 'prod'
108
- )
109
- event[:sneak] = 'attack'
110
- @client_with_transport << event
111
- event2 = wait_for { @client['service = "custom"'].first }
112
- event2.service.should.equal 'custom'
113
- event2.state.should.equal 'ok'
114
- event2[:cats].should.equal 'meow'
115
- event2[:env].should.equal 'prod'
116
- event2[:sneak].should.equal 'attack'
117
- end
118
-
119
- should 'send a state with a time' do
120
- Timecop.freeze do
121
- t = (Time.now - 10).to_i
122
- @client_with_transport << {
123
- state: 'ok',
124
- service: 'test',
125
- time: t
126
- }
127
- wait_for { @client.query('service = "test"').events.first.time == t }
128
- e = @client.query('service = "test"').events.first
129
- e.time.should.equal t
130
- e.time_micros.should.equal t * 1_000_000
131
- end
132
- end
133
-
134
- should 'send a state with a time_micros' do
135
- Timecop.freeze do
136
- t = ((Time.now - 10).to_f * 1_000_000).to_i
137
- @client_with_transport << {
138
- state: 'ok',
139
- service: 'test',
140
- time_micros: t
141
- }
142
- wait_for { @client.query('service = "test"').events.first.time_micros == t }
143
- e = @client.query('service = "test"').events.first
144
- e.time.should.equal (Time.now - 10).to_i
145
- e.time_micros.should.equal t
146
- end
147
- end
148
-
149
- should 'send a state without time nor time_micros' do
150
- time_before = (Time.now.to_f * 1_000_000).to_i
151
- @client_with_transport << {
152
- state: 'ok',
153
- service: 'timeless test'
154
- }
155
- wait_for { @client.query('service = "timeless test"').events.first.time_micros >= time_before }
156
- e = @client.query('service = "timeless test"').events.first
157
- time_after = (Time.now.to_f * 1_000_000).to_i
158
-
159
- [time_before, e.time_micros, time_after].sort.should.equal([time_before, e.time_micros, time_after])
160
- end
161
-
162
- should 'query states' do
163
- @client_with_transport << { state: 'critical', service: '1' }
164
- @client_with_transport << { state: 'warning', service: '2' }
165
- @client_with_transport << { state: 'critical', service: '3' }
166
- wait_for { @client.query('service = "3"').events.first }
167
- @client.query.events
168
- .map(&:service).to_set.should.superset %w[1 2 3].to_set
169
- @client.query('state = "critical" and (service = "1" or service = "2" or service = "3")').events
170
- .map(&:service).to_set.should.equal %w[1 3].to_set
171
- end
172
-
173
- it '[]' do
174
- # @client['state = "critical"'].should == []
175
- @client_with_transport << { state: 'critical' }
176
- wait_for { @client['state = "critical"'].first }.state.should.equal 'critical'
177
- end
178
-
179
- should 'query quickly' do
180
- t1 = Time.now
181
- total = 1000
182
- total.times do |_i|
183
- @client.query('state = "critical"')
184
- end
185
- t2 = Time.now
186
-
187
- rate = total / (t2 - t1)
188
- puts "\n #{format('%.2f', rate)} queries/sec (#{format('%.2f', (1000 / rate))}ms per query)"
189
- rate.should > 100
190
- end
191
-
192
- should 'be threadsafe' do
193
- concurrency = 10
194
- per_thread = 200
195
- total = concurrency * per_thread
196
-
197
- t1 = Time.now
198
- (0...concurrency).map do |_i|
199
- Thread.new do
200
- per_thread.times do
201
- @client_with_transport.<<({
202
- state: 'ok',
203
- service: 'test',
204
- description: 'desc',
205
- metric_f: 1.0
206
- })
207
- end
208
- end
209
- end.each(&:join)
210
- t2 = Time.now
211
-
212
- rate = total / (t2 - t1)
213
- puts "\n #{format('%.2f', rate)} inserts/sec (#{format('%.2f', (1000 / rate))}ms per insert)"
214
- rate.should > @expected_rate
215
- end
216
- end
217
-
218
- describe 'Riemann::Client (TLS transport)' do
219
- before do
220
- @client = Client.new(host: 'localhost', port: 5554, ssl: true,
221
- key_file: '/etc/riemann/riemann_server.pkcs8',
222
- cert_file: '/etc/riemann/riemann_server.crt',
223
- ca_file: '/etc/riemann/riemann_server.crt',
224
- ssl_verify: true)
225
- @client_with_transport = @client.tcp
226
- @expected_rate = 100
227
- end
228
- behaves_like 'a riemann client'
229
-
230
- should 'send a state' do
231
- res = @client_with_transport << {
232
- state: 'ok',
233
- service: 'test',
234
- description: 'desc',
235
- metric_f: 1.0
236
- }
237
-
238
- res.ok.should.be truthy
239
- wait_for { @client['service = "test"'].first }.state.should.equal 'ok'
240
- end
241
-
242
- should 'survive inactivity' do
243
- @client_with_transport.<<({
244
- state: 'warning',
245
- service: 'survive TCP inactivity'
246
- })
247
- wait_for { @client['service = "survive TCP inactivity"'].first.state == 'warning' }
248
-
249
- sleep INACTIVITY_TIME
250
-
251
- @client_with_transport.<<({
252
- state: 'ok',
253
- service: 'survive TCP inactivity'
254
- }).ok.should.be truthy
255
- wait_for { @client['service = "survive TCP inactivity"'].first.state == 'ok' }
256
- end
257
-
258
- should 'survive local close' do
259
- @client_with_transport.<<({
260
- state: 'warning',
261
- service: 'survive TCP local close'
262
- }).ok.should.be truthy
263
- wait_for { @client['service = "survive TCP local close"'].first.state == 'warning' }
264
-
265
- @client.close
266
-
267
- @client_with_transport.<<({
268
- state: 'ok',
269
- service: 'survive TCP local close'
270
- }).ok.should.be truthy
271
- wait_for { @client['service = "survive TCP local close"'].first.state == 'ok' }
272
- end
273
- end
274
-
275
- describe 'Riemann::Client (TCP transport)' do
276
- before do
277
- @client = Client.new(host: 'localhost', port: 5555)
278
- @client_with_transport = @client.tcp
279
- @expected_rate = 100
280
- end
281
- behaves_like 'a riemann client'
282
-
283
- should 'send a state' do
284
- res = @client_with_transport << {
285
- state: 'ok',
286
- service: 'test',
287
- description: 'desc',
288
- metric_f: 1.0
289
- }
290
-
291
- res.ok.should.be truthy
292
- wait_for { @client['service = "test"'].first }.state.should.equal 'ok'
293
- end
294
-
295
- should 'survive inactivity' do
296
- @client_with_transport.<<({
297
- state: 'warning',
298
- service: 'survive TCP inactivity'
299
- })
300
- wait_for { @client['service = "survive TCP inactivity"'].first.state == 'warning' }
301
-
302
- sleep INACTIVITY_TIME
303
-
304
- @client_with_transport.<<({
305
- state: 'ok',
306
- service: 'survive TCP inactivity'
307
- }).ok.should.be truthy
308
- wait_for { @client['service = "survive TCP inactivity"'].first.state == 'ok' }
309
- end
310
-
311
- should 'survive local close' do
312
- @client_with_transport.<<({
313
- state: 'warning',
314
- service: 'survive TCP local close'
315
- }).ok.should.be truthy
316
- wait_for { @client['service = "survive TCP local close"'].first.state == 'warning' }
317
-
318
- @client.close
319
-
320
- @client_with_transport.<<({
321
- state: 'ok',
322
- service: 'survive TCP local close'
323
- }).ok.should.be truthy
324
- wait_for { @client['service = "survive TCP local close"'].first.state == 'ok' }
325
- end
326
- end
327
-
328
- describe 'Riemann::Client (UDP transport)' do
329
- before do
330
- @client = Client.new(host: 'localhost', port: 5555)
331
- @client_with_transport = @client.udp
332
- @expected_rate = 1000
333
- end
334
- behaves_like 'a riemann client'
335
-
336
- should 'send a state' do
337
- res = @client_with_transport << {
338
- state: 'ok',
339
- service: 'test',
340
- description: 'desc',
341
- metric_f: 1.0
342
- }
343
-
344
- res.should.be.nil
345
- wait_for { @client['service = "test"'].first }.state.should.equal 'ok'
346
- end
347
-
348
- should 'survive inactivity' do
349
- @client_with_transport.<<({
350
- state: 'warning',
351
- service: 'survive UDP inactivity'
352
- }).should.be.nil
353
- wait_for { @client['service = "survive UDP inactivity"'].first.state == 'warning' }
354
-
355
- sleep INACTIVITY_TIME
356
-
357
- @client_with_transport.<<({
358
- state: 'ok',
359
- service: 'survive UDP inactivity'
360
- }).should.be.nil
361
- wait_for { @client['service = "survive UDP inactivity"'].first.state == 'ok' }
362
- end
363
-
364
- should 'survive local close' do
365
- @client_with_transport.<<({
366
- state: 'warning',
367
- service: 'survive UDP local close'
368
- }).should.be.nil
369
- wait_for { @client['service = "survive UDP local close"'].first.state == 'warning' }
370
-
371
- @client.close
372
-
373
- @client_with_transport.<<({
374
- state: 'ok',
375
- service: 'survive UDP local close'
376
- }).should.be.nil
377
- wait_for { @client['service = "survive UDP local close"'].first.state == 'ok' }
378
- end
379
-
380
- should 'raise Riemann::Client::Unsupported exception on query' do
381
- should.raise(Riemann::Client::Unsupported) { @client_with_transport['service = "test"'] }
382
- should.raise(Riemann::Client::Unsupported) { @client_with_transport.query('service = "test"') }
383
- end
384
- end