@@ -61,14 +61,29 @@ func (repo *Repository) IsBranchExist(name string) bool {
6161 return repo .IsReferenceExist (BranchPrefix + name )
6262}
6363
64- // GetBranches returns branches from the repository, skipping skip initial branches and
64+ // GetBranchNames returns branches from the repository, skipping skip initial branches and
6565// returning at most limit branches, or all branches if limit is 0.
66- func (repo * Repository ) GetBranches (skip , limit int ) ([]string , int , error ) {
66+ func (repo * Repository ) GetBranchNames (skip , limit int ) ([]string , int , error ) {
6767 return callShowRef (repo .Ctx , repo .Path , BranchPrefix , "--heads" , skip , limit )
6868}
6969
70+ // WalkReferences walks all the references from the repository
71+ func WalkReferences (ctx context.Context , repoPath string , walkfn func (string ) error ) (int , error ) {
72+ return walkShowRef (ctx , repoPath , "" , 0 , 0 , walkfn )
73+ }
74+
7075// callShowRef return refs, if limit = 0 it will not limit
7176func callShowRef (ctx context.Context , repoPath , prefix , arg string , skip , limit int ) (branchNames []string , countAll int , err error ) {
77+ countAll , err = walkShowRef (ctx , repoPath , arg , skip , limit , func (branchName string ) error {
78+ branchName = strings .TrimPrefix (branchName , prefix )
79+ branchNames = append (branchNames , branchName )
80+
81+ return nil
82+ })
83+ return
84+ }
85+
86+ func walkShowRef (ctx context.Context , repoPath , arg string , skip , limit int , walkfn func (string ) error ) (countAll int , err error ) {
7287 stdoutReader , stdoutWriter := io .Pipe ()
7388 defer func () {
7489 _ = stdoutReader .Close ()
@@ -77,7 +92,11 @@ func callShowRef(ctx context.Context, repoPath, prefix, arg string, skip, limit
7792
7893 go func () {
7994 stderrBuilder := & strings.Builder {}
80- err := NewCommandContext (ctx , "show-ref" , arg ).RunInDirPipeline (repoPath , stdoutWriter , stderrBuilder )
95+ args := []string {"show-ref" }
96+ if arg != "" {
97+ args = append (args , arg )
98+ }
99+ err := NewCommandContext (ctx , args ... ).RunInDirPipeline (repoPath , stdoutWriter , stderrBuilder )
81100 if err != nil {
82101 if stderrBuilder .Len () == 0 {
83102 _ = stdoutWriter .Close ()
@@ -94,10 +113,10 @@ func callShowRef(ctx context.Context, repoPath, prefix, arg string, skip, limit
94113 for i < skip {
95114 _ , isPrefix , err := bufReader .ReadLine ()
96115 if err == io .EOF {
97- return branchNames , i , nil
116+ return i , nil
98117 }
99118 if err != nil {
100- return nil , 0 , err
119+ return 0 , err
101120 }
102121 if ! isPrefix {
103122 i ++
@@ -112,39 +131,42 @@ func callShowRef(ctx context.Context, repoPath, prefix, arg string, skip, limit
112131 _ , err = bufReader .ReadSlice (' ' )
113132 }
114133 if err == io .EOF {
115- return branchNames , i , nil
134+ return i , nil
116135 }
117136 if err != nil {
118- return nil , 0 , err
137+ return 0 , err
119138 }
120139
121140 branchName , err := bufReader .ReadString ('\n' )
122141 if err == io .EOF {
123142 // This shouldn't happen... but we'll tolerate it for the sake of peace
124- return branchNames , i , nil
143+ return i , nil
125144 }
126145 if err != nil {
127- return nil , i , err
146+ return i , err
128147 }
129- branchName = strings . TrimPrefix ( branchName , prefix )
148+
130149 if len (branchName ) > 0 {
131150 branchName = branchName [:len (branchName )- 1 ]
132151 }
133- branchNames = append (branchNames , branchName )
152+ err = walkfn (branchName )
153+ if err != nil {
154+ return i , err
155+ }
134156 i ++
135157 }
136158 // count all refs
137159 for limit != 0 {
138160 _ , isPrefix , err := bufReader .ReadLine ()
139161 if err == io .EOF {
140- return branchNames , i , nil
162+ return i , nil
141163 }
142164 if err != nil {
143- return nil , 0 , err
165+ return 0 , err
144166 }
145167 if ! isPrefix {
146168 i ++
147169 }
148170 }
149- return branchNames , i , nil
171+ return i , nil
150172}
0 commit comments