/
repo_update.go
134 lines (112 loc) · 3.33 KB
/
repo_update.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
package repo
import (
"errors"
"fmt"
"io"
"os"
"sync"
"github.com/spf13/cobra"
"k8s.io/helm/cmd/helm/installer"
"k8s.io/helm/pkg/getter"
"k8s.io/helm/pkg/helm/helmpath"
"k8s.io/helm/pkg/repo"
"github.com/flant/werf/cmd/werf/common"
helmCommon "github.com/flant/werf/cmd/werf/helm/common"
)
const updateDesc = `
Update gets the latest information about charts from the respective chart repositories.
Information is cached locally, where it is used by commands like 'werf helm repo search'.
`
var errNoRepositories = errors.New("no repositories found. You must add one before updating")
type repoUpdateCmd struct {
update func([]*repo.ChartRepository, io.Writer, helmpath.Home, bool) error
home helmpath.Home
out io.Writer
strict bool
}
func newRepoUpdateCmd() *cobra.Command {
var commonCmdData common.CmdData
var helmCommonCmdData helmCommon.HelmCmdData
u := &repoUpdateCmd{
out: os.Stdout,
update: updateCharts,
}
cmd := &cobra.Command{
Use: "update",
Short: "Update information of available charts locally from chart repositories",
Long: updateDesc,
DisableFlagsInUseLine: true,
RunE: func(cmd *cobra.Command, args []string) error {
if err := common.ProcessLogOptions(&commonCmdData); err != nil {
common.PrintHelp(cmd)
return err
}
helmCommon.InitHelmSettings(&helmCommonCmdData)
u.home = helmCommon.HelmSettings.Home
return u.run()
},
}
f := cmd.Flags()
f.BoolVar(&u.strict, "strict", false, "fail on update warnings")
common.SetupLogOptions(&commonCmdData, cmd)
helmCommon.SetupHelmHome(&helmCommonCmdData, cmd)
return cmd
}
func (u *repoUpdateCmd) run() error {
f, err := repo.LoadRepositoriesFile(u.home.RepositoryFile())
if err != nil {
if helmCommon.IsCouldNotLoadRepositoriesFileError(err) {
return fmt.Errorf(helmCommon.CouldNotLoadRepositoriesFileErrorFormat, u.home.RepositoryFile())
}
return err
}
if len(f.Repositories) == 0 {
return errNoRepositories
}
var repos []*repo.ChartRepository
for _, cfg := range f.Repositories {
r, err := repo.NewChartRepository(cfg, getter.All(*helmCommon.HelmSettings))
if err != nil {
return err
}
repos = append(repos, r)
}
return u.update(repos, u.out, u.home, u.strict)
}
func updateCharts(repos []*repo.ChartRepository, out io.Writer, home helmpath.Home, strict bool) error {
fmt.Fprintln(out, "Hang tight while we grab the latest from your chart repositories...")
var (
errorCounter int
wg sync.WaitGroup
mu sync.Mutex
)
for _, re := range repos {
wg.Add(1)
go func(re *repo.ChartRepository) {
defer wg.Done()
if re.Config.Name == installer.LocalRepository {
mu.Lock()
fmt.Fprintf(out, "...Skip %s chart repository\n", re.Config.Name)
mu.Unlock()
return
}
err := re.DownloadIndexFile(home.Cache())
if err != nil {
mu.Lock()
errorCounter++
fmt.Fprintf(out, "...Unable to get an update from the %q chart repository (%s):\n\t%s\n", re.Config.Name, re.Config.URL, err)
mu.Unlock()
} else {
mu.Lock()
fmt.Fprintf(out, "...Successfully got an update from the %q chart repository\n", re.Config.Name)
mu.Unlock()
}
}(re)
}
wg.Wait()
if errorCounter != 0 && strict {
return errors.New("Update Failed. Check log for details")
}
fmt.Fprintln(out, "Update Complete.")
return nil
}