fix(downloader): do not error for remote chart when local repo cache is missing

When resolving an absolute chart URL, scanReposForURL scans known repositories to check if any match the chart URL in order to apply repository-specific TLS or authentication options.

Previously, if any repository in repositories.yaml lacked a local cached index file (for example because the cache was cleared or never updated), scanReposForURL immediately aborted with an error ('no cached repo found'). This caused ResolveChartVersion to fail completely, preventing the user from downloading or templating an unrelated remote chart even when fetching directly by URL or when another repository had a valid cache.

This change skips repositories whose index cache does not exist (fs.ErrNotExist) rather than returning an early error. If no repository matches, ErrNoOwnerRepo is returned and swallowed by ResolveChartVersion to fall back to the default HTTP client as intended.

Closes #11961

Signed-off-by: abdouladieng <diengabdoulaziz110@gmail.com>
pull/32648/head
abdouladieng 3 weeks ago
parent bfa3b6c325
commit ac54143db7

@ -567,6 +567,10 @@ func (c *ChartDownloader) scanReposForURL(u string, rf *repo.File) (*repo.Entry,
idxFile := filepath.Join(c.RepositoryCache, helmpath.CacheIndexFile(r.Config.Name))
i, err := repo.LoadIndexFile(idxFile)
if err != nil {
if errors.Is(err, fs.ErrNotExist) {
// No cache for this repository; skip and keep looking rather than erroring
continue
}
return nil, fmt.Errorf("no cached repo found. (try 'helm repo update'): %w", err)
}

@ -328,6 +328,71 @@ func TestScanReposForURL(t *testing.T) {
require.ErrorIs(t, err, ErrNoOwnerRepo)
}
func TestScanReposForURLWithEmptyCache(t *testing.T) {
emptyCache := t.TempDir()
c := ChartDownloader{
Out: os.Stderr,
Verify: VerifyLater,
RepositoryConfig: repoConfig,
RepositoryCache: emptyCache,
Getters: getter.All(&cli.EnvSettings{
RepositoryConfig: repoConfig,
RepositoryCache: emptyCache,
}),
}
u := "http://example.com/alpine-0.2.0.tgz"
rf, err := repo.LoadFile(repoConfig)
require.NoError(t, err)
_, err = c.scanReposForURL(u, rf)
require.ErrorIs(t, err, ErrNoOwnerRepo)
}
func TestScanReposForURLWithMissingCacheForUnrelatedRepo(t *testing.T) {
rf := &repo.File{
APIVersion: "v1",
Repositories: []*repo.Entry{
{Name: "missing-repo", URL: "http://missing.example.com"},
{Name: "testing", URL: "http://example.com"},
},
}
c := ChartDownloader{
Out: os.Stderr,
Verify: VerifyLater,
RepositoryConfig: repoConfig,
RepositoryCache: repoCache,
Getters: getter.All(&cli.EnvSettings{
RepositoryConfig: repoConfig,
RepositoryCache: repoCache,
}),
}
u := "http://example.com/alpine-0.2.0.tgz"
entry, err := c.scanReposForURL(u, rf)
require.NoError(t, err)
assert.Equal(t, "testing", entry.Name, "Unexpected repo %q for URL %q", entry.Name, u)
}
func TestResolveChartVersionWithEmptyCache(t *testing.T) {
emptyCache := t.TempDir()
c := ChartDownloader{
Out: os.Stderr,
Verify: VerifyLater,
RepositoryConfig: repoConfig,
RepositoryCache: emptyCache,
Getters: getter.All(&cli.EnvSettings{
RepositoryConfig: repoConfig,
RepositoryCache: emptyCache,
}),
}
u := "http://example.com/alpine-0.2.0.tgz"
_, resolvedURL, err := c.ResolveChartVersion(u, "")
require.NoError(t, err)
assert.Equal(t, u, resolvedURL.String())
}
func TestDownloadToCache(t *testing.T) {
srv := repotest.NewTempServer(t,
repotest.WithChartSourceGlob("testdata/*.tgz*"),

Loading…
Cancel
Save