github.com/golang/dep@v0.5.4/cmd/dep/ensure_test.go (about)

     1  // Copyright 2017 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package main
     6  
     7  import (
     8  	"bytes"
     9  	"errors"
    10  	"go/build"
    11  	"io/ioutil"
    12  	"log"
    13  	"strings"
    14  	"testing"
    15  
    16  	"github.com/golang/dep"
    17  	"github.com/golang/dep/gps"
    18  	"github.com/golang/dep/gps/pkgtree"
    19  	"github.com/golang/dep/internal/test"
    20  )
    21  
    22  func TestInvalidEnsureFlagCombinations(t *testing.T) {
    23  	ec := &ensureCommand{
    24  		update: true,
    25  		add:    true,
    26  	}
    27  
    28  	if err := ec.validateFlags(); err == nil {
    29  		t.Error("-add and -update together should fail validation")
    30  	}
    31  
    32  	ec.vendorOnly, ec.add = true, false
    33  	if err := ec.validateFlags(); err == nil {
    34  		t.Error("-vendor-only with -update should fail validation")
    35  	}
    36  
    37  	ec.add, ec.update = true, false
    38  	if err := ec.validateFlags(); err == nil {
    39  		t.Error("-vendor-only with -add should fail validation")
    40  	}
    41  
    42  	ec.noVendor, ec.add = true, false
    43  	if err := ec.validateFlags(); err == nil {
    44  		t.Error("-vendor-only with -no-vendor should fail validation")
    45  	}
    46  	ec.noVendor = false
    47  
    48  	// Also verify that the plain ensure path takes no args. This is a shady
    49  	// test, as lots of other things COULD return errors, and we don't check
    50  	// anything other than the error being non-nil. For now, it works well
    51  	// because a panic will quickly result if the initial arg length validation
    52  	// checks are incorrectly handled.
    53  	if err := ec.runDefault(nil, []string{"foo"}, nil, nil, gps.SolveParameters{}); err == nil {
    54  		t.Errorf("no args to plain ensure with -vendor-only")
    55  	}
    56  	ec.vendorOnly = false
    57  	if err := ec.runDefault(nil, []string{"foo"}, nil, nil, gps.SolveParameters{}); err == nil {
    58  		t.Errorf("no args to plain ensure")
    59  	}
    60  }
    61  
    62  func TestCheckErrors(t *testing.T) {
    63  	tt := []struct {
    64  		name        string
    65  		fatal       bool
    66  		pkgOrErrMap map[string]pkgtree.PackageOrErr
    67  	}{
    68  		{
    69  			name:  "noErrors",
    70  			fatal: false,
    71  			pkgOrErrMap: map[string]pkgtree.PackageOrErr{
    72  				"mypkg": {
    73  					P: pkgtree.Package{},
    74  				},
    75  			},
    76  		},
    77  		{
    78  			name:  "hasErrors",
    79  			fatal: true,
    80  			pkgOrErrMap: map[string]pkgtree.PackageOrErr{
    81  				"github.com/me/pkg": {
    82  					Err: &build.NoGoError{},
    83  				},
    84  				"github.com/someone/pkg": {
    85  					Err: errors.New("code is busted"),
    86  				},
    87  			},
    88  		},
    89  		{
    90  			name:  "onlyGoErrors",
    91  			fatal: false,
    92  			pkgOrErrMap: map[string]pkgtree.PackageOrErr{
    93  				"github.com/me/pkg": {
    94  					Err: &build.NoGoError{},
    95  				},
    96  				"github.com/someone/pkg": {
    97  					P: pkgtree.Package{},
    98  				},
    99  			},
   100  		},
   101  		{
   102  			name:  "onlyBuildErrors",
   103  			fatal: false,
   104  			pkgOrErrMap: map[string]pkgtree.PackageOrErr{
   105  				"github.com/me/pkg": {
   106  					Err: &build.NoGoError{},
   107  				},
   108  				"github.com/someone/pkg": {
   109  					P: pkgtree.Package{},
   110  				},
   111  			},
   112  		},
   113  		{
   114  			name:  "allGoErrors",
   115  			fatal: true,
   116  			pkgOrErrMap: map[string]pkgtree.PackageOrErr{
   117  				"github.com/me/pkg": {
   118  					Err: &build.NoGoError{},
   119  				},
   120  			},
   121  		},
   122  		{
   123  			name:  "allMixedErrors",
   124  			fatal: true,
   125  			pkgOrErrMap: map[string]pkgtree.PackageOrErr{
   126  				"github.com/me/pkg": {
   127  					Err: &build.NoGoError{},
   128  				},
   129  				"github.com/someone/pkg": {
   130  					Err: errors.New("code is busted"),
   131  				},
   132  			},
   133  		},
   134  	}
   135  
   136  	for _, tc := range tt {
   137  		t.Run(tc.name, func(t *testing.T) {
   138  			fatal, err := checkErrors(tc.pkgOrErrMap, nil)
   139  			if tc.fatal != fatal {
   140  				t.Fatalf("expected fatal flag to be %T, got %T", tc.fatal, fatal)
   141  			}
   142  			if err == nil && fatal {
   143  				t.Fatal("unexpected fatal flag value while err is nil")
   144  			}
   145  		})
   146  	}
   147  }
   148  
   149  func TestValidateUpdateArgs(t *testing.T) {
   150  	cases := []struct {
   151  		name           string
   152  		args           []string
   153  		wantError      error
   154  		wantWarn       []string
   155  		lockedProjects []string
   156  	}{
   157  		{
   158  			name:      "empty args",
   159  			args:      []string{},
   160  			wantError: nil,
   161  		},
   162  		{
   163  			name:      "not project root",
   164  			args:      []string{"github.com/golang/dep/cmd"},
   165  			wantError: errUpdateArgsValidation,
   166  			wantWarn: []string{
   167  				"github.com/golang/dep/cmd is not a project root, try github.com/golang/dep instead",
   168  			},
   169  		},
   170  		{
   171  			name:      "not present in lock",
   172  			args:      []string{"github.com/golang/dep"},
   173  			wantError: errUpdateArgsValidation,
   174  			wantWarn: []string{
   175  				"github.com/golang/dep is not present in Gopkg.lock, cannot -update it",
   176  			},
   177  		},
   178  		{
   179  			name:      "cannot specify alternate sources",
   180  			args:      []string{"github.com/golang/dep:github.com/example/dep"},
   181  			wantError: errUpdateArgsValidation,
   182  			wantWarn: []string{
   183  				"cannot specify alternate sources on -update (github.com/example/dep)",
   184  			},
   185  			lockedProjects: []string{"github.com/golang/dep"},
   186  		},
   187  		{
   188  			name:      "version constraint passed",
   189  			args:      []string{"github.com/golang/dep@master"},
   190  			wantError: errUpdateArgsValidation,
   191  			wantWarn: []string{
   192  				"version constraint master passed for github.com/golang/dep, but -update follows constraints declared in Gopkg.toml, not CLI arguments",
   193  			},
   194  			lockedProjects: []string{"github.com/golang/dep"},
   195  		},
   196  		{
   197  			name:      "flags after spec",
   198  			args:      []string{"github.com/golang/dep@master", "-v"},
   199  			wantError: errUpdateArgsValidation,
   200  			wantWarn: []string{
   201  				"could not infer project root from dependency path",
   202  			},
   203  			lockedProjects: []string{"github.com/golang/dep"},
   204  		},
   205  	}
   206  
   207  	h := test.NewHelper(t)
   208  	defer h.Cleanup()
   209  
   210  	h.TempDir("src")
   211  	pwd := h.Path(".")
   212  
   213  	stderrOutput := &bytes.Buffer{}
   214  	errLogger := log.New(stderrOutput, "", 0)
   215  	ctx := &dep.Ctx{
   216  		GOPATH: pwd,
   217  		Out:    log.New(ioutil.Discard, "", 0),
   218  		Err:    errLogger,
   219  	}
   220  
   221  	sm, err := ctx.SourceManager()
   222  	h.Must(err)
   223  	defer sm.Release()
   224  
   225  	p := new(dep.Project)
   226  	params := p.MakeParams()
   227  
   228  	for _, c := range cases {
   229  		t.Run(c.name, func(t *testing.T) {
   230  			// Empty the buffer for every case
   231  			stderrOutput.Reset()
   232  
   233  			// Fill up the locked projects
   234  			lockedProjects := make([]gps.LockedProject, 0, len(c.lockedProjects))
   235  			for _, lp := range c.lockedProjects {
   236  				pi := gps.ProjectIdentifier{ProjectRoot: gps.ProjectRoot(lp)}
   237  				lockedProjects = append(lockedProjects, gps.NewLockedProject(pi, gps.NewVersion("v1.0.0"), []string{}))
   238  			}
   239  
   240  			// Add lock to project
   241  			p.Lock = &dep.Lock{P: lockedProjects}
   242  
   243  			err := validateUpdateArgs(ctx, c.args, p, sm, &params)
   244  			if err != c.wantError {
   245  				t.Fatalf("Unexpected error while validating update args:\n\t(GOT): %v\n\t(WNT): %v", err, c.wantError)
   246  			}
   247  
   248  			warnings := stderrOutput.String()
   249  			for _, warn := range c.wantWarn {
   250  				if !strings.Contains(warnings, warn) {
   251  					t.Fatalf("Expected validateUpdateArgs errors to contain: %q", warn)
   252  				}
   253  			}
   254  		})
   255  	}
   256  }