Skip to content

Commit e6eb0e6

Browse files
authored
add specific error when a git operation fails because it's unreachable or limited (#302)
1 parent 5805e79 commit e6eb0e6

File tree

1 file changed

+48
-0
lines changed

1 file changed

+48
-0
lines changed

providers/gitops/gitops.go

Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,8 @@ import (
1717
"github.com/rs/zerolog/log"
1818
)
1919

20+
var ErrRepoNotReachable = errors.New("repo or ref not reachable")
21+
2022
type GitClient struct {
2123
Command GitCommand
2224
}
@@ -154,6 +156,13 @@ func (g *GitClient) Clone(ctx context.Context, clonePath string, url string, tok
154156

155157
for _, c := range commands {
156158
if _, err := g.Command.Run(ctx, c.cmd, c.args, clonePath); err != nil {
159+
if IsGitRepoUnauthorizedOrNotReachable(err) {
160+
msg := err.Error()
161+
if token != "" {
162+
msg = strings.ReplaceAll(msg, token, "REDACTED")
163+
}
164+
return fmt.Errorf("%w: %s", ErrRepoNotReachable, msg) //nolint:errorlint
165+
}
157166
if token != "" && strings.Contains(err.Error(), token) {
158167
return errors.New(strings.ReplaceAll(err.Error(), token, "REDACTED"))
159168
}
@@ -185,6 +194,13 @@ func (g *GitClient) FetchCone(ctx context.Context, clonePath, url, token, ref st
185194

186195
for _, c := range commands {
187196
if _, err := g.Command.Run(ctx, c.cmd, c.args, clonePath); err != nil {
197+
if IsGitRepoUnauthorizedOrNotReachable(err) {
198+
msg := err.Error()
199+
if token != "" {
200+
msg = strings.ReplaceAll(msg, token, "REDACTED")
201+
}
202+
return fmt.Errorf("%w: %s", ErrRepoNotReachable, msg) //nolint:errorlint
203+
}
188204
if token != "" && strings.Contains(err.Error(), token) {
189205
return errors.New(strings.ReplaceAll(err.Error(), token, "REDACTED"))
190206
}
@@ -472,3 +488,35 @@ func (g *LocalGitClient) GetRepoHeadBranchName(ctx context.Context, repoPath str
472488

473489
return headBranch, nil
474490
}
491+
492+
func IsGitRepoUnauthorizedOrNotReachable(err error) bool {
493+
var gitExitErr *GitExitError
494+
if !errors.As(err, &gitExitErr) {
495+
return false
496+
}
497+
498+
stderr := strings.ToLower(gitExitErr.Stderr)
499+
500+
// Common error patterns for authentication and repository access issues
501+
unreachablePatterns := []string{
502+
"could not read username for 'https://github.com'",
503+
"authentication failed",
504+
"fatal: repository not found",
505+
"access denied",
506+
"permission denied",
507+
"error: could not fetch",
508+
"fatal: could not read from remote repository",
509+
"no such device or address",
510+
"fatal: remote error: upload-pack: not our ref",
511+
"couldn't find remote ref",
512+
"Connection reset by peer",
513+
}
514+
515+
for _, pattern := range unreachablePatterns {
516+
if strings.Contains(stderr, pattern) {
517+
return true
518+
}
519+
}
520+
521+
return false
522+
}

0 commit comments

Comments
 (0)