Skip to content

Commit 1f75b49

Browse files
committed
Finish the entire merge implementation and cover everything with tests.
1 parent 01b072c commit 1f75b49

File tree

7 files changed

+823
-153
lines changed

7 files changed

+823
-153
lines changed

Cargo.lock

+1
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

gix-merge/Cargo.toml

+1
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@ document-features = { version = "0.2.0", optional = true }
4343
[dev-dependencies]
4444
gix-testtools = { path = "../tests/tools" }
4545
gix-odb = { path = "../gix-odb" }
46+
gix-utils = { version = "^0.1.12", path = "../gix-utils" }
4647
pretty_assertions = "1.4.0"
4748

4849
[package.metadata.docs.rs]

gix-merge/src/commit.rs

+17-8
Original file line numberDiff line numberDiff line change
@@ -18,16 +18,16 @@ pub enum Error {
1818
}
1919

2020
/// A way to configure [`commit()`](crate::commit()).
21-
#[derive(Default, Debug, Copy, Clone)]
21+
#[derive(Default, Debug, Clone)]
2222
pub struct Options {
2323
/// If `true`, merging unrelated commits is allowed, with the merge-base being assumed as empty tree.
2424
pub allow_missing_merge_base: bool,
2525
/// Options to define how trees should be merged.
2626
pub tree_merge: crate::tree::Options,
27-
/// Options to define how to merge blobs.
28-
///
29-
/// Note that these are temporarily overwritten if multiple merge-bases are merged into one.
30-
pub blob_merge: crate::blob::platform::merge::Options,
27+
/// If `true`, do not merge multiple merge-bases into one. Instead, just use the first one.
28+
// TODO: test
29+
#[doc(alias = "no_recursive", alias = "git2")]
30+
pub use_first_merge_base: bool,
3131
}
3232

3333
pub(super) mod function {
@@ -51,21 +51,29 @@ pub(super) mod function {
5151
///
5252
/// Note that `objects` *should* have an object cache to greatly accelerate tree-retrieval.
5353
#[allow(clippy::too_many_arguments)]
54-
pub fn commit<'objects>(
54+
pub fn commit<'objects, E>(
5555
our_commit: gix_hash::ObjectId,
5656
their_commit: gix_hash::ObjectId,
5757
mut labels: crate::blob::builtin_driver::text::Labels<'_>,
5858
graph: &mut gix_revwalk::Graph<'_, '_, gix_revwalk::graph::Commit<gix_revision::merge_base::Flags>>,
5959
diff_resource_cache: &mut gix_diff::blob::Platform,
6060
blob_merge: &mut crate::blob::Platform,
6161
objects: &'objects impl gix_object::FindObjectOrHeader,
62+
write_blob_to_odb: impl FnMut(&[u8]) -> Result<gix_hash::ObjectId, E>,
6263
options: Options,
63-
) -> Result<crate::tree::Outcome<'objects>, Error> {
64+
) -> Result<crate::tree::Outcome<'objects>, Error>
65+
where
66+
E: Into<Box<dyn std::error::Error + Send + Sync + 'static>>,
67+
{
6468
let merge_bases_commit_ids = gix_revision::merge_base(our_commit, &[their_commit], graph)?;
6569
let (merge_base_commit_id, ancestor_name) = match merge_bases_commit_ids {
6670
Some(base_commit) if base_commit.len() == 1 => (base_commit[0], None),
6771
Some(base_commits) => {
68-
let virtual_base_tree = *base_commits.first().expect("TODO: merge multiple bases into one");
72+
let virtual_base_tree = if options.use_first_merge_base {
73+
*base_commits.first().expect("TODO: merge multiple bases into one")
74+
} else {
75+
todo!("merge multiple merge bases")
76+
};
6977
(virtual_base_tree, Some("merged common ancestors".into()))
7078
}
7179
None => {
@@ -97,6 +105,7 @@ pub(super) mod function {
97105
&their_tree_id,
98106
labels,
99107
objects,
108+
write_blob_to_odb,
100109
&mut state,
101110
diff_resource_cache,
102111
blob_merge,

0 commit comments

Comments
 (0)