1use std::{
19 fmt::Display,
20 hash::{Hash, Hasher},
21 ops::{Deref, DerefMut},
22};
23
24use nautilus_core::{
25 UnixNanos,
26 correctness::{FAILED, check_predicate_true},
27};
28use serde::{Deserialize, Serialize};
29
30use super::{HasTsInit, OrderBookDelta};
31use crate::identifiers::InstrumentId;
32
33#[derive(Clone, Debug, Serialize, Deserialize)]
37#[cfg_attr(
38 feature = "python",
39 pyo3::pyclass(module = "nautilus_trader.core.nautilus_pyo3.model", from_py_object)
40)]
41pub struct OrderBookDeltas {
42 pub instrument_id: InstrumentId,
44 pub deltas: Vec<OrderBookDelta>,
46 pub flags: u8,
48 pub sequence: u64,
50 pub ts_event: UnixNanos,
52 pub ts_init: UnixNanos,
54}
55
56impl OrderBookDeltas {
57 #[must_use]
63 #[allow(clippy::too_many_arguments)]
64 pub fn new(instrument_id: InstrumentId, deltas: Vec<OrderBookDelta>) -> Self {
65 Self::new_checked(instrument_id, deltas).expect(FAILED)
66 }
67
68 #[allow(clippy::too_many_arguments)]
74 #[allow(clippy::missing_panics_doc)] pub fn new_checked(
81 instrument_id: InstrumentId,
82 deltas: Vec<OrderBookDelta>,
83 ) -> anyhow::Result<Self> {
84 check_predicate_true(!deltas.is_empty(), "`deltas` cannot be empty")?;
85 let last = deltas.last().expect("deltas not empty");
86 let flags = last.flags;
87 let sequence = last.sequence;
88 let ts_event = last.ts_event;
89 let ts_init = last.ts_init;
90 Ok(Self {
91 instrument_id,
92 deltas,
93 flags,
94 sequence,
95 ts_event,
96 ts_init,
97 })
98 }
99}
100
101impl PartialEq<Self> for OrderBookDeltas {
102 fn eq(&self, other: &Self) -> bool {
103 self.instrument_id == other.instrument_id && self.sequence == other.sequence
104 }
105}
106
107impl Eq for OrderBookDeltas {}
108
109impl Hash for OrderBookDeltas {
110 fn hash<H: Hasher>(&self, state: &mut H) {
111 self.instrument_id.hash(state);
112 self.sequence.hash(state);
113 }
114}
115
116impl Display for OrderBookDeltas {
121 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
122 write!(
123 f,
124 "{},len={},flags={},sequence={},ts_event={},ts_init={}",
125 self.instrument_id,
126 self.deltas.len(),
127 self.flags,
128 self.sequence,
129 self.ts_event,
130 self.ts_init
131 )
132 }
133}
134
135impl HasTsInit for OrderBookDeltas {
136 fn ts_init(&self) -> UnixNanos {
137 self.ts_init
138 }
139}
140
141#[repr(C)]
150#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
151#[allow(non_camel_case_types)]
152pub struct OrderBookDeltas_API(Box<OrderBookDeltas>);
153
154impl OrderBookDeltas_API {
156 #[must_use]
157 pub fn new(deltas: OrderBookDeltas) -> Self {
158 Self(Box::new(deltas))
159 }
160
161 #[must_use]
163 pub fn into_inner(self) -> OrderBookDeltas {
164 *self.0
165 }
166}
167
168impl Deref for OrderBookDeltas_API {
169 type Target = OrderBookDeltas;
170
171 fn deref(&self) -> &Self::Target {
172 &self.0
173 }
174}
175
176impl DerefMut for OrderBookDeltas_API {
177 fn deref_mut(&mut self) -> &mut Self::Target {
178 &mut self.0
179 }
180}
181
182#[cfg(test)]
183mod tests {
184 use std::{
185 collections::hash_map::DefaultHasher,
186 hash::{Hash, Hasher},
187 };
188
189 use rstest::rstest;
190 use serde_json;
191
192 use super::*;
193 use crate::{
194 data::{order::BookOrder, stubs::stub_deltas},
195 enums::{BookAction, OrderSide},
196 types::{Price, Quantity},
197 };
198
199 fn create_test_delta() -> OrderBookDelta {
200 let instrument_id = InstrumentId::from("EURUSD.SIM");
201 OrderBookDelta::new(
202 instrument_id,
203 BookAction::Add,
204 BookOrder::new(
205 OrderSide::Buy,
206 Price::from("1.0500"),
207 Quantity::from("100000"),
208 1,
209 ),
210 0,
211 123,
212 UnixNanos::from(1_000_000_000),
213 UnixNanos::from(2_000_000_000),
214 )
215 }
216
217 fn create_test_deltas() -> OrderBookDeltas {
218 let instrument_id = InstrumentId::from("EURUSD.SIM");
219 let flags = 32;
220 let sequence = 123;
221 let ts_event = UnixNanos::from(1_000_000_000);
222 let ts_init = UnixNanos::from(2_000_000_000);
223
224 let delta1 = OrderBookDelta::new(
225 instrument_id,
226 BookAction::Add,
227 BookOrder::new(
228 OrderSide::Sell,
229 Price::from("1.0520"),
230 Quantity::from("50000"),
231 1,
232 ),
233 flags,
234 sequence,
235 ts_event,
236 ts_init,
237 );
238 let delta2 = OrderBookDelta::new(
239 instrument_id,
240 BookAction::Add,
241 BookOrder::new(
242 OrderSide::Buy,
243 Price::from("1.0500"),
244 Quantity::from("75000"),
245 2,
246 ),
247 flags,
248 sequence,
249 ts_event,
250 ts_init,
251 );
252
253 OrderBookDeltas::new(instrument_id, vec![delta1, delta2])
254 }
255
256 fn create_test_deltas_multiple() -> OrderBookDeltas {
257 let instrument_id = InstrumentId::from("GBPUSD.SIM");
258 let flags = 16;
259 let sequence = 456;
260 let ts_event = UnixNanos::from(3_000_000_000);
261 let ts_init = UnixNanos::from(4_000_000_000);
262
263 let deltas = vec![
264 OrderBookDelta::clear(instrument_id, sequence, ts_event, ts_init),
265 OrderBookDelta::new(
266 instrument_id,
267 BookAction::Add,
268 BookOrder::new(
269 OrderSide::Sell,
270 Price::from("1.2550"),
271 Quantity::from("100000"),
272 1,
273 ),
274 flags,
275 sequence,
276 ts_event,
277 ts_init,
278 ),
279 OrderBookDelta::new(
280 instrument_id,
281 BookAction::Update,
282 BookOrder::new(
283 OrderSide::Buy,
284 Price::from("1.2530"),
285 Quantity::from("200000"),
286 2,
287 ),
288 flags,
289 sequence,
290 ts_event,
291 ts_init,
292 ),
293 OrderBookDelta::new(
294 instrument_id,
295 BookAction::Delete,
296 BookOrder::new(
297 OrderSide::Sell,
298 Price::from("1.2560"),
299 Quantity::from("0"),
300 3,
301 ),
302 flags,
303 sequence,
304 ts_event,
305 ts_init,
306 ),
307 ];
308
309 OrderBookDeltas::new(instrument_id, deltas)
310 }
311
312 #[rstest]
313 fn test_order_book_deltas_new() {
314 let deltas = create_test_deltas();
315
316 assert_eq!(deltas.instrument_id, InstrumentId::from("EURUSD.SIM"));
317 assert_eq!(deltas.deltas.len(), 2);
318 assert_eq!(deltas.flags, 32);
319 assert_eq!(deltas.sequence, 123);
320 assert_eq!(deltas.ts_event, UnixNanos::from(1_000_000_000));
321 assert_eq!(deltas.ts_init, UnixNanos::from(2_000_000_000));
322 }
323
324 #[rstest]
325 fn test_order_book_deltas_new_checked_valid() {
326 let instrument_id = InstrumentId::from("EURUSD.SIM");
327 let delta = create_test_delta();
328
329 let result = OrderBookDeltas::new_checked(instrument_id, vec![delta]);
330
331 assert!(result.is_ok());
332 let deltas = result.unwrap();
333 assert_eq!(deltas.instrument_id, instrument_id);
334 assert_eq!(deltas.deltas.len(), 1);
335 }
336
337 #[rstest]
338 fn test_order_book_deltas_new_checked_empty_deltas() {
339 let instrument_id = InstrumentId::from("EURUSD.SIM");
340
341 let result = OrderBookDeltas::new_checked(instrument_id, vec![]);
342
343 assert!(result.is_err());
344 assert!(
345 result
346 .unwrap_err()
347 .to_string()
348 .contains("`deltas` cannot be empty")
349 );
350 }
351
352 #[rstest]
353 #[should_panic(expected = "Condition failed")]
354 fn test_order_book_deltas_new_empty_deltas_panics() {
355 let instrument_id = InstrumentId::from("EURUSD.SIM");
356 let _ = OrderBookDeltas::new(instrument_id, vec![]);
357 }
358
359 #[rstest]
360 fn test_order_book_deltas_uses_last_delta_properties() {
361 let instrument_id = InstrumentId::from("EURUSD.SIM");
362
363 let delta1 = OrderBookDelta::new(
364 instrument_id,
365 BookAction::Add,
366 BookOrder::new(
367 OrderSide::Buy,
368 Price::from("1.0500"),
369 Quantity::from("100000"),
370 1,
371 ),
372 16, 100, UnixNanos::from(500_000_000), UnixNanos::from(1_000_000_000), );
377
378 let delta2 = OrderBookDelta::new(
379 instrument_id,
380 BookAction::Add,
381 BookOrder::new(
382 OrderSide::Sell,
383 Price::from("1.0520"),
384 Quantity::from("50000"),
385 2,
386 ),
387 32, 200, UnixNanos::from(1_500_000_000), UnixNanos::from(2_000_000_000), );
392
393 let deltas = OrderBookDeltas::new(instrument_id, vec![delta1, delta2]);
394
395 assert_eq!(deltas.flags, 32);
397 assert_eq!(deltas.sequence, 200);
398 assert_eq!(deltas.ts_event, UnixNanos::from(1_500_000_000));
399 assert_eq!(deltas.ts_init, UnixNanos::from(2_000_000_000));
400 }
401
402 #[rstest]
403 fn test_order_book_deltas_hash_different_objects() {
404 let deltas1 = create_test_deltas();
405 let deltas2 = create_test_deltas_multiple();
406
407 let mut hasher1 = DefaultHasher::new();
408 let mut hasher2 = DefaultHasher::new();
409
410 deltas1.hash(&mut hasher1);
411 deltas2.hash(&mut hasher2);
412
413 assert_ne!(hasher1.finish(), hasher2.finish()); }
415
416 #[rstest]
417 fn test_order_book_deltas_hash_uses_instrument_id_and_sequence() {
418 let instrument_id = InstrumentId::from("EURUSD.SIM");
419 let sequence = 123u64;
420
421 let mut expected_hasher = DefaultHasher::new();
423 instrument_id.hash(&mut expected_hasher);
424 sequence.hash(&mut expected_hasher);
425 let expected_hash = expected_hasher.finish();
426
427 let delta = OrderBookDelta::new(
428 instrument_id,
429 BookAction::Add,
430 BookOrder::new(
431 OrderSide::Buy,
432 Price::from("1.0500"),
433 Quantity::from("100000"),
434 1,
435 ),
436 0,
437 sequence,
438 UnixNanos::from(1_000_000_000),
439 UnixNanos::from(2_000_000_000),
440 );
441
442 let deltas = OrderBookDeltas::new(instrument_id, vec![delta]);
443
444 let mut deltas_hasher = DefaultHasher::new();
445 deltas.hash(&mut deltas_hasher);
446
447 assert_eq!(deltas_hasher.finish(), expected_hash);
448 }
449
450 #[rstest]
451 fn test_order_book_deltas_display() {
452 let deltas = create_test_deltas();
453 let display_str = format!("{deltas}");
454
455 assert!(display_str.contains("EURUSD.SIM"));
456 assert!(display_str.contains("len=2"));
457 assert!(display_str.contains("flags=32"));
458 assert!(display_str.contains("sequence=123"));
459 assert!(display_str.contains("ts_event=1000000000"));
460 assert!(display_str.contains("ts_init=2000000000"));
461 }
462
463 #[rstest]
464 fn test_order_book_deltas_display_format() {
465 let deltas = create_test_deltas();
466 let expected =
467 "EURUSD.SIM,len=2,flags=32,sequence=123,ts_event=1000000000,ts_init=2000000000";
468
469 assert_eq!(format!("{deltas}"), expected);
470 }
471
472 #[rstest]
473 fn test_order_book_deltas_has_ts_init() {
474 let deltas = create_test_deltas();
475
476 assert_eq!(deltas.ts_init(), UnixNanos::from(2_000_000_000));
477 }
478
479 #[rstest]
480 fn test_order_book_deltas_clone() {
481 let deltas1 = create_test_deltas();
482 let deltas2 = deltas1.clone();
483
484 assert_eq!(deltas1.instrument_id, deltas2.instrument_id);
485 assert_eq!(deltas1.deltas.len(), deltas2.deltas.len());
486 assert_eq!(deltas1.flags, deltas2.flags);
487 assert_eq!(deltas1.sequence, deltas2.sequence);
488 assert_eq!(deltas1.ts_event, deltas2.ts_event);
489 assert_eq!(deltas1.ts_init, deltas2.ts_init);
490 assert_eq!(deltas1, deltas2);
491 }
492
493 #[rstest]
494 fn test_order_book_deltas_debug() {
495 let deltas = create_test_deltas();
496 let debug_str = format!("{deltas:?}");
497
498 assert!(debug_str.contains("OrderBookDeltas"));
499 assert!(debug_str.contains("EURUSD.SIM"));
500 assert!(debug_str.contains("flags: 32"));
501 assert!(debug_str.contains("sequence: 123"));
502 }
503
504 #[rstest]
505 fn test_order_book_deltas_serialization() {
506 let deltas = create_test_deltas();
507
508 let json = serde_json::to_string(&deltas).unwrap();
510 let deserialized: OrderBookDeltas = serde_json::from_str(&json).unwrap();
511
512 assert_eq!(deltas.instrument_id, deserialized.instrument_id);
513 assert_eq!(deltas.deltas.len(), deserialized.deltas.len());
514 assert_eq!(deltas.flags, deserialized.flags);
515 assert_eq!(deltas.sequence, deserialized.sequence);
516 assert_eq!(deltas.ts_event, deserialized.ts_event);
517 assert_eq!(deltas.ts_init, deserialized.ts_init);
518 }
519
520 #[rstest]
521 fn test_order_book_deltas_single_delta() {
522 let instrument_id = InstrumentId::from("BTCUSD.CRYPTO");
523 let delta = create_test_delta();
524
525 let deltas = OrderBookDeltas::new(instrument_id, vec![delta]);
526
527 assert_eq!(deltas.instrument_id, instrument_id);
528 assert_eq!(deltas.deltas.len(), 1);
529 assert_eq!(deltas.flags, delta.flags);
530 assert_eq!(deltas.sequence, delta.sequence);
531 assert_eq!(deltas.ts_event, delta.ts_event);
532 assert_eq!(deltas.ts_init, delta.ts_init);
533 }
534
535 #[rstest]
536 fn test_order_book_deltas_large_number_of_deltas() {
537 let instrument_id = InstrumentId::from("ETHUSD.CRYPTO");
538 let mut delta_vec = Vec::new();
539
540 for i in 0..100 {
542 let delta = OrderBookDelta::new(
543 instrument_id,
544 BookAction::Add,
545 BookOrder::new(
546 OrderSide::Buy,
547 Price::from(&format!("1000.{i:02}")),
548 Quantity::from("1000"),
549 i as u64,
550 ),
551 0,
552 i as u64,
553 UnixNanos::from(1_000_000_000 + i as u64),
554 UnixNanos::from(2_000_000_000 + i as u64),
555 );
556 delta_vec.push(delta);
557 }
558
559 let deltas = OrderBookDeltas::new(instrument_id, delta_vec);
560
561 assert_eq!(deltas.deltas.len(), 100);
562 assert_eq!(deltas.sequence, 99); assert_eq!(deltas.ts_event, UnixNanos::from(1_000_000_000 + 99));
564 assert_eq!(deltas.ts_init, UnixNanos::from(2_000_000_000 + 99));
565 }
566
567 #[rstest]
568 fn test_order_book_deltas_different_action_types() {
569 let deltas = create_test_deltas_multiple();
570
571 assert_eq!(deltas.deltas.len(), 4);
572
573 assert_eq!(deltas.deltas[0].action, BookAction::Clear);
575 assert_eq!(deltas.deltas[1].action, BookAction::Add);
576 assert_eq!(deltas.deltas[2].action, BookAction::Update);
577 assert_eq!(deltas.deltas[3].action, BookAction::Delete);
578 }
579
580 #[rstest]
581 fn test_order_book_deltas_api_new() {
582 let deltas = create_test_deltas();
583 let api_wrapper = OrderBookDeltas_API::new(deltas.clone());
584
585 assert_eq!(api_wrapper.instrument_id, deltas.instrument_id);
586 assert_eq!(api_wrapper.deltas.len(), deltas.deltas.len());
587 assert_eq!(api_wrapper.flags, deltas.flags);
588 assert_eq!(api_wrapper.sequence, deltas.sequence);
589 }
590
591 #[rstest]
592 fn test_order_book_deltas_api_into_inner() {
593 let deltas = create_test_deltas();
594 let api_wrapper = OrderBookDeltas_API::new(deltas.clone());
595 let inner_deltas = api_wrapper.into_inner();
596
597 assert_eq!(inner_deltas, deltas);
598 }
599
600 #[rstest]
601 fn test_order_book_deltas_api_deref() {
602 let deltas = create_test_deltas();
603 let api_wrapper = OrderBookDeltas_API::new(deltas.clone());
604
605 assert_eq!(api_wrapper.instrument_id, deltas.instrument_id);
607 assert_eq!(api_wrapper.ts_init(), deltas.ts_init());
608
609 let display_str = format!("{}", &*api_wrapper);
611 assert!(display_str.contains("EURUSD.SIM"));
612 }
613
614 #[rstest]
615 fn test_order_book_deltas_api_deref_mut() {
616 let deltas = create_test_deltas();
617 let mut api_wrapper = OrderBookDeltas_API::new(deltas);
618
619 let original_flags = api_wrapper.flags;
621 api_wrapper.flags = 64;
622
623 assert_ne!(api_wrapper.flags, original_flags);
624 assert_eq!(api_wrapper.flags, 64);
625 }
626
627 #[rstest]
628 fn test_order_book_deltas_api_clone() {
629 let deltas = create_test_deltas();
630 let api_wrapper1 = OrderBookDeltas_API::new(deltas);
631 let api_wrapper2 = api_wrapper1.clone();
632
633 assert_eq!(api_wrapper1.instrument_id, api_wrapper2.instrument_id);
634 assert_eq!(api_wrapper1.sequence, api_wrapper2.sequence);
635 assert_eq!(api_wrapper1, api_wrapper2);
636 }
637
638 #[rstest]
639 fn test_order_book_deltas_api_debug() {
640 let deltas = create_test_deltas();
641 let api_wrapper = OrderBookDeltas_API::new(deltas);
642 let debug_str = format!("{api_wrapper:?}");
643
644 assert!(debug_str.contains("OrderBookDeltas_API"));
645 assert!(debug_str.contains("EURUSD.SIM"));
646 }
647
648 #[rstest]
649 fn test_order_book_deltas_api_serialization() {
650 let deltas = create_test_deltas();
651 let api_wrapper = OrderBookDeltas_API::new(deltas);
652
653 let json = serde_json::to_string(&api_wrapper).unwrap();
655 let deserialized: OrderBookDeltas_API = serde_json::from_str(&json).unwrap();
656
657 assert_eq!(api_wrapper.instrument_id, deserialized.instrument_id);
658 assert_eq!(api_wrapper.sequence, deserialized.sequence);
659 assert_eq!(api_wrapper, deserialized);
660 }
661
662 #[rstest]
663 fn test_order_book_deltas_with_stub(stub_deltas: OrderBookDeltas) {
664 let deltas = stub_deltas;
665
666 assert_eq!(deltas.instrument_id, InstrumentId::from("AAPL.XNAS"));
667 assert_eq!(deltas.deltas.len(), 7);
668 assert_eq!(deltas.flags, 32);
669 assert_eq!(deltas.sequence, 0);
670 assert_eq!(deltas.ts_event, UnixNanos::from(1));
671 assert_eq!(deltas.ts_init, UnixNanos::from(2));
672 }
673
674 #[rstest]
675 fn test_display_with_stub(stub_deltas: OrderBookDeltas) {
676 let deltas = stub_deltas;
677 assert_eq!(
678 format!("{deltas}"),
679 "AAPL.XNAS,len=7,flags=32,sequence=0,ts_event=1,ts_init=2".to_string()
680 );
681 }
682
683 #[rstest]
684 fn test_order_book_deltas_zero_sequence() {
685 let instrument_id = InstrumentId::from("ZERO.TEST");
686 let delta = OrderBookDelta::new(
687 instrument_id,
688 BookAction::Add,
689 BookOrder::new(
690 OrderSide::Buy,
691 Price::from("100.0"),
692 Quantity::from("1000"),
693 1,
694 ),
695 0,
696 0, UnixNanos::from(0), UnixNanos::from(0),
699 );
700
701 let deltas = OrderBookDeltas::new(instrument_id, vec![delta]);
702
703 assert_eq!(deltas.sequence, 0);
704 assert_eq!(deltas.ts_event, UnixNanos::from(0));
705 assert_eq!(deltas.ts_init, UnixNanos::from(0));
706 }
707
708 #[rstest]
709 fn test_order_book_deltas_max_values() {
710 let instrument_id = InstrumentId::from("MAX.TEST");
711 let delta = OrderBookDelta::new(
712 instrument_id,
713 BookAction::Add,
714 BookOrder::new(
715 OrderSide::Buy,
716 Price::from("999999.99"),
717 Quantity::from("999999999"),
718 u64::MAX,
719 ),
720 u8::MAX,
721 u64::MAX,
722 UnixNanos::from(u64::MAX),
723 UnixNanos::from(u64::MAX),
724 );
725
726 let deltas = OrderBookDeltas::new(instrument_id, vec![delta]);
727
728 assert_eq!(deltas.flags, u8::MAX);
729 assert_eq!(deltas.sequence, u64::MAX);
730 assert_eq!(deltas.ts_event, UnixNanos::from(u64::MAX));
731 assert_eq!(deltas.ts_init, UnixNanos::from(u64::MAX));
732 }
733
734 #[rstest]
735 fn test_new() {
736 let instrument_id = InstrumentId::from("AAPL.XNAS");
737 let flags = 32; let sequence = 0;
739 let ts_event = 1;
740 let ts_init = 2;
741
742 let delta0 =
743 OrderBookDelta::clear(instrument_id, sequence, ts_event.into(), ts_init.into());
744 let delta1 = OrderBookDelta::new(
745 instrument_id,
746 BookAction::Add,
747 BookOrder::new(
748 OrderSide::Sell,
749 Price::from("102.00"),
750 Quantity::from("300"),
751 1,
752 ),
753 flags,
754 sequence,
755 ts_event.into(),
756 ts_init.into(),
757 );
758 let delta2 = OrderBookDelta::new(
759 instrument_id,
760 BookAction::Add,
761 BookOrder::new(
762 OrderSide::Sell,
763 Price::from("101.00"),
764 Quantity::from("200"),
765 2,
766 ),
767 flags,
768 sequence,
769 ts_event.into(),
770 ts_init.into(),
771 );
772 let delta3 = OrderBookDelta::new(
773 instrument_id,
774 BookAction::Add,
775 BookOrder::new(
776 OrderSide::Sell,
777 Price::from("100.00"),
778 Quantity::from("100"),
779 3,
780 ),
781 flags,
782 sequence,
783 ts_event.into(),
784 ts_init.into(),
785 );
786 let delta4 = OrderBookDelta::new(
787 instrument_id,
788 BookAction::Add,
789 BookOrder::new(
790 OrderSide::Buy,
791 Price::from("99.00"),
792 Quantity::from("100"),
793 4,
794 ),
795 flags,
796 sequence,
797 ts_event.into(),
798 ts_init.into(),
799 );
800 let delta5 = OrderBookDelta::new(
801 instrument_id,
802 BookAction::Add,
803 BookOrder::new(
804 OrderSide::Buy,
805 Price::from("98.00"),
806 Quantity::from("200"),
807 5,
808 ),
809 flags,
810 sequence,
811 ts_event.into(),
812 ts_init.into(),
813 );
814 let delta6 = OrderBookDelta::new(
815 instrument_id,
816 BookAction::Add,
817 BookOrder::new(
818 OrderSide::Buy,
819 Price::from("97.00"),
820 Quantity::from("300"),
821 6,
822 ),
823 flags,
824 sequence,
825 ts_event.into(),
826 ts_init.into(),
827 );
828
829 let deltas = OrderBookDeltas::new(
830 instrument_id,
831 vec![delta0, delta1, delta2, delta3, delta4, delta5, delta6],
832 );
833
834 assert_eq!(deltas.instrument_id, instrument_id);
835 assert_eq!(deltas.deltas.len(), 7);
836 assert_eq!(deltas.flags, flags);
837 assert_eq!(deltas.sequence, sequence);
838 assert_eq!(deltas.ts_event, ts_event);
839 assert_eq!(deltas.ts_init, ts_init);
840 }
841}