ok/jj
1
0
Fork 0
forked from mirrors/jj

next/prev: Fetch descendants with more correctness.

See context in [this discussion](https://github.com/martinvonz/jj/pull/3935#discussion_r1649520967)

Fixes #3947
This commit is contained in:
Essien Ita Essien 2024-08-16 01:10:44 +01:00 committed by Essien Ita Essien
parent 6d0a092410
commit e25ec536ed
2 changed files with 91 additions and 16 deletions

View file

@ -121,27 +121,27 @@ impl Direction {
start_revset: &Rc<RevsetExpression>, start_revset: &Rc<RevsetExpression>,
args: &MovementArgsInternal, args: &MovementArgsInternal,
) -> Result<Rc<RevsetExpression>, CommandError> { ) -> Result<Rc<RevsetExpression>, CommandError> {
let target_revset = match (self, args.conflict) { let nth = match (self, args.should_edit) {
(Direction::Next, true) => start_revset (Direction::Next, true) => start_revset.descendants_at(args.offset),
(Direction::Next, false) => start_revset
.children() .children()
.minus(working_revset)
.descendants_at(args.offset - 1),
(Direction::Prev, _) => start_revset.ancestors_at(args.offset),
};
let target_revset = match (self, args.conflict) {
(_, false) => nth,
(Direction::Next, true) => nth
.descendants() .descendants()
.filtered(RevsetFilterPredicate::HasConflict) .filtered(RevsetFilterPredicate::HasConflict)
.roots() .roots(),
.minus(working_revset),
(Direction::Next, false) => start_revset
.descendants_at(args.offset)
.minus(working_revset),
(Direction::Prev, true) =>
// If people desire to move to the root conflict, replace the `heads()` below // If people desire to move to the root conflict, replace the `heads()` below
// with `roots(). But let's wait for feedback. // with `roots(). But let's wait for feedback.
{ (Direction::Prev, true) => nth
start_revset .ancestors()
.parents() .filtered(RevsetFilterPredicate::HasConflict)
.ancestors() .heads(),
.filtered(RevsetFilterPredicate::HasConflict)
.heads()
}
(Direction::Prev, false) => start_revset.ancestors_at(args.offset),
}; };
Ok(target_revset) Ok(target_revset)

View file

@ -1112,6 +1112,81 @@ fn test_movement_edit_mode_false() {
"###); "###);
} }
#[test]
fn test_next_offset_when_wc_has_descendants() {
let test_env = TestEnvironment::default();
test_env.add_config(r#"ui.movement.edit = false"#);
test_env.jj_cmd_ok(test_env.env_root(), &["init", "repo", "--git"]);
let repo_path = test_env.env_root().join("repo");
test_env.jj_cmd_ok(&repo_path, &["commit", "-m", "base"]);
test_env.jj_cmd_ok(&repo_path, &["commit", "-m", "right-wc"]);
test_env.jj_cmd_ok(&repo_path, &["commit", "-m", "right-1"]);
test_env.jj_cmd_ok(&repo_path, &["commit", "-m", "right-2"]);
test_env.jj_cmd_ok(&repo_path, &["new", "description(base)"]);
test_env.jj_cmd_ok(&repo_path, &["commit", "-m", "left-wc"]);
test_env.jj_cmd_ok(&repo_path, &["commit", "-m", "left-1"]);
test_env.jj_cmd_ok(&repo_path, &["commit", "-m", "left-2"]);
test_env.jj_cmd_ok(&repo_path, &["edit", "description(right-wc)"]);
insta::assert_snapshot!(get_log_output(&test_env, &repo_path), @r###"
vruxwmqvtpmx left-2
yqosqzytrlsw left-1
royxmykxtrkr left-wc
zsuskulnrvyr right-2
kkmpptxzrspx right-1
@ rlvkpnrzqnoo right-wc
qpvuntsmwlqt base
zzzzzzzzzzzz
"###);
test_env.jj_cmd_ok(&repo_path, &["next", "2"]);
insta::assert_snapshot!(get_log_output(&test_env, &repo_path), @r###"
@ kmkuslswpqwq
vruxwmqvtpmx left-2
yqosqzytrlsw left-1
royxmykxtrkr left-wc
zsuskulnrvyr right-2
kkmpptxzrspx right-1
rlvkpnrzqnoo right-wc
qpvuntsmwlqt base
zzzzzzzzzzzz
"###);
test_env.jj_cmd_ok(&repo_path, &["edit", "description(left-wc)"]);
insta::assert_snapshot!(get_log_output(&test_env, &repo_path), @r###"
vruxwmqvtpmx left-2
yqosqzytrlsw left-1
@ royxmykxtrkr left-wc
zsuskulnrvyr right-2
kkmpptxzrspx right-1
rlvkpnrzqnoo right-wc
qpvuntsmwlqt base
zzzzzzzzzzzz
"###);
test_env.jj_cmd_ok(&repo_path, &["next"]);
insta::assert_snapshot!(get_log_output(&test_env, &repo_path), @r###"
@ nkmrtpmomlro
zsuskulnrvyr right-2
kkmpptxzrspx right-1
rlvkpnrzqnoo right-wc
vruxwmqvtpmx left-2
yqosqzytrlsw left-1
royxmykxtrkr left-wc
qpvuntsmwlqt base
zzzzzzzzzzzz
"###);
}
fn get_log_output(test_env: &TestEnvironment, cwd: &Path) -> String { fn get_log_output(test_env: &TestEnvironment, cwd: &Path) -> String {
let template = r#"separate(" ", change_id.short(), local_bookmarks, if(conflict, "conflict"), description)"#; let template = r#"separate(" ", change_id.short(), local_bookmarks, if(conflict, "conflict"), description)"#;
test_env.jj_cmd_success(cwd, &["log", "-T", template]) test_env.jj_cmd_success(cwd, &["log", "-T", template])