automerge/patches/
patch.rs

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
use crate::{
    marks::{Mark, MarkSet},
    ObjId, Prop, Value,
};
use core::fmt::Debug;
use std::fmt;

use crate::sequence_tree::SequenceTree;
use crate::text_value::TextValue;

/// A change to the current state of the document
///
/// [`Patch`]es are obtained from a [`PatchLog`](super::PatchLog) which has been passed to any of
/// the various methods which mutate a document and add incremental changes to the
/// [`PatchLog`](super::PatchLog)
#[derive(Debug, Clone, PartialEq)]
pub struct Patch {
    /// The object this patch modifies
    pub obj: ObjId,
    /// The path to the property in the parent object where this object lives
    pub path: Vec<(ObjId, Prop)>,
    /// The change this patch represents
    pub action: PatchAction,
}

#[derive(Debug, Clone, PartialEq)]
pub enum PatchAction {
    /// A key was created or updated in a map
    PutMap {
        key: String,
        /// The value that was inserted and the object ID of the object that was inserted. Note
        /// that the Object ID is only meaningful for `Value::Obj` values
        value: (Value<'static>, ObjId),
        /// Whether there is a conflict at this key. If there is a conflict this patch represents
        /// the "winning" value of the conflict. The conflicting values can be obtained with
        /// [`crate::ReadDoc::get_all`]
        conflict: bool,
    },
    /// An index in a sequence was updated
    PutSeq {
        index: usize,
        /// The value that was set and the object ID of the object that was set. Note that the
        /// Object ID is only meaningful for `Value::Obj` values
        value: (Value<'static>, ObjId),
        /// Whether there is a conflict at this index. If there is a conflict this patch represents
        /// the "winning" value of the conflict. The conflicting values can be obtained with
        /// [`crate::ReadDoc::get_all`]
        conflict: bool,
    },
    /// One or more elements were inserted into a sequence
    Insert {
        index: usize,
        /// The values that were inserted, in order that they appear. As with [`Self::PutMap`] and
        /// [`Self::PutSeq`] the object ID is only meaningful for `Value::Obj` values
        values: SequenceTree<(Value<'static>, ObjId, bool)>,
    },
    /// Some text was spliced into a text object
    SpliceText {
        index: usize,
        /// The text that was inserted
        value: TextValue,
        /// All marks currently active for this span of text
        marks: Option<MarkSet>,
    },
    /// A counter was incremented
    Increment {
        /// The property of the counter that was incremented within the target object
        prop: Prop,
        /// The amount incremented, may be negative
        value: i64,
    },
    /// A new conflict has appeared
    Conflict {
        /// The conflicted property
        prop: Prop,
    },
    /// A key was deleted from a map
    DeleteMap { key: String },
    /// One or more indices were removed from a sequence
    DeleteSeq { index: usize, length: usize },
    /// Some marks within a text object were added or removed
    Mark { marks: Vec<Mark<'static>> },
}

impl fmt::Display for PatchAction {
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        write!(f, "{:?}", self)
    }
}