Browse Source

feat(vcs): refactor and test cover

jguer 4 years ago
parent
commit
1db50882e9
8 changed files with 307 additions and 11 deletions
  1. 2 2
      cmd.go
  2. 0 4
      config.go
  3. 11 0
      pkg/vcs/.snapshots/TestInfoStore_Update-simple
  4. 1 1
      pkg/vcs/vcs.go
  5. 289 0
      pkg/vcs/vcs_test.go
  6. 2 2
      upgrade.go
  7. 1 1
      upgrade_test.go
  8. 1 1
      vcs.go

+ 2 - 2
cmd.go

@@ -160,7 +160,7 @@ func handleCmd(cmdArgs *settings.Arguments, dbExecutor db.Executor) error {
 	case "Q", "query":
 		return handleQuery(cmdArgs, dbExecutor)
 	case "R", "remove":
-		return handleRemove(cmdArgs, savedInfo)
+		return handleRemove(cmdArgs, config.Runtime.VCSStore)
 	case "S", "sync":
 		return handleSync(cmdArgs, dbExecutor)
 	case "T", "deptest":
@@ -285,7 +285,7 @@ func handleSync(cmdArgs *settings.Arguments, dbExecutor db.Executor) error {
 	return nil
 }
 
-func handleRemove(cmdArgs *settings.Arguments, localCache vcs.InfoStore) error {
+func handleRemove(cmdArgs *settings.Arguments, localCache *vcs.InfoStore) error {
 	err := config.Runtime.CmdRunner.Show(passToPacman(cmdArgs))
 	if err == nil {
 		localCache.RemovePackage(cmdArgs.Targets)

+ 0 - 4
config.go

@@ -11,7 +11,6 @@ import (
 
 	"github.com/Jguer/yay/v10/pkg/settings"
 	"github.com/Jguer/yay/v10/pkg/text"
-	"github.com/Jguer/yay/v10/pkg/vcs"
 )
 
 // Verbosity settings for search
@@ -25,9 +24,6 @@ var yayVersion = "10.0.0"
 
 var localePath = "/usr/share/locale"
 
-// savedInfo holds the current vcs info
-var savedInfo vcs.InfoStore
-
 // YayConf holds the current config values for yay.
 var config *settings.Configuration
 

+ 11 - 0
pkg/vcs/.snapshots/TestInfoStore_Update-simple

@@ -0,0 +1,11 @@
+{
+	"hello": {
+		"github.com/jguer/yay.git": {
+			"protocols": [
+				"git"
+			],
+			"branch": "master",
+			"sha": "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"
+		}
+	}
+}

+ 1 - 1
pkg/vcs/vcs.go

@@ -200,7 +200,7 @@ func (v *InfoStore) NeedsUpdate(infos OriginInfoByURL) bool {
 }
 
 func (v *InfoStore) Save() error {
-	marshalledinfo, err := json.MarshalIndent(v, "", "\t")
+	marshalledinfo, err := json.MarshalIndent(v.OriginsByPackage, "", "\t")
 	if err != nil || string(marshalledinfo) == "null" {
 		return err
 	}

+ 289 - 0
pkg/vcs/vcs_test.go

@@ -1,9 +1,20 @@
 package vcs
 
 import (
+	"encoding/json"
+	"errors"
+	"fmt"
+	"io/ioutil"
+	"os"
+	"os/exec"
+	"sync"
 	"testing"
 
+	gosrc "github.com/Morganamilo/go-srcinfo"
+	"github.com/bradleyjkemp/cupaloy"
 	"github.com/stretchr/testify/assert"
+
+	"github.com/Jguer/yay/v10/pkg/settings/exe"
 )
 
 func TestParsing(t *testing.T) {
@@ -40,3 +51,281 @@ func TestParsing(t *testing.T) {
 		assert.Equal(t, compare.Protocols, protocols)
 	}
 }
+
+func TestNewInfoStore(t *testing.T) {
+	type args struct {
+		filePath   string
+		runner     exe.Runner
+		cmdBuilder *exe.CmdBuilder
+	}
+	tests := []struct {
+		name string
+		args args
+	}{
+		{
+			name: "normal",
+			args: args{"/tmp/a.json", &exe.OSRunner{}, exe.NewCmdBuilder("git", "--a --b")},
+		},
+	}
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+			got := NewInfoStore(tt.args.filePath, tt.args.runner, tt.args.cmdBuilder)
+			assert.NotNil(t, got)
+			assert.Equal(t, []string{"--a", "--b"}, got.CmdBuilder.GitFlags)
+			assert.Equal(t, tt.args.cmdBuilder, got.CmdBuilder)
+			assert.Equal(t, tt.args.runner, got.Runner)
+			assert.Equal(t, "/tmp/a.json", got.FilePath)
+		})
+	}
+}
+
+type MockRunner struct {
+	Returned []string
+	Index    int
+}
+
+func (r *MockRunner) Show(cmd *exec.Cmd) error {
+	return nil
+}
+
+func (r *MockRunner) Capture(cmd *exec.Cmd, timeout int64) (stdout, stderr string, err error) {
+	stdout = r.Returned[r.Index]
+	if r.Returned[0] == "error" {
+		err = errors.New("possible error")
+	}
+	return stdout, stderr, err
+}
+
+func TestInfoStore_NeedsUpdate(t *testing.T) {
+	type fields struct {
+		Runner     exe.Runner
+		CmdBuilder *exe.CmdBuilder
+	}
+	type args struct {
+		infos OriginInfoByURL
+	}
+	tests := []struct {
+		name   string
+		fields fields
+		args   args
+		want   bool
+	}{
+		{
+			name: "simple-has_update",
+			args: args{infos: OriginInfoByURL{
+				"github.com/Jguer/z.git": OriginInfo{
+					Protocols: []string{"https"},
+					Branch:    "0",
+					SHA:       "991c5b4146fd27f4aacf4e3111258a848934aaa1",
+				},
+			}}, fields: fields{
+				Runner: &MockRunner{
+					Returned: []string{"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa	HEAD"},
+				},
+				CmdBuilder: exe.NewCmdBuilder("git", ""),
+			},
+			want: true,
+		},
+		{
+			name: "double-has_update",
+			args: args{infos: OriginInfoByURL{
+				"github.com/Jguer/z.git": OriginInfo{
+					Protocols: []string{"https"},
+					Branch:    "0",
+					SHA:       "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
+				},
+				"github.com/Jguer/a.git": OriginInfo{
+					Protocols: []string{"https"},
+					Branch:    "0",
+					SHA:       "991c5b4146fd27f4aacf4e3111258a848934aaa1",
+				},
+			}}, fields: fields{
+				Runner: &MockRunner{
+					Returned: []string{
+						"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa	HEAD",
+						"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa	HEAD",
+					},
+				},
+				CmdBuilder: exe.NewCmdBuilder("git", ""),
+			},
+			want: true,
+		},
+		{
+			name: "simple-no_update",
+			args: args{infos: OriginInfoByURL{
+				"github.com/Jguer/z.git": OriginInfo{
+					Protocols: []string{"https"},
+					Branch:    "0",
+					SHA:       "991c5b4146fd27f4aacf4e3111258a848934aaa1",
+				},
+			}}, fields: fields{
+				Runner: &MockRunner{
+					Returned: []string{"991c5b4146fd27f4aacf4e3111258a848934aaa1	HEAD"},
+				},
+				CmdBuilder: exe.NewCmdBuilder("git", ""),
+			},
+			want: false,
+		},
+		{
+			name: "simple-no_split",
+			args: args{infos: OriginInfoByURL{
+				"github.com/Jguer/z.git": OriginInfo{
+					Protocols: []string{"https"},
+					Branch:    "0",
+					SHA:       "991c5b4146fd27f4aacf4e3111258a848934aaa1",
+				},
+			}}, fields: fields{
+				Runner: &MockRunner{
+					Returned: []string{"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"},
+				},
+				CmdBuilder: exe.NewCmdBuilder("git", ""),
+			},
+			want: false,
+		},
+		{
+			name: "simple-error",
+			args: args{infos: OriginInfoByURL{
+				"github.com/Jguer/z.git": OriginInfo{
+					Protocols: []string{"https"},
+					Branch:    "0",
+					SHA:       "991c5b4146fd27f4aacf4e3111258a848934aaa1",
+				},
+			}}, fields: fields{
+				Runner: &MockRunner{
+					Returned: []string{"error"},
+				},
+				CmdBuilder: exe.NewCmdBuilder("git", ""),
+			},
+			want: false,
+		},
+		{
+			name: "simple-no protocol",
+			args: args{infos: OriginInfoByURL{
+				"github.com/Jguer/z.git": OriginInfo{
+					Protocols: []string{},
+					Branch:    "0",
+					SHA:       "991c5b4146fd27f4aacf4e3111258a848934aaa1",
+				},
+			}}, fields: fields{
+				Runner: &MockRunner{
+					Returned: []string{"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"},
+				},
+				CmdBuilder: exe.NewCmdBuilder("git", ""),
+			},
+			want: false,
+		},
+	}
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+			v := &InfoStore{
+				Runner:     tt.fields.Runner,
+				CmdBuilder: tt.fields.CmdBuilder,
+			}
+			got := v.NeedsUpdate(tt.args.infos)
+			assert.Equal(t, tt.want, got)
+		})
+	}
+}
+
+func TestInfoStore_Update(t *testing.T) {
+	type fields struct {
+		OriginsByPackage map[string]OriginInfoByURL
+		Runner           exe.Runner
+		CmdBuilder       *exe.CmdBuilder
+	}
+	type args struct {
+		pkgName string
+		sources []gosrc.ArchString
+	}
+	tests := []struct {
+		name   string
+		fields fields
+		args   args
+	}{
+		{name: "simple",
+			args: args{pkgName: "hello",
+				sources: []gosrc.ArchString{{Value: "git://github.com/jguer/yay.git#branch=master"}}},
+			fields: fields{
+				OriginsByPackage: make(map[string]OriginInfoByURL),
+				CmdBuilder:       exe.NewCmdBuilder("git", ""),
+				Runner:           &MockRunner{Returned: []string{"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa HEAD"}},
+			},
+		},
+	}
+
+	file, err := ioutil.TempFile("/tmp", "yay-vcs-test")
+	assert.NoError(t, err)
+	defer os.Remove(file.Name())
+
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+			v := &InfoStore{
+				OriginsByPackage: tt.fields.OriginsByPackage,
+				FilePath:         file.Name(),
+				Runner:           tt.fields.Runner,
+				CmdBuilder:       tt.fields.CmdBuilder,
+			}
+			var mux sync.Mutex
+			var wg sync.WaitGroup
+			wg.Add(1)
+			v.Update(tt.args.pkgName, tt.args.sources, &mux, &wg)
+			wg.Wait()
+			assert.Len(t, tt.fields.OriginsByPackage, 1)
+
+			marshalledinfo, err := json.MarshalIndent(tt.fields.OriginsByPackage, "", "\t")
+			assert.NoError(t, err)
+
+			cupaloy.SnapshotT(t, marshalledinfo)
+
+			v.Load()
+			fmt.Println(v.OriginsByPackage)
+			assert.Len(t, tt.fields.OriginsByPackage, 1)
+
+			marshalledinfo, err = json.MarshalIndent(tt.fields.OriginsByPackage, "", "\t")
+			assert.NoError(t, err)
+
+			cupaloy.SnapshotT(t, marshalledinfo)
+		})
+	}
+}
+
+func TestInfoStore_Remove(t *testing.T) {
+	type fields struct {
+		OriginsByPackage map[string]OriginInfoByURL
+	}
+	type args struct {
+		pkgs []string
+	}
+	tests := []struct {
+		name   string
+		fields fields
+		args   args
+	}{
+		{name: "simple",
+			args: args{pkgs: []string{"a", "c"}},
+			fields: fields{
+				OriginsByPackage: map[string]OriginInfoByURL{
+					"a": {},
+					"b": {},
+					"c": {},
+					"d": {},
+				},
+			},
+		},
+	}
+
+	file, err := ioutil.TempFile("/tmp", "yay-vcs-test")
+	assert.NoError(t, err)
+	defer os.Remove(file.Name())
+
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+			v := &InfoStore{
+				OriginsByPackage: tt.fields.OriginsByPackage,
+				FilePath:         file.Name(),
+			}
+			v.RemovePackage(tt.args.pkgs)
+			assert.Len(t, tt.fields.OriginsByPackage, 2)
+		})
+	}
+}

+ 2 - 2
upgrade.go

@@ -70,7 +70,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, savedInfo)
+					develUp = upDevel(remote, aurdata, config.Runtime.VCSStore)
 					wg.Done()
 				}()
 			}
@@ -101,7 +101,7 @@ func upList(warnings *query.AURWarnings, dbExecutor db.Executor, enableDowngrade
 func upDevel(
 	remote []db.RepoPackage,
 	aurdata map[string]*rpc.Pkg,
-	localCache vcs.InfoStore) upgrade.UpSlice {
+	localCache *vcs.InfoStore) upgrade.UpSlice {
 	toUpdate := make([]db.RepoPackage, 0, len(aurdata))
 	toRemove := make([]string, 0)
 

+ 1 - 1
upgrade_test.go

@@ -266,7 +266,7 @@ func Test_upDevel(t *testing.T) {
 	for _, tt := range tests {
 		t.Run(tt.name, func(t *testing.T) {
 			config.Runtime.CmdRunner.(*MockRunner).t = t
-			got := upDevel(tt.args.remote, tt.args.aurdata, tt.args.cached)
+			got := upDevel(tt.args.remote, tt.args.aurdata, &tt.args.cached)
 			assert.ElementsMatch(t, tt.want, got)
 			assert.Equal(t, tt.finalLen, len(tt.args.cached.OriginsByPackage))
 		})

+ 1 - 1
vcs.go

@@ -43,7 +43,7 @@ func createDevelDB(config *settings.Configuration, dbExecutor db.Executor) error
 	for i := range srcinfos {
 		for iP := range srcinfos[i].Packages {
 			wg.Add(1)
-			go savedInfo.Update(srcinfos[i].Packages[iP].Pkgname, srcinfos[i].Source, &mux, &wg)
+			go config.Runtime.VCSStore.Update(srcinfos[i].Packages[iP].Pkgname, srcinfos[i].Source, &mux, &wg)
 		}
 	}