fix: pull OCI charts one by one (#1706)

* fix: pull OCI charts one by one

* fix: gofmt
This commit is contained in:
Thomas Loubiou 2021-03-04 01:24:22 +01:00 committed by GitHub
parent 19cbea49f7
commit 453b498ccb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
1 changed files with 37 additions and 3 deletions

View File

@ -73,6 +73,11 @@ type ReleaseSetSpec struct {
MissingFileHandler string `yaml:"missingFileHandler,omitempty"`
}
type PullCommand struct {
ChartRef string
responseChan chan error
}
// HelmState structure for the helmfile
type HelmState struct {
basePath string
@ -961,6 +966,11 @@ func (st *HelmState) PrepareCharts(helm helmexec.Interface, dir string, concurre
}
var builds []*chartPrepareResult
pullChan := make(chan *PullCommand)
defer func() {
pullChan <- nil
}()
go st.pullChartWorker(pullChan, helm)
st.scatterGather(
concurrency,
@ -993,7 +1003,7 @@ func (st *HelmState) PrepareCharts(helm helmexec.Interface, dir string, concurre
chartFetchedByGoGetter := chartPath != chartName
if !chartFetchedByGoGetter {
ociChartPath, err := st.getOCIChart(release, dir, helm)
ociChartPath, err := st.getOCIChart(pullChan, release, dir, helm)
if err != nil {
results <- &chartPrepareResult{err: fmt.Errorf("release %q: %w", release.Name, err)}
@ -2991,7 +3001,7 @@ func (st *HelmState) Reverse() {
}
}
func (st *HelmState) getOCIChart(release *ReleaseSpec, tempDir string, helm helmexec.Interface) (*string, error) {
func (st *HelmState) getOCIChart(pullChan chan *PullCommand, release *ReleaseSpec, tempDir string, helm helmexec.Interface) (*string, error) {
repo, name := st.GetRepositoryAndNameFromChartName(release.Chart)
if repo == nil {
return nil, nil
@ -3008,7 +3018,7 @@ func (st *HelmState) getOCIChart(release *ReleaseSpec, tempDir string, helm helm
qualifiedChartName := fmt.Sprintf("%s/%s:%s", repo.URL, name, chartVersion)
err := helm.ChartPull(qualifiedChartName)
err := st.pullChart(pullChan, qualifiedChartName)
if err != nil {
return nil, err
}
@ -3039,3 +3049,27 @@ func (st *HelmState) getOCIChart(release *ReleaseSpec, tempDir string, helm helm
return &chartPath, nil
}
// Pull charts one by one to prevent concurrent pull problems with Helm
func (st *HelmState) pullChartWorker(pullChan chan *PullCommand, helm helmexec.Interface) {
for {
pullCmd := <-pullChan
if pullCmd != nil {
err := helm.ChartPull(pullCmd.ChartRef)
pullCmd.responseChan <- err
} else {
return
}
}
}
// Send a pull command to the pull worker
func (st *HelmState) pullChart(pullChan chan *PullCommand, chartRef string) error {
response := make(chan error, 1)
cmd := &PullCommand{
responseChan: response,
ChartRef: chartRef,
}
pullChan <- cmd
return <-response
}