Skip to content

Commit

Permalink
fix: update
Browse files Browse the repository at this point in the history
Signed-off-by: Junjie Gao <[email protected]>
  • Loading branch information
JeyJeyGao committed Aug 9, 2024
1 parent 87d618a commit e128f6d
Show file tree
Hide file tree
Showing 4 changed files with 61 additions and 32 deletions.
26 changes: 26 additions & 0 deletions revocation/crl/cache/errors_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
package cache

import (
"errors"
"testing"
"time"
)

func TestCacheExpiredError(t *testing.T) {
expirationTime := time.Now()
err := &CacheExpiredError{Expires: expirationTime}

expectedMessage := "cache expired at " + expirationTime.String()
if err.Error() != expectedMessage {
t.Errorf("expected %q, got %q", expectedMessage, err.Error())
}
}

func TestBrokenFileError(t *testing.T) {
innerErr := errors.New("inner error")
err := &BrokenFileError{Err: innerErr}

if err.Error() != innerErr.Error() {
t.Errorf("expected %q, got %q", innerErr.Error(), err.Error())
}
}
4 changes: 3 additions & 1 deletion revocation/crl/cache/file.go
Original file line number Diff line number Diff line change
Expand Up @@ -90,12 +90,13 @@ func (c *fileCache) Set(ctx context.Context, key string, bundle *Bundle) error {
}
tempFile.Close()

Check warning on line 91 in revocation/crl/cache/file.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/cache/file.go#L91

Added line #L91 was not covered by tests

// rename is atomic on UNIX platforms
// rename is atomic on UNIX-like platforms
return os.Rename(tempFile.Name(), filepath.Join(c.dir, key))

Check warning on line 94 in revocation/crl/cache/file.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/cache/file.go#L94

Added line #L94 was not covered by tests
}

// Delete removes the CRL bundle file from file system
func (c *fileCache) Delete(ctx context.Context, key string) error {

Check warning on line 98 in revocation/crl/cache/file.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/cache/file.go#L98

Added line #L98 was not covered by tests
// remove is atomic on UNIX-like platforms
return os.Remove(filepath.Join(c.dir, key))

Check warning on line 100 in revocation/crl/cache/file.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/cache/file.go#L100

Added line #L100 was not covered by tests
}

Expand All @@ -109,6 +110,7 @@ func (c *fileCache) Flush(ctx context.Context) error {
return nil

Check warning on line 110 in revocation/crl/cache/file.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/cache/file.go#L109-L110

Added lines #L109 - L110 were not covered by tests
}

// remove is atomic on UNIX-like platforms
return os.Remove(path)

Check warning on line 114 in revocation/crl/cache/file.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/cache/file.go#L114

Added line #L114 was not covered by tests
})
}
5 changes: 3 additions & 2 deletions revocation/crl/cache/memory.go
Original file line number Diff line number Diff line change
Expand Up @@ -47,8 +47,9 @@ func (c *memoryCache) Get(ctx context.Context, key string) (*Bundle, error) {
return nil, fmt.Errorf("invalid type: %T", value)

Check warning on line 47 in revocation/crl/cache/memory.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/cache/memory.go#L45-L47

Added lines #L45 - L47 were not covered by tests
}

if c.maxAge > 0 && time.Now().After(bundle.Metadata.CreateAt.Add(c.maxAge)) {
return nil, os.ErrNotExist
expires := bundle.Metadata.CreateAt.Add(c.maxAge)
if c.maxAge > 0 && time.Now().After(expires) {
return nil, &CacheExpiredError{Expires: expires}

Check warning on line 52 in revocation/crl/cache/memory.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/cache/memory.go#L50-L52

Added lines #L50 - L52 were not covered by tests
}

return bundle, nil

Check warning on line 55 in revocation/crl/cache/memory.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/cache/memory.go#L55

Added line #L55 was not covered by tests
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package crl
package fetcher

import (
"context"
Expand All @@ -20,71 +20,76 @@ const maxCRLSize = 64 * 1024 * 1024 // 64 MiB

// Fetcher is an interface that specifies methods used for fetching CRL
// from the given URL
//
// The interface is useful for pre-loading CRLs cache before the verification
type Fetcher interface {
Fetch(ctx context.Context, crlURL string) (bundle *cache.Bundle, fromCache bool, err error)
}

type fetcher struct {
type cachedFetcher struct {
httpClient *http.Client
cacheClient cache.Cache
}

// NewFetcher creates a new Fetcher with the given HTTP client and cache client
// NewCachedFetcher creates a new Fetcher with the given HTTP client and cache client
// - if httpClient is nil, http.DefaultClient will be used
// - if cacheClient is nil, no cache will be used
func NewFetcher(httpClient *http.Client, cacheClient cache.Cache) Fetcher {
func NewCachedFetcher(httpClient *http.Client, cacheClient cache.Cache) (Fetcher, error) {
if httpClient == nil {
httpClient = http.DefaultClient

Check warning on line 37 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L35-L37

Added lines #L35 - L37 were not covered by tests
}

return &fetcher{
if cacheClient == nil {
return nil, errors.New("cache client is nil")

Check warning on line 41 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L40-L41

Added lines #L40 - L41 were not covered by tests
}

return &cachedFetcher{
httpClient: httpClient,
cacheClient: cacheClient,
}
}, nil

Check warning on line 47 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L44-L47

Added lines #L44 - L47 were not covered by tests
}

// Fetch retrieves the CRL from the given URL
// - if the cache is enabled, it will try to get the CRL from the cache first
// - if the CRL is not in the cache or expired, it will download the CRL from
// the URL
func (f *fetcher) Fetch(ctx context.Context, crlURL string) (bundle *cache.Bundle, fromCache bool, err error) {
//
// Steps:
// 1. Try to get from cache
// 2. If not exist or broken, download and save to cache
func (f *cachedFetcher) Fetch(ctx context.Context, crlURL string) (bundle *cache.Bundle, fromCache bool, err error) {
if crlURL == "" {
return nil, false, errors.New("CRL URL is empty")

Check warning on line 57 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L55-L57

Added lines #L55 - L57 were not covered by tests
}

if f.cacheClient == nil {
// no cache, download directly
return f.downloadAndCache(ctx, crlURL)
}

// try to get from cache
bundle, err = f.cacheClient.Get(ctx, tarStoreName(crlURL))
if err != nil {
var cacheBrokenError *cache.BrokenFileError
if os.IsNotExist(err) || errors.As(err, &cacheBrokenError) {

Check warning on line 64 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L61-L64

Added lines #L61 - L64 were not covered by tests
// download if not exist or broken
return f.downloadAndCache(ctx, crlURL)
bundle, err = f.Download(ctx, crlURL)
if err != nil {
return nil, false, err

Check warning on line 68 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L66-L68

Added lines #L66 - L68 were not covered by tests
}
return bundle, false, nil

Check warning on line 70 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L70

Added line #L70 was not covered by tests
}

return nil, false, err

Check warning on line 73 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L73

Added line #L73 was not covered by tests
}

return bundle, true, nil

Check warning on line 76 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L76

Added line #L76 was not covered by tests
}

func (f *fetcher) downloadAndCache(ctx context.Context, crlURL string) (bundle *cache.Bundle, fromCache bool, err error) {
// Download downloads the CRL from the given URL and saves it to the
// cache
func (f *cachedFetcher) Download(ctx context.Context, crlURL string) (bundle *cache.Bundle, err error) {
bundle, err = download(ctx, crlURL, f.httpClient)
if err != nil {
return nil, false, err
return nil, err

Check warning on line 84 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L81-L84

Added lines #L81 - L84 were not covered by tests
}

// save to cache
if err := f.cacheClient.Set(ctx, tarStoreName(crlURL), bundle); err != nil {
return nil, false, fmt.Errorf("failed to save to cache: %w", err)
return nil, fmt.Errorf("failed to save to cache: %w", err)

Check warning on line 89 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L88-L89

Added lines #L88 - L89 were not covered by tests
}

return bundle, false, nil
return bundle, nil

Check warning on line 92 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L92

Added line #L92 was not covered by tests
}

func download(ctx context.Context, crlURL string, client *http.Client) (bundle *cache.Bundle, err error) {

Check warning on line 95 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L95

Added line #L95 was not covered by tests
Expand All @@ -111,8 +116,7 @@ func download(ctx context.Context, crlURL string, client *http.Client) (bundle *
return nil, fmt.Errorf("failed to download with status code: %d", resp.StatusCode)

Check warning on line 116 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L114-L116

Added lines #L114 - L116 were not covered by tests
}
// read with size limit
limitedReader := io.LimitReader(resp.Body, maxCRLSize)
data, err := io.ReadAll(limitedReader)
data, err := io.ReadAll(io.LimitReader(resp.Body, maxCRLSize))
if err != nil {
return nil, fmt.Errorf("failed to read CRL response: %w", err)

Check warning on line 121 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L119-L121

Added lines #L119 - L121 were not covered by tests
}
Expand All @@ -125,11 +129,7 @@ func download(ctx context.Context, crlURL string, client *http.Client) (bundle *
if err != nil {
return nil, fmt.Errorf("failed to parse CRL: %w", err)

Check warning on line 130 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L128-L130

Added lines #L128 - L130 were not covered by tests
}
bundle, err = cache.NewBundle(crl, crlURL)
if err != nil {
return nil, fmt.Errorf("failed to create bundle: %w", err)
}
return bundle, nil
return cache.NewBundle(crl, crlURL)

Check warning on line 132 in revocation/crl/fetcher/fetcher.go

View check run for this annotation

Codecov / codecov/patch

revocation/crl/fetcher/fetcher.go#L132

Added line #L132 was not covered by tests
}

func tarStoreName(url string) string {
Expand Down

0 comments on commit e128f6d

Please sign in to comment.