util.rs 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118
  1. use crate::{
  2. entities::revision::{RepeatedRevision, Revision},
  3. errors::{CollaborateError, CollaborateResult},
  4. protobuf::{RepeatedRevision as RepeatedRevisionPB, Revision as RevisionPB},
  5. };
  6. use lib_ot::{
  7. core::{OperationTransformable, NEW_LINE, WHITESPACE},
  8. rich_text::RichTextDelta,
  9. };
  10. use std::{
  11. convert::TryInto,
  12. sync::atomic::{AtomicI64, Ordering::SeqCst},
  13. };
  14. #[inline]
  15. pub fn find_newline(s: &str) -> Option<usize> { s.find(NEW_LINE) }
  16. #[inline]
  17. pub fn is_newline(s: &str) -> bool { s == NEW_LINE }
  18. #[inline]
  19. pub fn is_whitespace(s: &str) -> bool { s == WHITESPACE }
  20. #[inline]
  21. pub fn contain_newline(s: &str) -> bool { s.contains(NEW_LINE) }
  22. #[inline]
  23. pub fn md5<T: AsRef<[u8]>>(data: T) -> String {
  24. let md5 = format!("{:x}", md5::compute(data));
  25. md5
  26. }
  27. #[derive(Debug)]
  28. pub struct RevIdCounter(pub AtomicI64);
  29. impl RevIdCounter {
  30. pub fn new(n: i64) -> Self { Self(AtomicI64::new(n)) }
  31. pub fn next(&self) -> i64 {
  32. let _ = self.0.fetch_add(1, SeqCst);
  33. self.value()
  34. }
  35. pub fn value(&self) -> i64 { self.0.load(SeqCst) }
  36. pub fn set(&self, n: i64) { let _ = self.0.fetch_update(SeqCst, SeqCst, |_| Some(n)); }
  37. }
  38. pub fn make_delta_from_revisions(revisions: Vec<Revision>) -> CollaborateResult<RichTextDelta> {
  39. let mut delta = RichTextDelta::new();
  40. for revision in revisions {
  41. let revision_delta = RichTextDelta::from_bytes(revision.delta_data).map_err(|e| {
  42. let err_msg = format!("Deserialize remote revision failed: {:?}", e);
  43. CollaborateError::internal().context(err_msg)
  44. })?;
  45. delta = delta.compose(&revision_delta)?;
  46. }
  47. Ok(delta)
  48. }
  49. pub fn make_delta_from_revision_pb(revisions: Vec<RevisionPB>) -> CollaborateResult<RichTextDelta> {
  50. let mut new_delta = RichTextDelta::new();
  51. for revision in revisions {
  52. let delta = RichTextDelta::from_bytes(revision.delta_data).map_err(|e| {
  53. let err_msg = format!("Deserialize remote revision failed: {:?}", e);
  54. CollaborateError::internal().context(err_msg)
  55. })?;
  56. new_delta = new_delta.compose(&delta)?;
  57. }
  58. Ok(new_delta)
  59. }
  60. pub fn repeated_revision_from_revision_pbs(revisions: Vec<RevisionPB>) -> CollaborateResult<RepeatedRevision> {
  61. let repeated_revision_pb = repeated_revision_pb_from_revisions(revisions);
  62. repeated_revision_from_repeated_revision_pb(repeated_revision_pb)
  63. }
  64. pub fn repeated_revision_pb_from_revisions(revisions: Vec<RevisionPB>) -> RepeatedRevisionPB {
  65. let mut repeated_revision_pb = RepeatedRevisionPB::new();
  66. repeated_revision_pb.set_items(revisions.into());
  67. repeated_revision_pb
  68. }
  69. pub fn repeated_revision_from_repeated_revision_pb(
  70. mut repeated_revision: RepeatedRevisionPB,
  71. ) -> CollaborateResult<RepeatedRevision> {
  72. (&mut repeated_revision)
  73. .try_into()
  74. .map_err(|e| CollaborateError::internal().context(format!("Cast repeated revision failed: {:?}", e)))
  75. }
  76. pub fn pair_rev_id_from_revision_pbs(revisions: &[RevisionPB]) -> (i64, i64) {
  77. let mut rev_id = 0;
  78. revisions.iter().for_each(|revision| {
  79. if rev_id < revision.rev_id {
  80. rev_id = revision.rev_id;
  81. }
  82. });
  83. if rev_id > 0 {
  84. (rev_id - 1, rev_id)
  85. } else {
  86. (0, rev_id)
  87. }
  88. }
  89. pub fn pair_rev_id_from_revisions(revisions: &[Revision]) -> (i64, i64) {
  90. let mut rev_id = 0;
  91. revisions.iter().for_each(|revision| {
  92. if rev_id < revision.rev_id {
  93. rev_id = revision.rev_id;
  94. }
  95. });
  96. if rev_id > 0 {
  97. (rev_id - 1, rev_id)
  98. } else {
  99. (0, rev_id)
  100. }
  101. }