mirror of
https://github.com/martinvonz/jj.git
synced 2025-01-16 00:56:23 +00:00
working_copy: update file states in bulk
This helps migrate BTreeMap<RepoPath, _> to sorted Vec.
This commit is contained in:
parent
c9150d02fc
commit
9292af5e52
1 changed files with 32 additions and 20 deletions
|
@ -672,12 +672,12 @@ impl TreeState {
|
||||||
)
|
)
|
||||||
})?;
|
})?;
|
||||||
|
|
||||||
let file_states = self.file_states.make_mut();
|
|
||||||
let mut tree_builder = MergedTreeBuilder::new(self.tree_id.clone());
|
let mut tree_builder = MergedTreeBuilder::new(self.tree_id.clone());
|
||||||
let mut deleted_files: HashSet<_> =
|
let mut deleted_files: HashSet<_> =
|
||||||
trace_span!("collecting existing files").in_scope(|| {
|
trace_span!("collecting existing files").in_scope(|| {
|
||||||
// Since file_states shouldn't contain files excluded by the sparse patterns,
|
// Since file_states shouldn't contain files excluded by the sparse patterns,
|
||||||
// fsmonitor_matcher here is identical to the intersected matcher.
|
// fsmonitor_matcher here is identical to the intersected matcher.
|
||||||
|
let file_states = self.file_states.get_or_load();
|
||||||
file_states
|
file_states
|
||||||
.iter()
|
.iter()
|
||||||
.filter(|&(path, state)| {
|
.filter(|&(path, state)| {
|
||||||
|
@ -692,24 +692,26 @@ impl TreeState {
|
||||||
}
|
}
|
||||||
Ok(())
|
Ok(())
|
||||||
})?;
|
})?;
|
||||||
trace_span!("process file states").in_scope(|| {
|
|
||||||
while let Ok((path, file_state)) = file_states_rx.recv() {
|
|
||||||
is_dirty = true;
|
|
||||||
file_states.insert(path, file_state);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
trace_span!("process present files").in_scope(|| {
|
trace_span!("process present files").in_scope(|| {
|
||||||
while let Ok(path) = present_files_rx.recv() {
|
while let Ok(path) = present_files_rx.recv() {
|
||||||
deleted_files.remove(&path);
|
deleted_files.remove(&path);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
trace_span!("process deleted files").in_scope(|| {
|
trace_span!("process deleted tree entries").in_scope(|| {
|
||||||
|
is_dirty |= !deleted_files.is_empty();
|
||||||
for file in &deleted_files {
|
for file in &deleted_files {
|
||||||
is_dirty = true;
|
|
||||||
file_states.remove(file);
|
|
||||||
tree_builder.set_or_remove(file.clone(), Merge::absent());
|
tree_builder.set_or_remove(file.clone(), Merge::absent());
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
trace_span!("process file states").in_scope(|| {
|
||||||
|
let changed_file_states = file_states_rx.iter().collect_vec();
|
||||||
|
is_dirty |= !changed_file_states.is_empty();
|
||||||
|
let file_states = self.file_states.make_mut();
|
||||||
|
file_states.extend(changed_file_states);
|
||||||
|
for file in &deleted_files {
|
||||||
|
file_states.remove(file);
|
||||||
|
}
|
||||||
|
});
|
||||||
trace_span!("write tree").in_scope(|| {
|
trace_span!("write tree").in_scope(|| {
|
||||||
let new_tree_id = tree_builder.write_tree(&self.store).unwrap();
|
let new_tree_id = tree_builder.write_tree(&self.store).unwrap();
|
||||||
is_dirty |= new_tree_id != self.tree_id;
|
is_dirty |= new_tree_id != self.tree_id;
|
||||||
|
@ -1205,6 +1207,8 @@ impl TreeState {
|
||||||
removed_files: 0,
|
removed_files: 0,
|
||||||
skipped_files: 0,
|
skipped_files: 0,
|
||||||
};
|
};
|
||||||
|
let mut changed_file_states = Vec::new();
|
||||||
|
let mut deleted_files = HashSet::new();
|
||||||
let mut diff_stream = old_tree.diff_stream(new_tree, matcher);
|
let mut diff_stream = old_tree.diff_stream(new_tree, matcher);
|
||||||
while let Some((path, diff)) = diff_stream.next().await {
|
while let Some((path, diff)) = diff_stream.next().await {
|
||||||
let (before, after) = diff?;
|
let (before, after) = diff?;
|
||||||
|
@ -1221,18 +1225,14 @@ impl TreeState {
|
||||||
fs::remove_file(&disk_path).ok();
|
fs::remove_file(&disk_path).ok();
|
||||||
}
|
}
|
||||||
if before.is_absent() && disk_path.exists() {
|
if before.is_absent() && disk_path.exists() {
|
||||||
self.file_states
|
changed_file_states.push((path, FileState::placeholder()));
|
||||||
.make_mut()
|
|
||||||
.insert(path, FileState::placeholder());
|
|
||||||
stats.skipped_files += 1;
|
stats.skipped_files += 1;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
if after.is_present() {
|
if after.is_present() {
|
||||||
let skip = create_parent_dirs(&self.working_copy_path, &path)?;
|
let skip = create_parent_dirs(&self.working_copy_path, &path)?;
|
||||||
if skip {
|
if skip {
|
||||||
self.file_states
|
changed_file_states.push((path, FileState::placeholder()));
|
||||||
.make_mut()
|
|
||||||
.insert(path, FileState::placeholder());
|
|
||||||
stats.skipped_files += 1;
|
stats.skipped_files += 1;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
@ -1248,7 +1248,7 @@ impl TreeState {
|
||||||
}
|
}
|
||||||
parent_dir = parent_dir.parent().unwrap();
|
parent_dir = parent_dir.parent().unwrap();
|
||||||
}
|
}
|
||||||
self.file_states.make_mut().remove(&path);
|
deleted_files.insert(path);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
MaterializedTreeValue::File {
|
MaterializedTreeValue::File {
|
||||||
|
@ -1270,7 +1270,12 @@ impl TreeState {
|
||||||
self.write_conflict(&disk_path, contents)?
|
self.write_conflict(&disk_path, contents)?
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
self.file_states.make_mut().insert(path, file_state);
|
changed_file_states.push((path, file_state));
|
||||||
|
}
|
||||||
|
let file_states = self.file_states.make_mut();
|
||||||
|
file_states.extend(changed_file_states);
|
||||||
|
for file in &deleted_files {
|
||||||
|
file_states.remove(file);
|
||||||
}
|
}
|
||||||
Ok(stats)
|
Ok(stats)
|
||||||
}
|
}
|
||||||
|
@ -1284,11 +1289,13 @@ impl TreeState {
|
||||||
})?;
|
})?;
|
||||||
|
|
||||||
let matcher = self.sparse_matcher();
|
let matcher = self.sparse_matcher();
|
||||||
|
let mut changed_file_states = Vec::new();
|
||||||
|
let mut deleted_files = HashSet::new();
|
||||||
let mut diff_stream = old_tree.diff_stream(new_tree, matcher.as_ref());
|
let mut diff_stream = old_tree.diff_stream(new_tree, matcher.as_ref());
|
||||||
while let Some((path, diff)) = diff_stream.next().await {
|
while let Some((path, diff)) = diff_stream.next().await {
|
||||||
let (_before, after) = diff?;
|
let (_before, after) = diff?;
|
||||||
if after.is_absent() {
|
if after.is_absent() {
|
||||||
self.file_states.make_mut().remove(&path);
|
deleted_files.insert(path);
|
||||||
} else {
|
} else {
|
||||||
let file_type = match after.into_resolved() {
|
let file_type = match after.into_resolved() {
|
||||||
Ok(value) => match value.unwrap() {
|
Ok(value) => match value.unwrap() {
|
||||||
|
@ -1320,9 +1327,14 @@ impl TreeState {
|
||||||
mtime: MillisSinceEpoch(0),
|
mtime: MillisSinceEpoch(0),
|
||||||
size: 0,
|
size: 0,
|
||||||
};
|
};
|
||||||
self.file_states.make_mut().insert(path.clone(), file_state);
|
changed_file_states.push((path, file_state));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
let file_states = self.file_states.make_mut();
|
||||||
|
file_states.extend(changed_file_states);
|
||||||
|
for file in &deleted_files {
|
||||||
|
file_states.remove(file);
|
||||||
|
}
|
||||||
self.tree_id = new_tree.id();
|
self.tree_id = new_tree.id();
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue