From 92af544de0880c80a6d1c5db536ce534afbd402d Mon Sep 17 00:00:00 2001 From: Martin von Zweigbergk Date: Wed, 2 Feb 2022 10:14:03 -0800 Subject: [PATCH] templater: make `current_checkout` be about the current workspace (#13) We don't use the `current_checkout` keyword in out default templates, but let's still fix it, so it refers to the current workspace. --- src/commands.rs | 63 ++++++++++++++++++++++++++++++++---------- src/template_parser.rs | 43 +++++++++++++++++++--------- src/templater.rs | 4 ++- src/ui.rs | 11 ++++++-- 4 files changed, 90 insertions(+), 31 deletions(-) diff --git a/src/commands.rs b/src/commands.rs index 6d2897e9a..37c926642 100644 --- a/src/commands.rs +++ b/src/commands.rs @@ -809,7 +809,7 @@ fn update_working_copy( )) })?; ui.write("Working copy now at: ")?; - ui.write_commit_summary(repo.as_repo_ref(), &new_commit)?; + ui.write_commit_summary(repo.as_repo_ref(), workspace_id, &new_commit)?; ui.write("\n")?; Ok(Some(stats)) } @@ -1929,8 +1929,11 @@ fn cmd_show(ui: &mut Ui, command: &CommandHelper, args: &ArgMatches) -> Result<( description "\n" )"#; - let template = - crate::template_parser::parse_commit_template(repo.as_repo_ref(), template_string); + let template = crate::template_parser::parse_commit_template( + repo.as_repo_ref(), + &workspace_command.workspace_id(), + template_string, + ); template.format(&commit, ui.stdout_formatter().as_mut())?; show_diff(ui, repo, workspace_root, args, diff_iterator)?; Ok(()) @@ -2426,10 +2429,15 @@ fn cmd_status( let maybe_checkout = maybe_checkout_id.map(|id| repo.store().get_commit(id).unwrap()); if let Some(checkout_commit) = &maybe_checkout { ui.write("Parent commit: ")?; - ui.write_commit_summary(repo.as_repo_ref(), &checkout_commit.parents()[0])?; + let workspace_id = workspace_command.workspace_id(); + ui.write_commit_summary( + repo.as_repo_ref(), + &workspace_id, + &checkout_commit.parents()[0], + )?; ui.write("\n")?; ui.write("Working copy : ")?; - ui.write_commit_summary(repo.as_repo_ref(), checkout_commit)?; + ui.write_commit_summary(repo.as_repo_ref(), &workspace_id, checkout_commit)?; ui.write("\n")?; } @@ -2551,8 +2559,11 @@ fn cmd_log(ui: &mut Ui, command: &CommandHelper, args: &ArgMatches) -> Result<() Some(value) => value.to_string(), None => log_template(ui.settings()), }; - let template = - crate::template_parser::parse_commit_template(repo.as_repo_ref(), &template_string); + let template = crate::template_parser::parse_commit_template( + repo.as_repo_ref(), + &workspace_command.workspace_id(), + &template_string, + ); let mut formatter = ui.stdout_formatter(); let mut formatter = formatter.as_mut(); @@ -2631,6 +2642,7 @@ fn cmd_obslog(ui: &mut Ui, command: &CommandHelper, args: &ArgMatches) -> Result }; let template = crate::template_parser::parse_commit_template( workspace_command.repo().as_repo_ref(), + &workspace_command.workspace_id(), &template_string, ); @@ -2807,7 +2819,11 @@ fn cmd_duplicate( .generate_new_change_id() .write_to_repo(mut_repo); ui.write("Created: ")?; - ui.write_commit_summary(mut_repo.as_repo_ref(), &new_commit)?; + ui.write_commit_summary( + mut_repo.as_repo_ref(), + &workspace_command.workspace_id(), + &new_commit, + )?; ui.write("\n")?; workspace_command.finish_transaction(ui, tx)?; Ok(()) @@ -3142,7 +3158,11 @@ side. If you don't make any changes, then the operation will be aborted. .set_tree(tree_id) .write_to_repo(mut_repo); ui.write("Created ")?; - ui.write_commit_summary(mut_repo.as_repo_ref(), &new_commit)?; + ui.write_commit_summary( + mut_repo.as_repo_ref(), + &workspace_command.workspace_id(), + &new_commit, + )?; ui.write("\n")?; workspace_command.finish_transaction(ui, tx)?; } @@ -3176,7 +3196,11 @@ don't make any changes, then the operation will be aborted.", .set_tree(tree_id) .write_to_repo(mut_repo); ui.write("Created ")?; - ui.write_commit_summary(mut_repo.as_repo_ref(), &new_commit)?; + ui.write_commit_summary( + mut_repo.as_repo_ref(), + &workspace_command.workspace_id(), + &new_commit, + )?; ui.write("\n")?; workspace_command.finish_transaction(ui, tx)?; } @@ -3240,9 +3264,17 @@ any changes, then the operation will be aborted. writeln!(ui, "Rebased {} descendant commits", num_rebased)?; } ui.write("First part: ")?; - ui.write_commit_summary(mut_repo.as_repo_ref(), &first_commit)?; + ui.write_commit_summary( + mut_repo.as_repo_ref(), + &workspace_command.workspace_id(), + &first_commit, + )?; ui.write("\nSecond part: ")?; - ui.write_commit_summary(mut_repo.as_repo_ref(), &second_commit)?; + ui.write_commit_summary( + mut_repo.as_repo_ref(), + &workspace_command.workspace_id(), + &second_commit, + )?; ui.write("\n")?; workspace_command.finish_transaction(ui, tx)?; } @@ -3473,13 +3505,14 @@ fn cmd_branches( let workspace_command = command.workspace_helper(ui)?; let repo = workspace_command.repo(); + let workspace_id = workspace_command.workspace_id(); let print_branch_target = |ui: &mut Ui, target: Option<&RefTarget>| -> Result<(), CommandError> { match target { Some(RefTarget::Normal(id)) => { write!(ui, ": ")?; let commit = repo.store().get_commit(id)?; - ui.write_commit_summary(repo.as_repo_ref(), &commit)?; + ui.write_commit_summary(repo.as_repo_ref(), &workspace_id, &commit)?; writeln!(ui)?; } Some(RefTarget::Conflict { adds, removes }) => { @@ -3491,13 +3524,13 @@ fn cmd_branches( for id in removes { let commit = repo.store().get_commit(id)?; write!(ui, " - ")?; - ui.write_commit_summary(repo.as_repo_ref(), &commit)?; + ui.write_commit_summary(repo.as_repo_ref(), &workspace_id, &commit)?; writeln!(ui)?; } for id in adds { let commit = repo.store().get_commit(id)?; write!(ui, " + ")?; - ui.write_commit_summary(repo.as_repo_ref(), &commit)?; + ui.write_commit_summary(repo.as_repo_ref(), &workspace_id, &commit)?; writeln!(ui)?; } } diff --git a/src/template_parser.rs b/src/template_parser.rs index 4089ea7bf..2db330d80 100644 --- a/src/template_parser.rs +++ b/src/template_parser.rs @@ -17,6 +17,7 @@ extern crate pest; use chrono::{FixedOffset, TimeZone, Utc}; use jujutsu_lib::backend::{CommitId, Signature}; use jujutsu_lib::commit::Commit; +use jujutsu_lib::op_store::WorkspaceId; use jujutsu_lib::repo::RepoRef; use pest::iterators::{Pair, Pairs}; use pest::Parser; @@ -229,7 +230,11 @@ impl<'a, I: 'a> Property<'a, I> { } } -fn parse_commit_keyword<'a>(repo: RepoRef<'a>, pair: Pair) -> (Property<'a, Commit>, String) { +fn parse_commit_keyword<'a>( + repo: RepoRef<'a>, + workspace_id: &WorkspaceId, + pair: Pair, +) -> (Property<'a, Commit>, String) { assert_eq!(pair.as_rule(), Rule::identifier); let property = match pair.as_str() { "description" => Property::String(Box::new(DescriptionProperty)), @@ -238,7 +243,10 @@ fn parse_commit_keyword<'a>(repo: RepoRef<'a>, pair: Pair) -> (Property<'a "author" => Property::Signature(Box::new(AuthorProperty)), "committer" => Property::Signature(Box::new(CommitterProperty)), "open" => Property::Boolean(Box::new(OpenProperty)), - "current_checkout" => Property::Boolean(Box::new(CurrentCheckoutProperty { repo })), + "current_checkout" => Property::Boolean(Box::new(CurrentCheckoutProperty { + repo, + workspace_id: workspace_id.clone(), + })), "branches" => Property::String(Box::new(BranchProperty { repo })), "tags" => Property::String(Box::new(TagProperty { repo })), "git_refs" => Property::String(Box::new(GitRefsProperty { repo })), @@ -272,6 +280,7 @@ fn coerce_to_string<'a, I: 'a>( fn parse_boolean_commit_property<'a>( repo: RepoRef<'a>, + workspace_id: &WorkspaceId, pair: Pair, ) -> Box + 'a> { let mut inner = pair.into_inner(); @@ -279,7 +288,7 @@ fn parse_boolean_commit_property<'a>( let _method = inner.next().unwrap(); assert!(inner.next().is_none()); match pair.as_rule() { - Rule::identifier => match parse_commit_keyword(repo, pair.clone()).0 { + Rule::identifier => match parse_commit_keyword(repo, workspace_id, pair.clone()).0 { Property::Boolean(property) => property, _ => panic!("cannot yet use this as boolean: {:?}", pair), }, @@ -287,7 +296,11 @@ fn parse_boolean_commit_property<'a>( } } -fn parse_commit_term<'a>(repo: RepoRef<'a>, pair: Pair) -> Box + 'a> { +fn parse_commit_term<'a>( + repo: RepoRef<'a>, + workspace_id: &WorkspaceId, + pair: Pair, +) -> Box + 'a> { assert_eq!(pair.as_rule(), Rule::term); if pair.as_str().is_empty() { Box::new(LiteralTemplate(String::new())) @@ -312,7 +325,7 @@ fn parse_commit_term<'a>(repo: RepoRef<'a>, pair: Pair) -> Box { - let (term_property, labels) = parse_commit_keyword(repo, expr); + let (term_property, labels) = parse_commit_keyword(repo, workspace_id, expr); let property = parse_method_chain(maybe_method, term_property); let string_property = coerce_to_string(property); Box::new(LabelTemplate::new( @@ -330,6 +343,7 @@ fn parse_commit_term<'a>(repo: RepoRef<'a>, pair: Pair) -> Box(repo: RepoRef<'a>, pair: Pair) -> Box + 'a> = - parse_commit_template_rule(repo, arg_template); + parse_commit_template_rule(repo, workspace_id, arg_template); let get_labels = move |commit: &Commit| -> String { let mut buf: Vec = vec![]; { @@ -355,15 +369,16 @@ fn parse_commit_term<'a>(repo: RepoRef<'a>, pair: Pair) -> Box { let condition_pair = inner.next().unwrap(); let condition_template = condition_pair.into_inner().next().unwrap(); - let condition = parse_boolean_commit_property(repo, condition_template); + let condition = + parse_boolean_commit_property(repo, workspace_id, condition_template); let true_template = match inner.next() { None => panic!("if() requires at least two arguments"), - Some(pair) => parse_commit_template_rule(repo, pair), + Some(pair) => parse_commit_template_rule(repo, workspace_id, pair), }; let false_template = inner .next() - .map(|pair| parse_commit_template_rule(repo, pair)); + .map(|pair| parse_commit_template_rule(repo, workspace_id, pair)); if inner.next().is_some() { panic!("if() accepts at most three arguments") } @@ -383,20 +398,21 @@ fn parse_commit_term<'a>(repo: RepoRef<'a>, pair: Pair) -> Box( repo: RepoRef<'a>, + workspace_id: &WorkspaceId, pair: Pair, ) -> Box + 'a> { match pair.as_rule() { Rule::template => { let mut inner = pair.into_inner(); - let formatter = parse_commit_template_rule(repo, inner.next().unwrap()); + let formatter = parse_commit_template_rule(repo, workspace_id, inner.next().unwrap()); assert!(inner.next().is_none()); formatter } - Rule::term => parse_commit_term(repo, pair), + Rule::term => parse_commit_term(repo, workspace_id, pair), Rule::list => { let mut formatters: Vec>> = vec![]; for inner_pair in pair.into_inner() { - formatters.push(parse_commit_template_rule(repo, inner_pair)); + formatters.push(parse_commit_template_rule(repo, workspace_id, inner_pair)); } Box::new(ListTemplate(formatters)) } @@ -406,6 +422,7 @@ fn parse_commit_template_rule<'a>( pub fn parse_commit_template<'a>( repo: RepoRef<'a>, + workspace_id: &WorkspaceId, template_text: &str, ) -> Box + 'a> { let mut pairs: Pairs = TemplateParser::parse(Rule::template, template_text).unwrap(); @@ -419,5 +436,5 @@ pub fn parse_commit_template<'a>( first_pair.as_span().end() ); - parse_commit_template_rule(repo, first_pair) + parse_commit_template_rule(repo, workspace_id, first_pair) } diff --git a/src/templater.rs b/src/templater.rs index 88b3805ad..471ba810e 100644 --- a/src/templater.rs +++ b/src/templater.rs @@ -20,6 +20,7 @@ use std::ops::{Add, AddAssign}; use itertools::Itertools; use jujutsu_lib::backend::{ChangeId, CommitId, Signature}; use jujutsu_lib::commit::Commit; +use jujutsu_lib::op_store::WorkspaceId; use jujutsu_lib::repo::RepoRef; use jujutsu_lib::revset::RevsetExpression; @@ -206,11 +207,12 @@ impl<'r> TemplateProperty for OpenProperty { pub struct CurrentCheckoutProperty<'a> { pub repo: RepoRef<'a>, + pub workspace_id: WorkspaceId, } impl TemplateProperty for CurrentCheckoutProperty<'_> { fn extract(&self, context: &Commit) -> bool { - context.id() == self.repo.view().checkout() + Some(context.id()) == self.repo.view().get_checkout(&self.workspace_id) } } diff --git a/src/ui.rs b/src/ui.rs index 49a8d7af0..6d214b939 100644 --- a/src/ui.rs +++ b/src/ui.rs @@ -19,6 +19,7 @@ use std::{fmt, io}; use atty::Stream; use jujutsu_lib::commit::Commit; +use jujutsu_lib::op_store::WorkspaceId; use jujutsu_lib::repo::RepoRef; use jujutsu_lib::repo_path::{RepoPath, RepoPathComponent, RepoPathJoin}; use jujutsu_lib::settings::UserSettings; @@ -111,7 +112,12 @@ impl<'stdout> Ui<'stdout> { Ok(()) } - pub fn write_commit_summary(&mut self, repo: RepoRef, commit: &Commit) -> io::Result<()> { + pub fn write_commit_summary( + &mut self, + repo: RepoRef, + workspace_id: &WorkspaceId, + commit: &Commit, + ) -> io::Result<()> { let template_string = self .settings .config() @@ -121,7 +127,8 @@ impl<'stdout> Ui<'stdout> { r#"label(if(open, "open"), commit_id.short() " " description.first_line())"#, ) }); - let template = crate::template_parser::parse_commit_template(repo, &template_string); + let template = + crate::template_parser::parse_commit_template(repo, workspace_id, &template_string); let mut formatter = self.stdout_formatter(); let mut template_writer = TemplateFormatter::new(template, formatter.as_mut()); template_writer.format(commit)?;