48
48
fmt:: Debug ,
49
49
net:: SocketAddr ,
50
50
sync:: Arc ,
51
+ time:: Duration ,
51
52
} ,
52
53
tokio:: sync:: mpsc,
53
54
tracing:: instrument,
@@ -115,6 +116,7 @@ async fn handle_connection<S>(
115
116
state : Arc < S > ,
116
117
notify_price_tx_buffer : usize ,
117
118
notify_price_sched_tx_buffer : usize ,
119
+ flush_interval_duration : Duration ,
118
120
) where
119
121
S : state:: Prices ,
120
122
S : Send ,
@@ -127,6 +129,8 @@ async fn handle_connection<S>(
127
129
let ( mut notify_price_sched_tx, mut notify_price_sched_rx) =
128
130
mpsc:: channel ( notify_price_sched_tx_buffer) ;
129
131
132
+ let mut flush_interval = tokio:: time:: interval ( flush_interval_duration) ;
133
+
130
134
loop {
131
135
if let Err ( err) = handle_next (
132
136
& * state,
@@ -136,6 +140,7 @@ async fn handle_connection<S>(
136
140
& mut notify_price_rx,
137
141
& mut notify_price_sched_tx,
138
142
& mut notify_price_sched_rx,
143
+ & mut flush_interval,
139
144
)
140
145
. await
141
146
{
@@ -159,6 +164,7 @@ async fn handle_next<S>(
159
164
notify_price_rx : & mut mpsc:: Receiver < NotifyPrice > ,
160
165
notify_price_sched_tx : & mut mpsc:: Sender < NotifyPriceSched > ,
161
166
notify_price_sched_rx : & mut mpsc:: Receiver < NotifyPriceSched > ,
167
+ flush_interval : & mut tokio:: time:: Interval ,
162
168
) -> Result < ( ) >
163
169
where
164
170
S : state:: Prices ,
@@ -183,13 +189,16 @@ where
183
189
}
184
190
}
185
191
Some ( notify_price) = notify_price_rx. recv( ) => {
186
- send_notification ( ws_tx, Method :: NotifyPrice , Some ( notify_price) )
192
+ feed_notification ( ws_tx, Method :: NotifyPrice , Some ( notify_price) )
187
193
. await
188
194
}
189
195
Some ( notify_price_sched) = notify_price_sched_rx. recv( ) => {
190
- send_notification ( ws_tx, Method :: NotifyPriceSched , Some ( notify_price_sched) )
196
+ feed_notification ( ws_tx, Method :: NotifyPriceSched , Some ( notify_price_sched) )
191
197
. await
192
198
}
199
+ _ = flush_interval. tick( ) => {
200
+ flush( ws_tx) . await
201
+ }
193
202
}
194
203
}
195
204
@@ -229,9 +238,9 @@ where
229
238
// Send an array if we're handling a batch
230
239
// request, single response object otherwise
231
240
if is_batch {
232
- send_text ( ws_tx, & serde_json:: to_string ( & responses) ?) . await ?;
241
+ feed_text ( ws_tx, & serde_json:: to_string ( & responses) ?) . await ?;
233
242
} else {
234
- send_text ( ws_tx, & serde_json:: to_string ( & responses[ 0 ] ) ?) . await ?;
243
+ feed_text ( ws_tx, & serde_json:: to_string ( & responses[ 0 ] ) ?) . await ?;
235
244
}
236
245
}
237
246
// The top-level parsing errors are fine to share with client
@@ -354,21 +363,21 @@ async fn send_error(
354
363
error. to_string ( ) ,
355
364
None ,
356
365
) ;
357
- send_text ( ws_tx, & response. to_string ( ) ) . await
366
+ feed_text ( ws_tx, & response. to_string ( ) ) . await
358
367
}
359
368
360
- async fn send_notification < T > (
369
+ async fn feed_notification < T > (
361
370
ws_tx : & mut SplitSink < WebSocket , Message > ,
362
371
method : Method ,
363
372
params : Option < T > ,
364
373
) -> Result < ( ) >
365
374
where
366
375
T : Sized + Serialize + DeserializeOwned ,
367
376
{
368
- send_request ( ws_tx, IdReq :: Notification , method, params) . await
377
+ feed_request ( ws_tx, IdReq :: Notification , method, params) . await
369
378
}
370
379
371
- async fn send_request < I , T > (
380
+ async fn feed_request < I , T > (
372
381
ws_tx : & mut SplitSink < WebSocket , Message > ,
373
382
id : I ,
374
383
method : Method ,
@@ -379,16 +388,20 @@ where
379
388
T : Sized + Serialize + DeserializeOwned ,
380
389
{
381
390
let request = Request :: with_params ( id, method, params) ;
382
- send_text ( ws_tx, & request. to_string ( ) ) . await
391
+ feed_text ( ws_tx, & request. to_string ( ) ) . await
383
392
}
384
393
385
- async fn send_text ( ws_tx : & mut SplitSink < WebSocket , Message > , msg : & str ) -> Result < ( ) > {
394
+ async fn feed_text ( ws_tx : & mut SplitSink < WebSocket , Message > , msg : & str ) -> Result < ( ) > {
386
395
ws_tx
387
- . send ( Message :: text ( msg. to_string ( ) ) )
396
+ . feed ( Message :: text ( msg. to_string ( ) ) )
388
397
. await
389
398
. map_err ( |e| e. into ( ) )
390
399
}
391
400
401
+ async fn flush ( ws_tx : & mut SplitSink < WebSocket , Message > ) -> Result < ( ) > {
402
+ ws_tx. flush ( ) . await . map_err ( |e| e. into ( ) )
403
+ }
404
+
392
405
#[ derive( Clone , Debug , Serialize , Deserialize ) ]
393
406
#[ serde( default ) ]
394
407
pub struct Config {
@@ -400,6 +413,9 @@ pub struct Config {
400
413
/// Size of the buffer of each Server's channel on which `notify_price_sched` events are
401
414
/// received from the Price state.
402
415
pub notify_price_sched_tx_buffer : usize ,
416
+ /// Flush interval duration for the notifications.
417
+ #[ serde( with = "humantime_serde" ) ]
418
+ pub flush_interval_duration : Duration ,
403
419
}
404
420
405
421
impl Default for Config {
@@ -408,6 +424,7 @@ impl Default for Config {
408
424
listen_address : "127.0.0.1:8910" . to_string ( ) ,
409
425
notify_price_tx_buffer : 10000 ,
410
426
notify_price_sched_tx_buffer : 10000 ,
427
+ flush_interval_duration : Duration :: from_millis ( 50 ) ,
411
428
}
412
429
}
413
430
}
@@ -448,6 +465,7 @@ where
448
465
state,
449
466
config. notify_price_tx_buffer ,
450
467
config. notify_price_sched_tx_buffer ,
468
+ config. flush_interval_duration ,
451
469
)
452
470
. await
453
471
} )
0 commit comments