forked from mirrors/jj
templater: fast-path empty
and conflict
to not read trees
When there's a single parent, we can determine if a commit is empty by just comparing the tree ids. Also, when using tree-level conflicts, we don't need to read the trees to determine if there's a conflict. This patch adds both of those fast paths, speeding up `jj log -r ::main` from 317 ms to 227 ms (-28.4%). It has much larger impact with our cloud-based backend at Google (~5x faster). I made the same fix in the revset engine and the Git push code (thanks to Yuya for the suggestion).
This commit is contained in:
parent
e5ad32e29e
commit
e50f6acab1
4 changed files with 16 additions and 5 deletions
|
@ -905,7 +905,7 @@ fn cmd_git_push(
|
|||
{
|
||||
reasons.push("it has no author and/or committer set");
|
||||
}
|
||||
if commit.tree()?.has_conflict() {
|
||||
if commit.has_conflict()? {
|
||||
reasons.push("it has conflicts");
|
||||
}
|
||||
if !reasons.is_empty() {
|
||||
|
|
|
@ -299,10 +299,13 @@ fn build_commit_keyword_opt<'repo>(
|
|||
let maybe_entries = repo.resolve_change_id(commit.change_id());
|
||||
maybe_entries.map_or(true, |entries| !entries.contains(commit.id()))
|
||||
})),
|
||||
"conflict" => language.wrap_boolean(wrap_fn(property, |commit| {
|
||||
commit.tree().unwrap().has_conflict()
|
||||
})),
|
||||
"conflict" => {
|
||||
language.wrap_boolean(wrap_fn(property, |commit| commit.has_conflict().unwrap()))
|
||||
}
|
||||
"empty" => language.wrap_boolean(wrap_fn(property, |commit| {
|
||||
if let [parent] = &commit.parents()[..] {
|
||||
return parent.tree_id() == commit.tree_id();
|
||||
}
|
||||
let parent_tree = rewrite::merge_commit_trees(repo, &commit.parents()).unwrap();
|
||||
*commit.tree_id() == parent_tree.id()
|
||||
})),
|
||||
|
|
|
@ -108,6 +108,14 @@ impl Commit {
|
|||
&self.data.root_tree
|
||||
}
|
||||
|
||||
pub fn has_conflict(&self) -> Result<bool, BackendError> {
|
||||
if let MergedTreeId::Merge(tree_ids) = self.tree_id() {
|
||||
Ok(!tree_ids.is_resolved())
|
||||
} else {
|
||||
Ok(self.tree()?.has_conflict())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn change_id(&self) -> &ChangeId {
|
||||
&self.data.change_id
|
||||
}
|
||||
|
|
|
@ -869,7 +869,7 @@ fn build_predicate_fn<'index>(
|
|||
}
|
||||
RevsetFilterPredicate::HasConflict => pure_predicate_fn(move |entry| {
|
||||
let commit = store.get_commit(&entry.commit_id()).unwrap();
|
||||
commit.tree().unwrap().has_conflict()
|
||||
commit.has_conflict().unwrap()
|
||||
}),
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue