mirror of
https://github.com/SkinnyMind/libgit2dart.git
synced 2025-05-04 20:29:08 -04:00
feat(merge): add ability to merge file from index
This commit is contained in:
parent
5c8d6647eb
commit
52707dcc63
4 changed files with 87 additions and 1 deletions
|
@ -89,6 +89,36 @@ void merge({
|
|||
}
|
||||
}
|
||||
|
||||
/// Merge two files as they exist in the index, using the given common ancestor
|
||||
/// as the baseline, producing a string that reflects the merge result containing
|
||||
/// possible conflicts.
|
||||
///
|
||||
/// Throws a [LibGit2Error] if error occured.
|
||||
String mergeFileFromIndex({
|
||||
required Pointer<git_repository> repoPointer,
|
||||
required Pointer<git_index_entry>? ancestorPointer,
|
||||
required Pointer<git_index_entry>? oursPointer,
|
||||
required Pointer<git_index_entry>? theirsPointer,
|
||||
}) {
|
||||
final out = calloc<git_merge_file_result>();
|
||||
final error = libgit2.git_merge_file_from_index(
|
||||
out,
|
||||
repoPointer,
|
||||
ancestorPointer ?? nullptr,
|
||||
oursPointer ?? nullptr,
|
||||
theirsPointer ?? nullptr,
|
||||
nullptr,
|
||||
);
|
||||
|
||||
if (error < 0) {
|
||||
throw LibGit2Error(libgit2.git_error_last());
|
||||
} else {
|
||||
final result = out.ref.ptr.cast<Utf8>().toDartString(length: out.ref.len);
|
||||
calloc.free(out);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
/// Merge two commits, producing a git_index that reflects the result of the merge.
|
||||
/// The index may be written as-is to the working directory or checked out. If the index
|
||||
/// is to be converted to a tree, the caller should resolve any conflicts that arose as
|
||||
|
|
|
@ -256,9 +256,11 @@ class IndexEntry {
|
|||
/// Initializes a new instance of [IndexEntry] class.
|
||||
const IndexEntry(this._indexEntryPointer);
|
||||
|
||||
/// Pointer to memory address for allocated index entry object.
|
||||
final Pointer<git_index_entry> _indexEntryPointer;
|
||||
|
||||
/// Pointer to memory address for allocated index entry object.
|
||||
Pointer<git_index_entry> get pointer => _indexEntryPointer;
|
||||
|
||||
/// Unique identity of the index entry.
|
||||
Oid get id => Oid.fromRaw(_indexEntryPointer.ref.id);
|
||||
|
||||
|
@ -282,6 +284,11 @@ class IndexEntry {
|
|||
/// Sets the UNIX file attributes of a index entry.
|
||||
set mode(GitFilemode mode) => _indexEntryPointer.ref.mode = mode.value;
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return 'IndexEntry{path: $path, sha: $sha}';
|
||||
}
|
||||
|
||||
String _oidToHex(git_oid oid) {
|
||||
var hex = StringBuffer();
|
||||
for (var i = 0; i < 20; i++) {
|
||||
|
|
|
@ -677,6 +677,24 @@ class Repository {
|
|||
commit_bindings.annotatedFree(theirHead.value);
|
||||
}
|
||||
|
||||
/// Merges two files as they exist in the index, using the given common ancestor
|
||||
/// as the baseline, producing a string that reflects the merge result containing
|
||||
/// possible conflicts.
|
||||
///
|
||||
/// Throws a [LibGit2Error] if error occured.
|
||||
String mergeFileFromIndex({
|
||||
required IndexEntry? ancestor,
|
||||
required IndexEntry? ours,
|
||||
required IndexEntry? theirs,
|
||||
}) {
|
||||
return merge_bindings.mergeFileFromIndex(
|
||||
repoPointer: _repoPointer,
|
||||
ancestorPointer: ancestor?.pointer,
|
||||
oursPointer: ours?.pointer,
|
||||
theirsPointer: theirs?.pointer,
|
||||
);
|
||||
}
|
||||
|
||||
/// Merges two commits, producing an index that reflects the result of the merge.
|
||||
/// The index may be written as-is to the working directory or checked out. If the index
|
||||
/// is to be converted to a tree, the caller should resolve any conflicts that arose as
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
// ignore_for_file: unnecessary_string_escapes
|
||||
|
||||
import 'dart:io';
|
||||
import 'package:test/test.dart';
|
||||
import 'package:libgit2dart/libgit2dart.dart';
|
||||
|
@ -139,6 +141,35 @@ void main() {
|
|||
conflictBranch.free();
|
||||
});
|
||||
|
||||
group('merge file from index', () {
|
||||
test('successfully merges', () {
|
||||
const diffExpected = """
|
||||
\<<<<<<< conflict_file
|
||||
master conflict edit
|
||||
=======
|
||||
conflict branch edit
|
||||
>>>>>>> conflict_file
|
||||
""";
|
||||
final conflictBranch = repo.branches['conflict-branch'];
|
||||
final index = repo.index;
|
||||
repo.merge(conflictBranch.target);
|
||||
|
||||
final diff = repo.mergeFileFromIndex(
|
||||
ancestor: index.conflicts['conflict_file']!.ancestor,
|
||||
ours: index.conflicts['conflict_file']!.our,
|
||||
theirs: index.conflicts['conflict_file']!.their,
|
||||
);
|
||||
|
||||
expect(
|
||||
diff,
|
||||
diffExpected,
|
||||
);
|
||||
|
||||
index.free();
|
||||
conflictBranch.free();
|
||||
});
|
||||
});
|
||||
|
||||
group('merge commits', () {
|
||||
test('successfully merges with default values', () {
|
||||
final theirCommit =
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue