Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add VNDR support #892

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
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
12 changes: 6 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ When a dependent package is encountered its imports are scanned to determine
dependencies of dependencies (transitive dependencies). If the dependent project
contains a `glide.yaml` file that information is used to help determine the
dependency rules when fetching from a location or version to use. Configuration
from Godep, GB, GOM, and GPM is also imported.
from Godep, GB, GOM, GPM, and Vndr is also imported.

The dependencies are exported to the `vendor/` directory where the `go` tools
can find and use them. A `glide.lock` file is generated containing all the
Expand Down Expand Up @@ -206,7 +206,7 @@ $ glide get github.com/Masterminds/cookoo
```

When `glide get` is used it will introspect the listed package to resolve its
dependencies including using Godep, GPM, Gom, and GB config files.
dependencies including using Godep, GPM, Gom, GB, and Vndr config files.

### glide update (aliased to up)

Expand All @@ -219,7 +219,7 @@ $ glide up
```

This will recurse over the packages looking for other projects managed by Glide,
Godep, gb, gom, and GPM. When one is found those packages will be installed as needed.
Godep, gb, gom, GPM, and Vndr. When one is found those packages will be installed as needed.

A `glide.lock` file will be created or updated with the dependencies pinned to
specific versions. For example, if in the `glide.yaml` file a version was
Expand Down Expand Up @@ -423,13 +423,13 @@ That's up to you. It's not necessary, but it may also cause you extra
work and lots of extra space in your VCS. There may also be unforeseen errors
([see an example](https://github.com/mattfarina/golang-broken-vendor)).

#### Q: How do I import settings from GPM, Godep, gom or gb?
#### Q: How do I import settings from GPM, Godep, gom, gb, or Vndr?

There are two parts to importing.

1. If a package you import has configuration for GPM, Godep, gom or gb Glide will
1. If a package you import has configuration for GPM, Godep, gom, gb, or Vndr Glide will
recursively install the dependencies automatically.
2. If you would like to import configuration from GPM, Godep, gom or gb to Glide see
2. If you would like to import configuration from GPM, Godep, gom, gb, or Vndr to Glide see
the `glide import` command. For example, you can run `glide import godep` for
Glide to detect the projects Godep configuration and generate a `glide.yaml`
file for you.
Expand Down
13 changes: 13 additions & 0 deletions action/create.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import (
"github.com/Masterminds/glide/msg"
gpath "github.com/Masterminds/glide/path"
"github.com/Masterminds/glide/util"
"github.com/Masterminds/glide/vndr"
)

// Create creates/initializes a new Glide repository.
Expand Down Expand Up @@ -204,6 +205,9 @@ func guessImportDeps(base string, config *cfg.Config) {
} else if d, ok := guessImportGB(absBase); ok {
msg.Info("Importing GB configuration")
deps = d
} else if d, ok := guessImportVNDR(absBase); ok {
msg.Info("Importing VNDR configuration")
deps = d
}

for _, i := range deps {
Expand Down Expand Up @@ -243,3 +247,12 @@ func guessImportGB(dir string) ([]*cfg.Dependency, bool) {

return d, true
}

func guessImportVNDR(dir string) ([]*cfg.Dependency, bool) {
d, err := vndr.Parse(dir)
if err != nil || len(d) == 0 {
return []*cfg.Dependency{}, false
}

return d, true
}
21 changes: 21 additions & 0 deletions action/import_vndr.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
package action

import (
"github.com/Masterminds/glide/msg"
"github.com/Masterminds/glide/vndr"
)

// ImportVNDR imports a vendor.conf file.
func ImportVNDR(dest string) {
base := "."
config := EnsureConfig()
if !vndr.Has(base) {
msg.Die("No VNDR data found.")
}
deps, err := vndr.Parse(base)
if err != nil {
msg.Die("Failed to extract VNDR file: %s", err)
}
appendImports(deps, config)
writeConfigToFileOrStdout(config, dest)
}
4 changes: 2 additions & 2 deletions docs/commands.md
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ You can download one or more packages to your `vendor` directory and have it add

$ glide get github.com/Masterminds/cookoo

When `glide get` is used it will introspect the listed package to resolve its dependencies including using Godep, GPM, Gom, and GB config files.
When `glide get` is used it will introspect the listed package to resolve its dependencies including using Godep, GPM, Gom, GB, and Vndr config files.

The `glide get` command can have a [version or range](versions.md) passed in with the package name. For example,

Expand All @@ -63,7 +63,7 @@ dependency packages to fetch anything that's needed and read in any configuratio
$ glide up

This will recurse over the packages looking for other projects managed by Glide,
Godep, gb, gom, and GPM. When one is found those packages will be installed as needed.
Godep, gb, gom, GPM, and Vndr. When one is found those packages will be installed as needed.

A `glide.lock` file will be created or updated with the dependencies pinned to
specific versions. For example, if in the `glide.yaml` file a version was
Expand Down
6 changes: 3 additions & 3 deletions docs/faq.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,12 +18,12 @@ By default, commands such as `glide update` and `glide install` install on-deman
* `--strip-vcs` (aliased to `-s`) to strip VCS metadata (e.g., `.git` directories) from the `vendor` folder.
* `--strip-vendor` (aliased to `-v`) to strip nested `vendor/` directories.

## Q: How do I import settings from GPM, Godep, Gom, or GB?
## Q: How do I import settings from GPM, Godep, Gom, GB, or Vndr?

There are two parts to importing.

1. If a package you import has configuration for GPM, Godep, Gom, or GB Glide will recursively install the dependencies automatically.
2. If you would like to import configuration from GPM, Godep, Gom, or GB to Glide see the `glide import` command. For example, you can run `glide import godep` for Glide to detect the projects Godep configuration and generate a `glide.yaml` file for you.
1. If a package you import has configuration for GPM, Godep, Gom, GB, or Vndr Glide will recursively install the dependencies automatically.
2. If you would like to import configuration from GPM, Godep, Gom, GB, or Vndr to Glide see the `glide import` command. For example, you can run `glide import godep` for Glide to detect the projects Godep configuration and generate a `glide.yaml` file for you.

Each of these will merge your existing `glide.yaml` file with the
dependencies it finds for those managers, and then emit the file as
Expand Down
4 changes: 2 additions & 2 deletions docs/getting-started.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ This is a quick start guide to using Glide once you have it installed.

## Initially Detecting Project Dependencies

Glide can detect the dependencies in use on a project and create an initial `glide.yaml` file for you. This detection can import the configuration from Godep, GPM, Gom, and GB. To do this change into the top level directory for the project and run:
Glide can detect the dependencies in use on a project and create an initial `glide.yaml` file for you. This detection can import the configuration from Godep, GPM, Gom, GB, and Vndr. To do this change into the top level directory for the project and run:

$ glide init

Expand All @@ -18,7 +18,7 @@ To fetch the dependencies and set them to any versions specified in the `glide.y

$ glide up

The `up` is short for `update`. This will fetch any dependencies specified in the `glide.yaml` file, walk the dependency tree to make sure any dependencies of the dependencies are fetched, and set them to the proper version. While walking the tree it will make sure versions are set and configuration from Godep, GPM, Gom, and GB is imported.
The `up` is short for `update`. This will fetch any dependencies specified in the `glide.yaml` file, walk the dependency tree to make sure any dependencies of the dependencies are fetched, and set them to the proper version. While walking the tree it will make sure versions are set and configuration from Godep, GPM, Gom, GB, and Vndr is imported.

The fetched dependencies are all placed in the `vendor/` folder at the root of the project. The `go` toolchain will use the dependencies here prior to looking in the `GOPATH` or `GOROOT` if you are using Go 1.6+ or Go 1.5 with the Go 1.5 Vendor Experiment enabled.

Expand Down
2 changes: 1 addition & 1 deletion docs/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ Glide provides the following functionality:
* Supports Git, Bzr, HG, and SVN. These are the same version control systems supported by `go get`.
* Utilizes `vendor/` directories, known as the Vendor Experiment, so that different projects can have differing versions of the same dependencies.
* Allows for aliasing packages which is useful for working with forks.
* Import configuration from Godep, GPM, Gom, and GB.
* Import configuration from Godep, GPM, Gom, GB, and Vndr.

## Installing Glide

Expand Down
6 changes: 3 additions & 3 deletions docs/resolving-imports.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ From this it will attempt to figure out the external packages. External packages

Again, this is the same way `go` tries to determine an external location when you use `go get`.

If the project has dependency configuration stored in a Godep, GPM, Gom, or GB file that information will be used to populate the version within the `glide.yaml` file.
If the project has dependency configuration stored in a Godep, GPM, Gom, GB, or Vndr file that information will be used to populate the version within the `glide.yaml` file.

## At Update

Expand All @@ -28,10 +28,10 @@ That means that only imports referenced in the source are fetched.

When a version control repo is fetched it does fetch the complete repo. But, it doesn't scan all the packages in the repo for dependencies. Instead, only the packages referenced in the tree are scanned with the imports being followed.

Along the way configuration stored in Glide, Godep, GPM, Gom, and GB files are used to work out the version to set and fetched repos to. The first version found while walking the import tree wins.
Along the way configuration stored in Glide, Godep, GPM, Gom, GB, and Vndr files are used to work out the version to set and fetched repos to. The first version found while walking the import tree wins.

### All Possible Dependencies

Using the `--all-dependencies` flag on `glide update` will change the behavior of the scan. Instead of walking the import tree it walks the filesystem and fetches all possible packages referenced everywhere. This downloads all packages in the tree. Even those not referenced in an applications source or in support of the applications imports.

As in other cases, Glide, Godep, GPM, Gom, and GB files are used to set the version of the fetched repo.
As in other cases, Glide, Godep, GPM, Gom, GB, and Vndr files are used to set the version of the fetched repo.
14 changes: 14 additions & 0 deletions glide.go
Original file line number Diff line number Diff line change
Expand Up @@ -374,6 +374,20 @@ func commands() []cli.Command {
return nil
},
},
{
Name: "vndr",
Usage: "Import VNDR's vendor.conf file and display the would-be yaml file",
Flags: []cli.Flag{
cli.StringFlag{
Name: "file, f",
Usage: "Save all of the discovered dependencies to a Glide YAML file.",
},
},
Action: func(c *cli.Context) error {
action.ImportVNDR(c.String("file"))
return nil
},
},
},
},
{
Expand Down
10 changes: 10 additions & 0 deletions importer/importer.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import (
"github.com/Masterminds/glide/godep"
"github.com/Masterminds/glide/gom"
"github.com/Masterminds/glide/gpm"
"github.com/Masterminds/glide/vndr"
)

var i = &DefaultImporter{}
Expand Down Expand Up @@ -87,6 +88,15 @@ func (d *DefaultImporter) Import(path string) (bool, []*cfg.Dependency, error) {
return true, deps, nil
}

// Try importing from vndr
if vndr.Has(path) {
deps, err := vndr.Parse(path)
if err != nil {
return false, []*cfg.Dependency{}, err
}
return true, deps, nil
}

// When none are found.
return false, []*cfg.Dependency{}, nil
}
81 changes: 81 additions & 0 deletions vndr/vndr.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
// Package vndr provides basic importing of Vendor.conf dependencies.
package vndr

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

"github.com/Masterminds/glide/cfg"
"github.com/Masterminds/glide/msg"
gpath "github.com/Masterminds/glide/path"
"github.com/Masterminds/glide/util"
)

// Has is a command to detect if a package contains a vendor.conf file.
func Has(dir string) bool {
path := filepath.Join(dir, "vendor.conf")
_, err := os.Stat(path)
return err == nil
}

// Parse parses a VNDR vendor.conf file.
//
// It returns the contents as a dependency array.
func Parse(dir string) ([]*cfg.Dependency, error) {
path := filepath.Join(dir, "vendor.conf")
msg.Info(dir)
if _, err := os.Stat(path); err != nil {
return []*cfg.Dependency{}, nil
}
msg.Info("Found vendor.conf file in %s", gpath.StripBasepath(dir))
msg.Info("--> Parsing vndr metadata...")

buf := []*cfg.Dependency{}

// Get a handle to the file.
file, err := os.Open(path)
if err != nil {
return buf, err
}
defer file.Close()

s := bufio.NewScanner(file)
for s.Scan() {
// Read and build the dependencies from the file
ln := strings.TrimSpace(s.Text())
if strings.HasPrefix(ln, "#") || ln == "" {
continue
}
cidx := strings.Index(ln, "#")
if cidx > 0 {
ln = ln[:cidx]
}
ln = strings.TrimSpace(ln)
parts := strings.Fields(ln)
if len(parts) != 2 && len(parts) != 3 {
return []*cfg.Dependency{}, fmt.Errorf("invalid config format: %s", ln)
}

dep := &cfg.Dependency{
Reference: parts[1],
}
if len(parts) == 3 {
dep.Repository = parts[2]
}
pkg, sub := util.NormalizeName(parts[0])
dep.Name = pkg
if len(sub) > 0 {
dep.Subpackages = []string{sub}
}

buf = append(buf, dep)
}
if err := s.Err(); err != nil {
return []*cfg.Dependency{}, err
}

return buf, nil
}