diff options
author | Grzegorz Bizon <grzesiek.bizon@gmail.com> | 2020-09-01 11:54:47 +0300 |
---|---|---|
committer | Grzegorz Bizon <grzesiek.bizon@gmail.com> | 2020-09-01 13:48:46 +0300 |
commit | 28dcd6241f9fd4ab20e7f4ac5103c9cff11a325b (patch) | |
tree | 84e61ce356c4679055e26f1a2dae4bf40efbdfbf /internal/source/gitlab | |
parent | 09449fb2e084b4a23759cbff38b1dce03b98aba2 (diff) |
Fix a bug that leads to blocking retrieval on canceled contextfix/gb/gitlab-api-cache-test-races
Diffstat (limited to 'internal/source/gitlab')
-rw-r--r-- | internal/source/gitlab/cache/cache_test.go | 9 | ||||
-rw-r--r-- | internal/source/gitlab/cache/entry.go | 4 |
2 files changed, 6 insertions, 7 deletions
diff --git a/internal/source/gitlab/cache/cache_test.go b/internal/source/gitlab/cache/cache_test.go index 5ae876bd..7ed56f5a 100644 --- a/internal/source/gitlab/cache/cache_test.go +++ b/internal/source/gitlab/cache/cache_test.go @@ -216,15 +216,12 @@ func TestResolve(t *testing.T) { withTestCache(resolverConfig{}, nil, func(cache *Cache, resolver *client) { cache.withTestEntry(entryConfig{expired: false, retrieved: false}, func(entry *Entry) { ctx, cancel := context.WithCancel(context.Background()) - - response := make(chan *api.Lookup, 1) - go func() { response <- cache.Resolve(ctx, "my.gitlab.com") }() - cancel() - resolver.domain <- "my.gitlab.com" - lookup := <-response + lookup := cache.Resolve(ctx, "my.gitlab.com") + resolver.domain <- "err.gitlab.com" + require.Equal(t, "my.gitlab.com", lookup.Name) require.EqualError(t, lookup.Error, "context done") }) }) diff --git a/internal/source/gitlab/cache/entry.go b/internal/source/gitlab/cache/entry.go index d33d2758..c960be8a 100644 --- a/internal/source/gitlab/cache/entry.go +++ b/internal/source/gitlab/cache/entry.go @@ -65,7 +65,9 @@ func (e *Entry) Lookup() *api.Lookup { // Retrieve perform a blocking retrieval of the cache entry response. func (e *Entry) Retrieve(ctx context.Context, client api.Client) (lookup *api.Lookup) { - e.retrieve.Do(func() { go e.setResponse(e.retriever.Retrieve(e.domain)) }) + // We run the code within an additional func() to run both `e.setResponse` + // and `e.retrieve.Retrieve` asynchronously. + e.retrieve.Do(func() { go func() { e.setResponse(e.retriever.Retrieve(e.domain)) }() }) select { case <-ctx.Done(): |