yrs-store 0.2.0

Simple store layer over Yrs documents
Documentation
use std::collections::HashMap;
use yrs::error::{Error, UpdateError};
use yrs::updates::decoder::Decode;
use yrs::{
    Doc, Out, ReadTxn, StateVector, Subscription, Transact, Transaction, TransactionAcqError,
    TransactionCleanupEvent, TransactionMut, Update,
};

pub trait ForStore {
    fn get_update(&self) -> Vec<u8>;
    fn diff_state_update(&self, state: &Vec<u8>) -> Result<Vec<u8>, Error>;
    fn apply_update(&self, txn: &mut TransactionMut, update: &Vec<u8>) -> Result<(), UpdateError>;
    fn roots(&self, txn: &Transaction<'static>) -> HashMap<String, Out>;
    fn observe<F>(&self, f: F) -> Result<Subscription, TransactionAcqError>
    where
        F: Fn(&TransactionMut, &TransactionCleanupEvent) + Send + Sync + 'static;
}

impl ForStore for Doc {
    fn get_update(&self) -> Vec<u8> {
        self.transact()
            .encode_state_as_update_v1(&StateVector::default())
            .into()
    }

    fn diff_state_update(&self, state: &Vec<u8>) -> Result<Vec<u8>, Error> {
        let state_vector = StateVector::decode_v1(&state.as_ref())?;
        let update = self.transact().encode_state_as_update_v1(&state_vector);
        Ok(update.into())
    }

    fn apply_update(&self, txn: &mut TransactionMut, update: &Vec<u8>) -> Result<(), UpdateError> {
        let u = Update::decode_v1(update.as_ref()).unwrap();
        txn.apply_update(u)
    }

    fn roots(&self, txn: &Transaction<'static>) -> HashMap<String, Out> {
        txn.root_refs()
            .map(|(key_slice, value)| (key_slice.to_string(), value))
            .collect::<HashMap<String, Out>>()
    }

    fn observe<F>(&self, f: F) -> Result<Subscription, TransactionAcqError>
    where
        F: Fn(&TransactionMut, &TransactionCleanupEvent) + Send + Sync + 'static,
    {
        self.observe_transaction_cleanup(move |txn, event| {
            if !event.delete_set.is_empty() || event.before_state != event.after_state {
                f(txn, event);
            }
        })
    }
}