Skip to content
This repository has been archived by the owner on Sep 9, 2020. It is now read-only.

Add importer for github.com/LK4D4/vndr #978

Merged
merged 7 commits into from
Aug 11, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
28 changes: 13 additions & 15 deletions cmd/dep/glide_importer_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,6 @@ import (
"github.com/pkg/errors"
)

const testGlideProjectRoot = "github.com/golang/notexist"

var (
discardLogger = log.New(ioutil.Discard, "", 0)
)
Expand Down Expand Up @@ -110,7 +108,7 @@ func TestGlideConfig_Convert(t *testing.T) {
yaml: glideYaml{
ExcludeDirs: []string{"samples"},
},
projectRoot: testGlideProjectRoot,
projectRoot: testProjectRoot,
wantIgnoreCount: 1,
wantIgnoredPackages: []string{"github.com/golang/notexist/samples"},
},
Expand All @@ -119,15 +117,15 @@ func TestGlideConfig_Convert(t *testing.T) {
Name: "github.com/golang/mismatched-package-name",
ExcludeDirs: []string{"samples"},
},
projectRoot: testGlideProjectRoot,
projectRoot: testProjectRoot,
wantIgnoreCount: 1,
wantIgnoredPackages: []string{"github.com/golang/notexist/samples"},
},
"bad input, empty package name": {
yaml: glideYaml{
Imports: []glidePackage{{Name: ""}},
},
projectRoot: testGlideProjectRoot,
projectRoot: testProjectRoot,
wantConvertErr: true,
},
}
Expand Down Expand Up @@ -243,10 +241,10 @@ func TestGlideConfig_Import(t *testing.T) {
h.Must(err)
defer sm.Release()

h.TempDir(filepath.Join("src", testGlideProjectRoot))
h.TempCopy(filepath.Join(testGlideProjectRoot, glideYamlName), "glide/glide.yaml")
h.TempCopy(filepath.Join(testGlideProjectRoot, glideLockName), "glide/glide.lock")
projectRoot := h.Path(testGlideProjectRoot)
h.TempDir(filepath.Join("src", testProjectRoot))
h.TempCopy(filepath.Join(testProjectRoot, glideYamlName), "glide/glide.yaml")
h.TempCopy(filepath.Join(testProjectRoot, glideLockName), "glide/glide.lock")
projectRoot := h.Path(testProjectRoot)

// Capture stderr so we can verify output
verboseOutput := &bytes.Buffer{}
Expand All @@ -257,7 +255,7 @@ func TestGlideConfig_Import(t *testing.T) {
t.Fatal("Expected the importer to detect the glide configuration files")
}

m, l, err := g.Import(projectRoot, testGlideProjectRoot)
m, l, err := g.Import(projectRoot, testProjectRoot)
h.Must(err)

if m == nil {
Expand Down Expand Up @@ -291,16 +289,16 @@ func TestGlideConfig_Import_MissingLockFile(t *testing.T) {
h.Must(err)
defer sm.Release()

h.TempDir(filepath.Join("src", testGlideProjectRoot))
h.TempCopy(filepath.Join(testGlideProjectRoot, glideYamlName), "glide/glide.yaml")
projectRoot := h.Path(testGlideProjectRoot)
h.TempDir(filepath.Join("src", testProjectRoot))
h.TempCopy(filepath.Join(testProjectRoot, glideYamlName), "glide/glide.yaml")
projectRoot := h.Path(testProjectRoot)

g := newGlideImporter(ctx.Err, true, sm)
if !g.HasDepMetadata(projectRoot) {
t.Fatal("The glide importer should gracefully handle when only glide.yaml is present")
}

m, l, err := g.Import(projectRoot, testGlideProjectRoot)
m, l, err := g.Import(projectRoot, testProjectRoot)
h.Must(err)

if m == nil {
Expand Down Expand Up @@ -340,7 +338,7 @@ func TestGlideConfig_Convert_WarnsForUnusedFields(t *testing.T) {
Imports: []glidePackage{pkg},
}

_, _, err = g.convert(testGlideProjectRoot)
_, _, err = g.convert(testProjectRoot)
if err != nil {
t.Fatal(err)
}
Expand Down
14 changes: 7 additions & 7 deletions cmd/dep/godep_importer_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ import (
"github.com/pkg/errors"
)

const testGodepProjectRoot = "github.com/golang/notexist"
const testProjectRoot = "github.com/golang/notexist"

func TestGodepConfig_Convert(t *testing.T) {
testCases := map[string]struct {
Expand Down Expand Up @@ -199,10 +199,10 @@ func TestGodepConfig_Import(t *testing.T) {
cacheDir := "gps-repocache"
h.TempDir(cacheDir)
h.TempDir("src")
h.TempDir(filepath.Join("src", testGodepProjectRoot))
h.TempCopy(filepath.Join(testGodepProjectRoot, godepPath), "godep/Godeps.json")
h.TempDir(filepath.Join("src", testProjectRoot))
h.TempCopy(filepath.Join(testProjectRoot, godepPath), "godep/Godeps.json")

projectRoot := h.Path(testGodepProjectRoot)
projectRoot := h.Path(testProjectRoot)
sm, err := gps.NewSourceManager(h.Path(cacheDir))
h.Must(err)
defer sm.Release()
Expand All @@ -216,7 +216,7 @@ func TestGodepConfig_Import(t *testing.T) {
t.Fatal("Expected the importer to detect godep configuration file")
}

m, l, err := g.Import(projectRoot, testGodepProjectRoot)
m, l, err := g.Import(projectRoot, testProjectRoot)
h.Must(err)

if m == nil {
Expand Down Expand Up @@ -262,9 +262,9 @@ func TestGodepConfig_JsonLoad(t *testing.T) {

ctx := newTestContext(h)

h.TempCopy(filepath.Join(testGodepProjectRoot, godepPath), "godep/Godeps.json")
h.TempCopy(filepath.Join(testProjectRoot, godepPath), "godep/Godeps.json")

projectRoot := h.Path(testGodepProjectRoot)
projectRoot := h.Path(testProjectRoot)

g := newGodepImporter(ctx.Err, true, nil)
err := g.load(projectRoot)
Expand Down
1 change: 1 addition & 0 deletions cmd/dep/root_analyzer.go
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,7 @@ func (a *rootAnalyzer) importManifestAndLock(dir string, pr gps.ProjectRoot, sup
importers := []importer{
newGlideImporter(logger, a.ctx.Verbose, a.sm),
newGodepImporter(logger, a.ctx.Verbose, a.sm),
newVndrImporter(logger, a.ctx.Verbose, a.sm),
}

for _, i := range importers {
Expand Down
21 changes: 21 additions & 0 deletions cmd/dep/testdata/harness_tests/init/vndr/case1/final/Gopkg.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@

[[constraint]]
name = "github.com/sdboyer/deptestdos"
version = "2.0.0"
16 changes: 16 additions & 0 deletions cmd/dep/testdata/harness_tests/init/vndr/case1/initial/main.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
// Copyright 2017 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package main

import (
"fmt"

"github.com/sdboyer/deptestdos"
)

func main() {
var x deptestdos.Bar
fmt.Println(x)
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# Comment on its own line
github.com/sdboyer/deptest 3f4c3bea144e112a69bbe5d8d01c1b09a544253f https://github.com/sdboyer/deptest.git
github.com/sdboyer/deptestdos v2.0.0
13 changes: 13 additions & 0 deletions cmd/dep/testdata/harness_tests/init/vndr/case1/testcase.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
{
"commands": [
["init", "-no-examples"]
],
"error-expected": "",
"gopath-initial": {
"github.com/sdboyer/deptest": "3f4c3bea144e112a69bbe5d8d01c1b09a544253f"
},
"vendor-final": [
"github.com/sdboyer/deptest",
"github.com/sdboyer/deptestdos"
]
}
6 changes: 6 additions & 0 deletions cmd/dep/testdata/vndr/golden.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
Detected vndr configuration file...
Converting from vendor.conf...
Using 3f4c3bea144e112a69bbe5d8d01c1b09a544253f as initial hint for imported dep github.com/sdboyer/deptest
Trying v0.8.1 (3f4c3be) as initial lock for imported dep github.com/sdboyer/deptest
Using ^2.0.0 as initial constraint for imported dep github.com/sdboyer/deptestdos
Trying * (v2.0.0) as initial lock for imported dep github.com/sdboyer/deptestdos
4 changes: 4 additions & 0 deletions cmd/dep/testdata/vndr/vendor.conf
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
github.com/sdboyer/deptest 3f4c3bea144e112a69bbe5d8d01c1b09a544253f https://github.com/sdboyer/deptest.git # trailing comment
# line comment

github.com/sdboyer/deptestdos v2.0.0 # trailing comment
161 changes: 161 additions & 0 deletions cmd/dep/vndr_importer.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,161 @@
// Copyright 2017 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

package main

import (
"bufio"
"log"
"os"
"path/filepath"
"strings"

"github.com/golang/dep"
fb "github.com/golang/dep/internal/feedback"
"github.com/golang/dep/internal/gps"
"github.com/pkg/errors"
)

func vndrFile(dir string) string {
return filepath.Join(dir, "vendor.conf")
}

type vndrImporter struct {
packages []vndrPackage

logger *log.Logger
verbose bool
sm gps.SourceManager
}

func newVndrImporter(log *log.Logger, verbose bool, sm gps.SourceManager) *vndrImporter {
return &vndrImporter{
logger: log,
verbose: verbose,
sm: sm,
}
}

func (v *vndrImporter) Name() string { return "vndr" }

func (v *vndrImporter) HasDepMetadata(dir string) bool {
_, err := os.Stat(vndrFile(dir))
return err == nil
}

func (v *vndrImporter) Import(dir string, pr gps.ProjectRoot) (*dep.Manifest, *dep.Lock, error) {
v.logger.Println("Detected vndr configuration file...")

err := v.loadVndrFile(dir)
if err != nil {
return nil, nil, errors.Wrapf(err, "unable to load vndr file")
}

return v.convert(pr)
}

func (v *vndrImporter) loadVndrFile(dir string) error {
v.logger.Printf("Converting from vendor.conf...")

f, err := os.Open(vndrFile(dir))
if err != nil {
return errors.Wrapf(err, "Unable to open %s", vndrFile(dir))
}
defer f.Close()

scanner := bufio.NewScanner(f)
for scanner.Scan() {
pkg, err := parseVndrLine(scanner.Text())
if err != nil {
return errors.Wrapf(err, "unable to parse line")
}
if pkg == nil {
// Could be an empty line or one which is just a comment
continue
}
v.packages = append(v.packages, *pkg)
}

if scanner.Err() != nil {
return errors.Wrapf(err, "unable to read %s", vndrFile(dir))
}

return nil
}

func (v *vndrImporter) convert(pr gps.ProjectRoot) (*dep.Manifest, *dep.Lock, error) {
var (
manifest = &dep.Manifest{
Constraints: make(gps.ProjectConstraints),
}
lock = &dep.Lock{}
err error
)

for _, pkg := range v.packages {
pc := gps.ProjectConstraint{
Ident: gps.ProjectIdentifier{
ProjectRoot: gps.ProjectRoot(pkg.importPath),
Source: pkg.repository,
},
}
pc.Constraint, err = v.sm.InferConstraint(pkg.revision, pc.Ident)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I know that moby uses short git hashes, which is a bit of a problem. I think it would be easiest to have that be a separate issue, so I created #987 to address that part.

if err != nil {
return nil, nil, errors.Wrapf(err, "Unable to interpret revision specifier '%s' for package %s", pkg.importPath, pkg.revision)
}

manifest.Constraints[pc.Ident.ProjectRoot] = gps.ProjectProperties{
Source: pc.Ident.Source,
Constraint: pc.Constraint,
}
fb.NewConstraintFeedback(pc, fb.DepTypeImported).LogFeedback(v.logger)

revision := gps.Revision(pkg.revision)
version, err := lookupVersionForLockedProject(pc.Ident, pc.Constraint, revision, v.sm)
if err != nil {
v.logger.Println(err.Error())
}

lp := gps.NewLockedProject(pc.Ident, version, nil)

lock.P = append(lock.P, lp)
fb.NewLockedProjectFeedback(lp, fb.DepTypeImported).LogFeedback(v.logger)
}

return manifest, lock, nil
}

type vndrPackage struct {
importPath string
revision string
repository string
}

func parseVndrLine(line string) (*vndrPackage, error) {
commentIdx := strings.Index(line, "#")
if commentIdx >= 0 {
line = line[:commentIdx]
}
line = strings.TrimSpace(line)

if line == "" {
return nil, nil
}

parts := strings.Fields(line)

if !(len(parts) == 2 || len(parts) == 3) {
return nil, errors.Errorf("invalid config format: %q", line)
}

pkg := &vndrPackage{
importPath: parts[0],
revision: parts[1],
}
if len(parts) == 3 {
pkg.repository = parts[2]
}

return pkg, nil
}
Loading