Skip to content

Commit 905f4fc

Browse files
authored
Merge pull request #1 from rainforestapp/pp/42
Allow configuring a name for the archived binary
2 parents 04a545f + 154e825 commit 905f4fc

3 files changed

Lines changed: 80 additions & 17 deletions

File tree

selfupdate/update.go

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -15,9 +15,13 @@ import (
1515
"github.com/inconshreveable/go-update"
1616
)
1717

18-
func uncompressAndUpdate(src io.Reader, assetURL, cmdPath string) error {
19-
_, cmd := filepath.Split(cmdPath)
20-
asset, err := UncompressCommand(src, assetURL, cmd)
18+
func uncompressAndUpdate(src io.Reader, assetURL, cmdPath string, binaryName string) error {
19+
if binaryName == "" {
20+
_, binaryName = filepath.Split(cmdPath)
21+
} else if runtime.GOOS == "windows" {
22+
binaryName += ".exe"
23+
}
24+
asset, err := UncompressCommand(src, assetURL, binaryName)
2125
if err != nil {
2226
return err
2327
}
@@ -76,7 +80,7 @@ func (up *Updater) UpdateTo(rel *Release, cmdPath string) error {
7680
}
7781

7882
if up.validator == nil {
79-
return uncompressAndUpdate(bytes.NewReader(data), rel.AssetURL, cmdPath)
83+
return uncompressAndUpdate(bytes.NewReader(data), rel.AssetURL, cmdPath, up.binaryName)
8084
}
8185

8286
validationSrc, validationRedirectURL, err := up.api.Repositories.DownloadReleaseAsset(up.apiCtx, rel.RepoOwner, rel.RepoName, rel.ValidationAssetID, &client)
@@ -102,7 +106,7 @@ func (up *Updater) UpdateTo(rel *Release, cmdPath string) error {
102106
return fmt.Errorf("Failed validating asset content: %v", err)
103107
}
104108

105-
return uncompressAndUpdate(bytes.NewReader(data), rel.AssetURL, cmdPath)
109+
return uncompressAndUpdate(bytes.NewReader(data), rel.AssetURL, cmdPath, up.binaryName)
106110
}
107111

108112
// UpdateCommand updates a given command binary to the latest version.
@@ -165,7 +169,7 @@ func UpdateTo(assetURL, cmdPath string) error {
165169
return err
166170
}
167171
defer src.Close()
168-
return uncompressAndUpdate(src, assetURL, cmdPath)
172+
return uncompressAndUpdate(src, assetURL, cmdPath, up.binaryName)
169173
}
170174

171175
// UpdateCommand updates a given command binary to the latest version.

selfupdate/update_test.go

Lines changed: 58 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -11,16 +11,34 @@ import (
1111
"github.com/blang/semver"
1212
)
1313

14-
func setupTestBinary() {
15-
if err := exec.Command("go", "build", "./testdata/github-release-test/").Run(); err != nil {
14+
func setupTestBinary(name ...string) {
15+
var options []string
16+
var output string
17+
if len(name) == 0 {
18+
options = []string{"build", "./testdata/github-release-test/"}
19+
} else {
20+
output = name[0]
21+
if runtime.GOOS == "windows" {
22+
output += ".exe"
23+
}
24+
options = []string{"build", "-o", output, "./testdata/github-release-test/"}
25+
}
26+
27+
if err := exec.Command("go", options...).Run(); err != nil {
1628
panic(err)
1729
}
1830
}
1931

20-
func teardownTestBinary() {
21-
bin := "github-release-test"
32+
func teardownTestBinary(name ...string) {
33+
var bin string
34+
if len(name) == 0 {
35+
bin = "github-release-test"
36+
} else {
37+
bin = name[0]
38+
}
39+
2240
if runtime.GOOS == "windows" {
23-
bin = "github-release-test.exe"
41+
bin += ".exe"
2442
}
2543
if err := os.Remove(bin); err != nil {
2644
panic(err)
@@ -64,6 +82,41 @@ func TestUpdateCommand(t *testing.T) {
6482
}
6583
}
6684

85+
func TestUpdateWithDifferentBinaryName(t *testing.T) {
86+
setupTestBinary("gh-release-test")
87+
defer teardownTestBinary("gh-release-test")
88+
latest := semver.MustParse("1.2.3")
89+
prev := semver.MustParse("1.2.2")
90+
91+
_, err := UpdateCommand("gh-release-test", prev, "rhysd-test/test-release-zip")
92+
if err == nil {
93+
t.Fatal("Error should occur for broken package")
94+
}
95+
if !strings.Contains(err.Error(), "the command is not found") {
96+
t.Fatal("Unexpected error:", err)
97+
}
98+
99+
up, err := NewUpdater(Config{BinaryName: "github-release-test", Filters: []string{"github-release-test"}})
100+
if err != nil {
101+
t.Fatal(err)
102+
}
103+
rel, err := up.UpdateCommand("gh-release-test", prev, "rhysd-test/test-release-zip")
104+
if err != nil {
105+
t.Fatal(err)
106+
}
107+
if rel.Version.NE(latest) {
108+
t.Error("Version is not latest", rel.Version)
109+
}
110+
bytes, err := exec.Command(filepath.FromSlash("./gh-release-test")).Output()
111+
if err != nil {
112+
t.Fatal("Failed to run test binary after update:", err)
113+
}
114+
out := string(bytes)
115+
if out != "v1.2.3\n" {
116+
t.Error("Output from test binary after update is unexpected:", out)
117+
}
118+
}
119+
67120
func TestUpdateViaSymlink(t *testing.T) {
68121
if testing.Short() {
69122
t.Skip("skip tests in short mode.")

selfupdate/updater.go

Lines changed: 12 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,11 @@ import (
1515
// Updater is responsible for managing the context of self-update.
1616
// It contains GitHub client and its context.
1717
type Updater struct {
18-
api *github.Client
19-
apiCtx context.Context
20-
validator Validator
21-
filters []*regexp.Regexp
18+
api *github.Client
19+
apiCtx context.Context
20+
validator Validator
21+
filters []*regexp.Regexp
22+
binaryName string
2223
}
2324

2425
// Config represents the configuration of self-update.
@@ -37,6 +38,10 @@ type Config struct {
3738
// An asset is selected if it matches any of those, in addition to the regular tag, os, arch, extensions.
3839
// Please make sure that your filter(s) uniquely match an asset.
3940
Filters []string
41+
42+
// BinaryName represents the name of the binary extracted from the archive downloaded from GitHub.
43+
// If unset, the current executable's name will be used to match.
44+
BinaryName string
4045
}
4146

4247
func newHTTPClient(ctx context.Context, token string) *http.Client {
@@ -71,7 +76,7 @@ func NewUpdater(config Config) (*Updater, error) {
7176

7277
if config.EnterpriseBaseURL == "" {
7378
client := github.NewClient(hc)
74-
return &Updater{api: client, apiCtx: ctx, validator: config.Validator, filters: filtersRe}, nil
79+
return &Updater{api: client, apiCtx: ctx, validator: config.Validator, filters: filtersRe, binaryName: config.BinaryName}, nil
7580
}
7681

7782
u := config.EnterpriseUploadURL
@@ -82,7 +87,8 @@ func NewUpdater(config Config) (*Updater, error) {
8287
if err != nil {
8388
return nil, err
8489
}
85-
return &Updater{api: client, apiCtx: ctx, validator: config.Validator, filters: filtersRe}, nil
90+
91+
return &Updater{api: client, apiCtx: ctx, validator: config.Validator, filters: filtersRe, binaryName: config.BinaryName}, nil
8692
}
8793

8894
// DefaultUpdater creates a new updater instance with default configuration.

0 commit comments

Comments
 (0)