From 4a761c287b463316918db8e3de1106bf50b61bc9 Mon Sep 17 00:00:00 2001 From: jguer Date: Mon, 17 Aug 2020 02:19:18 +0200 Subject: [PATCH] test(upgrade): test AUR upgrades --- .snapshots/Test_upAUR-No_Updates | 2 + .snapshots/Test_upAUR-Simple_Update | 1 + .snapshots/Test_upAUR-Time_Update | 1 + clean.go | 6 +- cmd.go | 6 +- exec.go | 41 ++++++++++ pkg/db/mock/repo.go | 51 +++++++++++++ upgrade.go | 19 +++-- upgrade_test.go | 113 ++++++++++++++++++++++++++++ 9 files changed, 224 insertions(+), 16 deletions(-) create mode 100644 .snapshots/Test_upAUR-No_Updates create mode 100644 .snapshots/Test_upAUR-Simple_Update create mode 100644 .snapshots/Test_upAUR-Time_Update create mode 100644 pkg/db/mock/repo.go create mode 100644 upgrade_test.go diff --git a/.snapshots/Test_upAUR-No_Updates b/.snapshots/Test_upAUR-No_Updates new file mode 100644 index 00000000..e9766df2 --- /dev/null +++ b/.snapshots/Test_upAUR-No_Updates @@ -0,0 +1,2 @@ + -> ignored: ignoring package upgrade (1.0.0 => 2.0.0) + diff --git a/.snapshots/Test_upAUR-Simple_Update b/.snapshots/Test_upAUR-Simple_Update new file mode 100644 index 00000000..8b137891 --- /dev/null +++ b/.snapshots/Test_upAUR-Simple_Update @@ -0,0 +1 @@ + diff --git a/.snapshots/Test_upAUR-Time_Update b/.snapshots/Test_upAUR-Time_Update new file mode 100644 index 00000000..8b137891 --- /dev/null +++ b/.snapshots/Test_upAUR-Time_Update @@ -0,0 +1 @@ + diff --git a/clean.go b/clean.go index 5d5e8fc1..9e258383 100644 --- a/clean.go +++ b/clean.go @@ -19,12 +19,12 @@ import ( // GetPkgbuild gets the pkgbuild of the package 'pkg' trying the ABS first and then the AUR trying the ABS first and then the AUR. // RemovePackage removes package from VCS information -func removeVCSPackage(pkgs []string) { +func removeVCSPackage(pkgs []string, localCache vcsInfo) { updated := false for _, pkgName := range pkgs { - if _, ok := savedInfo[pkgName]; ok { - delete(savedInfo, pkgName) + if _, ok := localCache[pkgName]; ok { + delete(localCache, pkgName) updated = true } } diff --git a/cmd.go b/cmd.go index 13985e86..19cad181 100644 --- a/cmd.go +++ b/cmd.go @@ -159,7 +159,7 @@ func handleCmd(cmdArgs *settings.Arguments, dbExecutor db.Executor) error { case "Q", "query": return handleQuery(cmdArgs, dbExecutor) case "R", "remove": - return handleRemove(cmdArgs) + return handleRemove(cmdArgs, savedInfo) case "S", "sync": return handleSync(cmdArgs, dbExecutor) case "T", "deptest": @@ -285,10 +285,10 @@ func handleSync(cmdArgs *settings.Arguments, dbExecutor db.Executor) error { return nil } -func handleRemove(cmdArgs *settings.Arguments) error { +func handleRemove(cmdArgs *settings.Arguments, localCache vcsInfo) error { err := show(passToPacman(cmdArgs)) if err == nil { - removeVCSPackage(cmdArgs.Targets) + removeVCSPackage(cmdArgs.Targets, localCache) } return err diff --git a/exec.go b/exec.go index 3a325fcf..da87affb 100644 --- a/exec.go +++ b/exec.go @@ -133,3 +133,44 @@ func passToGit(dir string, _args ...string) *exec.Cmd { func isTty() bool { return terminal.IsTerminal(int(os.Stdout.Fd())) } + +type Runner interface { + Capture(string, int64, ...string) (string, string, error) +} + +type OSRunner struct{} + +func (r *OSRunner) Capture(command string, timeout int64, args ...string) (stdout, stderr string, err error) { + var outbuf, errbuf bytes.Buffer + var timer *time.Timer + + cmd := exec.Command(command, args...) + cmd.Stdout = &outbuf + cmd.Stderr = &errbuf + err = cmd.Start() + if err != nil { + return "", "", err + } + + if timeout != 0 { + timer = time.AfterFunc(time.Duration(timeout)*time.Second, func() { + err = cmd.Process.Kill() + if err != nil { + text.Errorln(err) + } + }) + } + + err = cmd.Wait() + if timeout != 0 { + timer.Stop() + } + if err != nil { + return "", "", err + } + + stdout = strings.TrimSpace(outbuf.String()) + stderr = strings.TrimSpace(errbuf.String()) + + return stdout, stderr, err +} diff --git a/pkg/db/mock/repo.go b/pkg/db/mock/repo.go new file mode 100644 index 00000000..de6e5157 --- /dev/null +++ b/pkg/db/mock/repo.go @@ -0,0 +1,51 @@ +package mock + +import ( + "time" + + "github.com/Jguer/go-alpm" +) + +type Package struct { + PBase string + PBuildDate time.Time + PDB *alpm.DB + PDescription string + PISize int64 + PName string + PShouldIgnore bool + PSize int64 + PVersion string + PReason alpm.PkgReason +} + +func (p *Package) Base() string { + return p.PBase +} +func (p *Package) BuildDate() time.Time { + return p.PBuildDate +} +func (p *Package) DB() *alpm.DB { + return p.PDB +} +func (p *Package) Description() string { + return p.PDescription +} +func (p *Package) ISize() int64 { + return p.PISize +} +func (p *Package) Name() string { + return p.PName +} +func (p *Package) ShouldIgnore() bool { + return p.PShouldIgnore +} +func (p *Package) Size() int64 { + return p.PSize +} +func (p *Package) Version() string { + return p.PVersion +} +func (p *Package) Reason() alpm.PkgReason { + return p.PReason +} diff --git a/upgrade.go b/upgrade.go index e62b325f..9dd42845 100644 --- a/upgrade.go +++ b/upgrade.go @@ -61,7 +61,7 @@ func upList(warnings *query.AURWarnings, dbExecutor db.Executor, enableDowngrade wg.Add(1) go func() { - aurUp = upAUR(remote, aurdata) + aurUp = upAUR(remote, aurdata, config.TimeUpdate) wg.Done() }() @@ -69,7 +69,7 @@ func upList(warnings *query.AURWarnings, dbExecutor db.Executor, enableDowngrade text.OperationInfoln(gotext.Get("Checking development packages...")) wg.Add(1) go func() { - develUp = upDevel(remote, aurdata) + develUp = upDevel(remote, aurdata, savedInfo) wg.Done() }() } @@ -97,12 +97,11 @@ func upList(warnings *query.AURWarnings, dbExecutor db.Executor, enableDowngrade return aurUp, repoUp, errs.Return() } -func upDevel(remote []db.RepoPackage, aurdata map[string]*rpc.Pkg) upgrade.UpSlice { - toUpdate := make([]db.RepoPackage, 0) +func upDevel(remote []db.RepoPackage, aurdata map[string]*rpc.Pkg, localCache vcsInfo) upgrade.UpSlice { + toUpdate := make([]db.RepoPackage, 0, len(aurdata)) toRemove := make([]string, 0) - var mux1 sync.Mutex - var mux2 sync.Mutex + var mux1, mux2 sync.Mutex var wg sync.WaitGroup checkUpdate := func(vcsName string, e shaInfos) { @@ -126,7 +125,7 @@ func upDevel(remote []db.RepoPackage, aurdata map[string]*rpc.Pkg) upgrade.UpSli } } - for vcsName, e := range savedInfo { + for vcsName, e := range localCache { wg.Add(1) go checkUpdate(vcsName, e) } @@ -148,7 +147,7 @@ func upDevel(remote []db.RepoPackage, aurdata map[string]*rpc.Pkg) upgrade.UpSli } } - removeVCSPackage(toRemove) + removeVCSPackage(toRemove, localCache) return toUpgrade } @@ -163,7 +162,7 @@ func printIgnoringPackage(pkg db.RepoPackage, newPkgVersion string) { // upAUR gathers foreign packages and checks if they have new versions. // Output: Upgrade type package list. -func upAUR(remote []db.RepoPackage, aurdata map[string]*rpc.Pkg) upgrade.UpSlice { +func upAUR(remote []db.RepoPackage, aurdata map[string]*rpc.Pkg, timeUpdate bool) upgrade.UpSlice { toUpgrade := make(upgrade.UpSlice, 0) for _, pkg := range remote { @@ -172,7 +171,7 @@ func upAUR(remote []db.RepoPackage, aurdata map[string]*rpc.Pkg) upgrade.UpSlice continue } - if (config.TimeUpdate && (int64(aurPkg.LastModified) > pkg.BuildDate().Unix())) || + if (timeUpdate && (int64(aurPkg.LastModified) > pkg.BuildDate().Unix())) || (alpm.VerCmp(pkg.Version(), aurPkg.Version) < 0) { if pkg.ShouldIgnore() { printIgnoringPackage(pkg, aurPkg.Version) diff --git a/upgrade_test.go b/upgrade_test.go new file mode 100644 index 00000000..ed77fbc5 --- /dev/null +++ b/upgrade_test.go @@ -0,0 +1,113 @@ +package main + +import ( + "io/ioutil" + "os" + "testing" + "time" + + "github.com/Jguer/yay/v10/pkg/db" + "github.com/Jguer/yay/v10/pkg/db/mock" + "github.com/Jguer/yay/v10/pkg/upgrade" + "github.com/bradleyjkemp/cupaloy" + rpc "github.com/mikkeloscar/aur" + "github.com/stretchr/testify/assert" +) + +func Test_upAUR(t *testing.T) { + type args struct { + remote []db.RepoPackage + aurdata map[string]*rpc.Pkg + timeUpdate bool + } + tests := []struct { + name string + args args + want upgrade.UpSlice + }{ + {name: "No Updates", + args: args{ + remote: []db.RepoPackage{ + &mock.Package{PName: "hello", PVersion: "2.0.0"}, + &mock.Package{PName: "local_pkg", PVersion: "1.1.0"}, + &mock.Package{PName: "ignored", PVersion: "1.0.0", PShouldIgnore: true}}, + aurdata: map[string]*rpc.Pkg{ + "hello": {Version: "2.0.0", Name: "hello"}, + "ignored": {Version: "2.0.0", Name: "ignored"}}, + timeUpdate: false, + }, + want: upgrade.UpSlice{}}, + {name: "Simple Update", + args: args{ + remote: []db.RepoPackage{&mock.Package{PName: "hello", PVersion: "2.0.0"}}, + aurdata: map[string]*rpc.Pkg{"hello": {Version: "2.1.0", Name: "hello"}}, + timeUpdate: false, + }, + want: upgrade.UpSlice{upgrade.Upgrade{Name: "hello", Repository: "aur", LocalVersion: "2.0.0", RemoteVersion: "2.1.0"}}}, + {name: "Time Update", + args: args{ + remote: []db.RepoPackage{&mock.Package{PName: "hello", PVersion: "2.0.0", PBuildDate: time.Now()}}, + aurdata: map[string]*rpc.Pkg{"hello": {Version: "2.0.0", Name: "hello", LastModified: int(time.Now().AddDate(0, 0, 2).Unix())}}, + timeUpdate: true, + }, + want: upgrade.UpSlice{upgrade.Upgrade{Name: "hello", Repository: "aur", LocalVersion: "2.0.0", RemoteVersion: "2.0.0"}}}, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + rescueStdout := os.Stdout + r, w, _ := os.Pipe() + os.Stdout = w + got := upAUR(tt.args.remote, tt.args.aurdata, tt.args.timeUpdate) + assert.EqualValues(t, tt.want, got) + + w.Close() + out, _ := ioutil.ReadAll(r) + cupaloy.SnapshotT(t, out) + os.Stdout = rescueStdout + }) + } +} + +func Test_upDevel(t *testing.T) { + type args struct { + remote []db.RepoPackage + aurdata map[string]*rpc.Pkg + cached vcsInfo + } + tests := []struct { + name string + args args + want upgrade.UpSlice + }{ + {name: "No Updates", + args: args{ + cached: vcsInfo{}, + remote: []db.RepoPackage{ + &mock.Package{PName: "hello", PVersion: "2.0.0"}, + &mock.Package{PName: "local_pkg", PVersion: "1.1.0"}, + &mock.Package{PName: "ignored", PVersion: "1.0.0", PShouldIgnore: true}}, + aurdata: map[string]*rpc.Pkg{ + "hello": {Version: "2.0.0", Name: "hello"}, + "ignored": {Version: "2.0.0", Name: "ignored"}}, + }, + want: upgrade.UpSlice{}}, + {name: "Simple Update", + args: args{ + cached: vcsInfo{ + "hello": shaInfos{ + "github.com/Jguer/yay.git": shaInfo{ + Protocols: []string{"https"}, + Branch: "main", + SHA: "991c5b4146fd27f4aacf4e3111258a848934aaa1"}}}, + remote: []db.RepoPackage{&mock.Package{PName: "hello", PVersion: "2.0.0"}}, + aurdata: map[string]*rpc.Pkg{"hello": {Version: "2.1.0", Name: "hello"}}, + }, + want: upgrade.UpSlice{upgrade.Upgrade{Name: "hello", Repository: "aur", LocalVersion: "2.0.0", RemoteVersion: "2.1.0"}}}, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + got := upDevel(tt.args.remote, tt.args.aurdata, tt.args.cached) + assert.EqualValues(t, tt.want, got) + }) + } +}