mirror of
https://github.com/MedzikUser/go-github-selfupdate.git
synced 2024-08-15 03:25:29 +00:00
implement logger and DetectLatest()
This commit is contained in:
parent
d3edf54df9
commit
1124782254
6 changed files with 198 additions and 2 deletions
|
@ -30,7 +30,7 @@ It provides `selfupdate` package.
|
|||
```go
|
||||
import (
|
||||
"log"
|
||||
"github.com/rhysd/go-github-selfupdate"
|
||||
"github.com/rhysd/go-github-selfupdate/selfupdate"
|
||||
)
|
||||
|
||||
func doUpdate(version string) {
|
||||
|
|
|
@ -3,13 +3,13 @@ package main
|
|||
import (
|
||||
"flag"
|
||||
"fmt"
|
||||
"github.com/rhysd/go-github-selfupdate/selfupdate"
|
||||
"os"
|
||||
)
|
||||
|
||||
const version = "1.2.3"
|
||||
|
||||
func selfUpdate() error {
|
||||
return nil
|
||||
up, err := selfupdate.TryUpdate(version, "go-github-selfupdate", nil)
|
||||
if err != nil {
|
||||
return err
|
||||
|
|
71
selfupdate/detect.go
Normal file
71
selfupdate/detect.go
Normal file
|
@ -0,0 +1,71 @@
|
|||
package selfupdate
|
||||
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
"github.com/blang/semver"
|
||||
"github.com/google/go-github/github"
|
||||
"golang.org/x/oauth2"
|
||||
"net/http"
|
||||
"os"
|
||||
"strings"
|
||||
)
|
||||
|
||||
// ReleaseDetector is responsible for detecting the latest release using GitHub Releases API.
|
||||
type ReleaseDetector struct {
|
||||
verPrefix string
|
||||
api *github.Client
|
||||
apiCtx context.Context
|
||||
}
|
||||
|
||||
// NewDetector crates a new detector instance. It initializes GitHub API client.
|
||||
func NewDetector(versionPrefix string) *ReleaseDetector {
|
||||
token := os.Getenv("GITHUB_TOKEN")
|
||||
ctx := context.Background()
|
||||
|
||||
var auth *http.Client
|
||||
if token != "" {
|
||||
src := oauth2.StaticTokenSource(&oauth2.Token{AccessToken: token})
|
||||
auth = oauth2.NewClient(ctx, src)
|
||||
}
|
||||
|
||||
client := github.NewClient(auth)
|
||||
return &ReleaseDetector{versionPrefix, client, ctx}
|
||||
}
|
||||
|
||||
// DetectLatest tries to get the latest version of the repository on GitHub. 'slug' means 'owner/name' formatted string.
|
||||
func (d *ReleaseDetector) DetectLatest(slug string) (ver semver.Version, found bool, err error) {
|
||||
repo := strings.Split(slug, "/")
|
||||
if len(repo) != 2 || repo[0] == "" || repo[1] == "" {
|
||||
err = fmt.Errorf("Invalid slug format. It should be 'owner/name': %s", slug)
|
||||
return
|
||||
}
|
||||
|
||||
rel, res, err := d.api.Repositories.GetLatestRelease(d.apiCtx, repo[0], repo[1])
|
||||
if err != nil {
|
||||
if res.StatusCode == 404 {
|
||||
// 404 means repository not found or release not found. It's not an error here.
|
||||
found = false
|
||||
err = nil
|
||||
log.Println("API returned 404. Repository or release not found")
|
||||
} else {
|
||||
log.Println("API returned an error:", err)
|
||||
}
|
||||
return
|
||||
}
|
||||
|
||||
tag := rel.GetTagName()
|
||||
log.Println("Successfully fetched the latest release. tag:", tag, ", name:", rel.GetName(), ", URL:", rel.GetURL())
|
||||
|
||||
ver, err = semver.Make(strings.TrimPrefix(tag, d.verPrefix))
|
||||
if err == nil {
|
||||
found = true
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// DetectLatest detects the latest release of the slug (owner/repo). verPrefix is a prefix of version in tag name (i.e. 'v' for 'v1.2.3').
|
||||
func DetectLatest(slug, verPrefix string) (semver.Version, bool, error) {
|
||||
return NewDetector(verPrefix).DetectLatest(slug)
|
||||
}
|
67
selfupdate/detect_test.go
Normal file
67
selfupdate/detect_test.go
Normal file
|
@ -0,0 +1,67 @@
|
|||
package selfupdate
|
||||
|
||||
import (
|
||||
"github.com/blang/semver"
|
||||
"os"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestGitHubTokenEnv(t *testing.T) {
|
||||
token := os.Getenv("GITHUB_TOKEN")
|
||||
if token == "" {
|
||||
t.Skip("because $GITHUB_TOKEN is not set")
|
||||
}
|
||||
_ = NewDetector("")
|
||||
}
|
||||
|
||||
func TestDetectRelease(t *testing.T) {
|
||||
v, ok, err := DetectLatest("rhysd/github-clone-all", "v")
|
||||
if err != nil {
|
||||
t.Fatal("Fetch failed:", err)
|
||||
}
|
||||
if !ok {
|
||||
t.Fatal("Failed to detect latest")
|
||||
}
|
||||
if v.LE(semver.MustParse("2.0.0")) {
|
||||
t.Fatal("Incorrect version:", v)
|
||||
}
|
||||
}
|
||||
|
||||
func TestInvalidSlug(t *testing.T) {
|
||||
d := NewDetector("v")
|
||||
|
||||
for _, slug := range []string{
|
||||
"foo",
|
||||
"/",
|
||||
"foo/",
|
||||
"/bar",
|
||||
"foo/bar/piyo",
|
||||
} {
|
||||
_, _, err := d.DetectLatest(slug)
|
||||
if err == nil {
|
||||
t.Error(slug, "should be invalid slug")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestNonExistingRepo(t *testing.T) {
|
||||
d := NewDetector("")
|
||||
v, ok, err := d.DetectLatest("rhysd/non-existing-repo")
|
||||
if err != nil {
|
||||
t.Fatal("Non-existing repo should not cause an error:", v)
|
||||
}
|
||||
if ok {
|
||||
t.Fatal("Release for non-existing repo should not be found")
|
||||
}
|
||||
}
|
||||
|
||||
func TestNoReleaseFound(t *testing.T) {
|
||||
d := NewDetector("")
|
||||
_, ok, err := d.DetectLatest("rhysd/misc")
|
||||
if err != nil {
|
||||
t.Fatal("Repo having no release should not cause an error:", err)
|
||||
}
|
||||
if ok {
|
||||
t.Fatal("Repo having no release should not be found")
|
||||
}
|
||||
}
|
28
selfupdate/log.go
Normal file
28
selfupdate/log.go
Normal file
|
@ -0,0 +1,28 @@
|
|||
package selfupdate
|
||||
|
||||
import (
|
||||
"io/ioutil"
|
||||
stdlog "log"
|
||||
"os"
|
||||
)
|
||||
|
||||
var log = stdlog.New(os.Stderr, "", stdlog.Ltime)
|
||||
var logEnabled = true
|
||||
|
||||
// EnableLog enables to output logging messages in library
|
||||
func EnableLog() {
|
||||
if logEnabled {
|
||||
return
|
||||
}
|
||||
logEnabled = true
|
||||
log.SetOutput(os.Stderr)
|
||||
}
|
||||
|
||||
// DisableLog disables to output logging messages in library
|
||||
func DisableLog() {
|
||||
if !logEnabled {
|
||||
return
|
||||
}
|
||||
logEnabled = false
|
||||
log.SetOutput(ioutil.Discard)
|
||||
}
|
30
selfupdate/log_test.go
Normal file
30
selfupdate/log_test.go
Normal file
|
@ -0,0 +1,30 @@
|
|||
package selfupdate
|
||||
|
||||
import (
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestEnableDisableLog(t *testing.T) {
|
||||
defer EnableLog()
|
||||
|
||||
EnableLog()
|
||||
if !logEnabled {
|
||||
t.Fatal("Log should be enabled")
|
||||
}
|
||||
EnableLog()
|
||||
if !logEnabled {
|
||||
t.Fatal("Log should be enabled")
|
||||
}
|
||||
DisableLog()
|
||||
if logEnabled {
|
||||
t.Fatal("Log should not be enabled")
|
||||
}
|
||||
DisableLog()
|
||||
if logEnabled {
|
||||
t.Fatal("Log should not be enabled")
|
||||
}
|
||||
EnableLog()
|
||||
if !logEnabled {
|
||||
t.Fatal("Log should be enabled")
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue