buffer.rs

   1mod anchor;
   2mod point;
   3pub mod rope;
   4mod selection;
   5
   6pub use anchor::*;
   7use parking_lot::Mutex;
   8pub use point::*;
   9pub use rope::{Chunks, Rope, TextSummary};
  10use seahash::SeaHasher;
  11pub use selection::*;
  12use similar::{ChangeTag, TextDiff};
  13use tree_sitter::{InputEdit, Parser, QueryCursor};
  14use zrpc::proto;
  15
  16use crate::{
  17    language::{Language, Tree},
  18    operation_queue::{self, OperationQueue},
  19    settings::{StyleId, ThemeMap},
  20    sum_tree::{self, FilterCursor, SumTree},
  21    time::{self, ReplicaId},
  22    util::Bias,
  23    worktree::{File, Worktree},
  24};
  25use anyhow::{anyhow, Result};
  26use gpui::{AppContext, Entity, ModelContext, ModelHandle, Task};
  27use lazy_static::lazy_static;
  28use std::{
  29    cell::RefCell,
  30    cmp,
  31    convert::{TryFrom, TryInto},
  32    hash::BuildHasher,
  33    iter::Iterator,
  34    ops::{Deref, DerefMut, Range},
  35    path::Path,
  36    str,
  37    sync::Arc,
  38    time::{Duration, Instant, SystemTime, UNIX_EPOCH},
  39};
  40
  41#[derive(Clone, Default)]
  42struct DeterministicState;
  43
  44impl BuildHasher for DeterministicState {
  45    type Hasher = SeaHasher;
  46
  47    fn build_hasher(&self) -> Self::Hasher {
  48        SeaHasher::new()
  49    }
  50}
  51
  52#[cfg(test)]
  53type HashMap<K, V> = std::collections::HashMap<K, V, DeterministicState>;
  54
  55#[cfg(test)]
  56type HashSet<T> = std::collections::HashSet<T, DeterministicState>;
  57
  58#[cfg(not(test))]
  59type HashMap<K, V> = std::collections::HashMap<K, V>;
  60
  61#[cfg(not(test))]
  62type HashSet<T> = std::collections::HashSet<T>;
  63
  64thread_local! {
  65    static PARSER: RefCell<Parser> = RefCell::new(Parser::new());
  66}
  67
  68lazy_static! {
  69    static ref QUERY_CURSORS: Mutex<Vec<QueryCursor>> = Default::default();
  70}
  71
  72struct QueryCursorHandle(Option<QueryCursor>);
  73
  74impl QueryCursorHandle {
  75    fn new() -> Self {
  76        QueryCursorHandle(Some(
  77            QUERY_CURSORS
  78                .lock()
  79                .pop()
  80                .unwrap_or_else(|| QueryCursor::new()),
  81        ))
  82    }
  83}
  84
  85impl Deref for QueryCursorHandle {
  86    type Target = QueryCursor;
  87
  88    fn deref(&self) -> &Self::Target {
  89        self.0.as_ref().unwrap()
  90    }
  91}
  92
  93impl DerefMut for QueryCursorHandle {
  94    fn deref_mut(&mut self) -> &mut Self::Target {
  95        self.0.as_mut().unwrap()
  96    }
  97}
  98
  99impl Drop for QueryCursorHandle {
 100    fn drop(&mut self) {
 101        let mut cursor = self.0.take().unwrap();
 102        cursor.set_byte_range(0..usize::MAX);
 103        cursor.set_point_range(Point::zero().into()..Point::MAX.into());
 104        QUERY_CURSORS.lock().push(cursor)
 105    }
 106}
 107
 108pub struct Buffer {
 109    fragments: SumTree<Fragment>,
 110    visible_text: Rope,
 111    deleted_text: Rope,
 112    pub version: time::Global,
 113    saved_version: time::Global,
 114    saved_mtime: SystemTime,
 115    last_edit: time::Local,
 116    undo_map: UndoMap,
 117    history: History,
 118    file: Option<File>,
 119    language: Option<Arc<Language>>,
 120    syntax_tree: Mutex<Option<SyntaxTree>>,
 121    is_parsing: bool,
 122    selections: HashMap<SelectionSetId, SelectionSet>,
 123    deferred_ops: OperationQueue<Operation>,
 124    deferred_replicas: HashSet<ReplicaId>,
 125    replica_id: ReplicaId,
 126    remote_id: u64,
 127    local_clock: time::Local,
 128    lamport_clock: time::Lamport,
 129    #[cfg(test)]
 130    operations: Vec<Operation>,
 131}
 132
 133#[derive(Clone, Debug, Eq, PartialEq)]
 134pub struct SelectionSet {
 135    pub selections: Arc<[Selection]>,
 136    pub active: bool,
 137}
 138
 139#[derive(Clone)]
 140struct SyntaxTree {
 141    tree: Tree,
 142    parsed: bool,
 143    version: time::Global,
 144}
 145
 146#[derive(Clone, Debug)]
 147struct Transaction {
 148    start: time::Global,
 149    end: time::Global,
 150    buffer_was_dirty: bool,
 151    edits: Vec<time::Local>,
 152    ranges: Vec<Range<usize>>,
 153    selections_before: Option<(SelectionSetId, Arc<[Selection]>)>,
 154    selections_after: Option<(SelectionSetId, Arc<[Selection]>)>,
 155    first_edit_at: Instant,
 156    last_edit_at: Instant,
 157}
 158
 159impl Transaction {
 160    fn push_edit(&mut self, edit: &EditOperation) {
 161        self.edits.push(edit.timestamp.local());
 162        self.end.observe(edit.timestamp.local());
 163
 164        let mut other_ranges = edit.ranges.iter().peekable();
 165        let mut new_ranges: Vec<Range<usize>> = Vec::new();
 166        let insertion_len = edit.new_text.as_ref().map_or(0, |t| t.len());
 167        let mut delta = 0;
 168
 169        for mut self_range in self.ranges.iter().cloned() {
 170            self_range.start += delta;
 171            self_range.end += delta;
 172
 173            while let Some(other_range) = other_ranges.peek() {
 174                let mut other_range = (*other_range).clone();
 175                other_range.start += delta;
 176                other_range.end += delta;
 177
 178                if other_range.start <= self_range.end {
 179                    other_ranges.next().unwrap();
 180                    delta += insertion_len;
 181
 182                    if other_range.end < self_range.start {
 183                        new_ranges.push(other_range.start..other_range.end + insertion_len);
 184                        self_range.start += insertion_len;
 185                        self_range.end += insertion_len;
 186                    } else {
 187                        self_range.start = cmp::min(self_range.start, other_range.start);
 188                        self_range.end = cmp::max(self_range.end, other_range.end) + insertion_len;
 189                    }
 190                } else {
 191                    break;
 192                }
 193            }
 194
 195            new_ranges.push(self_range);
 196        }
 197
 198        for other_range in other_ranges {
 199            new_ranges.push(other_range.start + delta..other_range.end + delta + insertion_len);
 200            delta += insertion_len;
 201        }
 202
 203        self.ranges = new_ranges;
 204    }
 205}
 206
 207#[derive(Clone)]
 208pub struct History {
 209    // TODO: Turn this into a String or Rope, maybe.
 210    pub base_text: Arc<str>,
 211    ops: HashMap<time::Local, EditOperation>,
 212    undo_stack: Vec<Transaction>,
 213    redo_stack: Vec<Transaction>,
 214    transaction_depth: usize,
 215    group_interval: Duration,
 216}
 217
 218impl History {
 219    pub fn new(base_text: Arc<str>) -> Self {
 220        Self {
 221            base_text,
 222            ops: Default::default(),
 223            undo_stack: Vec::new(),
 224            redo_stack: Vec::new(),
 225            transaction_depth: 0,
 226            group_interval: Duration::from_millis(300),
 227        }
 228    }
 229
 230    fn push(&mut self, op: EditOperation) {
 231        self.ops.insert(op.timestamp.local(), op);
 232    }
 233
 234    fn start_transaction(
 235        &mut self,
 236        start: time::Global,
 237        buffer_was_dirty: bool,
 238        selections: Option<(SelectionSetId, Arc<[Selection]>)>,
 239        now: Instant,
 240    ) {
 241        self.transaction_depth += 1;
 242        if self.transaction_depth == 1 {
 243            self.undo_stack.push(Transaction {
 244                start: start.clone(),
 245                end: start,
 246                buffer_was_dirty,
 247                edits: Vec::new(),
 248                ranges: Vec::new(),
 249                selections_before: selections,
 250                selections_after: None,
 251                first_edit_at: now,
 252                last_edit_at: now,
 253            });
 254        }
 255    }
 256
 257    fn end_transaction(
 258        &mut self,
 259        selections: Option<(SelectionSetId, Arc<[Selection]>)>,
 260        now: Instant,
 261    ) -> Option<&Transaction> {
 262        assert_ne!(self.transaction_depth, 0);
 263        self.transaction_depth -= 1;
 264        if self.transaction_depth == 0 {
 265            let transaction = self.undo_stack.last_mut().unwrap();
 266            transaction.selections_after = selections;
 267            transaction.last_edit_at = now;
 268            Some(transaction)
 269        } else {
 270            None
 271        }
 272    }
 273
 274    fn group(&mut self) {
 275        let mut new_len = self.undo_stack.len();
 276        let mut transactions = self.undo_stack.iter_mut();
 277
 278        if let Some(mut transaction) = transactions.next_back() {
 279            while let Some(prev_transaction) = transactions.next_back() {
 280                if transaction.first_edit_at - prev_transaction.last_edit_at <= self.group_interval
 281                    && transaction.start == prev_transaction.end
 282                {
 283                    transaction = prev_transaction;
 284                    new_len -= 1;
 285                } else {
 286                    break;
 287                }
 288            }
 289        }
 290
 291        let (transactions_to_keep, transactions_to_merge) = self.undo_stack.split_at_mut(new_len);
 292        if let Some(last_transaction) = transactions_to_keep.last_mut() {
 293            for transaction in &*transactions_to_merge {
 294                for edit_id in &transaction.edits {
 295                    last_transaction.push_edit(&self.ops[edit_id]);
 296                }
 297            }
 298
 299            if let Some(transaction) = transactions_to_merge.last_mut() {
 300                last_transaction.last_edit_at = transaction.last_edit_at;
 301                last_transaction.selections_after = transaction.selections_after.take();
 302                last_transaction.end = transaction.end.clone();
 303            }
 304        }
 305
 306        self.undo_stack.truncate(new_len);
 307    }
 308
 309    fn push_undo(&mut self, edit_id: time::Local) {
 310        assert_ne!(self.transaction_depth, 0);
 311        let last_transaction = self.undo_stack.last_mut().unwrap();
 312        last_transaction.push_edit(&self.ops[&edit_id]);
 313    }
 314
 315    fn pop_undo(&mut self) -> Option<&Transaction> {
 316        assert_eq!(self.transaction_depth, 0);
 317        if let Some(transaction) = self.undo_stack.pop() {
 318            self.redo_stack.push(transaction);
 319            self.redo_stack.last()
 320        } else {
 321            None
 322        }
 323    }
 324
 325    fn pop_redo(&mut self) -> Option<&Transaction> {
 326        assert_eq!(self.transaction_depth, 0);
 327        if let Some(transaction) = self.redo_stack.pop() {
 328            self.undo_stack.push(transaction);
 329            self.undo_stack.last()
 330        } else {
 331            None
 332        }
 333    }
 334}
 335
 336#[derive(Clone, Default, Debug)]
 337struct UndoMap(HashMap<time::Local, Vec<(time::Local, u32)>>);
 338
 339impl UndoMap {
 340    fn insert(&mut self, undo: &UndoOperation) {
 341        for (edit_id, count) in &undo.counts {
 342            self.0.entry(*edit_id).or_default().push((undo.id, *count));
 343        }
 344    }
 345
 346    fn is_undone(&self, edit_id: time::Local) -> bool {
 347        self.undo_count(edit_id) % 2 == 1
 348    }
 349
 350    fn was_undone(&self, edit_id: time::Local, version: &time::Global) -> bool {
 351        let undo_count = self
 352            .0
 353            .get(&edit_id)
 354            .unwrap_or(&Vec::new())
 355            .iter()
 356            .filter(|(undo_id, _)| version.observed(*undo_id))
 357            .map(|(_, undo_count)| *undo_count)
 358            .max()
 359            .unwrap_or(0);
 360        undo_count % 2 == 1
 361    }
 362
 363    fn undo_count(&self, edit_id: time::Local) -> u32 {
 364        self.0
 365            .get(&edit_id)
 366            .unwrap_or(&Vec::new())
 367            .iter()
 368            .map(|(_, undo_count)| *undo_count)
 369            .max()
 370            .unwrap_or(0)
 371    }
 372}
 373
 374struct Edits<'a, F: Fn(&FragmentSummary) -> bool> {
 375    visible_text: &'a Rope,
 376    deleted_text: &'a Rope,
 377    cursor: FilterCursor<'a, F, Fragment, FragmentTextSummary>,
 378    undos: &'a UndoMap,
 379    since: time::Global,
 380    old_offset: usize,
 381    new_offset: usize,
 382    old_point: Point,
 383    new_point: Point,
 384}
 385
 386#[derive(Clone, Debug, Default, Eq, PartialEq)]
 387pub struct Edit {
 388    pub old_bytes: Range<usize>,
 389    pub new_bytes: Range<usize>,
 390    pub old_lines: Range<Point>,
 391}
 392
 393impl Edit {
 394    pub fn delta(&self) -> isize {
 395        self.inserted_bytes() as isize - self.deleted_bytes() as isize
 396    }
 397
 398    pub fn deleted_bytes(&self) -> usize {
 399        self.old_bytes.end - self.old_bytes.start
 400    }
 401
 402    pub fn inserted_bytes(&self) -> usize {
 403        self.new_bytes.end - self.new_bytes.start
 404    }
 405
 406    pub fn deleted_lines(&self) -> Point {
 407        self.old_lines.end - self.old_lines.start
 408    }
 409}
 410
 411struct Diff {
 412    base_version: time::Global,
 413    new_text: Arc<str>,
 414    changes: Vec<(ChangeTag, usize)>,
 415}
 416
 417#[derive(Copy, Clone, Debug, Default, Eq, PartialEq)]
 418struct InsertionTimestamp {
 419    replica_id: ReplicaId,
 420    local: time::Seq,
 421    lamport: time::Seq,
 422}
 423
 424impl InsertionTimestamp {
 425    fn local(&self) -> time::Local {
 426        time::Local {
 427            replica_id: self.replica_id,
 428            value: self.local,
 429        }
 430    }
 431
 432    fn lamport(&self) -> time::Lamport {
 433        time::Lamport {
 434            replica_id: self.replica_id,
 435            value: self.lamport,
 436        }
 437    }
 438}
 439
 440#[derive(Eq, PartialEq, Clone, Debug)]
 441struct Fragment {
 442    timestamp: InsertionTimestamp,
 443    len: usize,
 444    visible: bool,
 445    deletions: HashSet<time::Local>,
 446    max_undos: time::Global,
 447}
 448
 449#[derive(Eq, PartialEq, Clone, Debug)]
 450pub struct FragmentSummary {
 451    text: FragmentTextSummary,
 452    max_version: time::Global,
 453    min_insertion_version: time::Global,
 454    max_insertion_version: time::Global,
 455}
 456
 457#[derive(Copy, Default, Clone, Debug, PartialEq, Eq)]
 458struct FragmentTextSummary {
 459    visible: usize,
 460    deleted: usize,
 461}
 462
 463impl<'a> sum_tree::Dimension<'a, FragmentSummary> for FragmentTextSummary {
 464    fn add_summary(&mut self, summary: &'a FragmentSummary, _: &Option<time::Global>) {
 465        self.visible += summary.text.visible;
 466        self.deleted += summary.text.deleted;
 467    }
 468}
 469
 470#[derive(Clone, Debug, Eq, PartialEq)]
 471pub enum Operation {
 472    Edit(EditOperation),
 473    Undo {
 474        undo: UndoOperation,
 475        lamport_timestamp: time::Lamport,
 476    },
 477    UpdateSelections {
 478        set_id: SelectionSetId,
 479        selections: Option<Arc<[Selection]>>,
 480        lamport_timestamp: time::Lamport,
 481    },
 482    SetActiveSelections {
 483        set_id: Option<SelectionSetId>,
 484        lamport_timestamp: time::Lamport,
 485    },
 486}
 487
 488#[derive(Clone, Debug, Eq, PartialEq)]
 489pub struct EditOperation {
 490    timestamp: InsertionTimestamp,
 491    version: time::Global,
 492    ranges: Vec<Range<usize>>,
 493    new_text: Option<String>,
 494}
 495
 496#[derive(Clone, Debug, Eq, PartialEq)]
 497pub struct UndoOperation {
 498    id: time::Local,
 499    counts: HashMap<time::Local, u32>,
 500    ranges: Vec<Range<usize>>,
 501    version: time::Global,
 502}
 503
 504impl Buffer {
 505    pub fn new<T: Into<Arc<str>>>(
 506        replica_id: ReplicaId,
 507        base_text: T,
 508        cx: &mut ModelContext<Self>,
 509    ) -> Self {
 510        Self::build(
 511            replica_id,
 512            History::new(base_text.into()),
 513            None,
 514            cx.model_id() as u64,
 515            None,
 516            cx,
 517        )
 518    }
 519
 520    pub fn from_history(
 521        replica_id: ReplicaId,
 522        history: History,
 523        file: Option<File>,
 524        language: Option<Arc<Language>>,
 525        cx: &mut ModelContext<Self>,
 526    ) -> Self {
 527        Self::build(
 528            replica_id,
 529            history,
 530            file,
 531            cx.model_id() as u64,
 532            language,
 533            cx,
 534        )
 535    }
 536
 537    fn build(
 538        replica_id: ReplicaId,
 539        history: History,
 540        file: Option<File>,
 541        remote_id: u64,
 542        language: Option<Arc<Language>>,
 543        cx: &mut ModelContext<Self>,
 544    ) -> Self {
 545        let saved_mtime;
 546        if let Some(file) = file.as_ref() {
 547            saved_mtime = file.mtime;
 548        } else {
 549            saved_mtime = UNIX_EPOCH;
 550        }
 551
 552        let mut fragments = SumTree::new();
 553
 554        let visible_text = Rope::from(history.base_text.as_ref());
 555        if visible_text.len() > 0 {
 556            fragments.push(
 557                Fragment {
 558                    timestamp: Default::default(),
 559                    len: visible_text.len(),
 560                    visible: true,
 561                    deletions: Default::default(),
 562                    max_undos: Default::default(),
 563                },
 564                &None,
 565            );
 566        }
 567
 568        let mut result = Self {
 569            visible_text,
 570            deleted_text: Rope::new(),
 571            fragments,
 572            version: time::Global::new(),
 573            saved_version: time::Global::new(),
 574            last_edit: time::Local::default(),
 575            undo_map: Default::default(),
 576            history,
 577            file,
 578            syntax_tree: Mutex::new(None),
 579            is_parsing: false,
 580            language,
 581            saved_mtime,
 582            selections: HashMap::default(),
 583            deferred_ops: OperationQueue::new(),
 584            deferred_replicas: HashSet::default(),
 585            replica_id,
 586            remote_id,
 587            local_clock: time::Local::new(replica_id),
 588            lamport_clock: time::Lamport::new(replica_id),
 589
 590            #[cfg(test)]
 591            operations: Default::default(),
 592        };
 593        result.reparse(cx);
 594        result
 595    }
 596
 597    pub fn replica_id(&self) -> ReplicaId {
 598        self.local_clock.replica_id
 599    }
 600
 601    pub fn snapshot(&self) -> Snapshot {
 602        Snapshot {
 603            visible_text: self.visible_text.clone(),
 604            fragments: self.fragments.clone(),
 605            version: self.version.clone(),
 606            tree: self.syntax_tree(),
 607            language: self.language.clone(),
 608            query_cursor: QueryCursorHandle::new(),
 609        }
 610    }
 611
 612    pub fn from_proto(
 613        replica_id: ReplicaId,
 614        message: proto::Buffer,
 615        file: Option<File>,
 616        language: Option<Arc<Language>>,
 617        cx: &mut ModelContext<Self>,
 618    ) -> Result<Self> {
 619        let mut buffer = Buffer::build(
 620            replica_id,
 621            History::new(message.content.into()),
 622            file,
 623            message.id,
 624            language,
 625            cx,
 626        );
 627        let ops = message
 628            .history
 629            .into_iter()
 630            .map(|op| Operation::Edit(op.into()));
 631        buffer.apply_ops(ops, cx)?;
 632        buffer.selections = message
 633            .selections
 634            .into_iter()
 635            .map(|set| {
 636                let set_id = time::Lamport {
 637                    replica_id: set.replica_id as ReplicaId,
 638                    value: set.local_timestamp,
 639                };
 640                let selections: Vec<Selection> = set
 641                    .selections
 642                    .into_iter()
 643                    .map(TryFrom::try_from)
 644                    .collect::<Result<_, _>>()?;
 645                let set = SelectionSet {
 646                    selections: Arc::from(selections),
 647                    active: set.is_active,
 648                };
 649                Result::<_, anyhow::Error>::Ok((set_id, set))
 650            })
 651            .collect::<Result<_, _>>()?;
 652        Ok(buffer)
 653    }
 654
 655    pub fn to_proto(&self, cx: &mut ModelContext<Self>) -> proto::Buffer {
 656        let ops = self.history.ops.values().map(Into::into).collect();
 657        proto::Buffer {
 658            id: cx.model_id() as u64,
 659            content: self.history.base_text.to_string(),
 660            history: ops,
 661            selections: self
 662                .selections
 663                .iter()
 664                .map(|(set_id, set)| proto::SelectionSetSnapshot {
 665                    replica_id: set_id.replica_id as u32,
 666                    local_timestamp: set_id.value,
 667                    selections: set.selections.iter().map(Into::into).collect(),
 668                    is_active: set.active,
 669                })
 670                .collect(),
 671        }
 672    }
 673
 674    pub fn file(&self) -> Option<&File> {
 675        self.file.as_ref()
 676    }
 677
 678    pub fn file_mut(&mut self) -> Option<&mut File> {
 679        self.file.as_mut()
 680    }
 681
 682    pub fn save(
 683        &mut self,
 684        cx: &mut ModelContext<Self>,
 685    ) -> Result<Task<Result<(time::Global, SystemTime)>>> {
 686        let file = self
 687            .file
 688            .as_ref()
 689            .ok_or_else(|| anyhow!("buffer has no file"))?;
 690        let text = self.visible_text.clone();
 691        let version = self.version.clone();
 692        let save = file.save(self.remote_id, text, version, cx.as_mut());
 693        Ok(cx.spawn(|this, mut cx| async move {
 694            let (version, mtime) = save.await?;
 695            this.update(&mut cx, |this, cx| {
 696                this.did_save(version.clone(), mtime, cx);
 697            });
 698            Ok((version, mtime))
 699        }))
 700    }
 701
 702    pub fn save_as(
 703        &mut self,
 704        worktree: &ModelHandle<Worktree>,
 705        path: impl Into<Arc<Path>>,
 706        cx: &mut ModelContext<Self>,
 707    ) -> Task<Result<()>> {
 708        let handle = cx.handle();
 709        let text = self.visible_text.clone();
 710        let version = self.version.clone();
 711        let save_as = worktree.update(cx, |worktree, cx| {
 712            worktree
 713                .as_local_mut()
 714                .unwrap()
 715                .save_buffer_as(handle, path, text, cx)
 716        });
 717
 718        cx.spawn(|this, mut cx| async move {
 719            save_as.await.map(|new_file| {
 720                this.update(&mut cx, |this, cx| {
 721                    let mtime = new_file.mtime;
 722                    this.file = Some(new_file);
 723                    this.did_save(version, mtime, cx);
 724                });
 725            })
 726        })
 727    }
 728
 729    pub fn did_save(
 730        &mut self,
 731        version: time::Global,
 732        mtime: SystemTime,
 733        cx: &mut ModelContext<Self>,
 734    ) {
 735        self.saved_mtime = mtime;
 736        self.saved_version = version;
 737        cx.emit(Event::Saved);
 738    }
 739
 740    pub fn file_updated(
 741        &mut self,
 742        path: Arc<Path>,
 743        mtime: SystemTime,
 744        new_text: Option<String>,
 745        cx: &mut ModelContext<Self>,
 746    ) {
 747        let file = self.file.as_mut().unwrap();
 748        let mut changed = false;
 749        if path != file.path {
 750            file.path = path;
 751            changed = true;
 752        }
 753
 754        if mtime != file.mtime {
 755            file.mtime = mtime;
 756            changed = true;
 757            if let Some(new_text) = new_text {
 758                if self.version == self.saved_version {
 759                    cx.spawn(|this, mut cx| async move {
 760                        let diff = this
 761                            .read_with(&cx, |this, cx| this.diff(new_text.into(), cx))
 762                            .await;
 763                        this.update(&mut cx, |this, cx| {
 764                            if this.apply_diff(diff, cx) {
 765                                this.saved_version = this.version.clone();
 766                                this.saved_mtime = mtime;
 767                                cx.emit(Event::Reloaded);
 768                            }
 769                        });
 770                    })
 771                    .detach();
 772                }
 773            }
 774        }
 775
 776        if changed {
 777            cx.emit(Event::FileHandleChanged);
 778        }
 779    }
 780
 781    pub fn file_deleted(&mut self, cx: &mut ModelContext<Self>) {
 782        if self.version == self.saved_version {
 783            cx.emit(Event::Dirtied);
 784        }
 785        cx.emit(Event::FileHandleChanged);
 786    }
 787
 788    pub fn syntax_tree(&self) -> Option<Tree> {
 789        if let Some(syntax_tree) = self.syntax_tree.lock().as_mut() {
 790            let mut edited = false;
 791            let mut delta = 0_isize;
 792            for edit in self.edits_since(syntax_tree.version.clone()) {
 793                let start_offset = (edit.old_bytes.start as isize + delta) as usize;
 794                let start_point = self.visible_text.to_point(start_offset);
 795                syntax_tree.tree.edit(&InputEdit {
 796                    start_byte: start_offset,
 797                    old_end_byte: start_offset + edit.deleted_bytes(),
 798                    new_end_byte: start_offset + edit.inserted_bytes(),
 799                    start_position: start_point.into(),
 800                    old_end_position: (start_point + edit.deleted_lines()).into(),
 801                    new_end_position: self
 802                        .visible_text
 803                        .to_point(start_offset + edit.inserted_bytes())
 804                        .into(),
 805                });
 806                delta += edit.inserted_bytes() as isize - edit.deleted_bytes() as isize;
 807                edited = true;
 808            }
 809            syntax_tree.parsed &= !edited;
 810            syntax_tree.version = self.version();
 811            Some(syntax_tree.tree.clone())
 812        } else {
 813            None
 814        }
 815    }
 816
 817    pub fn is_parsing(&self) -> bool {
 818        self.is_parsing
 819    }
 820
 821    fn should_reparse(&self) -> bool {
 822        if let Some(syntax_tree) = self.syntax_tree.lock().as_ref() {
 823            !syntax_tree.parsed || syntax_tree.version != self.version
 824        } else {
 825            self.language.is_some()
 826        }
 827    }
 828
 829    fn reparse(&mut self, cx: &mut ModelContext<Self>) {
 830        // Avoid spawning a new parsing task if the buffer is already being reparsed
 831        // due to an earlier edit.
 832        if self.is_parsing {
 833            return;
 834        }
 835
 836        if let Some(language) = self.language.clone() {
 837            self.is_parsing = true;
 838            cx.spawn(|handle, mut cx| async move {
 839                while handle.read_with(&cx, |this, _| this.should_reparse()) {
 840                    // The parse tree is out of date, so grab the syntax tree to synchronously
 841                    // splice all the edits that have happened since the last parse.
 842                    let new_tree = handle.update(&mut cx, |this, _| this.syntax_tree());
 843                    let (new_text, new_version) = handle
 844                        .read_with(&cx, |this, _| (this.visible_text.clone(), this.version()));
 845
 846                    // Parse the current text in a background thread.
 847                    let new_tree = cx
 848                        .background()
 849                        .spawn({
 850                            let language = language.clone();
 851                            async move { Self::parse_text(&new_text, new_tree, &language) }
 852                        })
 853                        .await;
 854
 855                    handle.update(&mut cx, |this, cx| {
 856                        *this.syntax_tree.lock() = Some(SyntaxTree {
 857                            tree: new_tree,
 858                            parsed: true,
 859                            version: new_version,
 860                        });
 861                        cx.emit(Event::Reparsed);
 862                        cx.notify();
 863                    });
 864                }
 865                handle.update(&mut cx, |this, _| this.is_parsing = false);
 866            })
 867            .detach();
 868        }
 869    }
 870
 871    fn parse_text(text: &Rope, old_tree: Option<Tree>, language: &Language) -> Tree {
 872        PARSER.with(|parser| {
 873            let mut parser = parser.borrow_mut();
 874            parser
 875                .set_language(language.grammar)
 876                .expect("incompatible grammar");
 877            let mut chunks = text.chunks_in_range(0..text.len());
 878            let tree = parser
 879                .parse_with(
 880                    &mut move |offset, _| {
 881                        chunks.seek(offset);
 882                        chunks.next().unwrap_or("").as_bytes()
 883                    },
 884                    old_tree.as_ref(),
 885                )
 886                .unwrap();
 887            tree
 888        })
 889    }
 890
 891    pub fn range_for_syntax_ancestor<T: ToOffset>(&self, range: Range<T>) -> Option<Range<usize>> {
 892        if let Some(tree) = self.syntax_tree() {
 893            let root = tree.root_node();
 894            let range = range.start.to_offset(self)..range.end.to_offset(self);
 895            let mut node = root.descendant_for_byte_range(range.start, range.end);
 896            while node.map_or(false, |n| n.byte_range() == range) {
 897                node = node.unwrap().parent();
 898            }
 899            node.map(|n| n.byte_range())
 900        } else {
 901            None
 902        }
 903    }
 904
 905    pub fn enclosing_bracket_ranges<T: ToOffset>(
 906        &self,
 907        range: Range<T>,
 908    ) -> Option<(Range<usize>, Range<usize>)> {
 909        let (lang, tree) = self.language.as_ref().zip(self.syntax_tree())?;
 910        let open_capture_ix = lang.brackets_query.capture_index_for_name("open")?;
 911        let close_capture_ix = lang.brackets_query.capture_index_for_name("close")?;
 912
 913        // Find bracket pairs that *inclusively* contain the given range.
 914        let range = range.start.to_offset(self).saturating_sub(1)..range.end.to_offset(self) + 1;
 915        let mut cursor = QueryCursorHandle::new();
 916        let matches = cursor.set_byte_range(range).matches(
 917            &lang.brackets_query,
 918            tree.root_node(),
 919            TextProvider(&self.visible_text),
 920        );
 921
 922        // Get the ranges of the innermost pair of brackets.
 923        matches
 924            .filter_map(|mat| {
 925                let open = mat.nodes_for_capture_index(open_capture_ix).next()?;
 926                let close = mat.nodes_for_capture_index(close_capture_ix).next()?;
 927                Some((open.byte_range(), close.byte_range()))
 928            })
 929            .min_by_key(|(open_range, close_range)| close_range.end - open_range.start)
 930    }
 931
 932    fn diff(&self, new_text: Arc<str>, cx: &AppContext) -> Task<Diff> {
 933        // TODO: it would be nice to not allocate here.
 934        let old_text = self.text();
 935        let base_version = self.version();
 936        cx.background().spawn(async move {
 937            let changes = TextDiff::from_lines(old_text.as_str(), new_text.as_ref())
 938                .iter_all_changes()
 939                .map(|c| (c.tag(), c.value().len()))
 940                .collect::<Vec<_>>();
 941            Diff {
 942                base_version,
 943                new_text,
 944                changes,
 945            }
 946        })
 947    }
 948
 949    pub fn set_text_from_disk(&self, new_text: Arc<str>, cx: &mut ModelContext<Self>) -> Task<()> {
 950        cx.spawn(|this, mut cx| async move {
 951            let diff = this
 952                .read_with(&cx, |this, cx| this.diff(new_text, cx))
 953                .await;
 954
 955            this.update(&mut cx, |this, cx| {
 956                if this.apply_diff(diff, cx) {
 957                    this.saved_version = this.version.clone();
 958                }
 959            });
 960        })
 961    }
 962
 963    fn apply_diff(&mut self, diff: Diff, cx: &mut ModelContext<Self>) -> bool {
 964        if self.version == diff.base_version {
 965            self.start_transaction(None).unwrap();
 966            let mut offset = 0;
 967            for (tag, len) in diff.changes {
 968                let range = offset..(offset + len);
 969                match tag {
 970                    ChangeTag::Equal => offset += len,
 971                    ChangeTag::Delete => self.edit(Some(range), "", cx),
 972                    ChangeTag::Insert => {
 973                        self.edit(Some(offset..offset), &diff.new_text[range], cx);
 974                        offset += len;
 975                    }
 976                }
 977            }
 978            self.end_transaction(None, cx).unwrap();
 979            true
 980        } else {
 981            false
 982        }
 983    }
 984
 985    pub fn is_dirty(&self) -> bool {
 986        self.version > self.saved_version
 987            || self.file.as_ref().map_or(false, |file| file.is_deleted())
 988    }
 989
 990    pub fn has_conflict(&self) -> bool {
 991        self.version > self.saved_version
 992            && self
 993                .file
 994                .as_ref()
 995                .map_or(false, |file| file.mtime > self.saved_mtime)
 996    }
 997
 998    pub fn remote_id(&self) -> u64 {
 999        self.remote_id
1000    }
1001
1002    pub fn version(&self) -> time::Global {
1003        self.version.clone()
1004    }
1005
1006    pub fn text_summary(&self) -> TextSummary {
1007        self.visible_text.summary()
1008    }
1009
1010    pub fn len(&self) -> usize {
1011        self.content().len()
1012    }
1013
1014    pub fn line_len(&self, row: u32) -> u32 {
1015        let row_start_offset = Point::new(row, 0).to_offset(self);
1016        let row_end_offset = if row >= self.max_point().row {
1017            self.len()
1018        } else {
1019            Point::new(row + 1, 0).to_offset(self) - 1
1020        };
1021        (row_end_offset - row_start_offset) as u32
1022    }
1023
1024    pub fn max_point(&self) -> Point {
1025        self.visible_text.max_point()
1026    }
1027
1028    pub fn row_count(&self) -> u32 {
1029        self.max_point().row + 1
1030    }
1031
1032    pub fn text(&self) -> String {
1033        self.text_for_range(0..self.len()).collect()
1034    }
1035
1036    pub fn text_for_range<'a, T: ToOffset>(&'a self, range: Range<T>) -> Chunks<'a> {
1037        let start = range.start.to_offset(self);
1038        let end = range.end.to_offset(self);
1039        self.visible_text.chunks_in_range(start..end)
1040    }
1041
1042    pub fn chars(&self) -> impl Iterator<Item = char> + '_ {
1043        self.chars_at(0)
1044    }
1045
1046    pub fn chars_at<T: ToOffset>(&self, position: T) -> impl Iterator<Item = char> + '_ {
1047        let offset = position.to_offset(self);
1048        self.visible_text.chars_at(offset)
1049    }
1050
1051    pub fn edits_since<'a>(&'a self, since: time::Global) -> impl 'a + Iterator<Item = Edit> {
1052        let since_2 = since.clone();
1053        let cursor = self.fragments.filter(
1054            move |summary| summary.max_version.changed_since(&since_2),
1055            &None,
1056        );
1057
1058        Edits {
1059            visible_text: &self.visible_text,
1060            deleted_text: &self.deleted_text,
1061            cursor,
1062            undos: &self.undo_map,
1063            since,
1064            old_offset: 0,
1065            new_offset: 0,
1066            old_point: Point::zero(),
1067            new_point: Point::zero(),
1068        }
1069    }
1070
1071    pub fn deferred_ops_len(&self) -> usize {
1072        self.deferred_ops.len()
1073    }
1074
1075    pub fn start_transaction(&mut self, set_id: Option<SelectionSetId>) -> Result<()> {
1076        self.start_transaction_at(set_id, Instant::now())
1077    }
1078
1079    fn start_transaction_at(&mut self, set_id: Option<SelectionSetId>, now: Instant) -> Result<()> {
1080        let selections = if let Some(set_id) = set_id {
1081            let set = self
1082                .selections
1083                .get(&set_id)
1084                .ok_or_else(|| anyhow!("invalid selection set {:?}", set_id))?;
1085            Some((set_id, set.selections.clone()))
1086        } else {
1087            None
1088        };
1089        self.history
1090            .start_transaction(self.version.clone(), self.is_dirty(), selections, now);
1091        Ok(())
1092    }
1093
1094    pub fn end_transaction(
1095        &mut self,
1096        set_id: Option<SelectionSetId>,
1097        cx: &mut ModelContext<Self>,
1098    ) -> Result<()> {
1099        self.end_transaction_at(set_id, Instant::now(), cx)
1100    }
1101
1102    fn end_transaction_at(
1103        &mut self,
1104        set_id: Option<SelectionSetId>,
1105        now: Instant,
1106        cx: &mut ModelContext<Self>,
1107    ) -> Result<()> {
1108        let selections = if let Some(set_id) = set_id {
1109            let set = self
1110                .selections
1111                .get(&set_id)
1112                .ok_or_else(|| anyhow!("invalid selection set {:?}", set_id))?;
1113            Some((set_id, set.selections.clone()))
1114        } else {
1115            None
1116        };
1117
1118        if let Some(transaction) = self.history.end_transaction(selections, now) {
1119            let since = transaction.start.clone();
1120            let was_dirty = transaction.buffer_was_dirty;
1121            self.history.group();
1122
1123            cx.notify();
1124            if self.edits_since(since).next().is_some() {
1125                self.did_edit(was_dirty, cx);
1126                self.reparse(cx);
1127            }
1128        }
1129
1130        Ok(())
1131    }
1132
1133    pub fn edit<I, S, T>(&mut self, ranges_iter: I, new_text: T, cx: &mut ModelContext<Self>)
1134    where
1135        I: IntoIterator<Item = Range<S>>,
1136        S: ToOffset,
1137        T: Into<String>,
1138    {
1139        let new_text = new_text.into();
1140        let new_text = if new_text.len() > 0 {
1141            Some(new_text)
1142        } else {
1143            None
1144        };
1145        let has_new_text = new_text.is_some();
1146
1147        // Skip invalid ranges and coalesce contiguous ones.
1148        let mut ranges: Vec<Range<usize>> = Vec::new();
1149        for range in ranges_iter {
1150            let range = range.start.to_offset(&*self)..range.end.to_offset(&*self);
1151            if has_new_text || !range.is_empty() {
1152                if let Some(prev_range) = ranges.last_mut() {
1153                    if prev_range.end >= range.start {
1154                        prev_range.end = cmp::max(prev_range.end, range.end);
1155                    } else {
1156                        ranges.push(range);
1157                    }
1158                } else {
1159                    ranges.push(range);
1160                }
1161            }
1162        }
1163
1164        if !ranges.is_empty() {
1165            self.start_transaction_at(None, Instant::now()).unwrap();
1166            let timestamp = InsertionTimestamp {
1167                replica_id: self.replica_id,
1168                local: self.local_clock.tick().value,
1169                lamport: self.lamport_clock.tick().value,
1170            };
1171            let edit = self.apply_local_edit(&ranges, new_text, timestamp);
1172
1173            self.history.push(edit.clone());
1174            self.history.push_undo(edit.timestamp.local());
1175            self.last_edit = edit.timestamp.local();
1176            self.version.observe(edit.timestamp.local());
1177
1178            self.end_transaction_at(None, Instant::now(), cx).unwrap();
1179            self.send_operation(Operation::Edit(edit), cx);
1180        };
1181    }
1182
1183    fn did_edit(&self, was_dirty: bool, cx: &mut ModelContext<Self>) {
1184        cx.emit(Event::Edited);
1185        if !was_dirty {
1186            cx.emit(Event::Dirtied);
1187        }
1188    }
1189
1190    pub fn add_selection_set(
1191        &mut self,
1192        selections: impl Into<Arc<[Selection]>>,
1193        cx: &mut ModelContext<Self>,
1194    ) -> SelectionSetId {
1195        let selections = selections.into();
1196        let lamport_timestamp = self.lamport_clock.tick();
1197        self.selections.insert(
1198            lamport_timestamp,
1199            SelectionSet {
1200                selections: selections.clone(),
1201                active: false,
1202            },
1203        );
1204        cx.notify();
1205
1206        self.send_operation(
1207            Operation::UpdateSelections {
1208                set_id: lamport_timestamp,
1209                selections: Some(selections),
1210                lamport_timestamp,
1211            },
1212            cx,
1213        );
1214
1215        lamport_timestamp
1216    }
1217
1218    pub fn update_selection_set(
1219        &mut self,
1220        set_id: SelectionSetId,
1221        selections: impl Into<Arc<[Selection]>>,
1222        cx: &mut ModelContext<Self>,
1223    ) -> Result<()> {
1224        let selections = selections.into();
1225        let set = self
1226            .selections
1227            .get_mut(&set_id)
1228            .ok_or_else(|| anyhow!("invalid selection set id {:?}", set_id))?;
1229        set.selections = selections.clone();
1230        let lamport_timestamp = self.lamport_clock.tick();
1231        cx.notify();
1232        self.send_operation(
1233            Operation::UpdateSelections {
1234                set_id,
1235                selections: Some(selections),
1236                lamport_timestamp,
1237            },
1238            cx,
1239        );
1240        Ok(())
1241    }
1242
1243    pub fn set_active_selection_set(
1244        &mut self,
1245        set_id: Option<SelectionSetId>,
1246        cx: &mut ModelContext<Self>,
1247    ) -> Result<()> {
1248        if let Some(set_id) = set_id {
1249            assert_eq!(set_id.replica_id, self.replica_id());
1250        }
1251
1252        for (id, set) in &mut self.selections {
1253            if id.replica_id == self.local_clock.replica_id {
1254                if Some(*id) == set_id {
1255                    set.active = true;
1256                } else {
1257                    set.active = false;
1258                }
1259            }
1260        }
1261
1262        let lamport_timestamp = self.lamport_clock.tick();
1263        self.send_operation(
1264            Operation::SetActiveSelections {
1265                set_id,
1266                lamport_timestamp,
1267            },
1268            cx,
1269        );
1270        Ok(())
1271    }
1272
1273    pub fn remove_selection_set(
1274        &mut self,
1275        set_id: SelectionSetId,
1276        cx: &mut ModelContext<Self>,
1277    ) -> Result<()> {
1278        self.selections
1279            .remove(&set_id)
1280            .ok_or_else(|| anyhow!("invalid selection set id {:?}", set_id))?;
1281        let lamport_timestamp = self.lamport_clock.tick();
1282        cx.notify();
1283        self.send_operation(
1284            Operation::UpdateSelections {
1285                set_id,
1286                selections: None,
1287                lamport_timestamp,
1288            },
1289            cx,
1290        );
1291        Ok(())
1292    }
1293
1294    pub fn selection_set(&self, set_id: SelectionSetId) -> Result<&SelectionSet> {
1295        self.selections
1296            .get(&set_id)
1297            .ok_or_else(|| anyhow!("invalid selection set id {:?}", set_id))
1298    }
1299
1300    pub fn selection_sets(&self) -> impl Iterator<Item = (&SelectionSetId, &SelectionSet)> {
1301        self.selections.iter()
1302    }
1303
1304    pub fn apply_ops<I: IntoIterator<Item = Operation>>(
1305        &mut self,
1306        ops: I,
1307        cx: &mut ModelContext<Self>,
1308    ) -> Result<()> {
1309        let was_dirty = self.is_dirty();
1310        let old_version = self.version.clone();
1311
1312        let mut deferred_ops = Vec::new();
1313        for op in ops {
1314            if self.can_apply_op(&op) {
1315                self.apply_op(op)?;
1316            } else {
1317                self.deferred_replicas.insert(op.replica_id());
1318                deferred_ops.push(op);
1319            }
1320        }
1321        self.deferred_ops.insert(deferred_ops);
1322        self.flush_deferred_ops()?;
1323
1324        cx.notify();
1325        if self.edits_since(old_version).next().is_some() {
1326            self.did_edit(was_dirty, cx);
1327            self.reparse(cx);
1328        }
1329
1330        Ok(())
1331    }
1332
1333    fn apply_op(&mut self, op: Operation) -> Result<()> {
1334        match op {
1335            Operation::Edit(edit) => {
1336                if !self.version.observed(edit.timestamp.local()) {
1337                    self.apply_remote_edit(
1338                        &edit.version,
1339                        &edit.ranges,
1340                        edit.new_text.as_deref(),
1341                        edit.timestamp,
1342                    );
1343                    self.version.observe(edit.timestamp.local());
1344                    self.history.push(edit);
1345                }
1346            }
1347            Operation::Undo {
1348                undo,
1349                lamport_timestamp,
1350            } => {
1351                if !self.version.observed(undo.id) {
1352                    self.apply_undo(&undo)?;
1353                    self.version.observe(undo.id);
1354                    self.lamport_clock.observe(lamport_timestamp);
1355                }
1356            }
1357            Operation::UpdateSelections {
1358                set_id,
1359                selections,
1360                lamport_timestamp,
1361            } => {
1362                if let Some(selections) = selections {
1363                    if let Some(set) = self.selections.get_mut(&set_id) {
1364                        set.selections = selections;
1365                    } else {
1366                        self.selections.insert(
1367                            set_id,
1368                            SelectionSet {
1369                                selections,
1370                                active: false,
1371                            },
1372                        );
1373                    }
1374                } else {
1375                    self.selections.remove(&set_id);
1376                }
1377                self.lamport_clock.observe(lamport_timestamp);
1378            }
1379            Operation::SetActiveSelections {
1380                set_id,
1381                lamport_timestamp,
1382            } => {
1383                for (id, set) in &mut self.selections {
1384                    if id.replica_id == lamport_timestamp.replica_id {
1385                        if Some(*id) == set_id {
1386                            set.active = true;
1387                        } else {
1388                            set.active = false;
1389                        }
1390                    }
1391                }
1392                self.lamport_clock.observe(lamport_timestamp);
1393            }
1394        }
1395        Ok(())
1396    }
1397
1398    fn apply_remote_edit(
1399        &mut self,
1400        version: &time::Global,
1401        ranges: &[Range<usize>],
1402        new_text: Option<&str>,
1403        timestamp: InsertionTimestamp,
1404    ) {
1405        if ranges.is_empty() {
1406            return;
1407        }
1408
1409        let cx = Some(version.clone());
1410        let mut new_ropes =
1411            RopeBuilder::new(self.visible_text.cursor(0), self.deleted_text.cursor(0));
1412        let mut old_fragments = self.fragments.cursor::<VersionedOffset, VersionedOffset>();
1413        let mut new_fragments =
1414            old_fragments.slice(&VersionedOffset::Offset(ranges[0].start), Bias::Left, &cx);
1415        new_ropes.push_tree(new_fragments.summary().text);
1416
1417        let mut fragment_start = old_fragments.sum_start().offset();
1418        for range in ranges {
1419            let fragment_end = old_fragments.end(&cx).offset();
1420
1421            // If the current fragment ends before this range, then jump ahead to the first fragment
1422            // that extends past the start of this range, reusing any intervening fragments.
1423            if fragment_end < range.start {
1424                // If the current fragment has been partially consumed, then consume the rest of it
1425                // and advance to the next fragment before slicing.
1426                if fragment_start > old_fragments.sum_start().offset() {
1427                    if fragment_end > fragment_start {
1428                        let mut suffix = old_fragments.item().unwrap().clone();
1429                        suffix.len = fragment_end - fragment_start;
1430                        new_ropes.push_fragment(&suffix, suffix.visible);
1431                        new_fragments.push(suffix, &None);
1432                    }
1433                    old_fragments.next(&cx);
1434                }
1435
1436                let slice =
1437                    old_fragments.slice(&VersionedOffset::Offset(range.start), Bias::Left, &cx);
1438                new_ropes.push_tree(slice.summary().text);
1439                new_fragments.push_tree(slice, &None);
1440                fragment_start = old_fragments.sum_start().offset();
1441            }
1442
1443            // If we are at the end of a non-concurrent fragment, advance to the next one.
1444            let fragment_end = old_fragments.end(&cx).offset();
1445            if fragment_end == range.start && fragment_end > fragment_start {
1446                let mut fragment = old_fragments.item().unwrap().clone();
1447                fragment.len = fragment_end - fragment_start;
1448                new_ropes.push_fragment(&fragment, fragment.visible);
1449                new_fragments.push(fragment, &None);
1450                old_fragments.next(&cx);
1451                fragment_start = old_fragments.sum_start().offset();
1452            }
1453
1454            // Skip over insertions that are concurrent to this edit, but have a lower lamport
1455            // timestamp.
1456            while let Some(fragment) = old_fragments.item() {
1457                if fragment_start == range.start
1458                    && fragment.timestamp.lamport() > timestamp.lamport()
1459                {
1460                    new_ropes.push_fragment(fragment, fragment.visible);
1461                    new_fragments.push(fragment.clone(), &None);
1462                    old_fragments.next(&cx);
1463                    debug_assert_eq!(fragment_start, range.start);
1464                } else {
1465                    break;
1466                }
1467            }
1468            debug_assert!(fragment_start <= range.start);
1469
1470            // Preserve any portion of the current fragment that precedes this range.
1471            if fragment_start < range.start {
1472                let mut prefix = old_fragments.item().unwrap().clone();
1473                prefix.len = range.start - fragment_start;
1474                fragment_start = range.start;
1475                new_ropes.push_fragment(&prefix, prefix.visible);
1476                new_fragments.push(prefix, &None);
1477            }
1478
1479            // Insert the new text before any existing fragments within the range.
1480            if let Some(new_text) = new_text {
1481                new_ropes.push_str(new_text);
1482                new_fragments.push(
1483                    Fragment {
1484                        timestamp,
1485                        len: new_text.len(),
1486                        deletions: Default::default(),
1487                        max_undos: Default::default(),
1488                        visible: true,
1489                    },
1490                    &None,
1491                );
1492            }
1493
1494            // Advance through every fragment that intersects this range, marking the intersecting
1495            // portions as deleted.
1496            while fragment_start < range.end {
1497                let fragment = old_fragments.item().unwrap();
1498                let fragment_end = old_fragments.end(&cx).offset();
1499                let mut intersection = fragment.clone();
1500                let intersection_end = cmp::min(range.end, fragment_end);
1501                if fragment.was_visible(version, &self.undo_map) {
1502                    intersection.len = intersection_end - fragment_start;
1503                    intersection.deletions.insert(timestamp.local());
1504                    intersection.visible = false;
1505                }
1506                if intersection.len > 0 {
1507                    new_ropes.push_fragment(&intersection, fragment.visible);
1508                    new_fragments.push(intersection, &None);
1509                    fragment_start = intersection_end;
1510                }
1511                if fragment_end <= range.end {
1512                    old_fragments.next(&cx);
1513                }
1514            }
1515        }
1516
1517        // If the current fragment has been partially consumed, then consume the rest of it
1518        // and advance to the next fragment before slicing.
1519        if fragment_start > old_fragments.sum_start().offset() {
1520            let fragment_end = old_fragments.end(&cx).offset();
1521            if fragment_end > fragment_start {
1522                let mut suffix = old_fragments.item().unwrap().clone();
1523                suffix.len = fragment_end - fragment_start;
1524                new_ropes.push_fragment(&suffix, suffix.visible);
1525                new_fragments.push(suffix, &None);
1526            }
1527            old_fragments.next(&cx);
1528        }
1529
1530        let suffix = old_fragments.suffix(&cx);
1531        new_ropes.push_tree(suffix.summary().text);
1532        new_fragments.push_tree(suffix, &None);
1533        let (visible_text, deleted_text) = new_ropes.finish();
1534        drop(old_fragments);
1535
1536        self.fragments = new_fragments;
1537        self.visible_text = visible_text;
1538        self.deleted_text = deleted_text;
1539        self.local_clock.observe(timestamp.local());
1540        self.lamport_clock.observe(timestamp.lamport());
1541    }
1542
1543    #[cfg(not(test))]
1544    pub fn send_operation(&mut self, operation: Operation, cx: &mut ModelContext<Self>) {
1545        if let Some(file) = &self.file {
1546            file.buffer_updated(self.remote_id, operation, cx.as_mut());
1547        }
1548    }
1549
1550    #[cfg(test)]
1551    pub fn send_operation(&mut self, operation: Operation, _: &mut ModelContext<Self>) {
1552        self.operations.push(operation);
1553    }
1554
1555    pub fn remove_peer(&mut self, replica_id: ReplicaId, cx: &mut ModelContext<Self>) {
1556        self.selections
1557            .retain(|set_id, _| set_id.replica_id != replica_id);
1558        cx.notify();
1559    }
1560
1561    pub fn undo(&mut self, cx: &mut ModelContext<Self>) {
1562        let was_dirty = self.is_dirty();
1563        let old_version = self.version.clone();
1564
1565        if let Some(transaction) = self.history.pop_undo().cloned() {
1566            let selections = transaction.selections_before.clone();
1567            self.undo_or_redo(transaction, cx).unwrap();
1568            if let Some((set_id, selections)) = selections {
1569                let _ = self.update_selection_set(set_id, selections, cx);
1570            }
1571        }
1572
1573        cx.notify();
1574        if self.edits_since(old_version).next().is_some() {
1575            self.did_edit(was_dirty, cx);
1576            self.reparse(cx);
1577        }
1578    }
1579
1580    pub fn redo(&mut self, cx: &mut ModelContext<Self>) {
1581        let was_dirty = self.is_dirty();
1582        let old_version = self.version.clone();
1583
1584        if let Some(transaction) = self.history.pop_redo().cloned() {
1585            let selections = transaction.selections_after.clone();
1586            self.undo_or_redo(transaction, cx).unwrap();
1587            if let Some((set_id, selections)) = selections {
1588                let _ = self.update_selection_set(set_id, selections, cx);
1589            }
1590        }
1591
1592        cx.notify();
1593        if self.edits_since(old_version).next().is_some() {
1594            self.did_edit(was_dirty, cx);
1595            self.reparse(cx);
1596        }
1597    }
1598
1599    fn undo_or_redo(
1600        &mut self,
1601        transaction: Transaction,
1602        cx: &mut ModelContext<Self>,
1603    ) -> Result<()> {
1604        let mut counts = HashMap::default();
1605        for edit_id in transaction.edits {
1606            counts.insert(edit_id, self.undo_map.undo_count(edit_id) + 1);
1607        }
1608
1609        let undo = UndoOperation {
1610            id: self.local_clock.tick(),
1611            counts,
1612            ranges: transaction.ranges,
1613            version: transaction.start.clone(),
1614        };
1615        self.apply_undo(&undo)?;
1616        self.version.observe(undo.id);
1617
1618        let operation = Operation::Undo {
1619            undo,
1620            lamport_timestamp: self.lamport_clock.tick(),
1621        };
1622        self.send_operation(operation, cx);
1623
1624        Ok(())
1625    }
1626
1627    fn apply_undo(&mut self, undo: &UndoOperation) -> Result<()> {
1628        self.undo_map.insert(undo);
1629
1630        let mut cx = undo.version.clone();
1631        for edit_id in undo.counts.keys().copied() {
1632            cx.observe(edit_id);
1633        }
1634        let cx = Some(cx);
1635
1636        let mut old_fragments = self.fragments.cursor::<VersionedOffset, VersionedOffset>();
1637        let mut new_fragments = old_fragments.slice(
1638            &VersionedOffset::Offset(undo.ranges[0].start),
1639            Bias::Right,
1640            &cx,
1641        );
1642        let mut new_ropes =
1643            RopeBuilder::new(self.visible_text.cursor(0), self.deleted_text.cursor(0));
1644        new_ropes.push_tree(new_fragments.summary().text);
1645
1646        for range in &undo.ranges {
1647            let mut end_offset = old_fragments.end(&cx).offset();
1648
1649            if end_offset < range.start {
1650                let preceding_fragments =
1651                    old_fragments.slice(&VersionedOffset::Offset(range.start), Bias::Right, &cx);
1652                new_ropes.push_tree(preceding_fragments.summary().text);
1653                new_fragments.push_tree(preceding_fragments, &None);
1654            }
1655
1656            while end_offset <= range.end {
1657                if let Some(fragment) = old_fragments.item() {
1658                    let mut fragment = fragment.clone();
1659                    let fragment_was_visible = fragment.visible;
1660
1661                    if fragment.was_visible(&undo.version, &self.undo_map)
1662                        || undo.counts.contains_key(&fragment.timestamp.local())
1663                    {
1664                        fragment.visible = fragment.is_visible(&self.undo_map);
1665                        fragment.max_undos.observe(undo.id);
1666                    }
1667                    new_ropes.push_fragment(&fragment, fragment_was_visible);
1668                    new_fragments.push(fragment, &None);
1669
1670                    old_fragments.next(&cx);
1671                    if end_offset == old_fragments.end(&cx).offset() {
1672                        let unseen_fragments = old_fragments.slice(
1673                            &VersionedOffset::Offset(end_offset),
1674                            Bias::Right,
1675                            &cx,
1676                        );
1677                        new_ropes.push_tree(unseen_fragments.summary().text);
1678                        new_fragments.push_tree(unseen_fragments, &None);
1679                    }
1680                    end_offset = old_fragments.end(&cx).offset();
1681                } else {
1682                    break;
1683                }
1684            }
1685        }
1686
1687        let suffix = old_fragments.suffix(&cx);
1688        new_ropes.push_tree(suffix.summary().text);
1689        new_fragments.push_tree(suffix, &None);
1690
1691        drop(old_fragments);
1692        let (visible_text, deleted_text) = new_ropes.finish();
1693        self.fragments = new_fragments;
1694        self.visible_text = visible_text;
1695        self.deleted_text = deleted_text;
1696        Ok(())
1697    }
1698
1699    fn flush_deferred_ops(&mut self) -> Result<()> {
1700        self.deferred_replicas.clear();
1701        let mut deferred_ops = Vec::new();
1702        for op in self.deferred_ops.drain().cursor().cloned() {
1703            if self.can_apply_op(&op) {
1704                self.apply_op(op)?;
1705            } else {
1706                self.deferred_replicas.insert(op.replica_id());
1707                deferred_ops.push(op);
1708            }
1709        }
1710        self.deferred_ops.insert(deferred_ops);
1711        Ok(())
1712    }
1713
1714    fn can_apply_op(&self, op: &Operation) -> bool {
1715        if self.deferred_replicas.contains(&op.replica_id()) {
1716            false
1717        } else {
1718            match op {
1719                Operation::Edit(edit) => self.version >= edit.version,
1720                Operation::Undo { undo, .. } => self.version >= undo.version,
1721                Operation::UpdateSelections { selections, .. } => {
1722                    if let Some(selections) = selections {
1723                        selections.iter().all(|selection| {
1724                            let contains_start = self.version >= selection.start.version;
1725                            let contains_end = self.version >= selection.end.version;
1726                            contains_start && contains_end
1727                        })
1728                    } else {
1729                        true
1730                    }
1731                }
1732                Operation::SetActiveSelections { set_id, .. } => {
1733                    set_id.map_or(true, |set_id| self.selections.contains_key(&set_id))
1734                }
1735            }
1736        }
1737    }
1738
1739    fn apply_local_edit(
1740        &mut self,
1741        ranges: &[Range<usize>],
1742        new_text: Option<String>,
1743        timestamp: InsertionTimestamp,
1744    ) -> EditOperation {
1745        let mut edit = EditOperation {
1746            timestamp,
1747            version: self.version(),
1748            ranges: Vec::with_capacity(ranges.len()),
1749            new_text: None,
1750        };
1751
1752        let mut new_ropes =
1753            RopeBuilder::new(self.visible_text.cursor(0), self.deleted_text.cursor(0));
1754        let mut old_fragments = self.fragments.cursor::<usize, FragmentTextSummary>();
1755        let mut new_fragments = old_fragments.slice(&ranges[0].start, Bias::Right, &None);
1756        new_ropes.push_tree(new_fragments.summary().text);
1757
1758        let mut fragment_start = old_fragments.sum_start().visible;
1759        for range in ranges {
1760            let fragment_end = old_fragments.end(&None).visible;
1761
1762            // If the current fragment ends before this range, then jump ahead to the first fragment
1763            // that extends past the start of this range, reusing any intervening fragments.
1764            if fragment_end < range.start {
1765                // If the current fragment has been partially consumed, then consume the rest of it
1766                // and advance to the next fragment before slicing.
1767                if fragment_start > old_fragments.sum_start().visible {
1768                    if fragment_end > fragment_start {
1769                        let mut suffix = old_fragments.item().unwrap().clone();
1770                        suffix.len = fragment_end - fragment_start;
1771                        new_ropes.push_fragment(&suffix, suffix.visible);
1772                        new_fragments.push(suffix, &None);
1773                    }
1774                    old_fragments.next(&None);
1775                }
1776
1777                let slice = old_fragments.slice(&range.start, Bias::Right, &None);
1778                new_ropes.push_tree(slice.summary().text);
1779                new_fragments.push_tree(slice, &None);
1780                fragment_start = old_fragments.sum_start().visible;
1781            }
1782
1783            let full_range_start = range.start + old_fragments.sum_start().deleted;
1784
1785            // Preserve any portion of the current fragment that precedes this range.
1786            if fragment_start < range.start {
1787                let mut prefix = old_fragments.item().unwrap().clone();
1788                prefix.len = range.start - fragment_start;
1789                new_ropes.push_fragment(&prefix, prefix.visible);
1790                new_fragments.push(prefix, &None);
1791                fragment_start = range.start;
1792            }
1793
1794            // Insert the new text before any existing fragments within the range.
1795            if let Some(new_text) = new_text.as_deref() {
1796                new_ropes.push_str(new_text);
1797                new_fragments.push(
1798                    Fragment {
1799                        timestamp,
1800                        len: new_text.len(),
1801                        deletions: Default::default(),
1802                        max_undos: Default::default(),
1803                        visible: true,
1804                    },
1805                    &None,
1806                );
1807            }
1808
1809            // Advance through every fragment that intersects this range, marking the intersecting
1810            // portions as deleted.
1811            while fragment_start < range.end {
1812                let fragment = old_fragments.item().unwrap();
1813                let fragment_end = old_fragments.end(&None).visible;
1814                let mut intersection = fragment.clone();
1815                let intersection_end = cmp::min(range.end, fragment_end);
1816                if fragment.visible {
1817                    intersection.len = intersection_end - fragment_start;
1818                    intersection.deletions.insert(timestamp.local());
1819                    intersection.visible = false;
1820                }
1821                if intersection.len > 0 {
1822                    new_ropes.push_fragment(&intersection, fragment.visible);
1823                    new_fragments.push(intersection, &None);
1824                    fragment_start = intersection_end;
1825                }
1826                if fragment_end <= range.end {
1827                    old_fragments.next(&None);
1828                }
1829            }
1830
1831            let full_range_end = range.end + old_fragments.sum_start().deleted;
1832            edit.ranges.push(full_range_start..full_range_end);
1833        }
1834
1835        // If the current fragment has been partially consumed, then consume the rest of it
1836        // and advance to the next fragment before slicing.
1837        if fragment_start > old_fragments.sum_start().visible {
1838            let fragment_end = old_fragments.end(&None).visible;
1839            if fragment_end > fragment_start {
1840                let mut suffix = old_fragments.item().unwrap().clone();
1841                suffix.len = fragment_end - fragment_start;
1842                new_ropes.push_fragment(&suffix, suffix.visible);
1843                new_fragments.push(suffix, &None);
1844            }
1845            old_fragments.next(&None);
1846        }
1847
1848        let suffix = old_fragments.suffix(&None);
1849        new_ropes.push_tree(suffix.summary().text);
1850        new_fragments.push_tree(suffix, &None);
1851        let (visible_text, deleted_text) = new_ropes.finish();
1852        drop(old_fragments);
1853
1854        self.fragments = new_fragments;
1855        self.visible_text = visible_text;
1856        self.deleted_text = deleted_text;
1857        edit.new_text = new_text;
1858        edit
1859    }
1860
1861    fn content<'a>(&'a self) -> Content<'a> {
1862        self.into()
1863    }
1864
1865    pub fn text_summary_for_range(&self, range: Range<usize>) -> TextSummary {
1866        self.content().text_summary_for_range(range)
1867    }
1868
1869    pub fn anchor_before<T: ToOffset>(&self, position: T) -> Anchor {
1870        self.anchor_at(position, Bias::Left)
1871    }
1872
1873    pub fn anchor_after<T: ToOffset>(&self, position: T) -> Anchor {
1874        self.anchor_at(position, Bias::Right)
1875    }
1876
1877    pub fn anchor_at<T: ToOffset>(&self, position: T, bias: Bias) -> Anchor {
1878        self.content().anchor_at(position, bias)
1879    }
1880
1881    pub fn point_for_offset(&self, offset: usize) -> Result<Point> {
1882        self.content().point_for_offset(offset)
1883    }
1884
1885    pub fn clip_point(&self, point: Point, bias: Bias) -> Point {
1886        self.visible_text.clip_point(point, bias)
1887    }
1888
1889    pub fn clip_offset(&self, offset: usize, bias: Bias) -> usize {
1890        self.visible_text.clip_offset(offset, bias)
1891    }
1892}
1893
1894impl Clone for Buffer {
1895    fn clone(&self) -> Self {
1896        Self {
1897            fragments: self.fragments.clone(),
1898            visible_text: self.visible_text.clone(),
1899            deleted_text: self.deleted_text.clone(),
1900            version: self.version.clone(),
1901            saved_version: self.saved_version.clone(),
1902            saved_mtime: self.saved_mtime,
1903            last_edit: self.last_edit.clone(),
1904            undo_map: self.undo_map.clone(),
1905            history: self.history.clone(),
1906            selections: self.selections.clone(),
1907            deferred_ops: self.deferred_ops.clone(),
1908            file: self.file.clone(),
1909            language: self.language.clone(),
1910            syntax_tree: Mutex::new(self.syntax_tree.lock().clone()),
1911            is_parsing: false,
1912            deferred_replicas: self.deferred_replicas.clone(),
1913            replica_id: self.replica_id,
1914            remote_id: self.remote_id.clone(),
1915            local_clock: self.local_clock.clone(),
1916            lamport_clock: self.lamport_clock.clone(),
1917
1918            #[cfg(test)]
1919            operations: self.operations.clone(),
1920        }
1921    }
1922}
1923
1924pub struct Snapshot {
1925    visible_text: Rope,
1926    fragments: SumTree<Fragment>,
1927    version: time::Global,
1928    tree: Option<Tree>,
1929    language: Option<Arc<Language>>,
1930    query_cursor: QueryCursorHandle,
1931}
1932
1933impl Snapshot {
1934    pub fn len(&self) -> usize {
1935        self.visible_text.len()
1936    }
1937
1938    pub fn text(&self) -> Rope {
1939        self.visible_text.clone()
1940    }
1941
1942    pub fn text_summary(&self) -> TextSummary {
1943        self.visible_text.summary()
1944    }
1945
1946    pub fn max_point(&self) -> Point {
1947        self.visible_text.max_point()
1948    }
1949
1950    pub fn text_for_range(&self, range: Range<usize>) -> Chunks {
1951        self.visible_text.chunks_in_range(range)
1952    }
1953
1954    pub fn highlighted_text_for_range(&mut self, range: Range<usize>) -> HighlightedChunks {
1955        let chunks = self.visible_text.chunks_in_range(range.clone());
1956        if let Some((language, tree)) = self.language.as_ref().zip(self.tree.as_ref()) {
1957            let captures = self.query_cursor.set_byte_range(range.clone()).captures(
1958                &language.highlight_query,
1959                tree.root_node(),
1960                TextProvider(&self.visible_text),
1961            );
1962
1963            HighlightedChunks {
1964                range,
1965                chunks,
1966                highlights: Some(Highlights {
1967                    captures,
1968                    next_capture: None,
1969                    stack: Default::default(),
1970                    theme_mapping: language.theme_mapping(),
1971                }),
1972            }
1973        } else {
1974            HighlightedChunks {
1975                range,
1976                chunks,
1977                highlights: None,
1978            }
1979        }
1980    }
1981
1982    pub fn text_summary_for_range(&self, range: Range<usize>) -> TextSummary {
1983        self.content().text_summary_for_range(range)
1984    }
1985
1986    pub fn point_for_offset(&self, offset: usize) -> Result<Point> {
1987        self.content().point_for_offset(offset)
1988    }
1989
1990    pub fn clip_offset(&self, offset: usize, bias: Bias) -> usize {
1991        self.visible_text.clip_offset(offset, bias)
1992    }
1993
1994    pub fn clip_point(&self, point: Point, bias: Bias) -> Point {
1995        self.visible_text.clip_point(point, bias)
1996    }
1997
1998    pub fn to_offset(&self, point: Point) -> usize {
1999        self.visible_text.to_offset(point)
2000    }
2001
2002    pub fn to_point(&self, offset: usize) -> Point {
2003        self.visible_text.to_point(offset)
2004    }
2005
2006    pub fn anchor_before<T: ToOffset>(&self, position: T) -> Anchor {
2007        self.content().anchor_at(position, Bias::Left)
2008    }
2009
2010    pub fn anchor_after<T: ToOffset>(&self, position: T) -> Anchor {
2011        self.content().anchor_at(position, Bias::Right)
2012    }
2013
2014    fn content(&self) -> Content {
2015        self.into()
2016    }
2017}
2018
2019pub struct Content<'a> {
2020    visible_text: &'a Rope,
2021    fragments: &'a SumTree<Fragment>,
2022    version: &'a time::Global,
2023}
2024
2025impl<'a> From<&'a Snapshot> for Content<'a> {
2026    fn from(snapshot: &'a Snapshot) -> Self {
2027        Self {
2028            visible_text: &snapshot.visible_text,
2029            fragments: &snapshot.fragments,
2030            version: &snapshot.version,
2031        }
2032    }
2033}
2034
2035impl<'a> From<&'a Buffer> for Content<'a> {
2036    fn from(buffer: &'a Buffer) -> Self {
2037        Self {
2038            visible_text: &buffer.visible_text,
2039            fragments: &buffer.fragments,
2040            version: &buffer.version,
2041        }
2042    }
2043}
2044
2045impl<'a> From<&'a mut Buffer> for Content<'a> {
2046    fn from(buffer: &'a mut Buffer) -> Self {
2047        Self {
2048            visible_text: &buffer.visible_text,
2049            fragments: &buffer.fragments,
2050            version: &buffer.version,
2051        }
2052    }
2053}
2054
2055impl<'a> From<&'a Content<'a>> for Content<'a> {
2056    fn from(content: &'a Content) -> Self {
2057        Self {
2058            visible_text: &content.visible_text,
2059            fragments: &content.fragments,
2060            version: &content.version,
2061        }
2062    }
2063}
2064
2065impl<'a> Content<'a> {
2066    fn len(&self) -> usize {
2067        self.fragments.extent::<usize>(&None)
2068    }
2069
2070    fn summary_for_anchor(&self, anchor: &Anchor) -> TextSummary {
2071        let cx = Some(anchor.version.clone());
2072        let mut cursor = self.fragments.cursor::<VersionedOffset, usize>();
2073        cursor.seek(&VersionedOffset::Offset(anchor.offset), anchor.bias, &cx);
2074        let overshoot = if cursor.item().map_or(false, |fragment| fragment.visible) {
2075            anchor.offset - cursor.seek_start().offset()
2076        } else {
2077            0
2078        };
2079        self.text_summary_for_range(0..*cursor.sum_start() + overshoot)
2080    }
2081
2082    fn text_summary_for_range(&self, range: Range<usize>) -> TextSummary {
2083        self.visible_text.cursor(range.start).summary(range.end)
2084    }
2085
2086    fn anchor_at<T: ToOffset>(&self, position: T, bias: Bias) -> Anchor {
2087        let offset = position.to_offset(self);
2088        let max_offset = self.len();
2089        assert!(offset <= max_offset, "offset is out of range");
2090        let mut cursor = self.fragments.cursor::<usize, FragmentTextSummary>();
2091        cursor.seek(&offset, bias, &None);
2092        Anchor {
2093            offset: offset + cursor.sum_start().deleted,
2094            bias,
2095            version: self.version.clone(),
2096        }
2097    }
2098
2099    fn full_offset_for_anchor(&self, anchor: &Anchor) -> usize {
2100        let cx = Some(anchor.version.clone());
2101        let mut cursor = self
2102            .fragments
2103            .cursor::<VersionedOffset, FragmentTextSummary>();
2104        cursor.seek(&VersionedOffset::Offset(anchor.offset), anchor.bias, &cx);
2105        let overshoot = if cursor.item().is_some() {
2106            anchor.offset - cursor.seek_start().offset()
2107        } else {
2108            0
2109        };
2110        let summary = cursor.sum_start();
2111        summary.visible + summary.deleted + overshoot
2112    }
2113
2114    fn point_for_offset(&self, offset: usize) -> Result<Point> {
2115        if offset <= self.len() {
2116            Ok(self.text_summary_for_range(0..offset).lines)
2117        } else {
2118            Err(anyhow!("offset out of bounds"))
2119        }
2120    }
2121}
2122
2123struct RopeBuilder<'a> {
2124    old_visible_cursor: rope::Cursor<'a>,
2125    old_deleted_cursor: rope::Cursor<'a>,
2126    new_visible: Rope,
2127    new_deleted: Rope,
2128}
2129
2130impl<'a> RopeBuilder<'a> {
2131    fn new(old_visible_cursor: rope::Cursor<'a>, old_deleted_cursor: rope::Cursor<'a>) -> Self {
2132        Self {
2133            old_visible_cursor,
2134            old_deleted_cursor,
2135            new_visible: Rope::new(),
2136            new_deleted: Rope::new(),
2137        }
2138    }
2139
2140    fn push_tree(&mut self, len: FragmentTextSummary) {
2141        self.push(len.visible, true, true);
2142        self.push(len.deleted, false, false);
2143    }
2144
2145    fn push_fragment(&mut self, fragment: &Fragment, was_visible: bool) {
2146        debug_assert!(fragment.len > 0);
2147        self.push(fragment.len, was_visible, fragment.visible)
2148    }
2149
2150    fn push(&mut self, len: usize, was_visible: bool, is_visible: bool) {
2151        let text = if was_visible {
2152            self.old_visible_cursor
2153                .slice(self.old_visible_cursor.offset() + len)
2154        } else {
2155            self.old_deleted_cursor
2156                .slice(self.old_deleted_cursor.offset() + len)
2157        };
2158        if is_visible {
2159            self.new_visible.append(text);
2160        } else {
2161            self.new_deleted.append(text);
2162        }
2163    }
2164
2165    fn push_str(&mut self, text: &str) {
2166        self.new_visible.push(text);
2167    }
2168
2169    fn finish(mut self) -> (Rope, Rope) {
2170        self.new_visible.append(self.old_visible_cursor.suffix());
2171        self.new_deleted.append(self.old_deleted_cursor.suffix());
2172        (self.new_visible, self.new_deleted)
2173    }
2174}
2175
2176#[derive(Clone, Debug, Eq, PartialEq)]
2177pub enum Event {
2178    Edited,
2179    Dirtied,
2180    Saved,
2181    FileHandleChanged,
2182    Reloaded,
2183    Reparsed,
2184}
2185
2186impl Entity for Buffer {
2187    type Event = Event;
2188
2189    fn release(&mut self, cx: &mut gpui::MutableAppContext) {
2190        if let Some(file) = self.file.as_ref() {
2191            file.buffer_removed(self.remote_id, cx);
2192        }
2193    }
2194}
2195
2196impl<'a, F: Fn(&FragmentSummary) -> bool> Iterator for Edits<'a, F> {
2197    type Item = Edit;
2198
2199    fn next(&mut self) -> Option<Self::Item> {
2200        let mut change: Option<Edit> = None;
2201
2202        while let Some(fragment) = self.cursor.item() {
2203            let bytes = self.cursor.start().visible - self.new_offset;
2204            let lines = self.visible_text.to_point(self.cursor.start().visible) - self.new_point;
2205            self.old_offset += bytes;
2206            self.old_point += &lines;
2207            self.new_offset += bytes;
2208            self.new_point += &lines;
2209
2210            if !fragment.was_visible(&self.since, &self.undos) && fragment.visible {
2211                let fragment_lines =
2212                    self.visible_text.to_point(self.new_offset + fragment.len) - self.new_point;
2213                if let Some(ref mut change) = change {
2214                    if change.new_bytes.end == self.new_offset {
2215                        change.new_bytes.end += fragment.len;
2216                    } else {
2217                        break;
2218                    }
2219                } else {
2220                    change = Some(Edit {
2221                        old_bytes: self.old_offset..self.old_offset,
2222                        new_bytes: self.new_offset..self.new_offset + fragment.len,
2223                        old_lines: self.old_point..self.old_point,
2224                    });
2225                }
2226
2227                self.new_offset += fragment.len;
2228                self.new_point += &fragment_lines;
2229            } else if fragment.was_visible(&self.since, &self.undos) && !fragment.visible {
2230                let deleted_start = self.cursor.start().deleted;
2231                let fragment_lines = self.deleted_text.to_point(deleted_start + fragment.len)
2232                    - self.deleted_text.to_point(deleted_start);
2233                if let Some(ref mut change) = change {
2234                    if change.new_bytes.end == self.new_offset {
2235                        change.old_bytes.end += fragment.len;
2236                        change.old_lines.end += &fragment_lines;
2237                    } else {
2238                        break;
2239                    }
2240                } else {
2241                    change = Some(Edit {
2242                        old_bytes: self.old_offset..self.old_offset + fragment.len,
2243                        new_bytes: self.new_offset..self.new_offset,
2244                        old_lines: self.old_point..self.old_point + &fragment_lines,
2245                    });
2246                }
2247
2248                self.old_offset += fragment.len;
2249                self.old_point += &fragment_lines;
2250            }
2251
2252            self.cursor.next(&None);
2253        }
2254
2255        change
2256    }
2257}
2258
2259struct ByteChunks<'a>(rope::Chunks<'a>);
2260
2261impl<'a> Iterator for ByteChunks<'a> {
2262    type Item = &'a [u8];
2263
2264    fn next(&mut self) -> Option<Self::Item> {
2265        self.0.next().map(str::as_bytes)
2266    }
2267}
2268
2269struct TextProvider<'a>(&'a Rope);
2270
2271impl<'a> tree_sitter::TextProvider<'a> for TextProvider<'a> {
2272    type I = ByteChunks<'a>;
2273
2274    fn text(&mut self, node: tree_sitter::Node) -> Self::I {
2275        ByteChunks(self.0.chunks_in_range(node.byte_range()))
2276    }
2277}
2278
2279struct Highlights<'a> {
2280    captures: tree_sitter::QueryCaptures<'a, 'a, TextProvider<'a>>,
2281    next_capture: Option<(tree_sitter::QueryMatch<'a, 'a>, usize)>,
2282    stack: Vec<(usize, StyleId)>,
2283    theme_mapping: ThemeMap,
2284}
2285
2286pub struct HighlightedChunks<'a> {
2287    range: Range<usize>,
2288    chunks: Chunks<'a>,
2289    highlights: Option<Highlights<'a>>,
2290}
2291
2292impl<'a> HighlightedChunks<'a> {
2293    pub fn seek(&mut self, offset: usize) {
2294        self.range.start = offset;
2295        self.chunks.seek(self.range.start);
2296        if let Some(highlights) = self.highlights.as_mut() {
2297            highlights
2298                .stack
2299                .retain(|(end_offset, _)| *end_offset > offset);
2300            if let Some((mat, capture_ix)) = &highlights.next_capture {
2301                let capture = mat.captures[*capture_ix as usize];
2302                if offset >= capture.node.start_byte() {
2303                    let next_capture_end = capture.node.end_byte();
2304                    if offset < next_capture_end {
2305                        highlights.stack.push((
2306                            next_capture_end,
2307                            highlights.theme_mapping.get(capture.index),
2308                        ));
2309                    }
2310                    highlights.next_capture.take();
2311                }
2312            }
2313            highlights.captures.set_byte_range(self.range.clone());
2314        }
2315    }
2316
2317    pub fn offset(&self) -> usize {
2318        self.range.start
2319    }
2320}
2321
2322impl<'a> Iterator for HighlightedChunks<'a> {
2323    type Item = (&'a str, StyleId);
2324
2325    fn next(&mut self) -> Option<Self::Item> {
2326        let mut next_capture_start = usize::MAX;
2327
2328        if let Some(highlights) = self.highlights.as_mut() {
2329            while let Some((parent_capture_end, _)) = highlights.stack.last() {
2330                if *parent_capture_end <= self.range.start {
2331                    highlights.stack.pop();
2332                } else {
2333                    break;
2334                }
2335            }
2336
2337            if highlights.next_capture.is_none() {
2338                highlights.next_capture = highlights.captures.next();
2339            }
2340
2341            while let Some((mat, capture_ix)) = highlights.next_capture.as_ref() {
2342                let capture = mat.captures[*capture_ix as usize];
2343                if self.range.start < capture.node.start_byte() {
2344                    next_capture_start = capture.node.start_byte();
2345                    break;
2346                } else {
2347                    let style_id = highlights.theme_mapping.get(capture.index);
2348                    highlights.stack.push((capture.node.end_byte(), style_id));
2349                    highlights.next_capture = highlights.captures.next();
2350                }
2351            }
2352        }
2353
2354        if let Some(chunk) = self.chunks.peek() {
2355            let chunk_start = self.range.start;
2356            let mut chunk_end = (self.chunks.offset() + chunk.len()).min(next_capture_start);
2357            let mut style_id = StyleId::default();
2358            if let Some((parent_capture_end, parent_style_id)) =
2359                self.highlights.as_ref().and_then(|h| h.stack.last())
2360            {
2361                chunk_end = chunk_end.min(*parent_capture_end);
2362                style_id = *parent_style_id;
2363            }
2364
2365            let slice =
2366                &chunk[chunk_start - self.chunks.offset()..chunk_end - self.chunks.offset()];
2367            self.range.start = chunk_end;
2368            if self.range.start == self.chunks.offset() + chunk.len() {
2369                self.chunks.next().unwrap();
2370            }
2371
2372            Some((slice, style_id))
2373        } else {
2374            None
2375        }
2376    }
2377}
2378
2379impl Fragment {
2380    fn is_visible(&self, undos: &UndoMap) -> bool {
2381        !undos.is_undone(self.timestamp.local())
2382            && self.deletions.iter().all(|d| undos.is_undone(*d))
2383    }
2384
2385    fn was_visible(&self, version: &time::Global, undos: &UndoMap) -> bool {
2386        (version.observed(self.timestamp.local())
2387            && !undos.was_undone(self.timestamp.local(), version))
2388            && self
2389                .deletions
2390                .iter()
2391                .all(|d| !version.observed(*d) || undos.was_undone(*d, version))
2392    }
2393}
2394
2395impl sum_tree::Item for Fragment {
2396    type Summary = FragmentSummary;
2397
2398    fn summary(&self) -> Self::Summary {
2399        let mut max_version = time::Global::new();
2400        max_version.observe(self.timestamp.local());
2401        for deletion in &self.deletions {
2402            max_version.observe(*deletion);
2403        }
2404        max_version.join(&self.max_undos);
2405
2406        let mut min_insertion_version = time::Global::new();
2407        min_insertion_version.observe(self.timestamp.local());
2408        let max_insertion_version = min_insertion_version.clone();
2409        if self.visible {
2410            FragmentSummary {
2411                text: FragmentTextSummary {
2412                    visible: self.len,
2413                    deleted: 0,
2414                },
2415                max_version,
2416                min_insertion_version,
2417                max_insertion_version,
2418            }
2419        } else {
2420            FragmentSummary {
2421                text: FragmentTextSummary {
2422                    visible: 0,
2423                    deleted: self.len,
2424                },
2425                max_version,
2426                min_insertion_version,
2427                max_insertion_version,
2428            }
2429        }
2430    }
2431}
2432
2433impl sum_tree::Summary for FragmentSummary {
2434    type Context = Option<time::Global>;
2435
2436    fn add_summary(&mut self, other: &Self, _: &Self::Context) {
2437        self.text.visible += &other.text.visible;
2438        self.text.deleted += &other.text.deleted;
2439        self.max_version.join(&other.max_version);
2440        self.min_insertion_version
2441            .meet(&other.min_insertion_version);
2442        self.max_insertion_version
2443            .join(&other.max_insertion_version);
2444    }
2445}
2446
2447impl Default for FragmentSummary {
2448    fn default() -> Self {
2449        FragmentSummary {
2450            text: FragmentTextSummary::default(),
2451            max_version: time::Global::new(),
2452            min_insertion_version: time::Global::new(),
2453            max_insertion_version: time::Global::new(),
2454        }
2455    }
2456}
2457
2458impl<'a> sum_tree::Dimension<'a, FragmentSummary> for usize {
2459    fn add_summary(&mut self, summary: &FragmentSummary, _: &Option<time::Global>) {
2460        *self += summary.text.visible;
2461    }
2462}
2463
2464#[derive(Copy, Clone, Debug, Eq, PartialEq)]
2465enum VersionedOffset {
2466    Offset(usize),
2467    InvalidVersion,
2468}
2469
2470impl VersionedOffset {
2471    fn offset(&self) -> usize {
2472        if let Self::Offset(offset) = self {
2473            *offset
2474        } else {
2475            panic!("invalid version")
2476        }
2477    }
2478}
2479
2480impl Default for VersionedOffset {
2481    fn default() -> Self {
2482        Self::Offset(0)
2483    }
2484}
2485
2486impl<'a> sum_tree::Dimension<'a, FragmentSummary> for VersionedOffset {
2487    fn add_summary(&mut self, summary: &'a FragmentSummary, cx: &Option<time::Global>) {
2488        if let Self::Offset(offset) = self {
2489            let version = cx.as_ref().unwrap();
2490            if *version >= summary.max_insertion_version {
2491                *offset += summary.text.visible + summary.text.deleted;
2492            } else if !summary
2493                .min_insertion_version
2494                .iter()
2495                .all(|t| !version.observed(*t))
2496            {
2497                *self = Self::InvalidVersion;
2498            }
2499        }
2500    }
2501}
2502
2503impl<'a> sum_tree::SeekDimension<'a, FragmentSummary> for VersionedOffset {
2504    fn cmp(&self, other: &Self, _: &Option<time::Global>) -> cmp::Ordering {
2505        match (self, other) {
2506            (Self::Offset(a), Self::Offset(b)) => Ord::cmp(a, b),
2507            (Self::Offset(_), Self::InvalidVersion) => cmp::Ordering::Less,
2508            (Self::InvalidVersion, _) => unreachable!(),
2509        }
2510    }
2511}
2512
2513impl Operation {
2514    fn replica_id(&self) -> ReplicaId {
2515        self.lamport_timestamp().replica_id
2516    }
2517
2518    fn lamport_timestamp(&self) -> time::Lamport {
2519        match self {
2520            Operation::Edit(edit) => edit.timestamp.lamport(),
2521            Operation::Undo {
2522                lamport_timestamp, ..
2523            } => *lamport_timestamp,
2524            Operation::UpdateSelections {
2525                lamport_timestamp, ..
2526            } => *lamport_timestamp,
2527            Operation::SetActiveSelections {
2528                lamport_timestamp, ..
2529            } => *lamport_timestamp,
2530        }
2531    }
2532
2533    pub fn is_edit(&self) -> bool {
2534        match self {
2535            Operation::Edit { .. } => true,
2536            _ => false,
2537        }
2538    }
2539}
2540
2541impl<'a> Into<proto::Operation> for &'a Operation {
2542    fn into(self) -> proto::Operation {
2543        proto::Operation {
2544            variant: Some(match self {
2545                Operation::Edit(edit) => proto::operation::Variant::Edit(edit.into()),
2546                Operation::Undo {
2547                    undo,
2548                    lamport_timestamp,
2549                } => proto::operation::Variant::Undo(proto::operation::Undo {
2550                    replica_id: undo.id.replica_id as u32,
2551                    local_timestamp: undo.id.value,
2552                    lamport_timestamp: lamport_timestamp.value,
2553                    ranges: undo
2554                        .ranges
2555                        .iter()
2556                        .map(|r| proto::Range {
2557                            start: r.start as u64,
2558                            end: r.end as u64,
2559                        })
2560                        .collect(),
2561                    counts: undo
2562                        .counts
2563                        .iter()
2564                        .map(|(edit_id, count)| proto::operation::UndoCount {
2565                            replica_id: edit_id.replica_id as u32,
2566                            local_timestamp: edit_id.value,
2567                            count: *count,
2568                        })
2569                        .collect(),
2570                    version: From::from(&undo.version),
2571                }),
2572                Operation::UpdateSelections {
2573                    set_id,
2574                    selections,
2575                    lamport_timestamp,
2576                } => proto::operation::Variant::UpdateSelections(
2577                    proto::operation::UpdateSelections {
2578                        replica_id: set_id.replica_id as u32,
2579                        local_timestamp: set_id.value,
2580                        lamport_timestamp: lamport_timestamp.value,
2581                        set: selections.as_ref().map(|selections| proto::SelectionSet {
2582                            selections: selections.iter().map(Into::into).collect(),
2583                        }),
2584                    },
2585                ),
2586                Operation::SetActiveSelections {
2587                    set_id,
2588                    lamport_timestamp,
2589                } => proto::operation::Variant::SetActiveSelections(
2590                    proto::operation::SetActiveSelections {
2591                        replica_id: lamport_timestamp.replica_id as u32,
2592                        local_timestamp: set_id.map(|set_id| set_id.value),
2593                        lamport_timestamp: lamport_timestamp.value,
2594                    },
2595                ),
2596            }),
2597        }
2598    }
2599}
2600
2601impl<'a> Into<proto::operation::Edit> for &'a EditOperation {
2602    fn into(self) -> proto::operation::Edit {
2603        let ranges = self
2604            .ranges
2605            .iter()
2606            .map(|range| proto::Range {
2607                start: range.start as u64,
2608                end: range.end as u64,
2609            })
2610            .collect();
2611        proto::operation::Edit {
2612            replica_id: self.timestamp.replica_id as u32,
2613            local_timestamp: self.timestamp.local,
2614            lamport_timestamp: self.timestamp.lamport,
2615            version: From::from(&self.version),
2616            ranges,
2617            new_text: self.new_text.clone(),
2618        }
2619    }
2620}
2621
2622impl<'a> Into<proto::Anchor> for &'a Anchor {
2623    fn into(self) -> proto::Anchor {
2624        proto::Anchor {
2625            version: self
2626                .version
2627                .iter()
2628                .map(|entry| proto::VectorClockEntry {
2629                    replica_id: entry.replica_id as u32,
2630                    timestamp: entry.value,
2631                })
2632                .collect(),
2633            offset: self.offset as u64,
2634            bias: match self.bias {
2635                Bias::Left => proto::anchor::Bias::Left as i32,
2636                Bias::Right => proto::anchor::Bias::Right as i32,
2637            },
2638        }
2639    }
2640}
2641
2642impl<'a> Into<proto::Selection> for &'a Selection {
2643    fn into(self) -> proto::Selection {
2644        proto::Selection {
2645            id: self.id as u64,
2646            start: Some((&self.start).into()),
2647            end: Some((&self.end).into()),
2648            reversed: self.reversed,
2649        }
2650    }
2651}
2652
2653impl TryFrom<proto::Operation> for Operation {
2654    type Error = anyhow::Error;
2655
2656    fn try_from(message: proto::Operation) -> Result<Self, Self::Error> {
2657        Ok(
2658            match message
2659                .variant
2660                .ok_or_else(|| anyhow!("missing operation variant"))?
2661            {
2662                proto::operation::Variant::Edit(edit) => Operation::Edit(edit.into()),
2663                proto::operation::Variant::Undo(undo) => Operation::Undo {
2664                    lamport_timestamp: time::Lamport {
2665                        replica_id: undo.replica_id as ReplicaId,
2666                        value: undo.lamport_timestamp,
2667                    },
2668                    undo: UndoOperation {
2669                        id: time::Local {
2670                            replica_id: undo.replica_id as ReplicaId,
2671                            value: undo.local_timestamp,
2672                        },
2673                        counts: undo
2674                            .counts
2675                            .into_iter()
2676                            .map(|c| {
2677                                (
2678                                    time::Local {
2679                                        replica_id: c.replica_id as ReplicaId,
2680                                        value: c.local_timestamp,
2681                                    },
2682                                    c.count,
2683                                )
2684                            })
2685                            .collect(),
2686                        ranges: undo
2687                            .ranges
2688                            .into_iter()
2689                            .map(|r| r.start as usize..r.end as usize)
2690                            .collect(),
2691                        version: undo.version.into(),
2692                    },
2693                },
2694                proto::operation::Variant::UpdateSelections(message) => {
2695                    let selections: Option<Vec<Selection>> = if let Some(set) = message.set {
2696                        Some(
2697                            set.selections
2698                                .into_iter()
2699                                .map(TryFrom::try_from)
2700                                .collect::<Result<_, _>>()?,
2701                        )
2702                    } else {
2703                        None
2704                    };
2705                    Operation::UpdateSelections {
2706                        set_id: time::Lamport {
2707                            replica_id: message.replica_id as ReplicaId,
2708                            value: message.local_timestamp,
2709                        },
2710                        lamport_timestamp: time::Lamport {
2711                            replica_id: message.replica_id as ReplicaId,
2712                            value: message.lamport_timestamp,
2713                        },
2714                        selections: selections.map(Arc::from),
2715                    }
2716                }
2717                proto::operation::Variant::SetActiveSelections(message) => {
2718                    Operation::SetActiveSelections {
2719                        set_id: message.local_timestamp.map(|value| time::Lamport {
2720                            replica_id: message.replica_id as ReplicaId,
2721                            value,
2722                        }),
2723                        lamport_timestamp: time::Lamport {
2724                            replica_id: message.replica_id as ReplicaId,
2725                            value: message.lamport_timestamp,
2726                        },
2727                    }
2728                }
2729            },
2730        )
2731    }
2732}
2733
2734impl From<proto::operation::Edit> for EditOperation {
2735    fn from(edit: proto::operation::Edit) -> Self {
2736        let ranges = edit
2737            .ranges
2738            .into_iter()
2739            .map(|range| range.start as usize..range.end as usize)
2740            .collect();
2741        EditOperation {
2742            timestamp: InsertionTimestamp {
2743                replica_id: edit.replica_id as ReplicaId,
2744                local: edit.local_timestamp,
2745                lamport: edit.lamport_timestamp,
2746            },
2747            version: edit.version.into(),
2748            ranges,
2749            new_text: edit.new_text,
2750        }
2751    }
2752}
2753
2754impl TryFrom<proto::Anchor> for Anchor {
2755    type Error = anyhow::Error;
2756
2757    fn try_from(message: proto::Anchor) -> Result<Self, Self::Error> {
2758        let mut version = time::Global::new();
2759        for entry in message.version {
2760            version.observe(time::Local {
2761                replica_id: entry.replica_id as ReplicaId,
2762                value: entry.timestamp,
2763            });
2764        }
2765
2766        Ok(Self {
2767            offset: message.offset as usize,
2768            bias: if message.bias == proto::anchor::Bias::Left as i32 {
2769                Bias::Left
2770            } else if message.bias == proto::anchor::Bias::Right as i32 {
2771                Bias::Right
2772            } else {
2773                Err(anyhow!("invalid anchor bias {}", message.bias))?
2774            },
2775            version,
2776        })
2777    }
2778}
2779
2780impl TryFrom<proto::Selection> for Selection {
2781    type Error = anyhow::Error;
2782
2783    fn try_from(selection: proto::Selection) -> Result<Self, Self::Error> {
2784        Ok(Selection {
2785            id: selection.id as usize,
2786            start: selection
2787                .start
2788                .ok_or_else(|| anyhow!("missing selection start"))?
2789                .try_into()?,
2790            end: selection
2791                .end
2792                .ok_or_else(|| anyhow!("missing selection end"))?
2793                .try_into()?,
2794            reversed: selection.reversed,
2795            goal: SelectionGoal::None,
2796        })
2797    }
2798}
2799
2800impl operation_queue::Operation for Operation {
2801    fn timestamp(&self) -> time::Lamport {
2802        self.lamport_timestamp()
2803    }
2804}
2805
2806pub trait ToOffset {
2807    fn to_offset<'a>(&self, content: impl Into<Content<'a>>) -> usize;
2808}
2809
2810impl ToOffset for Point {
2811    fn to_offset<'a>(&self, content: impl Into<Content<'a>>) -> usize {
2812        content.into().visible_text.to_offset(*self)
2813    }
2814}
2815
2816impl ToOffset for usize {
2817    fn to_offset<'a>(&self, _: impl Into<Content<'a>>) -> usize {
2818        *self
2819    }
2820}
2821
2822impl ToOffset for Anchor {
2823    fn to_offset<'a>(&self, content: impl Into<Content<'a>>) -> usize {
2824        content.into().summary_for_anchor(self).bytes
2825    }
2826}
2827
2828impl<'a> ToOffset for &'a Anchor {
2829    fn to_offset<'b>(&self, content: impl Into<Content<'b>>) -> usize {
2830        content.into().summary_for_anchor(self).bytes
2831    }
2832}
2833
2834pub trait ToPoint {
2835    fn to_point<'a>(&self, content: impl Into<Content<'a>>) -> Point;
2836}
2837
2838impl ToPoint for Anchor {
2839    fn to_point<'a>(&self, content: impl Into<Content<'a>>) -> Point {
2840        content.into().summary_for_anchor(self).lines
2841    }
2842}
2843
2844impl ToPoint for usize {
2845    fn to_point<'a>(&self, content: impl Into<Content<'a>>) -> Point {
2846        content.into().visible_text.to_point(*self)
2847    }
2848}
2849
2850#[cfg(test)]
2851mod tests {
2852    use super::*;
2853    use crate::{
2854        fs::RealFs,
2855        test::{build_app_state, temp_tree},
2856        util::RandomCharIter,
2857        worktree::{Worktree, WorktreeHandle as _},
2858    };
2859    use gpui::ModelHandle;
2860    use rand::prelude::*;
2861    use serde_json::json;
2862    use std::{
2863        cell::RefCell,
2864        cmp::Ordering,
2865        env, fs, mem,
2866        path::Path,
2867        rc::Rc,
2868        sync::atomic::{self, AtomicUsize},
2869    };
2870
2871    #[gpui::test]
2872    fn test_edit(cx: &mut gpui::MutableAppContext) {
2873        cx.add_model(|cx| {
2874            let mut buffer = Buffer::new(0, "abc", cx);
2875            assert_eq!(buffer.text(), "abc");
2876            buffer.edit(vec![3..3], "def", cx);
2877            assert_eq!(buffer.text(), "abcdef");
2878            buffer.edit(vec![0..0], "ghi", cx);
2879            assert_eq!(buffer.text(), "ghiabcdef");
2880            buffer.edit(vec![5..5], "jkl", cx);
2881            assert_eq!(buffer.text(), "ghiabjklcdef");
2882            buffer.edit(vec![6..7], "", cx);
2883            assert_eq!(buffer.text(), "ghiabjlcdef");
2884            buffer.edit(vec![4..9], "mno", cx);
2885            assert_eq!(buffer.text(), "ghiamnoef");
2886            buffer
2887        });
2888    }
2889
2890    #[gpui::test]
2891    fn test_edit_events(cx: &mut gpui::MutableAppContext) {
2892        let mut now = Instant::now();
2893        let buffer_1_events = Rc::new(RefCell::new(Vec::new()));
2894        let buffer_2_events = Rc::new(RefCell::new(Vec::new()));
2895
2896        let buffer1 = cx.add_model(|cx| Buffer::new(0, "abcdef", cx));
2897        let buffer2 = cx.add_model(|cx| Buffer::new(1, "abcdef", cx));
2898        let buffer_ops = buffer1.update(cx, |buffer, cx| {
2899            let buffer_1_events = buffer_1_events.clone();
2900            cx.subscribe(&buffer1, move |_, event, _| {
2901                buffer_1_events.borrow_mut().push(event.clone())
2902            });
2903            let buffer_2_events = buffer_2_events.clone();
2904            cx.subscribe(&buffer2, move |_, event, _| {
2905                buffer_2_events.borrow_mut().push(event.clone())
2906            });
2907
2908            // An edit emits an edited event, followed by a dirtied event,
2909            // since the buffer was previously in a clean state.
2910            buffer.edit(Some(2..4), "XYZ", cx);
2911
2912            // An empty transaction does not emit any events.
2913            buffer.start_transaction(None).unwrap();
2914            buffer.end_transaction(None, cx).unwrap();
2915
2916            // A transaction containing two edits emits one edited event.
2917            now += Duration::from_secs(1);
2918            buffer.start_transaction_at(None, now).unwrap();
2919            buffer.edit(Some(5..5), "u", cx);
2920            buffer.edit(Some(6..6), "w", cx);
2921            buffer.end_transaction_at(None, now, cx).unwrap();
2922
2923            // Undoing a transaction emits one edited event.
2924            buffer.undo(cx);
2925
2926            buffer.operations.clone()
2927        });
2928
2929        // Incorporating a set of remote ops emits a single edited event,
2930        // followed by a dirtied event.
2931        buffer2.update(cx, |buffer, cx| {
2932            buffer.apply_ops(buffer_ops, cx).unwrap();
2933        });
2934
2935        let buffer_1_events = buffer_1_events.borrow();
2936        assert_eq!(
2937            *buffer_1_events,
2938            vec![Event::Edited, Event::Dirtied, Event::Edited, Event::Edited]
2939        );
2940
2941        let buffer_2_events = buffer_2_events.borrow();
2942        assert_eq!(*buffer_2_events, vec![Event::Edited, Event::Dirtied]);
2943    }
2944
2945    #[gpui::test]
2946    fn test_random_edits(cx: &mut gpui::MutableAppContext) {
2947        let iterations = env::var("ITERATIONS")
2948            .map(|i| i.parse().expect("invalid `ITERATIONS` variable"))
2949            .unwrap_or(100);
2950        let operations = env::var("OPERATIONS")
2951            .map(|i| i.parse().expect("invalid `OPERATIONS` variable"))
2952            .unwrap_or(10);
2953        let start_seed =
2954            env::var("SEED").map_or(0, |seed| seed.parse().expect("invalid `SEED` variable"));
2955
2956        for seed in start_seed..start_seed + iterations {
2957            println!("{:?}", seed);
2958            let mut rng = &mut StdRng::seed_from_u64(seed);
2959
2960            let reference_string_len = rng.gen_range(0..3);
2961            let mut reference_string = RandomCharIter::new(&mut rng)
2962                .take(reference_string_len)
2963                .collect::<String>();
2964            cx.add_model(|cx| {
2965                let mut buffer = Buffer::new(0, reference_string.as_str(), cx);
2966                buffer.history.group_interval = Duration::from_millis(rng.gen_range(0..=200));
2967                let mut buffer_versions = Vec::new();
2968                log::info!(
2969                    "buffer text {:?}, version: {:?}",
2970                    buffer.text(),
2971                    buffer.version()
2972                );
2973
2974                for _i in 0..operations {
2975                    let (old_ranges, new_text) = buffer.randomly_mutate(rng, cx);
2976                    for old_range in old_ranges.iter().rev() {
2977                        reference_string.replace_range(old_range.clone(), &new_text);
2978                    }
2979                    assert_eq!(buffer.text(), reference_string);
2980                    log::info!(
2981                        "buffer text {:?}, version: {:?}",
2982                        buffer.text(),
2983                        buffer.version()
2984                    );
2985
2986                    if rng.gen_bool(0.25) {
2987                        buffer.randomly_undo_redo(rng, cx);
2988                        reference_string = buffer.text();
2989                        log::info!(
2990                            "buffer text {:?}, version: {:?}",
2991                            buffer.text(),
2992                            buffer.version()
2993                        );
2994                    }
2995
2996                    let range = buffer.random_byte_range(0, rng);
2997                    assert_eq!(
2998                        buffer.text_summary_for_range(range.clone()),
2999                        TextSummary::from(&reference_string[range])
3000                    );
3001
3002                    if rng.gen_bool(0.3) {
3003                        buffer_versions.push(buffer.clone());
3004                    }
3005                }
3006
3007                for mut old_buffer in buffer_versions {
3008                    let edits = buffer
3009                        .edits_since(old_buffer.version.clone())
3010                        .collect::<Vec<_>>();
3011
3012                    log::info!(
3013                        "mutating old buffer version {:?}, text: {:?}, edits since: {:?}",
3014                        old_buffer.version(),
3015                        old_buffer.text(),
3016                        edits,
3017                    );
3018
3019                    let mut delta = 0_isize;
3020                    for edit in edits {
3021                        let old_start = (edit.old_bytes.start as isize + delta) as usize;
3022                        let new_text: String =
3023                            buffer.text_for_range(edit.new_bytes.clone()).collect();
3024                        old_buffer.edit(
3025                            Some(old_start..old_start + edit.deleted_bytes()),
3026                            new_text,
3027                            cx,
3028                        );
3029                        delta += edit.delta();
3030                    }
3031                    assert_eq!(old_buffer.text(), buffer.text());
3032                }
3033
3034                buffer
3035            });
3036        }
3037    }
3038
3039    #[gpui::test]
3040    fn test_line_len(cx: &mut gpui::MutableAppContext) {
3041        cx.add_model(|cx| {
3042            let mut buffer = Buffer::new(0, "", cx);
3043            buffer.edit(vec![0..0], "abcd\nefg\nhij", cx);
3044            buffer.edit(vec![12..12], "kl\nmno", cx);
3045            buffer.edit(vec![18..18], "\npqrs\n", cx);
3046            buffer.edit(vec![18..21], "\nPQ", cx);
3047
3048            assert_eq!(buffer.line_len(0), 4);
3049            assert_eq!(buffer.line_len(1), 3);
3050            assert_eq!(buffer.line_len(2), 5);
3051            assert_eq!(buffer.line_len(3), 3);
3052            assert_eq!(buffer.line_len(4), 4);
3053            assert_eq!(buffer.line_len(5), 0);
3054            buffer
3055        });
3056    }
3057
3058    #[gpui::test]
3059    fn test_text_summary_for_range(cx: &mut gpui::MutableAppContext) {
3060        cx.add_model(|cx| {
3061            let buffer = Buffer::new(0, "ab\nefg\nhklm\nnopqrs\ntuvwxyz", cx);
3062            assert_eq!(
3063                buffer.text_summary_for_range(1..3),
3064                TextSummary {
3065                    bytes: 2,
3066                    lines: Point::new(1, 0),
3067                    first_line_chars: 1,
3068                    last_line_chars: 0,
3069                    longest_row: 0,
3070                    longest_row_chars: 1,
3071                }
3072            );
3073            assert_eq!(
3074                buffer.text_summary_for_range(1..12),
3075                TextSummary {
3076                    bytes: 11,
3077                    lines: Point::new(3, 0),
3078                    first_line_chars: 1,
3079                    last_line_chars: 0,
3080                    longest_row: 2,
3081                    longest_row_chars: 4,
3082                }
3083            );
3084            assert_eq!(
3085                buffer.text_summary_for_range(0..20),
3086                TextSummary {
3087                    bytes: 20,
3088                    lines: Point::new(4, 1),
3089                    first_line_chars: 2,
3090                    last_line_chars: 1,
3091                    longest_row: 3,
3092                    longest_row_chars: 6,
3093                }
3094            );
3095            assert_eq!(
3096                buffer.text_summary_for_range(0..22),
3097                TextSummary {
3098                    bytes: 22,
3099                    lines: Point::new(4, 3),
3100                    first_line_chars: 2,
3101                    last_line_chars: 3,
3102                    longest_row: 3,
3103                    longest_row_chars: 6,
3104                }
3105            );
3106            assert_eq!(
3107                buffer.text_summary_for_range(7..22),
3108                TextSummary {
3109                    bytes: 15,
3110                    lines: Point::new(2, 3),
3111                    first_line_chars: 4,
3112                    last_line_chars: 3,
3113                    longest_row: 1,
3114                    longest_row_chars: 6,
3115                }
3116            );
3117            buffer
3118        });
3119    }
3120
3121    #[gpui::test]
3122    fn test_chars_at(cx: &mut gpui::MutableAppContext) {
3123        cx.add_model(|cx| {
3124            let mut buffer = Buffer::new(0, "", cx);
3125            buffer.edit(vec![0..0], "abcd\nefgh\nij", cx);
3126            buffer.edit(vec![12..12], "kl\nmno", cx);
3127            buffer.edit(vec![18..18], "\npqrs", cx);
3128            buffer.edit(vec![18..21], "\nPQ", cx);
3129
3130            let chars = buffer.chars_at(Point::new(0, 0));
3131            assert_eq!(chars.collect::<String>(), "abcd\nefgh\nijkl\nmno\nPQrs");
3132
3133            let chars = buffer.chars_at(Point::new(1, 0));
3134            assert_eq!(chars.collect::<String>(), "efgh\nijkl\nmno\nPQrs");
3135
3136            let chars = buffer.chars_at(Point::new(2, 0));
3137            assert_eq!(chars.collect::<String>(), "ijkl\nmno\nPQrs");
3138
3139            let chars = buffer.chars_at(Point::new(3, 0));
3140            assert_eq!(chars.collect::<String>(), "mno\nPQrs");
3141
3142            let chars = buffer.chars_at(Point::new(4, 0));
3143            assert_eq!(chars.collect::<String>(), "PQrs");
3144
3145            // Regression test:
3146            let mut buffer = Buffer::new(0, "", cx);
3147            buffer.edit(vec![0..0], "[workspace]\nmembers = [\n    \"xray_core\",\n    \"xray_server\",\n    \"xray_cli\",\n    \"xray_wasm\",\n]\n", cx);
3148            buffer.edit(vec![60..60], "\n", cx);
3149
3150            let chars = buffer.chars_at(Point::new(6, 0));
3151            assert_eq!(chars.collect::<String>(), "    \"xray_wasm\",\n]\n");
3152
3153            buffer
3154        });
3155    }
3156
3157    #[gpui::test]
3158    fn test_anchors(cx: &mut gpui::MutableAppContext) {
3159        cx.add_model(|cx| {
3160            let mut buffer = Buffer::new(0, "", cx);
3161            buffer.edit(vec![0..0], "abc", cx);
3162            let left_anchor = buffer.anchor_before(2);
3163            let right_anchor = buffer.anchor_after(2);
3164
3165            buffer.edit(vec![1..1], "def\n", cx);
3166            assert_eq!(buffer.text(), "adef\nbc");
3167            assert_eq!(left_anchor.to_offset(&buffer), 6);
3168            assert_eq!(right_anchor.to_offset(&buffer), 6);
3169            assert_eq!(left_anchor.to_point(&buffer), Point { row: 1, column: 1 });
3170            assert_eq!(right_anchor.to_point(&buffer), Point { row: 1, column: 1 });
3171
3172            buffer.edit(vec![2..3], "", cx);
3173            assert_eq!(buffer.text(), "adf\nbc");
3174            assert_eq!(left_anchor.to_offset(&buffer), 5);
3175            assert_eq!(right_anchor.to_offset(&buffer), 5);
3176            assert_eq!(left_anchor.to_point(&buffer), Point { row: 1, column: 1 });
3177            assert_eq!(right_anchor.to_point(&buffer), Point { row: 1, column: 1 });
3178
3179            buffer.edit(vec![5..5], "ghi\n", cx);
3180            assert_eq!(buffer.text(), "adf\nbghi\nc");
3181            assert_eq!(left_anchor.to_offset(&buffer), 5);
3182            assert_eq!(right_anchor.to_offset(&buffer), 9);
3183            assert_eq!(left_anchor.to_point(&buffer), Point { row: 1, column: 1 });
3184            assert_eq!(right_anchor.to_point(&buffer), Point { row: 2, column: 0 });
3185
3186            buffer.edit(vec![7..9], "", cx);
3187            assert_eq!(buffer.text(), "adf\nbghc");
3188            assert_eq!(left_anchor.to_offset(&buffer), 5);
3189            assert_eq!(right_anchor.to_offset(&buffer), 7);
3190            assert_eq!(left_anchor.to_point(&buffer), Point { row: 1, column: 1 },);
3191            assert_eq!(right_anchor.to_point(&buffer), Point { row: 1, column: 3 });
3192
3193            // Ensure anchoring to a point is equivalent to anchoring to an offset.
3194            assert_eq!(
3195                buffer.anchor_before(Point { row: 0, column: 0 }),
3196                buffer.anchor_before(0)
3197            );
3198            assert_eq!(
3199                buffer.anchor_before(Point { row: 0, column: 1 }),
3200                buffer.anchor_before(1)
3201            );
3202            assert_eq!(
3203                buffer.anchor_before(Point { row: 0, column: 2 }),
3204                buffer.anchor_before(2)
3205            );
3206            assert_eq!(
3207                buffer.anchor_before(Point { row: 0, column: 3 }),
3208                buffer.anchor_before(3)
3209            );
3210            assert_eq!(
3211                buffer.anchor_before(Point { row: 1, column: 0 }),
3212                buffer.anchor_before(4)
3213            );
3214            assert_eq!(
3215                buffer.anchor_before(Point { row: 1, column: 1 }),
3216                buffer.anchor_before(5)
3217            );
3218            assert_eq!(
3219                buffer.anchor_before(Point { row: 1, column: 2 }),
3220                buffer.anchor_before(6)
3221            );
3222            assert_eq!(
3223                buffer.anchor_before(Point { row: 1, column: 3 }),
3224                buffer.anchor_before(7)
3225            );
3226            assert_eq!(
3227                buffer.anchor_before(Point { row: 1, column: 4 }),
3228                buffer.anchor_before(8)
3229            );
3230
3231            // Comparison between anchors.
3232            let anchor_at_offset_0 = buffer.anchor_before(0);
3233            let anchor_at_offset_1 = buffer.anchor_before(1);
3234            let anchor_at_offset_2 = buffer.anchor_before(2);
3235
3236            assert_eq!(
3237                anchor_at_offset_0
3238                    .cmp(&anchor_at_offset_0, &buffer)
3239                    .unwrap(),
3240                Ordering::Equal
3241            );
3242            assert_eq!(
3243                anchor_at_offset_1
3244                    .cmp(&anchor_at_offset_1, &buffer)
3245                    .unwrap(),
3246                Ordering::Equal
3247            );
3248            assert_eq!(
3249                anchor_at_offset_2
3250                    .cmp(&anchor_at_offset_2, &buffer)
3251                    .unwrap(),
3252                Ordering::Equal
3253            );
3254
3255            assert_eq!(
3256                anchor_at_offset_0
3257                    .cmp(&anchor_at_offset_1, &buffer)
3258                    .unwrap(),
3259                Ordering::Less
3260            );
3261            assert_eq!(
3262                anchor_at_offset_1
3263                    .cmp(&anchor_at_offset_2, &buffer)
3264                    .unwrap(),
3265                Ordering::Less
3266            );
3267            assert_eq!(
3268                anchor_at_offset_0
3269                    .cmp(&anchor_at_offset_2, &buffer)
3270                    .unwrap(),
3271                Ordering::Less
3272            );
3273
3274            assert_eq!(
3275                anchor_at_offset_1
3276                    .cmp(&anchor_at_offset_0, &buffer)
3277                    .unwrap(),
3278                Ordering::Greater
3279            );
3280            assert_eq!(
3281                anchor_at_offset_2
3282                    .cmp(&anchor_at_offset_1, &buffer)
3283                    .unwrap(),
3284                Ordering::Greater
3285            );
3286            assert_eq!(
3287                anchor_at_offset_2
3288                    .cmp(&anchor_at_offset_0, &buffer)
3289                    .unwrap(),
3290                Ordering::Greater
3291            );
3292            buffer
3293        });
3294    }
3295
3296    #[gpui::test]
3297    fn test_anchors_at_start_and_end(cx: &mut gpui::MutableAppContext) {
3298        cx.add_model(|cx| {
3299            let mut buffer = Buffer::new(0, "", cx);
3300            let before_start_anchor = buffer.anchor_before(0);
3301            let after_end_anchor = buffer.anchor_after(0);
3302
3303            buffer.edit(vec![0..0], "abc", cx);
3304            assert_eq!(buffer.text(), "abc");
3305            assert_eq!(before_start_anchor.to_offset(&buffer), 0);
3306            assert_eq!(after_end_anchor.to_offset(&buffer), 3);
3307
3308            let after_start_anchor = buffer.anchor_after(0);
3309            let before_end_anchor = buffer.anchor_before(3);
3310
3311            buffer.edit(vec![3..3], "def", cx);
3312            buffer.edit(vec![0..0], "ghi", cx);
3313            assert_eq!(buffer.text(), "ghiabcdef");
3314            assert_eq!(before_start_anchor.to_offset(&buffer), 0);
3315            assert_eq!(after_start_anchor.to_offset(&buffer), 3);
3316            assert_eq!(before_end_anchor.to_offset(&buffer), 6);
3317            assert_eq!(after_end_anchor.to_offset(&buffer), 9);
3318            buffer
3319        });
3320    }
3321
3322    #[gpui::test]
3323    async fn test_is_dirty(mut cx: gpui::TestAppContext) {
3324        let dir = temp_tree(json!({
3325            "file1": "abc",
3326            "file2": "def",
3327            "file3": "ghi",
3328        }));
3329        let tree = Worktree::open_local(
3330            dir.path(),
3331            Default::default(),
3332            Arc::new(RealFs),
3333            &mut cx.to_async(),
3334        )
3335        .await
3336        .unwrap();
3337        tree.flush_fs_events(&cx).await;
3338        cx.read(|cx| tree.read(cx).as_local().unwrap().scan_complete())
3339            .await;
3340
3341        let buffer1 = tree
3342            .update(&mut cx, |tree, cx| tree.open_buffer("file1", cx))
3343            .await
3344            .unwrap();
3345        let events = Rc::new(RefCell::new(Vec::new()));
3346
3347        // initially, the buffer isn't dirty.
3348        buffer1.update(&mut cx, |buffer, cx| {
3349            cx.subscribe(&buffer1, {
3350                let events = events.clone();
3351                move |_, event, _| events.borrow_mut().push(event.clone())
3352            });
3353
3354            assert!(!buffer.is_dirty());
3355            assert!(events.borrow().is_empty());
3356
3357            buffer.edit(vec![1..2], "", cx);
3358        });
3359
3360        // after the first edit, the buffer is dirty, and emits a dirtied event.
3361        buffer1.update(&mut cx, |buffer, cx| {
3362            assert!(buffer.text() == "ac");
3363            assert!(buffer.is_dirty());
3364            assert_eq!(*events.borrow(), &[Event::Edited, Event::Dirtied]);
3365            events.borrow_mut().clear();
3366            buffer.did_save(buffer.version(), buffer.file().unwrap().mtime, cx);
3367        });
3368
3369        // after saving, the buffer is not dirty, and emits a saved event.
3370        buffer1.update(&mut cx, |buffer, cx| {
3371            assert!(!buffer.is_dirty());
3372            assert_eq!(*events.borrow(), &[Event::Saved]);
3373            events.borrow_mut().clear();
3374
3375            buffer.edit(vec![1..1], "B", cx);
3376            buffer.edit(vec![2..2], "D", cx);
3377        });
3378
3379        // after editing again, the buffer is dirty, and emits another dirty event.
3380        buffer1.update(&mut cx, |buffer, cx| {
3381            assert!(buffer.text() == "aBDc");
3382            assert!(buffer.is_dirty());
3383            assert_eq!(
3384                *events.borrow(),
3385                &[Event::Edited, Event::Dirtied, Event::Edited],
3386            );
3387            events.borrow_mut().clear();
3388
3389            // TODO - currently, after restoring the buffer to its
3390            // previously-saved state, the is still considered dirty.
3391            buffer.edit(vec![1..3], "", cx);
3392            assert!(buffer.text() == "ac");
3393            assert!(buffer.is_dirty());
3394        });
3395
3396        assert_eq!(*events.borrow(), &[Event::Edited]);
3397
3398        // When a file is deleted, the buffer is considered dirty.
3399        let events = Rc::new(RefCell::new(Vec::new()));
3400        let buffer2 = tree
3401            .update(&mut cx, |tree, cx| tree.open_buffer("file2", cx))
3402            .await
3403            .unwrap();
3404        buffer2.update(&mut cx, |_, cx| {
3405            cx.subscribe(&buffer2, {
3406                let events = events.clone();
3407                move |_, event, _| events.borrow_mut().push(event.clone())
3408            });
3409        });
3410
3411        fs::remove_file(dir.path().join("file2")).unwrap();
3412        buffer2.condition(&cx, |b, _| b.is_dirty()).await;
3413        assert_eq!(
3414            *events.borrow(),
3415            &[Event::Dirtied, Event::FileHandleChanged]
3416        );
3417
3418        // When a file is already dirty when deleted, we don't emit a Dirtied event.
3419        let events = Rc::new(RefCell::new(Vec::new()));
3420        let buffer3 = tree
3421            .update(&mut cx, |tree, cx| tree.open_buffer("file3", cx))
3422            .await
3423            .unwrap();
3424        buffer3.update(&mut cx, |_, cx| {
3425            cx.subscribe(&buffer3, {
3426                let events = events.clone();
3427                move |_, event, _| events.borrow_mut().push(event.clone())
3428            });
3429        });
3430
3431        tree.flush_fs_events(&cx).await;
3432        buffer3.update(&mut cx, |buffer, cx| {
3433            buffer.edit(Some(0..0), "x", cx);
3434        });
3435        events.borrow_mut().clear();
3436        fs::remove_file(dir.path().join("file3")).unwrap();
3437        buffer3
3438            .condition(&cx, |_, _| !events.borrow().is_empty())
3439            .await;
3440        assert_eq!(*events.borrow(), &[Event::FileHandleChanged]);
3441        cx.read(|cx| assert!(buffer3.read(cx).is_dirty()));
3442    }
3443
3444    #[gpui::test]
3445    async fn test_file_changes_on_disk(mut cx: gpui::TestAppContext) {
3446        let initial_contents = "aaa\nbbbbb\nc\n";
3447        let dir = temp_tree(json!({ "the-file": initial_contents }));
3448        let tree = Worktree::open_local(
3449            dir.path(),
3450            Default::default(),
3451            Arc::new(RealFs),
3452            &mut cx.to_async(),
3453        )
3454        .await
3455        .unwrap();
3456        cx.read(|cx| tree.read(cx).as_local().unwrap().scan_complete())
3457            .await;
3458
3459        let abs_path = dir.path().join("the-file");
3460        let buffer = tree
3461            .update(&mut cx, |tree, cx| {
3462                tree.open_buffer(Path::new("the-file"), cx)
3463            })
3464            .await
3465            .unwrap();
3466
3467        // Add a cursor at the start of each row.
3468        let selection_set_id = buffer.update(&mut cx, |buffer, cx| {
3469            assert!(!buffer.is_dirty());
3470            buffer.add_selection_set(
3471                (0..3)
3472                    .map(|row| {
3473                        let anchor = buffer.anchor_at(Point::new(row, 0), Bias::Right);
3474                        Selection {
3475                            id: row as usize,
3476                            start: anchor.clone(),
3477                            end: anchor,
3478                            reversed: false,
3479                            goal: SelectionGoal::None,
3480                        }
3481                    })
3482                    .collect::<Vec<_>>(),
3483                cx,
3484            )
3485        });
3486
3487        // Change the file on disk, adding two new lines of text, and removing
3488        // one line.
3489        buffer.read_with(&cx, |buffer, _| {
3490            assert!(!buffer.is_dirty());
3491            assert!(!buffer.has_conflict());
3492        });
3493        let new_contents = "AAAA\naaa\nBB\nbbbbb\n";
3494        fs::write(&abs_path, new_contents).unwrap();
3495
3496        // Because the buffer was not modified, it is reloaded from disk. Its
3497        // contents are edited according to the diff between the old and new
3498        // file contents.
3499        buffer
3500            .condition(&cx, |buffer, _| buffer.text() != initial_contents)
3501            .await;
3502
3503        buffer.update(&mut cx, |buffer, _| {
3504            assert_eq!(buffer.text(), new_contents);
3505            assert!(!buffer.is_dirty());
3506            assert!(!buffer.has_conflict());
3507
3508            let set = buffer.selection_set(selection_set_id).unwrap();
3509            let cursor_positions = set
3510                .selections
3511                .iter()
3512                .map(|selection| {
3513                    assert_eq!(selection.start, selection.end);
3514                    selection.start.to_point(&*buffer)
3515                })
3516                .collect::<Vec<_>>();
3517            assert_eq!(
3518                cursor_positions,
3519                &[Point::new(1, 0), Point::new(3, 0), Point::new(4, 0),]
3520            );
3521        });
3522
3523        // Modify the buffer
3524        buffer.update(&mut cx, |buffer, cx| {
3525            buffer.edit(vec![0..0], " ", cx);
3526            assert!(buffer.is_dirty());
3527        });
3528
3529        // Change the file on disk again, adding blank lines to the beginning.
3530        fs::write(&abs_path, "\n\n\nAAAA\naaa\nBB\nbbbbb\n").unwrap();
3531
3532        // Becaues the buffer is modified, it doesn't reload from disk, but is
3533        // marked as having a conflict.
3534        buffer
3535            .condition(&cx, |buffer, _| buffer.has_conflict())
3536            .await;
3537    }
3538
3539    #[gpui::test]
3540    async fn test_apply_diff(mut cx: gpui::TestAppContext) {
3541        let text = "a\nbb\nccc\ndddd\neeeee\nffffff\n";
3542        let buffer = cx.add_model(|cx| Buffer::new(0, text, cx));
3543
3544        let text = "a\nccc\ndddd\nffffff\n";
3545        let diff = buffer.read_with(&cx, |b, cx| b.diff(text.into(), cx)).await;
3546        buffer.update(&mut cx, |b, cx| b.apply_diff(diff, cx));
3547        cx.read(|cx| assert_eq!(buffer.read(cx).text(), text));
3548
3549        let text = "a\n1\n\nccc\ndd2dd\nffffff\n";
3550        let diff = buffer.read_with(&cx, |b, cx| b.diff(text.into(), cx)).await;
3551        buffer.update(&mut cx, |b, cx| b.apply_diff(diff, cx));
3552        cx.read(|cx| assert_eq!(buffer.read(cx).text(), text));
3553    }
3554
3555    #[gpui::test]
3556    fn test_undo_redo(cx: &mut gpui::MutableAppContext) {
3557        cx.add_model(|cx| {
3558            let mut buffer = Buffer::new(0, "1234", cx);
3559            // Set group interval to zero so as to not group edits in the undo stack.
3560            buffer.history.group_interval = Duration::from_secs(0);
3561
3562            buffer.edit(vec![1..1], "abx", cx);
3563            buffer.edit(vec![3..4], "yzef", cx);
3564            buffer.edit(vec![3..5], "cd", cx);
3565            assert_eq!(buffer.text(), "1abcdef234");
3566
3567            let transactions = buffer.history.undo_stack.clone();
3568            assert_eq!(transactions.len(), 3);
3569
3570            buffer.undo_or_redo(transactions[0].clone(), cx).unwrap();
3571            assert_eq!(buffer.text(), "1cdef234");
3572            buffer.undo_or_redo(transactions[0].clone(), cx).unwrap();
3573            assert_eq!(buffer.text(), "1abcdef234");
3574
3575            buffer.undo_or_redo(transactions[1].clone(), cx).unwrap();
3576            assert_eq!(buffer.text(), "1abcdx234");
3577            buffer.undo_or_redo(transactions[2].clone(), cx).unwrap();
3578            assert_eq!(buffer.text(), "1abx234");
3579            buffer.undo_or_redo(transactions[1].clone(), cx).unwrap();
3580            assert_eq!(buffer.text(), "1abyzef234");
3581            buffer.undo_or_redo(transactions[2].clone(), cx).unwrap();
3582            assert_eq!(buffer.text(), "1abcdef234");
3583
3584            buffer.undo_or_redo(transactions[2].clone(), cx).unwrap();
3585            assert_eq!(buffer.text(), "1abyzef234");
3586            buffer.undo_or_redo(transactions[0].clone(), cx).unwrap();
3587            assert_eq!(buffer.text(), "1yzef234");
3588            buffer.undo_or_redo(transactions[1].clone(), cx).unwrap();
3589            assert_eq!(buffer.text(), "1234");
3590
3591            buffer
3592        });
3593    }
3594
3595    #[gpui::test]
3596    fn test_history(cx: &mut gpui::MutableAppContext) {
3597        cx.add_model(|cx| {
3598            let mut now = Instant::now();
3599            let mut buffer = Buffer::new(0, "123456", cx);
3600
3601            let set_id =
3602                buffer.add_selection_set(buffer.selections_from_ranges(vec![4..4]).unwrap(), cx);
3603            buffer.start_transaction_at(Some(set_id), now).unwrap();
3604            buffer.edit(vec![2..4], "cd", cx);
3605            buffer.end_transaction_at(Some(set_id), now, cx).unwrap();
3606            assert_eq!(buffer.text(), "12cd56");
3607            assert_eq!(buffer.selection_ranges(set_id).unwrap(), vec![4..4]);
3608
3609            buffer.start_transaction_at(Some(set_id), now).unwrap();
3610            buffer
3611                .update_selection_set(
3612                    set_id,
3613                    buffer.selections_from_ranges(vec![1..3]).unwrap(),
3614                    cx,
3615                )
3616                .unwrap();
3617            buffer.edit(vec![4..5], "e", cx);
3618            buffer.end_transaction_at(Some(set_id), now, cx).unwrap();
3619            assert_eq!(buffer.text(), "12cde6");
3620            assert_eq!(buffer.selection_ranges(set_id).unwrap(), vec![1..3]);
3621
3622            now += buffer.history.group_interval + Duration::from_millis(1);
3623            buffer.start_transaction_at(Some(set_id), now).unwrap();
3624            buffer
3625                .update_selection_set(
3626                    set_id,
3627                    buffer.selections_from_ranges(vec![2..2]).unwrap(),
3628                    cx,
3629                )
3630                .unwrap();
3631            buffer.edit(vec![0..1], "a", cx);
3632            buffer.edit(vec![1..1], "b", cx);
3633            buffer.end_transaction_at(Some(set_id), now, cx).unwrap();
3634            assert_eq!(buffer.text(), "ab2cde6");
3635            assert_eq!(buffer.selection_ranges(set_id).unwrap(), vec![3..3]);
3636
3637            // Last transaction happened past the group interval, undo it on its
3638            // own.
3639            buffer.undo(cx);
3640            assert_eq!(buffer.text(), "12cde6");
3641            assert_eq!(buffer.selection_ranges(set_id).unwrap(), vec![1..3]);
3642
3643            // First two transactions happened within the group interval, undo them
3644            // together.
3645            buffer.undo(cx);
3646            assert_eq!(buffer.text(), "123456");
3647            assert_eq!(buffer.selection_ranges(set_id).unwrap(), vec![4..4]);
3648
3649            // Redo the first two transactions together.
3650            buffer.redo(cx);
3651            assert_eq!(buffer.text(), "12cde6");
3652            assert_eq!(buffer.selection_ranges(set_id).unwrap(), vec![1..3]);
3653
3654            // Redo the last transaction on its own.
3655            buffer.redo(cx);
3656            assert_eq!(buffer.text(), "ab2cde6");
3657            assert_eq!(buffer.selection_ranges(set_id).unwrap(), vec![3..3]);
3658
3659            buffer
3660        });
3661    }
3662
3663    #[gpui::test]
3664    fn test_concurrent_edits(cx: &mut gpui::MutableAppContext) {
3665        let text = "abcdef";
3666
3667        let buffer1 = cx.add_model(|cx| Buffer::new(1, text, cx));
3668        let buffer2 = cx.add_model(|cx| Buffer::new(2, text, cx));
3669        let buffer3 = cx.add_model(|cx| Buffer::new(3, text, cx));
3670
3671        let buf1_op = buffer1.update(cx, |buffer, cx| {
3672            buffer.edit(vec![1..2], "12", cx);
3673            assert_eq!(buffer.text(), "a12cdef");
3674            buffer.operations.last().unwrap().clone()
3675        });
3676        let buf2_op = buffer2.update(cx, |buffer, cx| {
3677            buffer.edit(vec![3..4], "34", cx);
3678            assert_eq!(buffer.text(), "abc34ef");
3679            buffer.operations.last().unwrap().clone()
3680        });
3681        let buf3_op = buffer3.update(cx, |buffer, cx| {
3682            buffer.edit(vec![5..6], "56", cx);
3683            assert_eq!(buffer.text(), "abcde56");
3684            buffer.operations.last().unwrap().clone()
3685        });
3686
3687        buffer1.update(cx, |buffer, _| {
3688            buffer.apply_op(buf2_op.clone()).unwrap();
3689            buffer.apply_op(buf3_op.clone()).unwrap();
3690        });
3691        buffer2.update(cx, |buffer, _| {
3692            buffer.apply_op(buf1_op.clone()).unwrap();
3693            buffer.apply_op(buf3_op.clone()).unwrap();
3694        });
3695        buffer3.update(cx, |buffer, _| {
3696            buffer.apply_op(buf1_op.clone()).unwrap();
3697            buffer.apply_op(buf2_op.clone()).unwrap();
3698        });
3699
3700        assert_eq!(buffer1.read(cx).text(), "a12c34e56");
3701        assert_eq!(buffer2.read(cx).text(), "a12c34e56");
3702        assert_eq!(buffer3.read(cx).text(), "a12c34e56");
3703    }
3704
3705    #[gpui::test]
3706    fn test_random_concurrent_edits(cx: &mut gpui::MutableAppContext) {
3707        use crate::test::Network;
3708
3709        let peers = env::var("PEERS")
3710            .map(|i| i.parse().expect("invalid `PEERS` variable"))
3711            .unwrap_or(5);
3712        let iterations = env::var("ITERATIONS")
3713            .map(|i| i.parse().expect("invalid `ITERATIONS` variable"))
3714            .unwrap_or(100);
3715        let operations = env::var("OPERATIONS")
3716            .map(|i| i.parse().expect("invalid `OPERATIONS` variable"))
3717            .unwrap_or(10);
3718        let start_seed =
3719            env::var("SEED").map_or(0, |seed| seed.parse().expect("invalid `SEED` variable"));
3720
3721        for seed in start_seed..start_seed + iterations {
3722            dbg!(seed);
3723            let mut rng = StdRng::seed_from_u64(seed);
3724
3725            let base_text_len = rng.gen_range(0..10);
3726            let base_text = RandomCharIter::new(&mut rng)
3727                .take(base_text_len)
3728                .collect::<String>();
3729            let mut replica_ids = Vec::new();
3730            let mut buffers = Vec::new();
3731            let mut network = Network::new(StdRng::seed_from_u64(seed));
3732
3733            for i in 0..peers {
3734                let buffer = cx.add_model(|cx| {
3735                    let mut buf = Buffer::new(i as ReplicaId, base_text.as_str(), cx);
3736                    buf.history.group_interval = Duration::from_millis(rng.gen_range(0..=200));
3737                    buf
3738                });
3739                buffers.push(buffer);
3740                replica_ids.push(i as u16);
3741                network.add_peer(i as u16);
3742            }
3743
3744            log::info!("initial text: {:?}", base_text);
3745
3746            let mut mutation_count = operations;
3747            loop {
3748                let replica_index = rng.gen_range(0..peers);
3749                let replica_id = replica_ids[replica_index];
3750                buffers[replica_index].update(cx, |buffer, cx| match rng.gen_range(0..=100) {
3751                    0..=50 if mutation_count != 0 => {
3752                        buffer.randomly_mutate(&mut rng, cx);
3753                        network.broadcast(buffer.replica_id, mem::take(&mut buffer.operations));
3754                        log::info!("buffer {} text: {:?}", buffer.replica_id, buffer.text());
3755                        mutation_count -= 1;
3756                    }
3757                    51..=70 if mutation_count != 0 => {
3758                        buffer.randomly_undo_redo(&mut rng, cx);
3759                        network.broadcast(buffer.replica_id, mem::take(&mut buffer.operations));
3760                        mutation_count -= 1;
3761                    }
3762                    71..=100 if network.has_unreceived(replica_id) => {
3763                        let ops = network.receive(replica_id);
3764                        if !ops.is_empty() {
3765                            log::info!(
3766                                "peer {} applying {} ops from the network.",
3767                                replica_id,
3768                                ops.len()
3769                            );
3770                            buffer.apply_ops(ops, cx).unwrap();
3771                        }
3772                    }
3773                    _ => {}
3774                });
3775
3776                if mutation_count == 0 && network.is_idle() {
3777                    break;
3778                }
3779            }
3780
3781            let first_buffer = buffers[0].read(cx);
3782            for buffer in &buffers[1..] {
3783                let buffer = buffer.read(cx);
3784                assert_eq!(
3785                    buffer.text(),
3786                    first_buffer.text(),
3787                    "Replica {} text != Replica 0 text",
3788                    buffer.replica_id
3789                );
3790                assert_eq!(
3791                    buffer.selection_sets().collect::<HashMap<_, _>>(),
3792                    first_buffer.selection_sets().collect::<HashMap<_, _>>()
3793                );
3794                assert_eq!(
3795                    buffer.all_selection_ranges().collect::<HashMap<_, _>>(),
3796                    first_buffer
3797                        .all_selection_ranges()
3798                        .collect::<HashMap<_, _>>()
3799                );
3800            }
3801        }
3802    }
3803
3804    #[gpui::test]
3805    async fn test_reparse(mut cx: gpui::TestAppContext) {
3806        let app_state = cx.read(build_app_state);
3807        let rust_lang = app_state.languages.select_language("test.rs");
3808        assert!(rust_lang.is_some());
3809
3810        let buffer = cx.add_model(|cx| {
3811            let text = "fn a() {}".into();
3812            let buffer = Buffer::from_history(0, History::new(text), None, rust_lang.cloned(), cx);
3813            assert!(buffer.is_parsing());
3814            assert!(buffer.syntax_tree().is_none());
3815            buffer
3816        });
3817
3818        // Wait for the initial text to parse
3819        buffer
3820            .condition(&cx, |buffer, _| !buffer.is_parsing())
3821            .await;
3822        assert_eq!(
3823            get_tree_sexp(&buffer, &cx),
3824            concat!(
3825                "(source_file (function_item name: (identifier) ",
3826                "parameters: (parameters) ",
3827                "body: (block)))"
3828            )
3829        );
3830
3831        // Perform some edits (add parameter and variable reference)
3832        // Parsing doesn't begin until the transaction is complete
3833        buffer.update(&mut cx, |buf, cx| {
3834            buf.start_transaction(None).unwrap();
3835
3836            let offset = buf.text().find(")").unwrap();
3837            buf.edit(vec![offset..offset], "b: C", cx);
3838            assert!(!buf.is_parsing());
3839
3840            let offset = buf.text().find("}").unwrap();
3841            buf.edit(vec![offset..offset], " d; ", cx);
3842            assert!(!buf.is_parsing());
3843
3844            buf.end_transaction(None, cx).unwrap();
3845            assert_eq!(buf.text(), "fn a(b: C) { d; }");
3846            assert!(buf.is_parsing());
3847        });
3848        buffer
3849            .condition(&cx, |buffer, _| !buffer.is_parsing())
3850            .await;
3851        assert_eq!(
3852            get_tree_sexp(&buffer, &cx),
3853            concat!(
3854                "(source_file (function_item name: (identifier) ",
3855                    "parameters: (parameters (parameter pattern: (identifier) type: (type_identifier))) ",
3856                    "body: (block (identifier))))"
3857            )
3858        );
3859
3860        // Perform a series of edits without waiting for the current parse to complete:
3861        // * turn identifier into a field expression
3862        // * turn field expression into a method call
3863        // * add a turbofish to the method call
3864        buffer.update(&mut cx, |buf, cx| {
3865            let offset = buf.text().find(";").unwrap();
3866            buf.edit(vec![offset..offset], ".e", cx);
3867            assert_eq!(buf.text(), "fn a(b: C) { d.e; }");
3868            assert!(buf.is_parsing());
3869        });
3870        buffer.update(&mut cx, |buf, cx| {
3871            let offset = buf.text().find(";").unwrap();
3872            buf.edit(vec![offset..offset], "(f)", cx);
3873            assert_eq!(buf.text(), "fn a(b: C) { d.e(f); }");
3874            assert!(buf.is_parsing());
3875        });
3876        buffer.update(&mut cx, |buf, cx| {
3877            let offset = buf.text().find("(f)").unwrap();
3878            buf.edit(vec![offset..offset], "::<G>", cx);
3879            assert_eq!(buf.text(), "fn a(b: C) { d.e::<G>(f); }");
3880            assert!(buf.is_parsing());
3881        });
3882        buffer
3883            .condition(&cx, |buffer, _| !buffer.is_parsing())
3884            .await;
3885        assert_eq!(
3886            get_tree_sexp(&buffer, &cx),
3887            concat!(
3888                "(source_file (function_item name: (identifier) ",
3889                    "parameters: (parameters (parameter pattern: (identifier) type: (type_identifier))) ",
3890                    "body: (block (call_expression ",
3891                        "function: (generic_function ",
3892                            "function: (field_expression value: (identifier) field: (field_identifier)) ",
3893                            "type_arguments: (type_arguments (type_identifier))) ",
3894                            "arguments: (arguments (identifier))))))",
3895            )
3896        );
3897
3898        buffer.update(&mut cx, |buf, cx| {
3899            buf.undo(cx);
3900            assert_eq!(buf.text(), "fn a() {}");
3901            assert!(buf.is_parsing());
3902        });
3903        buffer
3904            .condition(&cx, |buffer, _| !buffer.is_parsing())
3905            .await;
3906        assert_eq!(
3907            get_tree_sexp(&buffer, &cx),
3908            concat!(
3909                "(source_file (function_item name: (identifier) ",
3910                "parameters: (parameters) ",
3911                "body: (block)))"
3912            )
3913        );
3914
3915        buffer.update(&mut cx, |buf, cx| {
3916            buf.redo(cx);
3917            assert_eq!(buf.text(), "fn a(b: C) { d.e::<G>(f); }");
3918            assert!(buf.is_parsing());
3919        });
3920        buffer
3921            .condition(&cx, |buffer, _| !buffer.is_parsing())
3922            .await;
3923        assert_eq!(
3924            get_tree_sexp(&buffer, &cx),
3925            concat!(
3926                "(source_file (function_item name: (identifier) ",
3927                    "parameters: (parameters (parameter pattern: (identifier) type: (type_identifier))) ",
3928                    "body: (block (call_expression ",
3929                        "function: (generic_function ",
3930                            "function: (field_expression value: (identifier) field: (field_identifier)) ",
3931                            "type_arguments: (type_arguments (type_identifier))) ",
3932                            "arguments: (arguments (identifier))))))",
3933            )
3934        );
3935
3936        fn get_tree_sexp(buffer: &ModelHandle<Buffer>, cx: &gpui::TestAppContext) -> String {
3937            buffer.read_with(cx, |buffer, _| {
3938                buffer.syntax_tree().unwrap().root_node().to_sexp()
3939            })
3940        }
3941    }
3942
3943    #[gpui::test]
3944    async fn test_enclosing_bracket_ranges(mut cx: gpui::TestAppContext) {
3945        use unindent::Unindent as _;
3946
3947        let app_state = cx.read(build_app_state);
3948        let rust_lang = app_state.languages.select_language("test.rs");
3949        assert!(rust_lang.is_some());
3950
3951        let buffer = cx.add_model(|cx| {
3952            let text = "
3953                mod x {
3954                    mod y {
3955
3956                    }
3957                }
3958            "
3959            .unindent()
3960            .into();
3961            Buffer::from_history(0, History::new(text), None, rust_lang.cloned(), cx)
3962        });
3963        buffer
3964            .condition(&cx, |buffer, _| !buffer.is_parsing())
3965            .await;
3966        buffer.read_with(&cx, |buf, _| {
3967            assert_eq!(
3968                buf.enclosing_bracket_point_ranges(Point::new(1, 6)..Point::new(1, 6)),
3969                Some((
3970                    Point::new(0, 6)..Point::new(0, 7),
3971                    Point::new(4, 0)..Point::new(4, 1)
3972                ))
3973            );
3974            assert_eq!(
3975                buf.enclosing_bracket_point_ranges(Point::new(1, 10)..Point::new(1, 10)),
3976                Some((
3977                    Point::new(1, 10)..Point::new(1, 11),
3978                    Point::new(3, 4)..Point::new(3, 5)
3979                ))
3980            );
3981            assert_eq!(
3982                buf.enclosing_bracket_point_ranges(Point::new(3, 5)..Point::new(3, 5)),
3983                Some((
3984                    Point::new(1, 10)..Point::new(1, 11),
3985                    Point::new(3, 4)..Point::new(3, 5)
3986                ))
3987            );
3988        });
3989    }
3990
3991    impl Buffer {
3992        fn random_byte_range(&mut self, start_offset: usize, rng: &mut impl Rng) -> Range<usize> {
3993            let end = self.clip_offset(rng.gen_range(start_offset..=self.len()), Bias::Right);
3994            let start = self.clip_offset(rng.gen_range(start_offset..=end), Bias::Right);
3995            start..end
3996        }
3997
3998        pub fn randomly_edit<T>(
3999            &mut self,
4000            rng: &mut T,
4001            old_range_count: usize,
4002            cx: &mut ModelContext<Self>,
4003        ) -> (Vec<Range<usize>>, String)
4004        where
4005            T: Rng,
4006        {
4007            let mut old_ranges: Vec<Range<usize>> = Vec::new();
4008            for _ in 0..old_range_count {
4009                let last_end = old_ranges.last().map_or(0, |last_range| last_range.end + 1);
4010                if last_end > self.len() {
4011                    break;
4012                }
4013                old_ranges.push(self.random_byte_range(last_end, rng));
4014            }
4015            let new_text_len = rng.gen_range(0..10);
4016            let new_text: String = RandomCharIter::new(&mut *rng).take(new_text_len).collect();
4017            log::info!(
4018                "mutating buffer {} at {:?}: {:?}",
4019                self.replica_id,
4020                old_ranges,
4021                new_text
4022            );
4023            self.edit(old_ranges.iter().cloned(), new_text.as_str(), cx);
4024            (old_ranges, new_text)
4025        }
4026
4027        pub fn randomly_mutate<T>(
4028            &mut self,
4029            rng: &mut T,
4030            cx: &mut ModelContext<Self>,
4031        ) -> (Vec<Range<usize>>, String)
4032        where
4033            T: Rng,
4034        {
4035            let (old_ranges, new_text) = self.randomly_edit(rng, 5, cx);
4036
4037            // Randomly add, remove or mutate selection sets.
4038            let replica_selection_sets = &self
4039                .selection_sets()
4040                .map(|(set_id, _)| *set_id)
4041                .filter(|set_id| self.replica_id == set_id.replica_id)
4042                .collect::<Vec<_>>();
4043            let set_id = replica_selection_sets.choose(rng);
4044            if set_id.is_some() && rng.gen_bool(1.0 / 6.0) {
4045                self.remove_selection_set(*set_id.unwrap(), cx).unwrap();
4046            } else {
4047                let mut ranges = Vec::new();
4048                for _ in 0..5 {
4049                    ranges.push(self.random_byte_range(0, rng));
4050                }
4051                let new_selections = self.selections_from_ranges(ranges).unwrap();
4052
4053                if set_id.is_none() || rng.gen_bool(1.0 / 5.0) {
4054                    self.add_selection_set(new_selections, cx);
4055                } else {
4056                    self.update_selection_set(*set_id.unwrap(), new_selections, cx)
4057                        .unwrap();
4058                }
4059            }
4060
4061            (old_ranges, new_text)
4062        }
4063
4064        pub fn randomly_undo_redo(&mut self, rng: &mut impl Rng, cx: &mut ModelContext<Self>) {
4065            for _ in 0..rng.gen_range(1..=5) {
4066                if let Some(transaction) = self.history.undo_stack.choose(rng).cloned() {
4067                    log::info!(
4068                        "undoing buffer {} transaction {:?}",
4069                        self.replica_id,
4070                        transaction
4071                    );
4072                    self.undo_or_redo(transaction, cx).unwrap();
4073                }
4074            }
4075        }
4076
4077        fn selections_from_ranges<I>(&self, ranges: I) -> Result<Vec<Selection>>
4078        where
4079            I: IntoIterator<Item = Range<usize>>,
4080        {
4081            static NEXT_SELECTION_ID: AtomicUsize = AtomicUsize::new(0);
4082
4083            let mut ranges = ranges.into_iter().collect::<Vec<_>>();
4084            ranges.sort_unstable_by_key(|range| range.start);
4085
4086            let mut selections = Vec::with_capacity(ranges.len());
4087            for range in ranges {
4088                if range.start > range.end {
4089                    selections.push(Selection {
4090                        id: NEXT_SELECTION_ID.fetch_add(1, atomic::Ordering::SeqCst),
4091                        start: self.anchor_before(range.end),
4092                        end: self.anchor_before(range.start),
4093                        reversed: true,
4094                        goal: SelectionGoal::None,
4095                    });
4096                } else {
4097                    selections.push(Selection {
4098                        id: NEXT_SELECTION_ID.fetch_add(1, atomic::Ordering::SeqCst),
4099                        start: self.anchor_after(range.start),
4100                        end: self.anchor_before(range.end),
4101                        reversed: false,
4102                        goal: SelectionGoal::None,
4103                    });
4104                }
4105            }
4106            Ok(selections)
4107        }
4108
4109        pub fn selection_ranges<'a>(&'a self, set_id: SelectionSetId) -> Result<Vec<Range<usize>>> {
4110            Ok(self
4111                .selection_set(set_id)?
4112                .selections
4113                .iter()
4114                .map(move |selection| {
4115                    let start = selection.start.to_offset(self);
4116                    let end = selection.end.to_offset(self);
4117                    if selection.reversed {
4118                        end..start
4119                    } else {
4120                        start..end
4121                    }
4122                })
4123                .collect())
4124        }
4125
4126        pub fn all_selection_ranges<'a>(
4127            &'a self,
4128        ) -> impl 'a + Iterator<Item = (SelectionSetId, Vec<Range<usize>>)> {
4129            self.selections
4130                .keys()
4131                .map(move |set_id| (*set_id, self.selection_ranges(*set_id).unwrap()))
4132        }
4133
4134        pub fn enclosing_bracket_point_ranges<T: ToOffset>(
4135            &self,
4136            range: Range<T>,
4137        ) -> Option<(Range<Point>, Range<Point>)> {
4138            self.enclosing_bracket_ranges(range).map(|(start, end)| {
4139                let point_start = start.start.to_point(self)..start.end.to_point(self);
4140                let point_end = end.start.to_point(self)..end.end.to_point(self);
4141                (point_start, point_end)
4142            })
4143        }
4144    }
4145}