mirror of
https://github.com/jj-vcs/jj.git
synced 2025-12-23 06:01:01 +00:00
We currently don't allow you to create two identical commits. It results in an internal error. I think we need to allow it. Let's start by testing the current behavior. I created these as CLI tests because I want to make sure that `evolog` and `op diff` get tested, including rendering.
223 lines
8 KiB
Rust
223 lines
8 KiB
Rust
// Copyright 2025 The Jujutsu Authors
|
|
//
|
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
|
// you may not use this file except in compliance with the License.
|
|
// You may obtain a copy of the License at
|
|
//
|
|
// https://www.apache.org/licenses/LICENSE-2.0
|
|
//
|
|
// Unless required by applicable law or agreed to in writing, software
|
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
// See the License for the specific language governing permissions and
|
|
// limitations under the License.
|
|
|
|
use crate::common::CommandOutput;
|
|
use crate::common::TestEnvironment;
|
|
use crate::common::TestWorkDir;
|
|
|
|
fn create_test_environment() -> TestEnvironment {
|
|
let mut test_env = TestEnvironment::default();
|
|
test_env.add_env_var("JJ_RANDOMNESS_SEED", "0");
|
|
test_env.add_env_var("JJ_TIMESTAMP", "2001-01-01T00:00:00+00:00");
|
|
test_env.add_config("experimental.record-predecessors-in-commit = false");
|
|
test_env
|
|
}
|
|
|
|
#[test]
|
|
fn test_identical_commits() {
|
|
let test_env = create_test_environment();
|
|
test_env.run_jj_in(".", ["git", "init", "repo"]).success();
|
|
let work_dir = test_env.work_dir("repo");
|
|
|
|
work_dir.run_jj(["new", "root()", "-m=test"]).success();
|
|
// TODO: Should not fail
|
|
insta::assert_snapshot!(work_dir.run_jj(["new", "root()", "-m=test"]), @r"
|
|
------- stderr -------
|
|
Internal error: Unexpected error from backend
|
|
Caused by: Newly-created commit e94ed463cbb0776612e308eba2ecaae74a7f8a73 already exists
|
|
[EOF]
|
|
[exit status: 255]
|
|
");
|
|
// There should be a single "test" commit
|
|
insta::assert_snapshot!(get_log_output(&work_dir), @r"
|
|
@ e94ed463cbb0 test
|
|
◆ 000000000000
|
|
[EOF]
|
|
");
|
|
}
|
|
|
|
/// Create "test1" commit, then rewrite it in the same way "concurrently" (by
|
|
/// starting at the same operation)
|
|
#[test]
|
|
fn test_identical_commits_concurrently() {
|
|
let test_env = create_test_environment();
|
|
test_env.run_jj_in(".", ["git", "init", "repo"]).success();
|
|
let work_dir = test_env.work_dir("repo");
|
|
|
|
work_dir.run_jj(["new", "root()", "-m=test1"]).success();
|
|
work_dir.run_jj(["describe", "-m=test2"]).success();
|
|
work_dir
|
|
.run_jj(["describe", "-m=test2", "--at-op=@-"])
|
|
.success();
|
|
// There should be a single "test2" commit
|
|
insta::assert_snapshot!(get_log_output(&work_dir), @r"
|
|
@ c5abd2256ac0 test2
|
|
◆ 000000000000
|
|
[EOF]
|
|
------- stderr -------
|
|
Concurrent modification detected, resolving automatically.
|
|
[EOF]
|
|
");
|
|
}
|
|
|
|
/// Create commit "test1", then rewrite it to "test2", then rewrite it back to
|
|
/// "test1"
|
|
#[test]
|
|
fn test_identical_commits_by_cycling_rewrite() {
|
|
let test_env = create_test_environment();
|
|
test_env.run_jj_in(".", ["git", "init", "repo"]).success();
|
|
let work_dir = test_env.work_dir("repo");
|
|
|
|
work_dir.run_jj(["new", "root()", "-m=test1"]).success();
|
|
work_dir.run_jj(["describe", "-m=test2"]).success();
|
|
// TODO: Should not fail
|
|
insta::assert_snapshot!(work_dir.run_jj(["describe", "-m=test1"]), @r"
|
|
------- stderr -------
|
|
Internal error: Unexpected error from backend
|
|
Caused by: Newly-created commit 053222c21fa06b9492e22346f8f70e732231ad4f already exists
|
|
[EOF]
|
|
[exit status: 255]
|
|
");
|
|
insta::assert_snapshot!(work_dir.run_jj(["evolog"]), @r"
|
|
@ oxmtprsl test.user@example.com 2001-01-01 11:00:00 c5abd225
|
|
│ (empty) test2
|
|
│ -- operation f184243937e9 describe commit 053222c21fa06b9492e22346f8f70e732231ad4f
|
|
○ oxmtprsl hidden test.user@example.com 2001-01-01 11:00:00 053222c2
|
|
(empty) test1
|
|
-- operation 509c18587028 new empty commit
|
|
[EOF]
|
|
");
|
|
// TODO: Test `jj op diff --from @--`
|
|
}
|
|
|
|
/// Create commits "test1" and "test2" and rewrite "test1". Then rewrite "test2"
|
|
/// to become identical to the rewritten "test1".
|
|
#[test]
|
|
fn test_identical_commits_by_convergent_rewrite() {
|
|
let test_env = create_test_environment();
|
|
test_env.run_jj_in(".", ["git", "init", "repo"]).success();
|
|
let work_dir = test_env.work_dir("repo");
|
|
|
|
work_dir.run_jj(["new", "root()", "-m=test1"]).success();
|
|
work_dir.run_jj(["new", "root()", "-m=test2"]).success();
|
|
work_dir
|
|
.run_jj(["describe", "-m=test3", "description(test1)"])
|
|
.success();
|
|
// TODO: Should not fail
|
|
insta::assert_snapshot!(work_dir.run_jj(["describe", "-m=test3", "description(test2)"]), @r"
|
|
------- stderr -------
|
|
Internal error: Unexpected error from backend
|
|
Caused by: Newly-created commit 460733f1f6f9283d5a810b231dd3f846fd3a6f04 already exists
|
|
[EOF]
|
|
[exit status: 255]
|
|
");
|
|
// TODO: The "test3" commit should have either "test1" or "test2" as predecessor
|
|
// (or both?)
|
|
insta::assert_snapshot!(work_dir.run_jj(["evolog"]), @r"
|
|
@ oxmtprsl?? test.user@example.com 2001-01-01 11:00:00 c5abd225
|
|
(empty) test2
|
|
-- operation a1561db9359b new empty commit
|
|
[EOF]
|
|
");
|
|
}
|
|
|
|
/// Create commits "test1" and "test2" and then rewrite both of them to be
|
|
/// identical in a single operation
|
|
#[test]
|
|
fn test_identical_commits_by_convergent_rewrite_one_operation() {
|
|
let test_env = create_test_environment();
|
|
test_env.run_jj_in(".", ["git", "init", "repo"]).success();
|
|
let work_dir = test_env.work_dir("repo");
|
|
|
|
work_dir.run_jj(["new", "root()", "-m=test1"]).success();
|
|
work_dir.run_jj(["new", "root()", "-m=test2"]).success();
|
|
// TODO: Should not fail
|
|
insta::assert_snapshot!(work_dir.run_jj(["describe", "-m=test3", "root()+"]), @r"
|
|
------- stderr -------
|
|
Internal error: Unexpected error from backend
|
|
Caused by: Newly-created commit 460733f1f6f9283d5a810b231dd3f846fd3a6f04 already exists
|
|
[EOF]
|
|
[exit status: 255]
|
|
");
|
|
// TODO: There should be a single "test3" commit
|
|
insta::assert_snapshot!(get_log_output(&work_dir), @r"
|
|
@ c5abd2256ac0 test2
|
|
│ ○ 053222c21fa0 test1
|
|
├─╯
|
|
◆ 000000000000
|
|
[EOF]
|
|
");
|
|
// TODO: The "test3" commit should have either "test1" or "test2" as predecessor
|
|
// (or both?)
|
|
insta::assert_snapshot!(work_dir.run_jj(["evolog"]), @r"
|
|
@ oxmtprsl?? test.user@example.com 2001-01-01 11:00:00 c5abd225
|
|
(empty) test2
|
|
-- operation a1561db9359b new empty commit
|
|
[EOF]
|
|
");
|
|
}
|
|
|
|
/// Create two stacked commits. Then reorder them so they become rewrites of
|
|
/// each other.
|
|
#[test]
|
|
fn test_identical_commits_swap_by_reordering() {
|
|
let test_env = create_test_environment();
|
|
test_env.run_jj_in(".", ["git", "init", "repo"]).success();
|
|
let work_dir = test_env.work_dir("repo");
|
|
|
|
work_dir.run_jj(["new", "root()", "-m=test"]).success();
|
|
work_dir.run_jj(["new", "-m=test"]).success();
|
|
// Test the setup
|
|
insta::assert_snapshot!(get_log_output(&work_dir), @r"
|
|
@ 5bae90c9b34d test
|
|
○ e94ed463cbb0 test
|
|
◆ 000000000000
|
|
[EOF]
|
|
");
|
|
// TODO: Should not fail
|
|
insta::assert_snapshot!(work_dir.run_jj(["rebase", "-r=@", "-B=@-"]), @r"
|
|
------- stderr -------
|
|
Internal error: Unexpected error from backend
|
|
Caused by: Newly-created commit e94ed463cbb0776612e308eba2ecaae74a7f8a73 already exists
|
|
[EOF]
|
|
[exit status: 255]
|
|
");
|
|
// There same two commits should still be visible
|
|
insta::assert_snapshot!(get_log_output(&work_dir), @r"
|
|
@ 5bae90c9b34d test
|
|
○ e94ed463cbb0 test
|
|
◆ 000000000000
|
|
[EOF]
|
|
");
|
|
// TODO: Each commit should be a predecessor of the other
|
|
insta::assert_snapshot!(work_dir.run_jj(["evolog", "-r=@"]), @r"
|
|
@ oxmtprsl?? test.user@example.com 2001-01-01 11:00:00 5bae90c9
|
|
(empty) test
|
|
-- operation 380fbe20623e new empty commit
|
|
[EOF]
|
|
");
|
|
insta::assert_snapshot!(work_dir.run_jj(["evolog", "-r=@-"]), @r"
|
|
○ oxmtprsl?? test.user@example.com 2001-01-01 11:00:00 e94ed463
|
|
(empty) test
|
|
-- operation 40e37b931010 new empty commit
|
|
[EOF]
|
|
");
|
|
// TODO: Test that `jj op show` displays something reasonable
|
|
}
|
|
|
|
#[must_use]
|
|
fn get_log_output(work_dir: &TestWorkDir) -> CommandOutput {
|
|
let template = r#"commit_id.short() ++ " " ++ description"#;
|
|
work_dir.run_jj(["log", "-T", template])
|
|
}
|