Problem with exnternal dependencies and new version of codeclimate-govet
tmaczukin opened this issue · 0 comments
With the recent update of codeclimate-govet
to a version that is compiled and executed in a Go 1.13 environment, the analyzer started to fail if any external dependency is used.
To reproduce the problem let's create a simple project:
mkdir /tmp/test-project
cd /tmp/test-project
go mod init test-project
cat > main.go <<EOF
package main
import (
"fmt"
"github.com/sirupsen/logrus"
)
func main() {
fmt.Println("Test program")
logrus.Info("Log line")
}
EOF
go build .
go mod tidy
./test-project
At this moment everything should work, go build
should download the dependency and compile the binary and binary execution should be finished successfully.
Now, let's execute codeclimate-govet
test using the official Docker image:
docker run --rm -t -i -v $(pwd):/code codeclimate/codeclimate-govet
{"type":"issue","check_name":"GoVet/BugRisk","description":"9: cannot find package \"github.com/sirupsen/logrus\" in any of:","remediation_points":50000,"location":{"path":"main.go","lines":{"begin":6,"end":6}},"categories":["Bug Risk"]}Unexpected format for the following output: /usr/local/go/src/github.com/sirupsen/logrus (from $GOROOT)
and it failed. It failed, because go vet
call fails with:
docker run --rm -t -i -v $(pwd):/code codeclimate/codeclimate-govet go vet /code/main.go
/code/main.go:6:9: cannot find package "github.com/sirupsen/logrus" in any of:
/usr/local/go/src/github.com/sirupsen/logrus (from $GOROOT)
/go/src/github.com/sirupsen/logrus (from $GOPATH)
Unfortunately, behavior of go vet
changed between Go 1.13 and Go 1.9 which was the source of previously working version of the image:
docker run --rm -t -i -v $(pwd):/code codeclimate/codeclimate-govet:b60
The behavior can be partially restored, when:
go vet
command (so also thecodeclimate-govet
) is executed from within the/code
directory where the project is placed, andCGO_ENABLED=0
is set (otherwiseexec: "gcc": executable file not found in $PATH
error is thrown)
docker run --rm -t -i -v $(pwd):/code -e CGO_ENABLED=0 codeclimate/codeclimate-govet sh -c "cd /code && go vet main.go"
go: downloading github.com/sirupsen/logrus v1.4.2
go: extracting github.com/sirupsen/logrus v1.4.2
go: downloading github.com/stretchr/testify v1.2.2
go: downloading golang.org/x/sys v0.0.0-20190422165155-953cdadca894
go: extracting github.com/stretchr/testify v1.2.2
go: downloading github.com/davecgh/go-spew v1.1.1
go: downloading github.com/pmezard/go-difflib v1.0.0
go: extracting github.com/pmezard/go-difflib v1.0.0
go: extracting github.com/davecgh/go-spew v1.1.1
go: extracting golang.org/x/sys v0.0.0-20190422165155-953cdadca894
go: finding github.com/sirupsen/logrus v1.4.2
go: finding golang.org/x/sys v0.0.0-20190422165155-953cdadca894
This however, as can be seen in the example output above, causes go vet
to download all dependencies, which next affects current expectations of codeclimate-govet
binary:
docker run --rm -t -i -v $(pwd):/code -e CGO_ENABLED=0 codeclimate/codeclimate-govet sh -c "cd /code && /usr/src/app/codeclimate-govet"
Unexpected format for the following output: go: downloading github.com/sirupsen/logrus v1.4.2
Having all of the above in mind I've prepared a patch and build a custom version of codeclimate-govet
image that works properly, being still based on Go 1.13:
patch
diff --git a/Dockerfile b/Dockerfile
index e5d055c..4273f03 100644
--- a/Dockerfile
+++ b/Dockerfile
@@ -26,5 +26,8 @@ COPY --from=build /usr/src/app/codeclimate-govet ./
USER app
VOLUME /code
+WORKDIR /code
+
+ENV CGO_ENABLED=0
CMD ["/usr/src/app/codeclimate-govet"]
diff --git a/codeclimate-govet.go b/codeclimate-govet.go
index f4f9e6b..63dc5e1 100644
--- a/codeclimate-govet.go
+++ b/codeclimate-govet.go
@@ -24,6 +24,13 @@ func main() {
os.Exit(1)
}
+ downloadCmd := exec.Command("go", "mod", "download")
+ err = downloadCmd.Run()
+ if err != nil {
+ fmt.Fprintf(os.Stderr, "Error downloading dependencies: %v\n", err)
+ os.Exit(1)
+ }
+
for _, path := range analysisFiles {
cmd := exec.Command("go", "vet", path)
Executing codeclimate-vet
test with this image works as expected:
docker run --rm -t -i -v $(pwd):/code codeclimate/codeclimate-govet:custom
The question now is: what can we do with this? Current behavior of codeclimate-govet
is wrong and should be fixed. If the project contains any external dependency, the analyzer will start failing.
My patch proposed above does the job, but it looks more like a nasty hack than a proper solution.