Reputation: 2654
I want to create a package in Go with tests and examples for the package as subdirectories to keep the workspace cleaner. Is this possible and if so how?
All the documentation always puts the testing code in the same place as the other code, is this better in some way or just convention?
Upvotes: 254
Views: 171397
Reputation: 23789
Put your tests alongside your code in the same directory in a file called file_test.go
where "file" is the name of the source code file you're testing. This is convention and I've found it to be best in my own experience.
If the go test
tool isn't quite automated enough for you, you might look into GoConvey, which has a web UI that will automatically update and run traditional Go tests as well as GoConvey tests (which are based on behavior, and are more self-documenting than traditional Go tests).
Upvotes: 22
Reputation: 1329452
Note that you can run go test
"recursively": you need to list all the packages you want to test.
If you are in the root folder of your Go project, type:
go test ./...
The './...
' notation is described in the section "Description of package lists" of the "command go
":
An import path is a pattern if it includes one or more "
...
" wildcards, each of which can match any string, including the empty string and strings containing slashes.Such a pattern expands to all package directories found in the
GOPATH
trees with names matching the patterns.As a special case,
x/...
matchesx
as well asx
's subdirectories.
For example,net/...
expands tonet
and packages in its subdirectories.
If you keep your _test.go
files in a subfolder, the 'go test ./...
' command will be able to pick them up.
But:
That being said, I would still prefer to keep the _test.go
file right beside the main source file: it is easier to find.
2022: For code coverage:
go test -coverpkg=./... ./...
See "How to plot Go test coverage over time" from Frédéric G. MARAND and fgmarand/gocoverstats
to produce aggregate coverage statistics for CI integration of Go projects.
Also, go-cover-treemap.io
is fun.
March 2023: As documented in "Code coverage for Go integration tests":
With the 1.20 release, Go’s coverage tooling is no longer limited to package tests, but supports collecting profiles from larger integration tests.
Example:
$ go build -cover -o myprogram.exe myprogram.go
$ mkdir somedata
$ GOCOVERDIR=somedata ./myprogram.exe
I say "Hello, world." and "see ya"
$ ls somedata
covcounters.c6de772f99010ef5925877a7b05db4cc.2424989.1670252383678349347
covmeta.c6de772f99010ef5925877a7b05db4cc
See Go 1.20 Cover.
As noted by kbolino in the comments:
You can put your tests in a separate package without putting them in a separate directory.
Test files for package foo can be in packagefoo_test
and still be in the same directory, while also not having any access to unexported (private) members of packagefoo
.
Upvotes: 422
Reputation: 6808
EDITED
Built on VonC's answer,
This answer is valid in go1.11
. No yet tested in upper go
versions.
For those of you who like to keep their tests in a sub-folder, say test
, then running
go test ./...
will attempt to run tests in every folder, even those that do not contain any test, thus having a ?
in the subsequent report for non-test folders.
Running
go test ./.../test
instead will target only your test
folders, thus having a clean report focused on your tests folders only.
CAUTION
Please be mindful that using test sub-folders will prevent coverage report computation. The phylosophy of go is to leave test files in the package folders.
Upvotes: 27
Reputation: 13
I normally don't do test, but you can group your file into directories and use import like
import "./models"
if is one level out
import "../models
if is one level out and one level in
For example, for:
./models/todo.go
./test/todo_test.go
to test todo.go
from todo_test.go
,
your import in the todo_test.go
will be
import "../models"
Upvotes: -8