将顶级模块及其子模块之一作为单独的版本分别导入时,如何解决冲突的go模块依赖关系?

I have two dependencies in my project.

go.mod:

module github.com/test-org/test-repo

go 1.12

require (
    github.com/foo/bar v1.0.0
    github.com/raz/mataz v1.0.0
)

After running go mod download, those two dependencies result in two different versions of a github.com/shared/dependency to be downloaded. The interesting thing is that the github.com/shared/dependency contains sub-modules, e.g.:

dependency
  -- go.mod
  -- api
      -- go.mod

Inspecting the downloaded modules shows two versions are downloaded to my local machine:

ls ${GOPATH}/pkg/mod/github.com/shared:

[dir] dependency    [dir] dependency@v1.1.0

ls ${GOPATH}/pkg/mod/github.com/shared/dependency:

[dir] api@v1.2.0

Looking at the contents of these directories:

${GOPATH}/pkg/mod/github.com/shared/dependency@v1.1.0:

The file contents of the whole repo in v1.1.0, including the api folder with its own go.mod file.

${GOPATH}/pkg/mod/github.com/shared/dependency/api@v1.2.0:

The file contents of the api folder of the repo in v1.2.0, including the go.mod file.


Finally, I have a .go file in my test-repo with the following setup:

package test-package

import (
    "github.com/foo/bar"
)

func MyFunc() {...bar.NewBar()...}

When I try to run a test of MyFunc (that exists elsewhere), I get an unknown import path...ambiguous import... error message. e.g.

go test github.com/test-org/test-repo/test-package -test.run=TestMyFunc -v:

unknown import path "github.com/shared/dependency/api": ambiguous import: found github.com/shared/dependency/api in multiple modules:
    github.com/shared/dependency v1.1.0 (${GOPATH}/pkg/mod/github.com/shared/dependency@v1.1.0/api)
    github.com/shared/dependency v1.2.0 (${GOPATH}/pkg/mod/github.com/shared/dependency/api@v1.2.0)

The error points to the import line of the .go file importing github.com/shared/dependency/api in the github.com/foo/bar repo. It doesn't know which api to choose in my local ${GOPATH}/pkg/mod folder, given the two versions available:

  1. ${GOPATH}/pkg/mod/github.com/shared/dependency@v1.1.0/api
  2. ${GOPATH}/pkg/mod/github.com/shared/dependency/api@v1.2.0

Is there any way that I can make that go test call work (solve the dependency conflicts)? Neither of my two dependencies explicitly call out downloading the full shared/dependency@v1.1.0, but for some reason it gets pulled in. If that weren't there, it would seemingly fix the issue.

The issue turned out to be that one of the dependencies was referencing a version of the github.com/shared/dependency/api that was pre-go-modules.

This caused the go tooling to have a module reference to the github.com/shared/dependency/api sub-module, but also a black box import of the entire github.com/shared/dependency repo for the pre-go-modules version. In this example, it would mean that v1.2.0 had go modules (had a go.mod file), and v1.1.0 did not.

Adding the following line to my go.mod file was able to fix the issue, and this solution worked with multiple dependencies I had with such conflicts:

replace (
    github.com/shared/dependency => github.com/shared/dependency v1.2.0
)

Note that this solution only works because we are forcing references to the shared dependency to use go-module-enabled versions (v1.2.0+).