github.com/gitbundle/modules@v0.0.0-20231025071548-85b91c5c3b01/git/repo_branch_gogit.go (about) 1 // Copyright 2023 The GitBundle Inc. All rights reserved. 2 // Copyright 2017 The Gitea Authors. All rights reserved. 3 // Use of this source code is governed by a MIT-style 4 // license that can be found in the LICENSE file. 5 6 //go:build gogit 7 8 package git 9 10 import ( 11 "context" 12 "strings" 13 14 "github.com/go-git/go-git/v5/plumbing" 15 "github.com/go-git/go-git/v5/plumbing/storer" 16 ) 17 18 // IsObjectExist returns true if given reference exists in the repository. 19 func (repo *Repository) IsObjectExist(name string) bool { 20 if name == "" { 21 return false 22 } 23 24 _, err := repo.gogitRepo.ResolveRevision(plumbing.Revision(name)) 25 26 return err == nil 27 } 28 29 // IsReferenceExist returns true if given reference exists in the repository. 30 func (repo *Repository) IsReferenceExist(name string) bool { 31 if name == "" { 32 return false 33 } 34 35 reference, err := repo.gogitRepo.Reference(plumbing.ReferenceName(name), true) 36 if err != nil { 37 return false 38 } 39 return reference.Type() != plumbing.InvalidReference 40 } 41 42 // IsBranchExist returns true if given branch exists in current repository. 43 func (repo *Repository) IsBranchExist(name string) bool { 44 if name == "" { 45 return false 46 } 47 reference, err := repo.gogitRepo.Reference(plumbing.ReferenceName(BranchPrefix+name), true) 48 if err != nil { 49 return false 50 } 51 return reference.Type() != plumbing.InvalidReference 52 } 53 54 // GetBranches returns branches from the repository, skipping skip initial branches and 55 // returning at most limit branches, or all branches if limit is 0. 56 func (repo *Repository) GetBranchNames(skip, limit int) ([]string, int, error) { 57 var branchNames []string 58 59 branches, err := repo.gogitRepo.Branches() 60 if err != nil { 61 return nil, 0, err 62 } 63 64 i := 0 65 count := 0 66 _ = branches.ForEach(func(branch *plumbing.Reference) error { 67 count++ 68 if i < skip { 69 i++ 70 return nil 71 } else if limit != 0 && count > skip+limit { 72 return nil 73 } 74 75 branchNames = append(branchNames, strings.TrimPrefix(branch.Name().String(), BranchPrefix)) 76 return nil 77 }) 78 79 // TODO: Sort? 80 81 return branchNames, count, nil 82 } 83 84 // WalkReferences walks all the references from the repository 85 // refType should be empty, ObjectTag or ObjectBranch. All other values are equivalent to empty. 86 func WalkReferences(ctx context.Context, repoPath string, walkfn func(sha1, refname string) error) (int, error) { 87 repo := RepositoryFromContext(ctx, repoPath) 88 if repo == nil { 89 var err error 90 repo, err = OpenRepository(ctx, repoPath) 91 if err != nil { 92 return 0, err 93 } 94 defer repo.Close() 95 } 96 97 i := 0 98 iter, err := repo.gogitRepo.References() 99 if err != nil { 100 return i, err 101 } 102 defer iter.Close() 103 104 err = iter.ForEach(func(ref *plumbing.Reference) error { 105 err := walkfn(ref.Hash().String(), string(ref.Name())) 106 i++ 107 return err 108 }) 109 return i, err 110 } 111 112 // WalkReferences walks all the references from the repository 113 func (repo *Repository) WalkReferences(arg ObjectType, skip, limit int, walkfn func(sha1, refname string) error) (int, error) { 114 i := 0 115 var iter storer.ReferenceIter 116 var err error 117 switch arg { 118 case ObjectTag: 119 iter, err = repo.gogitRepo.Tags() 120 case ObjectBranch: 121 iter, err = repo.gogitRepo.Branches() 122 default: 123 iter, err = repo.gogitRepo.References() 124 } 125 if err != nil { 126 return i, err 127 } 128 defer iter.Close() 129 130 err = iter.ForEach(func(ref *plumbing.Reference) error { 131 if i < skip { 132 i++ 133 return nil 134 } 135 err := walkfn(ref.Hash().String(), string(ref.Name())) 136 i++ 137 if err != nil { 138 return err 139 } 140 if limit != 0 && i >= skip+limit { 141 return storer.ErrStop 142 } 143 return nil 144 }) 145 return i, err 146 } 147 148 // GetRefsBySha returns all references filtered with prefix that belong to a sha commit hash 149 func (repo *Repository) GetRefsBySha(sha, prefix string) ([]string, error) { 150 var revList []string 151 iter, err := repo.gogitRepo.References() 152 if err != nil { 153 return nil, err 154 } 155 err = iter.ForEach(func(ref *plumbing.Reference) error { 156 if ref.Hash().String() == sha && strings.HasPrefix(string(ref.Name()), prefix) { 157 revList = append(revList, string(ref.Name())) 158 } 159 return nil 160 }) 161 return revList, err 162 }