@@ -89,6 +89,9 @@ def initialize(tag_prefix = nil, *args)
89
89
end
90
90
@packer = @factory . packer
91
91
92
+ @require_ack_response = options [ :require_ack_response ]
93
+ @ack_response_timeout = options [ :ack_response_timeout ] || 190
94
+
92
95
@mon = Monitor . new
93
96
@pending = nil
94
97
@connect_error_history = [ ]
@@ -143,7 +146,7 @@ def close
143
146
if @pending
144
147
begin
145
148
@pending . each do |tag , record |
146
- send_data ( [ tag , record ] . to_msgpack )
149
+ send_data ( tag , record )
147
150
end
148
151
rescue => e
149
152
set_last_error ( e )
@@ -231,7 +234,7 @@ def write(tag, time, map)
231
234
232
235
begin
233
236
@pending . each do |tag , record |
234
- send_data ( [ tag , record ] . to_msgpack )
237
+ send_data ( tag , record )
235
238
end
236
239
@pending = nil
237
240
true
@@ -249,11 +252,17 @@ def write(tag, time, map)
249
252
}
250
253
end
251
254
252
- def send_data ( data )
255
+ def send_data ( tag , record )
253
256
unless connect?
254
257
connect!
255
258
end
256
- @con . write data
259
+ if @require_ack_response
260
+ option = { }
261
+ option [ 'chunk' ] = generate_chunk
262
+ @con . write [ tag , record , option ] . to_msgpack
263
+ else
264
+ @con . write [ tag , record ] . to_msgpack
265
+ end
257
266
#while true
258
267
# puts "sending #{data.length} bytes"
259
268
# if data.length > 32*1024
@@ -268,6 +277,21 @@ def send_data(data)
268
277
# data = data[n..-1]
269
278
#end
270
279
280
+ if @require_ack_response && @ack_response_timeout > 0
281
+ if IO . select ( [ @con ] , nil , nil , @ack_response_timeout )
282
+ raw_data = @con . recv ( 1024 )
283
+
284
+ if raw_data . empty?
285
+ raise "Closed connection"
286
+ else
287
+ response = MessagePack . unpack ( raw_data )
288
+ if response [ 'ack' ] != option [ 'chunk' ]
289
+ raise "ack in response and chunk id in sent data are different"
290
+ end
291
+ end
292
+ end
293
+ end
294
+
271
295
true
272
296
end
273
297
@@ -306,6 +330,10 @@ def set_last_error(e)
306
330
# TODO: Check non GVL env
307
331
@last_error [ Thread . current . object_id ] = e
308
332
end
333
+
334
+ def generate_chunk
335
+ Base64 . encode64 ( ( [ SecureRandom . random_number ( 1 << 32 ) ] * 4 ) . pack ( 'NNNN' ) ) . chomp
336
+ end
309
337
end
310
338
end
311
339
end
0 commit comments