pkg / errors

Simple error handling primitives
https://godoc.org/github.com/pkg/errors
BSD 2-Clause "Simplified" License
8.18k stars 691 forks source link

Tests break when run as a modules dependency #211

Closed jamie-digital closed 5 years ago

jamie-digital commented 5 years ago

Go version

go version go1.13 darwin/amd64

Module version

v0.8.1

What went wrong?

The following tests fail when the module is tested as a dependency:

Steps to reproduce

$ mkdir /tmp/errors
$ cd /tmp/errors
$ go mod init example.com/foo
go: creating new go.mod: module example.com/foo
$ go get github.com/pkg/errors@v0.8.1
$ go test github.com/pkg/errors

Output:

--- FAIL: TestFormatNew (0.00s)
    format_test.go:379: test 3: line 3: fmt.Sprintf("%+v", err):
         got: "error\ngithub.com/pkg/errors.TestFormatNew\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:26\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357"
        want: "error\ngithub.com/pkg/errors.TestFormatNew\n\t.+/github.com/pkg/errors/format_test.go:26"
--- FAIL: TestFormatErrorf (0.00s)
    format_test.go:379: test 3: line 3: fmt.Sprintf("%+v", err):
         got: "error\ngithub.com/pkg/errors.TestFormatErrorf\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:56\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357"
        want: "error\ngithub.com/pkg/errors.TestFormatErrorf\n\t.+/github.com/pkg/errors/format_test.go:56"
--- FAIL: TestFormatWrap (0.00s)
    format_test.go:379: test 3: line 3: fmt.Sprintf("%+v", err):
         got: "error\ngithub.com/pkg/errors.TestFormatWrap\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:82\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357\nerror2\ngithub.com/pkg/errors.TestFormatWrap\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:82\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357"
        want: "error\ngithub.com/pkg/errors.TestFormatWrap\n\t.+/github.com/pkg/errors/format_test.go:82"
    format_test.go:379: test 6: line 4: fmt.Sprintf("%+v", err):
         got: "EOF\nerror\ngithub.com/pkg/errors.TestFormatWrap\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:96\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357"
        want: "EOF\nerror\ngithub.com/pkg/errors.TestFormatWrap\n\t.+/github.com/pkg/errors/format_test.go:96"
    format_test.go:379: test 7: line 4: fmt.Sprintf("%+v", err):
         got: "EOF\nerror1\ngithub.com/pkg/errors.TestFormatWrap\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:103\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357\nerror2\ngithub.com/pkg/errors.TestFormatWrap\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:103\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357"
        want: "EOF\nerror1\ngithub.com/pkg/errors.TestFormatWrap\n\t.+/github.com/pkg/errors/format_test.go:103\n"
--- FAIL: TestFormatWrapf (0.00s)
    format_test.go:379: test 3: line 4: fmt.Sprintf("%+v", err):
         got: "EOF\nerror2\ngithub.com/pkg/errors.TestFormatWrapf\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:134\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357"
        want: "EOF\nerror2\ngithub.com/pkg/errors.TestFormatWrapf\n\t.+/github.com/pkg/errors/format_test.go:134"
    format_test.go:379: test 6: line 3: fmt.Sprintf("%+v", err):
         got: "error\ngithub.com/pkg/errors.TestFormatWrapf\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:149\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357\nerror2\ngithub.com/pkg/errors.TestFormatWrapf\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:149\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357"
        want: "error\ngithub.com/pkg/errors.TestFormatWrapf\n\t.+/github.com/pkg/errors/format_test.go:149"
--- FAIL: TestFormatWithStack (0.00s)
    format_test.go:477: test 3: block 2: fmt.Sprintf("%+v", err):
        got:
        "github.com/pkg/errors.TestFormatWithStack\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:175\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357"
        want:
        "github.com/pkg/errors.TestFormatWithStack\n\t.+/github.com/pkg/errors/format_test.go:175"
        all-got:
           EOF
           github.com/pkg/errors.TestFormatWithStack
            /Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:175
        testing.tRunner
            /Users//go/src/testing/testing.go:909
        runtime.goexit
            /Users//go/src/runtime/asm_amd64.s:1357
        all-want:
           EOF
           github.com/pkg/errors.TestFormatWithStack
            .+/github.com/pkg/errors/format_test.go:175
--- FAIL: TestFormatWithMessage (0.00s)
    format_test.go:477: test 3: block 2: fmt.Sprintf("%+v", err):
        got:
        "github.com/pkg/errors.TestFormatWithMessage\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:244\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357"
        want:
        "github.com/pkg/errors.TestFormatWithMessage\n\t.+/github.com/pkg/errors/format_test.go:244"
        all-got:
           error
           github.com/pkg/errors.TestFormatWithMessage
            /Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:244
        testing.tRunner
            /Users//go/src/testing/testing.go:909
        runtime.goexit
            /Users//go/src/runtime/asm_amd64.s:1357
           error2
        all-want:
           error
           github.com/pkg/errors.TestFormatWithMessage
            .+/github.com/pkg/errors/format_test.go:244
           error2
--- FAIL: TestFormatGeneric (0.00s)
    format_test.go:477: test 1: block 2: fmt.Sprintf("%+v", err):
        got:
        "github.com/pkg/errors.TestFormatGeneric\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:315\ntesting.tRunner\n\t/Users//go/src/testing/testing.go:909\nruntime.goexit\n\t/Users//go/src/runtime/asm_amd64.s:1357"
        want:
        "github.com/pkg/errors.TestFormatGeneric\n\t.+/github.com/pkg/errors/format_test.go:315"
        all-got:
           new-error
           github.com/pkg/errors.TestFormatGeneric
            /Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/format_test.go:315
        testing.tRunner
            /Users//go/src/testing/testing.go:909
        runtime.goexit
            /Users//go/src/runtime/asm_amd64.s:1357
        all-want:
           new-error
           github.com/pkg/errors.TestFormatGeneric
            .+/github.com/pkg/errors/format_test.go:315
--- FAIL: TestFrameLine (0.00s)
    stack_test.go:39: Frame(17852097): want: 28, got: 22
--- FAIL: TestFrameFormat (0.00s)
    format_test.go:379: test 2: line 2: fmt.Sprintf("%+s", err):
         got: "github.com/pkg/errors.init\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go"
        want: "github.com/pkg/errors.init\n\t.+/github.com/pkg/errors/stack_test.go"
    format_test.go:379: test 12: line 2: fmt.Sprintf("%+v", err):
         got: "github.com/pkg/errors.init\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:9"
        want: "github.com/pkg/errors.init\n\t.+/github.com/pkg/errors/stack_test.go:9"
--- FAIL: TestStackTrace (0.00s)
    format_test.go:379: test 1: line 2: fmt.Sprintf("%+v", err):
         got: "github.com/pkg/errors.TestStackTrace\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:154"
        want: "github.com/pkg/errors.TestStackTrace\n\t.+/github.com/pkg/errors/stack_test.go:154"
    format_test.go:379: test 2: line 2: fmt.Sprintf("%+v", err):
         got: "github.com/pkg/errors.TestStackTrace\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:159"
        want: "github.com/pkg/errors.TestStackTrace\n\t.+/github.com/pkg/errors/stack_test.go:159"
    format_test.go:379: test 3: line 2: fmt.Sprintf("%+v", err):
         got: "github.com/pkg/errors.TestStackTrace\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:164"
        want: "github.com/pkg/errors.TestStackTrace\n\t.+/github.com/pkg/errors/stack_test.go:164"
    format_test.go:379: test 4: line 2: fmt.Sprintf("%+v", err):
         got: "github.com/pkg/errors.TestStackTrace.func1\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:169"
        want: "github.com/pkg/errors.(func·009|TestStackTrace.func1)\n\t.+/github.com/pkg/errors/stack_test.go:169"
    format_test.go:379: test 4: line 2: fmt.Sprintf("%+v", err):
         got: "github.com/pkg/errors.TestStackTrace\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:169"
        want: "github.com/pkg/errors.TestStackTrace\n\t.+/github.com/pkg/errors/stack_test.go:169"
    format_test.go:379: test 5: line 2: fmt.Sprintf("%+v", err):
         got: "github.com/pkg/errors.TestStackTrace.func2.1\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:178"
        want: "github.com/pkg/errors.(func·010|TestStackTrace.func2.1)\n\t.+/github.com/pkg/errors/stack_test.go:178"
    format_test.go:379: test 5: line 2: fmt.Sprintf("%+v", err):
         got: "github.com/pkg/errors.TestStackTrace.func2\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:179"
        want: "github.com/pkg/errors.(func·011|TestStackTrace.func2)\n\t.+/github.com/pkg/errors/stack_test.go:179"
    format_test.go:379: test 5: line 2: fmt.Sprintf("%+v", err):
         got: "github.com/pkg/errors.TestStackTrace\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:180"
        want: "github.com/pkg/errors.TestStackTrace\n\t.+/github.com/pkg/errors/stack_test.go:180"
--- FAIL: TestStackTraceFormat (0.00s)
    format_test.go:379: test 11: line 3: fmt.Sprintf("%+v", err):
         got: "\ngithub.com/pkg/errors.stackTrace\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:207\ngithub.com/pkg/errors.TestStackTraceFormat\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:258"
        want: "\ngithub.com/pkg/errors.stackTrace\n\t.+/github.com/pkg/errors/stack_test.go:207\ngithub.com/pkg/errors.TestStackTraceFormat\n\t.+/github.com/pkg/errors/stack_test.go:258"
    format_test.go:379: test 11: line 5: fmt.Sprintf("%+v", err):
         got: "\ngithub.com/pkg/errors.stackTrace\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:207\ngithub.com/pkg/errors.TestStackTraceFormat\n\t/Users//dev/go/pkg/mod/github.com/pkg/errors@v0.8.1/stack_test.go:258"
        want: "\ngithub.com/pkg/errors.stackTrace\n\t.+/github.com/pkg/errors/stack_test.go:207\ngithub.com/pkg/errors.TestStackTraceFormat\n\t.+/github.com/pkg/errors/stack_test.go:258"
FAIL
FAIL    github.com/pkg/errors   0.007s
FAIL

Cause

When Go modules' tests are run as a dependency (from outside their codebase), they execute in the module cache, which includes the module version in the filepath. This breaks several tests in this package, which expects the package filepath not to include a version.

davecheney commented 5 years ago

Thank you for raising this issue. Sadly it’s not feasible to fix this. If you want to run the tests of this project do so in the context of this repo.

ghost commented 4 years ago

I get the some error in GitHub actions CI. Have you found any solutions?

davecheney commented 4 years ago

@zmrenwu what did you do? What did you see when you did it?

ghost commented 4 years ago

Everything works fine on local enviroment, but can not run go test in GitHub actions CI.

My GitHub action config:

name: Build and test Go
on: [ push, pull_request ]
jobs:
  test:
    strategy:
      matrix:
        go-version: [ 1.15.x ]
        os: [ ubuntu-latest ]
        mongodb-version: [4.2]
    runs-on: ${{ matrix.os }}
    steps:
      - name: setup env
        shell: bash
        run: |
          echo "::set-env name=GOPATH::${{ github.workspace }}/go"
          echo "::add-path::${{ github.workspace }}/go/bin"

      - name: Install Go
        uses: actions/setup-go@v2
        with:
          go-version: ${{ matrix.go-version }}

      - name: Start MongoDB
        uses: supercharge/mongodb-github-action@1.3.0
        with:
          mongodb-version: ${{ matrix.mongodb-version }}

      - name: Checkout code
        uses: actions/checkout@v2

      - name: Build
        env:
          GOPROXY: "https://proxy.golang.org"
        run: go build .

      - name: Test
        run: go test ./...

Some GitHub action logs:

ok      github.com/klauspost/compress/zstd  30.515s
ok      github.com/klauspost/compress/zstd/internal/xxhash  0.016s
--- FAIL: TestFormatNew (0.00s)
    format_test.go:38: test 3: line 3: fmt.Sprintf("%+v", err):
         got: "error\ngithub.com/pkg/errors.TestFormatNew\n\t/home/runner/work/coinsmart-api/coinsmart-api/go/pkg/mod/github.com/pkg/errors@v0.9.1/format_test.go:26\ntesting.tRunner\n\t/opt/hostedtoolcache/go/1.15.0/x64/src/testing/testing.go:1108\nruntime.goexit\n\t/opt/hostedtoolcache/go/1.15.0/x64/src/runtime/asm_amd64.s:1374"
        want: "error\ngithub.com/pkg/errors.TestFormatNew\n\t.+/github.com/pkg/errors/format_test.go:26"
--- FAIL: TestFormatErrorf (0.00s)
    format_test.go:64: test 3: line 3: fmt.Sprintf("%+v", err):
         got: "error\ngithub.com/pkg/errors.TestFormatErrorf\n\t/home/runner/work/coinsmart-api/coinsmart-api/go/pkg/mod/github.com/pkg/errors@v0.9.1/format_test.go:56\ntesting.tRunner\n\t/opt/hostedtoolcache/go/1.15.0/x64/src/testing/testing.go:1108\nruntime.goexit\n\t/opt/hostedtoolcache/go/1.15.0/x64/src/runtime/asm_amd64.s:1374"
        want: "error\ngithub.com/pkg/errors.TestFormatErrorf\n\t.+/github.com/pkg/errors/format_test.go:56"

Thanks for helps!

davecheney commented 4 years ago

Thanks. I'm not sure what your test runner is doing but the resolution of this issue was -- do not test modules, only test your code. Have you vendored or copied the code for pkg/errors into your codebase?

ghost commented 4 years ago

No, I don't directly import any code of pkg/errors. go test command run all tests include direct and indirect modules. But I don't know how to just test my code. I am a go beginner. In python, only test project code is a default behavior. But I don't know how to active this behavior in golang.

davecheney commented 4 years ago

I'm sorry I'm not sure how to help. go test should only test the code in your module, not the tests in another module as that could lead to arbitrary code execution.

@pkg/errors-maintainers do you have any suggestions.

puellanivis commented 4 years ago

I was able to recreate the error situation. The issue causing the trouble is here: ::set-env name=GOPATH::${{ github.workspace }}/go This is setting your $GOPATH equal to a subdirectory of the working directory. While go test ./... knows to skip vendored packages, it does not know to skip the whole $GOPATH if it is rooted under the current working directory.

Given:

-- main.go --
package main

import (
    "fmt"

    "github.com/pkg/errors"
)

func main() {
    fmt.Printf("%+v\n", errors.New("oh noes!"))
}
-- go.mod --
module github.com/puellanivis/gopath-in-working-dir

go 1.14

require github.com/pkg/errors v0.9.1

Followed by:

gopath-in-working-dir$ export GOPATH="${PWD}/go"

gopath-in-working-dir$ go build # to setup the GOPATH and download the module
go: downloading github.com/pkg/errors v0.9.1

gopath-in-working-dir$ go test ./... # result is a dump of the same kind of test failures as above

The answer is: do not put your GOPATH into a sub-directory of your project. Given echo "::set-env name=GOPATH::${{ github.workspace }}/go" then actually checkout the source code into ${{ github.workspace }}/src or some other directory parallel to your GOPATH.