private static Commit LookUpCommit(IRepository repository, string committish) { GitObject obj = repository.Lookup(committish); Ensure.GitObjectIsNotNull(obj, committish); return(obj.Peel <Commit>(true)); }
/// <summary> /// Checkout the specified <see cref="Branch"/>, reference or SHA. /// <para> /// If the committishOrBranchSpec parameter resolves to a branch name, then the checked out HEAD will /// will point to the branch. Otherwise, the HEAD will be detached, pointing at the commit sha. /// </para> /// </summary> /// <param name="repository">The repository to act on</param> /// <param name="committishOrBranchSpec">A revparse spec for the commit or branch to checkout.</param> /// <param name="options"><see cref="CheckoutOptions"/> controlling checkout behavior.</param> /// <returns>The <see cref="Branch"/> that was checked out.</returns> public static Branch Checkout(IRepository repository, string committishOrBranchSpec, CheckoutOptions options) { Ensure.ArgumentNotNull(repository, "repository"); Ensure.ArgumentNotNullOrEmptyString(committishOrBranchSpec, "committishOrBranchSpec"); Ensure.ArgumentNotNull(options, "options"); Reference reference = null; GitObject obj = null; Branch branch = null; try { repository.RevParse(committishOrBranchSpec, out reference, out obj); } catch (NotFoundException) { // If committishOrBranchSpec is not a local branch but matches a tracking branch // in exactly one remote, use it. This is the "git checkout" command's default behavior. // https://git-scm.com/docs/git-checkout#Documentation/git-checkout.txt-emgitcheckoutemltbranchgt var remoteBranches = repository.Network.Remotes .SelectMany(r => repository.Branches.Where(b => b.IsRemote && b.CanonicalName == $"refs/remotes/{r.Name}/{committishOrBranchSpec}")) .ToList(); if (remoteBranches.Count == 1) { branch = repository.CreateBranch(committishOrBranchSpec, remoteBranches[0].Tip); repository.Branches.Update(branch, b => b.TrackedBranch = remoteBranches[0].CanonicalName); return(Checkout(repository, branch, options)); } if (remoteBranches.Count > 1) { throw new AmbiguousSpecificationException($"'{committishOrBranchSpec}' matched multiple ({remoteBranches.Count}) remote tracking branches"); } throw; } if (reference != null && reference.IsLocalBranch) { branch = repository.Branches[reference.CanonicalName]; return(Checkout(repository, branch, options)); } Commit commit = obj.Peel <Commit>(true); Checkout(repository, commit.Tree, options, committishOrBranchSpec); return(repository.Head); }