Skip to content

Commit 0610c7f

Browse files
committed
fix fast-forward and 'up to date' cases of rebase
1 parent 16580bb commit 0610c7f

2 files changed

Lines changed: 135 additions & 9 deletions

File tree

lib/repository.js

Lines changed: 33 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -798,13 +798,16 @@ Repository.prototype.rebaseBranches = function(
798798
signature)
799799
{
800800
var repo = this;
801+
var branchCommit;
802+
var upstreamCommit;
803+
var ontoCommit;
801804

802805
signature = signature || repo.defaultSignature();
803806

804807
return Promise.all([
805808
repo.getReference(branch),
806809
upstream ? repo.getReference(upstream) : null,
807-
onto ? repo.getReference(upstream) : null
810+
onto ? repo.getReference(onto) : null
808811
])
809812
.then(function(refs) {
810813
return Promise.all([
@@ -814,17 +817,38 @@ Repository.prototype.rebaseBranches = function(
814817
]);
815818
})
816819
.then(function(annotatedCommits) {
817-
return NodeGit.Rebase.init(repo, annotatedCommits[0], annotatedCommits[1],
818-
annotatedCommits[2], signature, null);
819-
})
820-
.then(function(rebase) {
821-
return performRebase(repo, rebase, signature);
820+
branchCommit = annotatedCommits[0];
821+
upstreamCommit = annotatedCommits[1];
822+
ontoCommit = annotatedCommits[2];
823+
824+
return NodeGit.Merge.base(repo, branchCommit.id(), upstreamCommit.id());
822825
})
823-
.then(function(error) {
824-
if (error) {
825-
throw error;
826+
.then(function(oid) {
827+
if (oid.toString() === branchCommit.id().toString()) {
828+
// we just need to fast-forward
829+
return repo.mergeBranches(branch, upstream)
830+
.then(function() {
831+
// checkout 'branch' to match the behavior of rebase
832+
return repo.checkoutBranch(branch);
833+
});
834+
} else if (oid.toString() === upstreamCommit.id().toString()) {
835+
// 'branch' is already on top of 'upstream'
836+
// checkout 'branch' to match the behavior of rebase
837+
return repo.checkoutBranch(branch);
826838
}
827839

840+
return NodeGit.Rebase.init(repo, branchCommit, upstreamCommit, ontoCommit,
841+
signature, null)
842+
.then(function(rebase) {
843+
return performRebase(repo, rebase, signature);
844+
})
845+
.then(function(error) {
846+
if (error) {
847+
throw error;
848+
}
849+
});
850+
})
851+
.then(function() {
828852
return repo.getBranchCommit("HEAD");
829853
});
830854
};

test/tests/rebase.js

Lines changed: 102 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -707,6 +707,108 @@ describe("Rebase", function() {
707707
});
708708
});
709709

710+
it("can fast-forward via rebase using the convenience methods", function() {
711+
var ourFileName = "ourNewFile.txt";
712+
var theirFileName = "theirNewFile.txt";
713+
714+
var ourFileContent = "I like Toll Roads. I have an EZ-Pass!";
715+
var theirFileContent = "I'm skeptical about Toll Roads";
716+
717+
var ourSignature = NodeGit.Signature.create
718+
("Ron Paul", "RonPaul@TollRoadsRBest.info", 123456789, 60);
719+
var theirSignature = NodeGit.Signature.create
720+
("Greg Abbott", "Gregggg@IllTollYourFace.us", 123456789, 60);
721+
722+
var repository = this.repository;
723+
var ourCommit;
724+
var theirBranch;
725+
726+
return fse.writeFile(path.join(repository.workdir(), ourFileName),
727+
ourFileContent)
728+
// Load up the repository index and make our initial commit to HEAD
729+
.then(function() {
730+
return addFileToIndex(repository, ourFileName);
731+
})
732+
.then(function(oid) {
733+
assert.equal(oid.toString(),
734+
"11ead82b1135b8e240fb5d61e703312fb9cc3d6a");
735+
736+
return repository.createCommit("HEAD", ourSignature,
737+
ourSignature, "we made a commit", oid, []);
738+
})
739+
.then(function(commitOid) {
740+
assert.equal(commitOid.toString(),
741+
"91a183f87842ebb7a9b08dad8bc2473985796844");
742+
743+
return repository.getCommit(commitOid).then(function(commit) {
744+
ourCommit = commit;
745+
}).then(function() {
746+
return repository.createBranch(ourBranchName, commitOid)
747+
.then(function(branch) {
748+
return repository.createBranch(theirBranchName, commitOid);
749+
});
750+
});
751+
})
752+
.then(function(branch) {
753+
theirBranch = branch;
754+
return fse.writeFile(path.join(repository.workdir(), theirFileName),
755+
theirFileContent);
756+
})
757+
.then(function() {
758+
return addFileToIndex(repository, theirFileName);
759+
})
760+
.then(function(oid) {
761+
assert.equal(oid.toString(),
762+
"76631cb5a290dafe2959152626bb90f2a6d8ec94");
763+
764+
return repository.createCommit(theirBranch.name(), theirSignature,
765+
theirSignature, "they made a commit", oid, [ourCommit]);
766+
})
767+
.then(function(commitOid) {
768+
assert.equal(commitOid.toString(),
769+
"0e9231d489b3f4303635fc4b0397830da095e7e7");
770+
})
771+
.then(function() {
772+
// unstage changes so that we can begin a rebase
773+
return removeFileFromIndex(repository, theirFileName);
774+
})
775+
.then(function() {
776+
return Promise.all([
777+
repository.getReference(ourBranchName),
778+
repository.getReference(theirBranchName)
779+
]);
780+
})
781+
.then(function(refs) {
782+
assert.equal(refs.length, 2);
783+
784+
return Promise.all([
785+
NodeGit.AnnotatedCommit.fromRef(repository, refs[0]),
786+
NodeGit.AnnotatedCommit.fromRef(repository, refs[1])
787+
]);
788+
})
789+
.then(function(annotatedCommits) {
790+
assert.equal(annotatedCommits.length, 2);
791+
792+
var ourAnnotatedCommit = annotatedCommits[0];
793+
var theirAnnotatedCommit = annotatedCommits[1];
794+
795+
assert.equal(ourAnnotatedCommit.id().toString(),
796+
"91a183f87842ebb7a9b08dad8bc2473985796844");
797+
assert.equal(theirAnnotatedCommit.id().toString(),
798+
"0e9231d489b3f4303635fc4b0397830da095e7e7");
799+
800+
return fse.remove(path.join(repository.workdir(), theirFileName));
801+
})
802+
.then(function() {
803+
return repository.rebaseBranches(ourBranchName, theirBranchName, null,
804+
ourSignature);
805+
})
806+
.then(function(commit) {
807+
assert.equal(commit.id().toString(),
808+
"0e9231d489b3f4303635fc4b0397830da095e7e7");
809+
});
810+
});
811+
710812
it("can rebase using the convenience method", function() {
711813
var baseFileName = "baseNewFile.txt";
712814
var ourFileName = "ourNewFile.txt";

0 commit comments

Comments
 (0)