1use enum_as_inner::EnumAsInner;
2use serde::Serialize;
3use std::fmt::Debug;
4
5#[derive(Debug, Clone, PartialEq, Eq)]
6pub struct Delta<Value, Meta = ()> {
7 pub(crate) vec: Vec<DeltaItem<Value, Meta>>,
8}
9
10impl<V: Serialize, M: Serialize> Serialize for Delta<V, M> {
11 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
12 where
13 S: serde::Serializer,
14 {
15 serializer.collect_seq(self.vec.iter())
16 }
17}
18
19#[derive(Debug, EnumAsInner, Clone, PartialEq, Eq, Serialize)]
20pub enum DeltaItem<Value, Meta> {
21 Retain { retain: usize, attributes: Meta },
22 Insert { insert: Value, attributes: Meta },
23 Delete { delete: usize, attributes: Meta },
24}
25
26#[derive(PartialEq, Debug, Eq)]
27pub enum DeltaType {
28 Retain,
29 Insert,
30 Delete,
31}
32
33pub trait Meta: Debug + Clone + PartialEq + Default {
36 fn empty() -> Self {
37 Self::default()
38 }
39 fn is_empty(&self) -> bool;
40
41 fn compose(&mut self, other: &Self, type_pair: (DeltaType, DeltaType));
43 #[allow(unused)]
44 fn take(&mut self, other: &Self) -> Self {
45 self.clone()
46 }
47
48 fn is_mergeable(&self, other: &Self) -> bool;
49 fn merge(&mut self, other: &Self);
52}
53
54impl Meta for () {
55 fn empty() -> Self {}
56 fn is_empty(&self) -> bool {
57 true
58 }
59
60 fn compose(&mut self, _other: &Self, _type_pair: (DeltaType, DeltaType)) {}
61
62 fn is_mergeable(&self, _other: &Self) -> bool {
63 true
64 }
65
66 fn merge(&mut self, _other: &Self) {}
67}
68
69pub trait DeltaValue: Debug + Sized {
71 fn value_extend(&mut self, other: Self) -> Result<(), Self>;
73 fn take(&mut self, length: usize) -> Self;
75 fn length(&self) -> usize;
77}
78
79impl<V: DeltaValue, M: Debug> DeltaValue for DeltaItem<V, M> {
80 fn value_extend(&mut self, _other: Self) -> Result<(), Self> {
81 unreachable!()
82 }
83
84 fn take(&mut self, _length: usize) -> Self {
85 unreachable!()
86 }
87
88 fn length(&self) -> usize {
89 match self {
90 DeltaItem::Retain {
91 retain: len,
92 attributes: _,
93 } => *len,
94 DeltaItem::Insert {
95 insert: value,
96 attributes: _,
97 } => value.length(),
98 DeltaItem::Delete {
99 delete: len,
100 attributes: _,
101 } => *len,
102 }
103 }
104}
105
106impl<Value: DeltaValue, M: Meta> DeltaItem<Value, M> {
107 pub fn meta(&self) -> &M {
108 match self {
109 DeltaItem::Insert {
110 attributes: meta, ..
111 } => meta,
112 DeltaItem::Retain {
113 attributes: meta, ..
114 } => meta,
115 DeltaItem::Delete {
116 delete: _,
117 attributes: meta,
118 } => meta,
119 }
120 }
121
122 pub fn meta_mut(&mut self) -> &mut M {
123 match self {
124 DeltaItem::Insert {
125 attributes: meta, ..
126 } => meta,
127 DeltaItem::Retain {
128 attributes: meta, ..
129 } => meta,
130 DeltaItem::Delete {
131 delete: _,
132 attributes: meta,
133 } => meta,
134 }
135 }
136
137 pub fn set_meta(&mut self, meta: M) {
138 match self {
139 DeltaItem::Insert { attributes: m, .. } => *m = meta,
140 DeltaItem::Retain { attributes: m, .. } => *m = meta,
141 DeltaItem::Delete {
142 delete: _,
143 attributes: m,
144 } => *m = meta,
145 }
146 }
147
148 fn type_(&self) -> DeltaType {
149 match self {
150 DeltaItem::Insert { .. } => DeltaType::Insert,
151 DeltaItem::Retain { .. } => DeltaType::Retain,
152 DeltaItem::Delete { .. } => DeltaType::Delete,
153 }
154 }
155
156 pub fn compose_meta(&mut self, other: &Self) {
157 let type_pair = (self.type_(), other.type_());
158 let meta = self.meta_mut();
159 let other_meta = other.meta();
160 Meta::compose(meta, other_meta, type_pair);
161 }
162
163 pub(crate) fn take(&mut self, length: usize) -> Self {
166 match self {
167 DeltaItem::Insert {
168 insert: value,
169 attributes: meta,
170 } => {
171 let v = value.take(length);
172 Self::Insert {
173 insert: v,
174 attributes: meta.clone(),
175 }
176 }
177 DeltaItem::Retain {
178 retain: len,
179 attributes: meta,
180 } => {
181 *len -= length;
182 Self::Retain {
183 retain: length,
184 attributes: meta.clone(),
185 }
186 }
187 DeltaItem::Delete {
188 delete: len,
189 attributes: _,
190 } => {
191 *len -= length;
192 Self::Delete {
193 delete: length,
194 attributes: M::empty(),
196 }
197 }
198 }
199 }
200
201 pub(crate) fn take_with_meta_ref(&mut self, length: usize, other_meta: &Self) -> Self {
202 match self {
203 DeltaItem::Insert {
204 insert: value,
205 attributes: meta,
206 } => {
207 let v = value.take(length);
208 Self::Insert {
209 insert: v,
210 attributes: meta.take(other_meta.meta()),
211 }
212 }
213 DeltaItem::Retain {
214 retain: len,
215 attributes: meta,
216 } => {
217 *len -= length;
218 Self::Retain {
219 retain: length,
220 attributes: meta.take(other_meta.meta()),
221 }
222 }
223 DeltaItem::Delete {
224 delete: len,
225 attributes: meta,
226 } => {
227 *len -= length;
228 Self::Delete {
229 delete: length,
230 attributes: meta.take(other_meta.meta()),
231 }
232 }
233 }
234 }
235
236 fn insert_inner(self) -> Value {
237 match self {
238 DeltaItem::Insert { insert: value, .. } => value,
239 _ => unreachable!(),
240 }
241 }
242}
243
244#[derive(Debug)]
245pub struct DeltaIterator<V, M: Meta> {
246 ops: Vec<DeltaItem<V, M>>,
248}
249
250impl<V: DeltaValue, M: Meta> DeltaIterator<V, M> {
251 fn new(ops: Vec<DeltaItem<V, M>>) -> Self {
252 Self { ops }
253 }
254
255 #[inline(always)]
256 fn next<L: Into<Option<usize>>>(&mut self, len: L) -> DeltaItem<V, M> {
257 self.next_impl(len.into())
258 }
259
260 fn next_impl(&mut self, len: Option<usize>) -> DeltaItem<V, M> {
261 let length = len.unwrap_or(usize::MAX);
262 let next_op = self.peek_mut();
263 if next_op.is_none() {
264 return DeltaItem::Retain {
265 retain: usize::MAX,
266 attributes: M::empty(),
267 };
268 }
269 let op = next_op.unwrap();
270 let op_length = op.length();
271 if length < op_length {
272 op.take(length)
274 } else {
275 self.take_peek().unwrap()
276 }
277 }
278
279 fn next_with_ref(&mut self, len: usize, other: &DeltaItem<V, M>) -> DeltaItem<V, M> {
280 let next_op = self.peek_mut();
281 if next_op.is_none() {
282 return DeltaItem::Retain {
283 retain: other.length(),
284 attributes: M::empty(),
285 };
286 }
287 let op = next_op.unwrap();
288 let op_length = op.length();
289 if len < op_length {
290 op.take_with_meta_ref(len, other)
292 } else {
293 self.take_peek().unwrap()
294 }
295 }
296
297 fn next_pair(&mut self, other: &mut Self) -> (DeltaItem<V, M>, DeltaItem<V, M>) {
298 let self_len = self.peek_length();
299 let other_len = other.peek_length();
300 if self_len > other_len {
301 let length = other_len;
302 let other_op = other.next(None);
303 debug_assert_eq!(other_op.length(), length);
304 let this_op = self.next_with_ref(length, &other_op);
305 (this_op, other_op)
306 } else {
307 let length = self_len;
308 let this_op = self.next(None);
309 debug_assert_eq!(this_op.length(), length);
310 let other_op = other.next_with_ref(length, &this_op);
311 (this_op, other_op)
312 }
313 }
314
315 fn peek_mut(&mut self) -> Option<&mut DeltaItem<V, M>> {
316 self.ops.last_mut()
317 }
318
319 fn take_peek(&mut self) -> Option<DeltaItem<V, M>> {
320 self.ops.pop()
321 }
322
323 fn rest(mut self) -> Vec<DeltaItem<V, M>> {
324 self.ops.reverse();
325 self.ops
326 }
327
328 fn has_next(&self) -> bool {
329 !self.ops.is_empty()
330 }
331
332 fn peek(&self) -> Option<&DeltaItem<V, M>> {
333 self.ops.last()
334 }
335
336 fn peek_length(&self) -> usize {
337 if let Some(op) = self.peek() {
338 op.length()
339 } else {
340 usize::MAX
341 }
342 }
343
344 fn peek_is_insert(&self) -> bool {
345 if let Some(op) = self.peek() {
346 op.is_insert()
347 } else {
348 false
349 }
350 }
351
352 fn peek_is_delete(&self) -> bool {
353 if let Some(op) = self.peek() {
354 op.is_delete()
355 } else {
356 false
357 }
358 }
359}
360
361impl<Value: DeltaValue, M: Meta> Delta<Value, M> {
362 pub fn new() -> Self {
363 Self { vec: Vec::new() }
364 }
365
366 pub fn items(&self) -> &[DeltaItem<Value, M>] {
367 &self.vec
368 }
369
370 pub fn inner(self) -> Vec<DeltaItem<Value, M>> {
371 self.vec
372 }
373
374 pub fn retain_with_meta(mut self, len: usize, meta: M) -> Self {
375 if len == 0 {
376 return self;
378 }
379
380 self.push(DeltaItem::Retain {
381 retain: len,
382 attributes: meta,
383 });
384 self
385 }
386
387 pub fn insert_with_meta<V: Into<Value>>(mut self, value: V, meta: M) -> Self {
388 self.push(DeltaItem::Insert {
389 insert: value.into(),
390 attributes: meta,
391 });
392 self
393 }
394
395 pub fn delete_with_meta(mut self, len: usize, meta: M) -> Self {
396 self.push(DeltaItem::Delete {
397 delete: len,
398 attributes: meta,
399 });
400 self
401 }
402
403 pub fn delete(mut self, len: usize) -> Self {
404 if len == 0 {
405 return self;
406 }
407 self.push(DeltaItem::Delete {
408 delete: len,
409 attributes: M::empty(),
410 });
411 self
412 }
413
414 pub fn retain(mut self, len: usize) -> Self {
415 if len == 0 {
416 return self;
417 }
418
419 self.push(DeltaItem::Retain {
420 retain: len,
421 attributes: M::empty(),
422 });
423 self
424 }
425
426 pub fn insert<V: Into<Value>>(mut self, value: V) -> Self {
427 self.push(DeltaItem::Insert {
428 insert: value.into(),
429 attributes: M::empty(),
430 });
431 self
432 }
433
434 pub fn push(&mut self, new_op: DeltaItem<Value, M>) -> bool {
436 let mut index = self.vec.len();
437 let last_op = self.vec.pop();
438 if let Some(mut last_op) = last_op {
439 if new_op.is_delete() && last_op.is_delete() {
440 *last_op.as_delete_mut().unwrap().0 += new_op.length();
441 self.vec.push(last_op);
442 return true;
443 }
444 if last_op.is_delete() && new_op.is_insert() {
447 index -= 1;
448 let _last_op = self.vec.pop();
449 self.vec.push(last_op);
450 if let Some(_last_op_inner) = _last_op {
451 last_op = _last_op_inner;
452 } else {
453 self.vec.insert(0, new_op);
454 return true;
455 };
456 }
457 if last_op.meta().is_mergeable(new_op.meta()) {
458 if new_op.is_insert() && last_op.is_insert() {
459 let value = last_op.as_insert_mut().unwrap().0;
460 let meta = new_op.meta().clone();
461 match value.value_extend(new_op.insert_inner()) {
462 Ok(_) => {
463 last_op.meta_mut().merge(&meta);
464 self.vec.insert(index - 1, last_op);
465 return true;
466 }
467 Err(inner) => {
468 self.vec.insert(index - 1, last_op);
469 self.vec.insert(
470 index,
471 DeltaItem::Insert {
472 insert: inner,
473 attributes: meta,
474 },
475 );
476 return false;
477 }
478 }
479 } else if new_op.is_retain() && last_op.is_retain() {
480 *last_op.as_retain_mut().unwrap().0 += new_op.length();
481 last_op.meta_mut().merge(new_op.meta());
482 self.vec.insert(index - 1, last_op);
484 return true;
485 }
486 }
487
488 self.vec.insert(index - 1, last_op);
490 }
491 if index == self.vec.len() {
492 self.vec.push(new_op);
493 false
494 } else {
495 self.vec.insert(index, new_op);
496 true
497 }
498 }
499
500 pub fn iter(&self) -> impl Iterator<Item = &DeltaItem<Value, M>> {
501 self.vec.iter()
502 }
503
504 pub fn iter_mut(&mut self) -> impl Iterator<Item = &mut DeltaItem<Value, M>> {
505 self.vec.iter_mut()
506 }
507
508 pub fn into_op_iter(self) -> DeltaIterator<Value, M> {
509 DeltaIterator::new(self.vec.into_iter().rev().collect())
510 }
511
512 pub fn len(&self) -> usize {
513 self.vec.len()
514 }
515
516 pub fn is_empty(&self) -> bool {
517 self.len() == 0
518 }
519
520 pub fn compose(self, other: Delta<Value, M>) -> Delta<Value, M> {
523 let mut this_iter = self.into_op_iter();
524 let mut other_iter = other.into_op_iter();
525 let mut ops = vec![];
526 let first_other = other_iter.peek();
527 if let Some(first_other) = first_other {
528 if first_other.is_retain() && first_other.meta().is_empty() {
530 let mut first_left = first_other.length();
531 let mut first_this = this_iter.peek();
532 while let Some(first_this_inner) = first_this {
533 if first_this_inner.is_insert() && first_this_inner.length() <= first_left {
534 first_left -= first_this_inner.length();
535 let mut op = this_iter.next(None);
536 op.compose_meta(first_other);
537 ops.push(op);
538 first_this = this_iter.peek();
539 } else {
540 break;
541 }
542 }
543 if first_other.length() - first_left > 0 {
544 other_iter.next(first_other.length() - first_left);
545 }
546 }
547 }
548 let mut delta = Delta { vec: ops };
549 while this_iter.has_next() || other_iter.has_next() {
550 if other_iter.peek_is_insert() {
551 delta.push(other_iter.next(None));
553 } else if this_iter.peek_is_delete() {
554 delta.push(this_iter.next(None));
556 } else {
557 let (mut this_op, mut other_op) = this_iter.next_pair(&mut other_iter);
564 if other_op.is_retain() {
565 this_op.compose_meta(&other_op);
568 let merged = delta.push(this_op);
569 let concat_rest = !other_iter.has_next() && !merged;
570 if concat_rest {
571 let vec = this_iter.rest();
572 if vec.is_empty() {
573 break;
574 }
575
576 let rest = Delta { vec };
577 delta = delta.concat(rest);
578 break;
579 }
580 } else if other_op.is_delete() && this_op.is_retain() {
581 other_op.compose_meta(&this_op);
583 delta.push(other_op);
585 } else {
586 }
589 }
590 }
591
592 delta.chop()
593 }
594
595 pub(crate) fn concat(mut self, mut other: Self) -> Self {
596 if !other.vec.is_empty() {
597 let other_first = other.vec.remove(0);
598 self.push(other_first);
599 self.vec.extend(other.vec);
600 }
601 self
602 }
603
604 pub fn chop(mut self) -> Self {
605 loop {
606 match self.vec.last() {
607 Some(last_op) if last_op.is_retain() && last_op.meta().is_empty() => {
608 self.vec.pop();
609 }
610 _ => break,
611 }
612 }
613
614 self
615 }
616
617 pub fn insert_len(&self) -> usize {
618 self.vec
619 .iter()
620 .map(|x| match x {
621 DeltaItem::Insert { insert, .. } => insert.length(),
622 _ => 0,
623 })
624 .sum()
625 }
626}
627
628impl<Value, M> IntoIterator for Delta<Value, M> {
629 type Item = DeltaItem<Value, M>;
630
631 type IntoIter = std::vec::IntoIter<DeltaItem<Value, M>>;
632 fn into_iter(self) -> Self::IntoIter {
633 self.vec.into_iter()
634 }
635}
636
637impl<Value: DeltaValue, M: Meta> Default for Delta<Value, M> {
638 fn default() -> Self {
639 Self::new()
640 }
641}
642
643impl<T: Debug> DeltaValue for Vec<T> {
644 fn value_extend(&mut self, other: Self) -> Result<(), Self> {
645 self.extend(other);
646 Ok(())
647 }
648
649 fn take(&mut self, length: usize) -> Self {
650 let mut new = self.split_off(length);
651 std::mem::swap(self, &mut new);
652 new
653 }
654
655 fn length(&self) -> usize {
656 self.len()
657 }
658}
659
660impl DeltaValue for String {
661 fn value_extend(&mut self, other: Self) -> Result<(), Self> {
662 self.push_str(&other);
663 Ok(())
664 }
665
666 fn take(&mut self, length: usize) -> Self {
667 let mut new = self.split_off(length);
668 std::mem::swap(self, &mut new);
669 new
670 }
671 fn length(&self) -> usize {
672 self.len()
673 }
674}
675
676#[cfg(test)]
677mod test {
678 use super::{Delta, DeltaItem, DeltaType, Meta};
679
680 #[derive(Debug, PartialEq, Clone, Default)]
681 struct TestMeta {
682 bold: Option<Option<bool>>,
683 color: Option<Option<()>>,
684 }
685
686 impl Meta for TestMeta {
687 fn empty() -> Self {
688 TestMeta {
689 bold: None,
690 color: None,
691 }
692 }
693 fn is_empty(&self) -> bool {
694 self.bold.is_none() && self.color.is_none()
695 }
696
697 fn compose(
698 &mut self,
699 other: &Self,
700 (this_type, other_type): (super::DeltaType, super::DeltaType),
701 ) {
702 if this_type != DeltaType::Delete && other_type != DeltaType::Delete {
703 if let Some(other_bold) = other.bold {
704 self.bold = Some(other_bold);
705 }
706 if let Some(other_color) = other.color {
707 self.color = Some(other_color);
708 }
709 }
710 }
711
712 fn is_mergeable(&self, other: &Self) -> bool {
713 self == other
714 }
715
716 fn merge(&mut self, _other: &Self) {}
717 }
718
719 type TestDelta = Delta<String, TestMeta>;
720 const BOLD_META: TestMeta = TestMeta {
721 bold: Some(Some(true)),
722 color: None,
723 };
724 const COLOR_META: TestMeta = TestMeta {
725 bold: None,
726 color: Some(Some(())),
727 };
728 const EMPTY_META: TestMeta = TestMeta {
729 bold: Some(None),
730 color: Some(None),
731 };
732 const BOTH_META: TestMeta = TestMeta {
733 bold: Some(Some(true)),
734 color: Some(Some(())),
735 };
736
737 #[test]
738 fn delta_push() {
739 let mut a: Delta<String, ()> = Delta::new().insert("a".to_string());
740 a.push(DeltaItem::Insert {
741 insert: "b".to_string(),
742 attributes: (),
743 });
744 assert_eq!(a, Delta::new().insert("ab".to_string()));
745 }
746
747 #[test]
748 fn delta_compose() {
749 let a: Delta<String, ()> = Delta::new().retain(3).insert("abcde".to_string());
750 let b = Delta::new().retain(5).delete(6);
751 assert_eq!(
752 a.compose(b),
753 Delta::new().retain(3).insert("ab".to_string()).delete(3)
754 );
755
756 let a: Delta<String, ()> = Delta::new().insert("123".to_string());
757 let b = Delta::new().retain(1).insert("123".to_string());
758 assert_eq!(a.compose(b), Delta::new().insert("112323".to_string()));
759 }
760
761 #[test]
762 fn delete_failed() {
763 let a: Delta<String, ()> = Delta::new()
764 .retain(2)
765 .insert("[31354]")
766 .retain(1)
767 .insert("[31354]")
768 .retain(12)
769 .insert("[31354]");
770 let b: Delta<String, ()> = Delta::new().retain(27).delete(3);
771 assert_eq!(
772 a.compose(b),
773 Delta::new()
774 .retain(2)
775 .insert("[31354]")
776 .retain(1)
777 .insert("[31354]")
778 .retain(10)
779 .insert("31354]")
780 .delete(2)
781 );
782 }
783
784 #[test]
785 fn insert_insert() {
786 let a = TestDelta::new().insert("a");
787 let b = TestDelta::new().insert("b");
788 assert_eq!(a.compose(b), TestDelta::new().insert("b").insert("a"));
789 }
790
791 #[test]
792 fn insert_retain() {
793 let a = TestDelta::new().insert("a");
794 let b = TestDelta::new().retain_with_meta(1, BOLD_META);
795 assert_eq!(
796 a.compose(b),
797 TestDelta::new().insert_with_meta("a", BOLD_META)
798 );
799 }
800
801 #[test]
802 fn insert_delete() {
803 let a = TestDelta::new().insert("a");
804 let b = TestDelta::new().delete(1);
805 assert_eq!(a.compose(b), TestDelta::new());
806 }
807
808 #[test]
809 fn delete_insert() {
810 let a = TestDelta::new().delete(1);
811 let b = TestDelta::new().insert("b");
812 assert_eq!(a.compose(b), TestDelta::new().insert("b").delete(1));
813 }
814
815 #[test]
816 fn delete_retain() {
817 let a = TestDelta::new().delete(1);
818 let b = TestDelta::new().retain_with_meta(1, BOLD_META);
819 assert_eq!(
820 a.compose(b),
821 TestDelta::new().delete(1).retain_with_meta(1, BOLD_META)
822 );
823 }
824
825 #[test]
826 fn delete_delete() {
827 let a = TestDelta::new().delete(1);
828 let b = TestDelta::new().delete(1);
829 assert_eq!(a.compose(b), TestDelta::new().delete(2));
830 }
831
832 #[test]
833 fn retain_insert() {
834 let a = TestDelta::new().retain_with_meta(1, BOLD_META);
835 let b = TestDelta::new().insert("b");
836 assert_eq!(
837 a.compose(b),
838 TestDelta::new().insert("b").retain_with_meta(1, BOLD_META)
839 );
840 }
841
842 #[test]
843 fn retain_retain() {
844 let a = TestDelta::new().retain_with_meta(1, BOLD_META);
845 let b = TestDelta::new().retain_with_meta(1, COLOR_META);
846 assert_eq!(
847 a.compose(b),
848 TestDelta::new().retain_with_meta(1, BOTH_META)
849 );
850 }
851
852 #[test]
853 fn retain_delete() {
854 let a = TestDelta::new().retain_with_meta(1, BOLD_META);
855 let b = TestDelta::new().delete(1);
856 assert_eq!(a.compose(b), TestDelta::new().delete(1));
857 }
858
859 #[test]
860 fn delete_entire() {
861 let a = TestDelta::new().retain(4).insert("abcde");
862 let b = TestDelta::new().delete(9);
863 assert_eq!(a.compose(b), TestDelta::new().delete(4));
864 }
865
866 #[test]
867 fn retain_more() {
868 let a = TestDelta::new().insert("abcde");
869 let b = TestDelta::new().retain(10);
870 assert_eq!(a.compose(b), TestDelta::new().insert("abcde"));
871 }
872
873 #[test]
874 fn remove_meta() {
875 let a = TestDelta::new().insert_with_meta("a", BOLD_META);
876 let b = TestDelta::new().retain_with_meta(1, EMPTY_META);
877 assert_eq!(
878 a.compose(b),
879 TestDelta::new().insert_with_meta("a", EMPTY_META)
880 );
881 }
882
883 #[test]
884 fn retain_start_opt() {
885 let a = TestDelta::new()
886 .insert_with_meta("a", BOLD_META)
887 .insert("b")
888 .insert_with_meta("c", BOLD_META)
889 .delete(1);
890 let b = TestDelta::new().retain(3).insert("d");
891 let expect = TestDelta::new()
892 .insert_with_meta("a", BOLD_META)
893 .insert("b")
894 .insert_with_meta("c", BOLD_META)
895 .insert("d")
896 .delete(1);
897 assert_eq!(a.compose(b), expect);
898 }
899
900 #[test]
901 fn retain_start_opt_split() {
902 let a = TestDelta::new()
903 .insert_with_meta("a", BOLD_META)
904 .insert("b")
905 .insert_with_meta("c", BOLD_META)
906 .retain(5)
907 .delete(1);
908 let b = TestDelta::new().retain(4).insert("d");
909 let expect = TestDelta::new()
910 .insert_with_meta("a", BOLD_META)
911 .insert("b")
912 .insert_with_meta("c", BOLD_META)
913 .retain(1)
914 .insert("d")
915 .retain(4)
916 .delete(1);
917 assert_eq!(a.compose(b), expect);
918 }
919
920 #[test]
921 fn retain_end_opt() {
922 let a = TestDelta::new()
923 .insert_with_meta("a", BOLD_META)
924 .insert("b")
925 .insert_with_meta("c", BOLD_META);
926 let b = TestDelta::new().delete(1);
927 let expect = TestDelta::new()
928 .insert("b")
929 .insert_with_meta("c", BOLD_META);
930 assert_eq!(a.compose(b), expect);
931 }
932
933 #[test]
934 fn retain_end_opt_join() {
935 let a = TestDelta::new()
936 .insert_with_meta("a", BOLD_META)
937 .insert("b")
938 .insert_with_meta("c", BOLD_META)
939 .insert("d")
940 .insert_with_meta("e", BOLD_META)
941 .insert("f");
942 let b = TestDelta::new().retain(1).delete(1);
943 let expect = TestDelta::new()
944 .insert_with_meta("ac", BOLD_META)
945 .insert("d")
946 .insert_with_meta("e", BOLD_META)
947 .insert("f");
948 assert_eq!(a.compose(b), expect);
949 }
950}