-
Notifications
You must be signed in to change notification settings - Fork 541
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
Vendor the dependencies of the sub-packages only, not of the parent package #166
Comments
Should I rather just use the following, - package: github.com/coreos/etcd/client
version: v2.2.2 |
Glide /could/ use the set of subpackages to only recursively vendor dependencies of the mentioned subpackages, instead of recursively vendoring the imports for all subfolders. See #165 for reasons why. |
Working with Go packages and versions is a bit complicated because there is technically no higher level "project" grouping. Version control systems group packages at a higher level and versions are at this level. So, you can't (and shouldn't) have two different versions of packages within When you use We could be better with sub-package handling for cleanup and walking the tree. Our first priority is to cleanup some internals in Glide so it's easier to maintain and contribute to. Better handling will come. Part of the reason we have issues like this is the use of monorepos where clients and everything is in one repo. It may be easier for the developers (or they think it is) of the project. But, for consumers of things like a client it's harder. I had not run into such a prevalence of clients being part of the repo/project it communicates with until working in Go. |
@mattfarina I just wanted to confirm what the expected behaviour of subpackages is. I think we agree that using subpackages should cause only the dependencies of the subpackages should be vendored. This is not how glide works currently, but is something that is being aimed at in a later release. Can we convert this issue to an enhancement request then? |
When you I agree with @kshlm that this issue could be labeled as enhancement request. Or maybe even bugfix. |
If we can accurately scan the dependency tree in use and only pull down those dependencies that would be a useful optimization. I welcome a pull request to add this in (with an opt-in feature flag initially). I don't see us adding this right away, unless someone comes in with a pull request, because
I like this idea and have marked it as an enhancement. |
The answer to the original question is this. We have tracked the list of subpackages for the following reasons:
|
I changed the title of the issue to make it more relevant to the enhancement request. |
My projects use |
I agree with @aboukirev in regards to this issue. For example, we use |
There are two things here. First, there are all the packages in something like Second, we could be smarter about pulling down dependencies of this project to pull down fewer. Maybe out of the box Glide only pulls down the code path in use and there's a switch (e.g., |
Right, I wasn't very clear. I understand there is no way to avoid pulling the repo and checking out the appropriate version. That is of course one of the major reasons for using glide to lock specific versions. I was more referring to your second point. Right now, glide also pulls the dependencies of all of the packages in the repo instead of just the ones needed by the active code path. For example, consider the gokit repository. You may only want to use the circuitbreaker and ratelimit packages. However, glide also pulls the dependencies for all of the other unused subpackages too which include dependencies that are not needed. For example, the metrics/prometheus subpackage has a dependency on the prometheus client which is not needed at all for any of the other packages, but glide pulls it too. Along the same lines, glide even pulls the dependencies only used by the tests, which, in my opinion, really should require a setting to enable (much like how |
@davecgh Glide doesn't pull the dependencies used by the tests following the Go rules for that (e.g., |
@mattfarina: Alright, so after looking more closely you're correct that it's the result of a I made a test repository to show the difference between $ export GOPATH=/d/tmpgo && go get -u -v github.com/davecgh/glidetest
github.com/davecgh/glidetest (download)
github.com/syndtr/goleveldb (download)
github.com/golang/snappy (download)
github.com/syndtr/goleveldb/leveldb/util
github.com/syndtr/goleveldb/leveldb/comparer
github.com/golang/snappy
github.com/syndtr/goleveldb/leveldb/cache
github.com/syndtr/goleveldb/leveldb/storage
github.com/syndtr/goleveldb/leveldb/filter
github.com/syndtr/goleveldb/leveldb/opt
github.com/syndtr/goleveldb/leveldb/errors
github.com/syndtr/goleveldb/leveldb/iterator
github.com/syndtr/goleveldb/leveldb/journal
github.com/syndtr/goleveldb/leveldb/memdb
github.com/syndtr/goleveldb/leveldb/table
github.com/syndtr/goleveldb/leveldb
github.com/davecgh/glidetest
$ tree -d $GOPATH/src
/d/tmpgo/src
└── github.com
├── davecgh
│ └── glidetest
├── golang
│ └── snappy
└── syndtr
└── goleveldb
├── leveldb
│ ├── cache
│ ├── comparer
│ ├── errors
│ ├── filter
│ ├── iterator
│ ├── journal
│ ├── memdb
│ ├── opt
│ ├── storage
│ ├── table
│ ├── testutil
│ └── util
└── manualtest
├── dbstress
└── filelock
23 directories Notice how Now, here is the same thing with $ cd $GOPATH/src/github.com/davecgh/glidetest && glide up
[INFO] Fetching updates for github.com/syndtr/goleveldb.
[INFO] Scanning github.com/syndtr/goleveldb for dependencies.
***[INFO] ==> Unknown github.com/onsi/ginkgo (github.com/onsi/ginkgo)
***[INFO] ==> Unknown github.com/onsi/ginkgo (github.com/onsi/ginkgo/config)
***[INFO] ==> Unknown github.com/onsi/gomega (github.com/onsi/gomega)
***[INFO] Fetching updates for github.com/onsi/ginkgo.
***[INFO] Fetching updates for github.com/onsi/gomega.
[INFO] Fetching updates for github.com/golang/snappy.
[INFO] Scanning github.com/golang/snappy for dependencies.
***[INFO] Scanning github.com/onsi/ginkgo for dependencies.
***[INFO] Scanning github.com/onsi/ginkgo for dependencies.
***[INFO] Scanning github.com/onsi/gomega for dependencies.
***[INFO] ==> Unknown github.com/golang/protobuf (github.com/golang/protobuf/proto)
***[INFO] ==> Unknown github.com/golang/protobuf (github.com/golang/protobuf/proto)
***[INFO] Fetching updates for github.com/golang/protobuf.
***[INFO] Scanning github.com/golang/protobuf for dependencies.
***[INFO] Scanning github.com/golang/protobuf for dependencies.
[INFO] Project relies on 5 dependencies.
[INFO] Writing glide.lock file
$ tree -d vendor
vendor
└── github.com
├── golang
│ ├── protobuf
│ │ ├── jsonpb
│ │ │ └── jsonpb_test_proto
│ │ ├── proto
│ │ │ ├── proto3_proto
│ │ │ └── testdata
│ │ └── protoc-gen-go
│ │ ├── descriptor
│ │ ├── generator
│ │ ├── internal
│ │ │ └── grpc
│ │ ├── plugin
│ │ └── testdata
│ │ ├── multi
│ │ └── my_test
│ └── snappy
├── onsi
│ ├── ginkgo
│ │ ├── config
│ │ ├── extensions
│ │ │ └── table
│ │ ├── ginkgo
│ │ │ ├── convert
│ │ │ ├── interrupthandler
│ │ │ ├── nodot
│ │ │ ├── testrunner
│ │ │ ├── testsuite
│ │ │ └── watch
│ │ ├── integration
│ │ │ └── _fixtures
│ │ │ ├── convert_fixtures
│ │ │ │ ├── nested
│ │ │ │ └── nested_without_gofiles
│ │ │ │ └── subpackage
│ │ │ ├── convert_goldmasters
│ │ │ ├── coverage_fixture
│ │ │ │ └── external_coverage_fixture
│ │ │ ├── does_not_compile
│ │ │ ├── eventually_failing
│ │ │ ├── exiting_synchronized_setup_tests
│ │ │ ├── fail_fixture
│ │ │ ├── failing_after_suite
│ │ │ ├── failing_before_suite
│ │ │ ├── failing_ginkgo_tests
│ │ │ ├── flags_tests
│ │ │ ├── focused_fixture
│ │ │ ├── hanging_suite
│ │ │ ├── more_ginkgo_tests
│ │ │ ├── no_tests
│ │ │ ├── passing_ginkgo_tests
│ │ │ ├── passing_suite_setup
│ │ │ ├── progress_fixture
│ │ │ ├── skip_fixture
│ │ │ ├── suite_command_tests
│ │ │ ├── synchronized_setup_tests
│ │ │ ├── tags_tests
│ │ │ ├── test_description
│ │ │ ├── watch_fixtures
│ │ │ │ ├── A
│ │ │ │ ├── B
│ │ │ │ ├── C
│ │ │ │ └── D
│ │ │ └── xunit_tests
│ │ ├── internal
│ │ │ ├── codelocation
│ │ │ ├── containernode
│ │ │ ├── failer
│ │ │ ├── leafnodes
│ │ │ ├── remote
│ │ │ ├── spec
│ │ │ ├── specrunner
│ │ │ ├── suite
│ │ │ ├── testingtproxy
│ │ │ └── writer
│ │ ├── reporters
│ │ │ └── stenographer
│ │ └── types
│ └── gomega
│ ├── format
│ ├── gbytes
│ ├── gexec
│ │ └── _fixture
│ │ └── firefly
│ ├── ghttp
│ │ └── protobuf
│ ├── internal
│ │ ├── assertion
│ │ ├── asyncassertion
│ │ ├── fakematcher
│ │ ├── oraclematcher
│ │ └── testingtsupport
│ ├── matchers
│ │ └── support
│ │ └── goraph
│ │ ├── bipartitegraph
│ │ ├── edge
│ │ ├── node
│ │ └── util
│ └── types
└── syndtr
└── goleveldb
├── leveldb
│ ├── cache
│ ├── comparer
│ ├── errors
│ ├── filter
│ ├── iterator
│ ├── journal
│ ├── memdb
│ ├── opt
│ ├── storage
│ ├── table
│ ├── testutil
│ └── util
└── manualtest
├── dbstress
└── filelock
119 directories So, the end result is glide is ending up with 119 directories in the tree of deps versus 23. |
Yup. Glide can get smarter with the packages imported. This this a great example of the difference. Thanks. |
When subpackages are specified, fetch only their dependencies instead of those from the whole project
Just a detail, but how would you name this flag? And another question concerning this case: #166 (comment) Should the new feature also kick-in in that case, or only if subpackages are explicitely listed? |
I added another example of a case where glide includes dependencies that are not needed by the project: I looked at the source of the golang.org/x/net package in search of where it uses the golang.org/x/crypto one (using To avoid such false positives, I wonder if it would be possible to (optionally) rely on
I would be happy to help with testing or implementation if needed. I pulled a patch by @hectorj from https://github.com/hectorj/glide/tree/feature-166 and it seems to work fine for this case - it created glide.lock with only one dependency - golang.org/x/net, as expected:
practically identical to my "wish" version https://github.com/dmitris/deptest4glide/blob/master/glide.lock.want |
On Monday, barring any major issues being found, I'm going to merge in the In the new setup the |
👍 - rooting for the success of that big refactoring piece you are doing. The world needs glide as a great dependency management tool - and it seems many people are eager to contribute in different ways! 😄 |
It took an extra day because I found a bug that should have been fixed before people started complaining on master. Blockers to this are now removed. |
I believe it is now fixed (thanks @hectorj for the patch!) as mentioned in https://github.com/Masterminds/glide/releases/tag/0.9.0-rc1 Does anyone still see this being a problem? I checked it with https://github.com/dmitris/deptest4glide (README has a description of the original problem) and it looks fine there; same with several of our projects I checked. I believe we can close the issue now. |
The merged fix is actually from @technosophos : #240 But yeah, this is fixed. |
I think I jumped up too soon... It may be partially fixed but still not working correctly. I updated my minimal case to demonstrate: github.com/dmitris/deptest4glide. This package imports github.com/dmitris/deptesthuge/deptestsmall which is a dependency-free subpackage of github.com/dmitris/deptesthuge where the root package has massive dependencies (coreos, docker). Of course both Here's the
(the dependency set is calculated correctly) The resulting glide.lock file is: https://gist.github.com/dmitris/ff6e10ffa0d2f678b12e I'm not sure which syntax in glide.yaml should be used when you just want to import a subpackage:
or
(@kshlm asked above as well) - I tried both but still, glide pulls unneeded packages with both configurations. /cc @technosophos |
I think we should close this unless anyone else sees any further problems. |
@dmitris way to catch this. A fix went out in 0.9.1. |
The dependent packages can have subpackages, but what is their use? They don't seem to be used any where.
For example, my project uses
github.com/coreos/etcd/client
. I have the following entry as a dependency,I had assumed that because subpackages had been provided, glide would just resolve the dependencies of the subpackages. But instead, glide resolves dependencies of etcd and pulls in way too many dependent packages, which I have no use of in my project.
I want to know if this is the expected behaviour?
The text was updated successfully, but these errors were encountered: