diff --git a/ObjectiveGit/GTRepository.h b/ObjectiveGit/GTRepository.h index 48733ed2e..566953624 100644 --- a/ObjectiveGit/GTRepository.h +++ b/ObjectiveGit/GTRepository.h @@ -269,6 +269,22 @@ extern NSString * const GTRepositoryInitOptionsOriginURLString; /// Returns a GTReference or nil if an error occurs. - (nullable GTReference *)headReferenceWithError:(NSError **)error; +/// Move HEAD reference safely, since deleting and recreating HEAD is always wrong. +/// +/// reference - The new target reference for HEAD. +/// error - If not NULL, set to any error that occurs. +/// +/// Returns NO if an error occurs. +- (BOOL)moveHEADToReference:(GTReference *)reference error:(NSError **)error; + +/// Move HEAD reference safely, since deleting and recreating HEAD is always wrong. +/// +/// commit - The commit which HEAD should point to. +/// error - If not NULL, set to any error that occurs. +/// +/// Returns NO if an error occurs. +- (BOOL)moveHEADToCommit:(GTCommit *)commit error:(NSError **)error; + /// Get the local branches. /// /// error - If not NULL, set to any error that occurs. @@ -286,7 +302,7 @@ extern NSString * const GTRepositoryInitOptionsOriginURLString; /// Get branches with names sharing a given prefix. /// /// prefix - The prefix to use for filtering. Must not be nil. -/// error - If not NULL, set to any error that occurs. +/// error - If not NULL, set to any error that occurs. /// /// Returns an array of GTBranches or nil if an error occurs. - (nullable NSArray *)branchesWithPrefix:(NSString *)prefix error:(NSError **)error; diff --git a/ObjectiveGitTests/GTRepositorySpec.m b/ObjectiveGitTests/GTRepositorySpec.m index 2f2983023..4837cea71 100644 --- a/ObjectiveGitTests/GTRepositorySpec.m +++ b/ObjectiveGitTests/GTRepositorySpec.m @@ -358,6 +358,58 @@ }); }); +describe(@"move head", ^{ + beforeEach(^{ + repository = self.testAppFixtureRepository; + }); + + //- (BOOL)moveHEADToReference:(GTReference *)reference error:(NSError **)error; + it(@"should move to reference", ^{ + NSError *error = nil; + GTReference *originalHead = [repository headReferenceWithError:NULL]; + + GTReference *targetReference = [repository lookUpReferenceWithName:@"refs/heads/other-branch" error:NULL]; + expect(targetReference).notTo(beNil()); + + // -> Test the move + BOOL success = [repository moveHEADToReference:targetReference error:&error]; + expect(@(success)).to(beTruthy()); + expect(error).to(beNil()); + + // Verify + GTReference *head = [repository headReferenceWithError:&error]; + expect(head).notTo(beNil()); + expect(head).notTo(equal(originalHead)); + expect(head.targetOID.SHA).to(equal(targetReference.targetOID.SHA)); + }); + + //- (BOOL)moveHEADToCommit:(GTCommit *)commit error:(NSError **)error; + it(@"should move to commit", ^{ + NSError *error = nil; + GTReference *originalHead = [repository headReferenceWithError:NULL]; + NSString *targetCommitSHA = @"f7ecd8f4404d3a388efbff6711f1bdf28ffd16a0"; + + GTCommit *commit = [repository lookUpObjectBySHA:targetCommitSHA error:NULL]; + expect(commit).notTo(beNil()); + + GTCommit *originalHeadCommit = [repository lookUpObjectByOID:originalHead.targetOID error:NULL]; + expect(originalHeadCommit).notTo(beNil()); + + // -> Test the move + BOOL success = [repository moveHEADToCommit:commit error:&error]; + expect(@(success)).to(beTruthy()); + expect(error).to(beNil()); + + // Test for detached? + + // Verify + GTReference *head = [repository headReferenceWithError:&error]; + expect(head).notTo(beNil()); + expect(head.targetOID.SHA).to(equal(targetCommitSHA)); + }); +}); + + describe(@"-checkout:strategy:error:progressBlock:", ^{ it(@"should allow references", ^{ NSError *error = nil;