Skip to content

Commit 4ec22dd

Browse files
committed
templater: port annotation line content to template
I originally thought we would have to add BString template type first, but we can use opaque Template type instead.
1 parent 6f51696 commit 4ec22dd

File tree

8 files changed

+37
-11
lines changed

8 files changed

+37
-11
lines changed

CHANGELOG.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,8 @@ to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
6363
using `templates.backout_description`.
6464

6565
* New `AnnotationLine` templater type. Used in `templates.file_annotate`.
66-
Provides `self.commit()`, `self.line_number()`, and `self.first_line_in_hunk()`.
66+
Provides `self.commit()`, `.content()`, `.line_number()`, and
67+
`.first_line_in_hunk()`.
6768

6869
### Fixed bugs
6970

cli/src/commands/file/annotate.rs

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -50,13 +50,13 @@ pub(crate) struct FileAnnotateArgs {
5050
add = ArgValueCandidates::new(complete::all_revisions)
5151
)]
5252
revision: Option<RevisionArg>,
53-
/// Render a prefix for each line using the given template
53+
/// Render each line using the given template
5454
///
5555
/// All 0-argument methods of the [`AnnotationLine` type] are available as
5656
/// keywords in the [template expression].
5757
///
58-
/// If not specified, this defaults to the
59-
/// `templates.file_annotate` setting.
58+
/// If not specified, this defaults to the `templates.file_annotate`
59+
/// setting.
6060
///
6161
/// [template expression]:
6262
/// https://jj-vcs.github.io/jj/latest/templates/
@@ -123,17 +123,17 @@ fn render_file_annotation(
123123
ui.request_pager();
124124
let mut formatter = ui.stdout_formatter();
125125
let mut last_id = None;
126-
for (line_number, (commit_id, line)) in annotation.lines().enumerate() {
126+
for (line_number, (commit_id, content)) in annotation.lines().enumerate() {
127127
let commit_id = commit_id.expect("should reached to the empty ancestor");
128128
let commit = repo.store().get_commit(commit_id)?;
129129
let first_line_in_hunk = last_id != Some(commit_id);
130130
let annotation_line = AnnotationLine {
131131
commit,
132+
content: content.to_owned(),
132133
line_number: line_number + 1,
133134
first_line_in_hunk,
134135
};
135136
template_render.format(&annotation_line, formatter.as_mut())?;
136-
formatter.write_all(line)?;
137137
last_id = Some(commit_id);
138138
}
139139

cli/src/commit_templater.rs

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ use std::collections::HashMap;
1919
use std::io;
2020
use std::rc::Rc;
2121

22+
use bstr::BString;
2223
use futures::stream::BoxStream;
2324
use futures::StreamExt as _;
2425
use futures::TryStreamExt as _;
@@ -2218,10 +2219,10 @@ pub fn builtin_cryptographic_signature_methods<'repo>(
22182219
map
22192220
}
22202221

2221-
// TODO: add `line: BString` field when available in template language
22222222
#[derive(Debug, Clone)]
22232223
pub struct AnnotationLine {
22242224
pub commit: Commit,
2225+
pub content: BString,
22252226
pub line_number: usize,
22262227
pub first_line_in_hunk: bool,
22272228
}
@@ -2238,6 +2239,15 @@ pub fn builtin_annotation_line_methods<'repo>(
22382239
Ok(L::wrap_commit(out_property))
22392240
},
22402241
);
2242+
map.insert(
2243+
"content",
2244+
|_language, _diagnostics, _build_ctx, self_property, function| {
2245+
function.expect_no_arguments()?;
2246+
let out_property = self_property.map(|line| line.content);
2247+
// TODO: Add Bytes or BString template type?
2248+
Ok(L::wrap_template(out_property.into_template()))
2249+
},
2250+
);
22412251
map.insert(
22422252
"line_number",
22432253
|_language, _diagnostics, _build_ctx, self_property, function| {

cli/src/config/templates.toml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,8 +27,8 @@ separate(" ",
2727
commit.change_id().shortest(8),
2828
pad_end(8, truncate_end(8, commit.author().email().local())),
2929
commit_timestamp(commit).local().format('%Y-%m-%d %H:%M:%S'),
30-
pad_start(4, line_number) ++ ": ",
31-
)
30+
pad_start(4, line_number),
31+
) ++ ": " ++ content
3232
'''
3333

3434
config_list = '''

cli/src/templater.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,8 @@ use std::io::Write;
2020
use std::iter;
2121
use std::rc::Rc;
2222

23+
use bstr::BStr;
24+
use bstr::BString;
2325
use jj_lib::backend::Signature;
2426
use jj_lib::backend::Timestamp;
2527
use jj_lib::config::ConfigValue;
@@ -69,6 +71,18 @@ impl<T: Template> Template for Option<T> {
6971
}
7072
}
7173

74+
impl Template for BString {
75+
fn format(&self, formatter: &mut TemplateFormatter) -> io::Result<()> {
76+
formatter.as_mut().write_all(self)
77+
}
78+
}
79+
80+
impl Template for &BStr {
81+
fn format(&self, formatter: &mut TemplateFormatter) -> io::Result<()> {
82+
formatter.as_mut().write_all(self)
83+
}
84+
}
85+
7286
impl Template for ConfigValue {
7387
fn format(&self, formatter: &mut TemplateFormatter) -> io::Result<()> {
7488
write!(formatter, "{self}")

cli/tests/[email protected]

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -898,7 +898,7 @@ Annotates a revision line by line. Each line includes the source change that int
898898
###### **Options:**
899899

900900
* `-r`, `--revision <REVSET>` — an optional revision to start at
901-
* `-T`, `--template <TEMPLATE>` — Render a prefix for each line using the given template
901+
* `-T`, `--template <TEMPLATE>` — Render each line using the given template
902902

903903
All 0-argument methods of the [`AnnotationLine` type] are available as keywords in the [template expression].
904904

cli/tests/test_file_annotate_command.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -179,7 +179,7 @@ fn test_annotate_with_template() {
179179
commit_timestamp(commit).local().format('%Y-%m-%d %H:%M:%S')
180180
++ " "
181181
++ commit.author(),
182-
) ++ "\n") ++ pad_start(4, line_number) ++ ": "
182+
) ++ "\n") ++ pad_start(4, line_number) ++ ": " ++ content
183183
"#};
184184

185185
let stdout = test_env.jj_cmd_success(

docs/templates.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,7 @@ The following functions are defined.
9595
The following methods are defined.
9696

9797
* `.commit() -> Commit`: Commit responsible for changing the relevant line.
98+
* `.content() -> Template`: Line content including newline character.
9899
* `.line_number() -> Integer`: 1-based line number.
99100
* `.first_line_in_hunk() -> Boolean`: False when the directly preceding line
100101
references the same commit.

0 commit comments

Comments
 (0)