Skip to content

Commit f09e14d

Browse files
committed
libgit2: ensure Timeout cancels transfer
Signed-off-by: Hidde Beydals <hello@hidde.co>
1 parent d3ea648 commit f09e14d

2 files changed

Lines changed: 21 additions & 5 deletions

File tree

pkg/git/libgit2/checkout.go

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ func (c *CheckoutBranch) Checkout(ctx context.Context, path, url string, opts *g
6363
repo, err := git2go.Clone(url, path, &git2go.CloneOptions{
6464
FetchOptions: &git2go.FetchOptions{
6565
DownloadTags: git2go.DownloadTagsNone,
66-
RemoteCallbacks: RemoteCallbacks(opts),
66+
RemoteCallbacks: RemoteCallbacks(ctx, opts),
6767
},
6868
CheckoutBranch: c.Branch,
6969
})
@@ -92,7 +92,7 @@ func (c *CheckoutTag) Checkout(ctx context.Context, path, url string, opts *git.
9292
repo, err := git2go.Clone(url, path, &git2go.CloneOptions{
9393
FetchOptions: &git2go.FetchOptions{
9494
DownloadTags: git2go.DownloadTagsAll,
95-
RemoteCallbacks: RemoteCallbacks(opts),
95+
RemoteCallbacks: RemoteCallbacks(ctx, opts),
9696
},
9797
})
9898
if err != nil {
@@ -115,7 +115,7 @@ func (c *CheckoutCommit) Checkout(ctx context.Context, path, url string, opts *g
115115
repo, err := git2go.Clone(url, path, &git2go.CloneOptions{
116116
FetchOptions: &git2go.FetchOptions{
117117
DownloadTags: git2go.DownloadTagsNone,
118-
RemoteCallbacks: RemoteCallbacks(opts),
118+
RemoteCallbacks: RemoteCallbacks(ctx, opts),
119119
},
120120
})
121121
if err != nil {
@@ -146,7 +146,7 @@ func (c *CheckoutSemVer) Checkout(ctx context.Context, path, url string, opts *g
146146
repo, err := git2go.Clone(url, path, &git2go.CloneOptions{
147147
FetchOptions: &git2go.FetchOptions{
148148
DownloadTags: git2go.DownloadTagsAll,
149-
RemoteCallbacks: RemoteCallbacks(opts),
149+
RemoteCallbacks: RemoteCallbacks(ctx, opts),
150150
},
151151
})
152152
if err != nil {

pkg/git/libgit2/transport.go

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ package libgit2
1919
import (
2020
"bufio"
2121
"bytes"
22+
"context"
2223
"crypto/md5"
2324
"crypto/sha1"
2425
"crypto/sha256"
@@ -43,16 +44,31 @@ var (
4344

4445
// RemoteCallbacks constructs RemoteCallbacks with credentialsCallback and
4546
// certificateCallback, and the given options if the given opts is not nil.
46-
func RemoteCallbacks(opts *git.AuthOptions) git2go.RemoteCallbacks {
47+
func RemoteCallbacks(ctx context.Context, opts *git.AuthOptions) git2go.RemoteCallbacks {
4748
if opts != nil {
4849
return git2go.RemoteCallbacks{
50+
TransferProgressCallback: transferProgressCallback(ctx),
4951
CredentialsCallback: credentialsCallback(opts),
5052
CertificateCheckCallback: certificateCallback(opts),
5153
}
5254
}
5355
return git2go.RemoteCallbacks{}
5456
}
5557

58+
// transferProgressCallback constructs TransferProgressCallbacks which signals
59+
// libgit2 it should stop the transfer when the given context is closed (due to
60+
// e.g. a timeout).
61+
func transferProgressCallback(ctx context.Context) git2go.TransferProgressCallback {
62+
return func(_ git2go.TransferProgress) git2go.ErrorCode {
63+
select {
64+
case <-ctx.Done():
65+
return git2go.ErrorCodeUser
66+
default:
67+
return git2go.ErrorCodeOK
68+
}
69+
}
70+
}
71+
5672
// credentialsCallback constructs CredentialsCallbacks with the given options
5773
// for git.Transport, and returns the result.
5874
func credentialsCallback(opts *git.AuthOptions) git2go.CredentialsCallback {

0 commit comments

Comments
 (0)