diff --git a/buildtools.json b/buildtools.json index 6b3e85e..433b176 100644 --- a/buildtools.json +++ b/buildtools.json @@ -77,4 +77,4 @@ "checksum": "6317c36bec63158038381e8878601151ae996310fef58306f70cb03f1b46ef7f" } ] -} +} \ No newline at end of file diff --git a/cmd/bindownloader/config.go b/cmd/bindownloader/config.go index 2bd9572..e3af7cd 100644 --- a/cmd/bindownloader/config.go +++ b/cmd/bindownloader/config.go @@ -2,19 +2,23 @@ package main import ( "encoding/json" + "fmt" "io/ioutil" + "path" "github.com/alecthomas/kong" "github.com/willabides/bindownloader" ) var configKongVars = kong.Vars{ - "config_format_help": `formats the config file`, - "config_checksums_help": `update checksums in the config file`, + "config_format_help": `formats the config file`, + "config_checksums_help": `update checksums in the config file`, + "config_checksums_bin_help": `name of the binary to update`, } type configCmd struct { - Format configFmtCmd `kong:"cmd,help=${config_format_help}"` + Format configFmtCmd `kong:"cmd,help=${config_format_help}"` + UpdateChecksums configUpdateChecksumsCmd `kong:"cmd,help=${config_checksums_bin_help}"` } type configFmtCmd struct{} @@ -30,3 +34,39 @@ func (c configFmtCmd) Run() error { } return ioutil.WriteFile(cli.Configfile, b, 0600) } + +type configUpdateChecksumsCmd struct { + TargetFile string `kong:"required=true,arg,help=${config_checksums_bin_help}"` +} + +func (d *configUpdateChecksumsCmd) Run(*kong.Context) error { + config, err := bindownloader.LoadConfigFile(cli.Configfile) + if err != nil { + return fmt.Errorf("error loading config from %q", cli.Configfile) + } + binary := path.Base(d.TargetFile) + binDir := path.Dir(d.TargetFile) + + downloaders, ok := config[binary] + if !ok { + return fmt.Errorf("nothing configured for %q", binary) + } + + for _, downloader := range downloaders { + err = downloader.UpdateChecksum(bindownloader.UpdateChecksumOpts{ + DownloaderName: binary, + CellarDir: cli.CellarDir, + TargetDir: binDir, + }) + if err != nil { + return err + } + } + + b, err := json.MarshalIndent(&config, "", " ") + if err != nil { + return err + } + + return ioutil.WriteFile(cli.Configfile, b, 0600) +} diff --git a/downloader.go b/downloader.go index 1189fa2..66ac393 100644 --- a/downloader.go +++ b/downloader.go @@ -139,6 +139,12 @@ func (d *Downloader) download(downloadDir string) error { return downloadFile(dlPath, d.URL) } +func (d *Downloader) setDefaultBinName(defaultName string) { + if d.BinName == "" { + d.BinName = defaultName + } +} + func (d *Downloader) validateChecksum(targetDir string) error { targetFile, err := d.downloadablePath(targetDir) if err != nil { @@ -162,6 +168,45 @@ got: %s`, targetFile, d.Checksum, result) return nil } +//UpdateChecksumOpts options for UpdateChecksum +type UpdateChecksumOpts struct { + // DownloaderName is the downloader's key from the config file + DownloaderName string + // CellarDir is the directory where downloads and extractions will be placed. Default is a /.bindownloader + CellarDir string + // TargetDir is the directory where the executable should end up + TargetDir string +} + +//UpdateChecksum updates the checksum based on a fresh download +func (d *Downloader) UpdateChecksum(opts UpdateChecksumOpts) error { + cellarDir := opts.CellarDir + if cellarDir == "" { + cellarDir = filepath.Join(opts.TargetDir, ".bindownloader") + } + + downloadDir := filepath.Join(cellarDir, "downloads", d.downloadsSubName()) + + err := d.download(downloadDir) + if err != nil { + log.Printf("error downloading: %v", err) + return err + } + + dlPath, err := d.downloadablePath(downloadDir) + if err != nil { + return err + } + + checkSum, err := fileChecksum(dlPath) + if err != nil { + return err + } + + d.Checksum = checkSum + return nil +} + //InstallOpts options for Install type InstallOpts struct { // DownloaderName is the downloader's key from the config file @@ -184,9 +229,7 @@ func (d *Downloader) extractsSubName() string { //Install downloads and installs a bin func (d *Downloader) Install(opts InstallOpts) error { - if d.BinName == "" { - d.BinName = opts.DownloaderName - } + d.setDefaultBinName(opts.DownloaderName) cellarDir := opts.CellarDir if cellarDir == "" { cellarDir = filepath.Join(opts.TargetDir, ".bindownloader")