This topic comes up a lot because Go is a newer language and has some quirks that many developers aren’t used to.
One Go tool that’s particular useful is ‘go get’ — which is used to fetch a remote package and add it to your current Go workspace. Naturally, a Go developer may at some point want his code to be usable by others and thus it should be ‘go gettable’. Here’s where things start to get quirky.
Most law-abiding developers keep their code in one of the major version control systems (Git, Mercurial, Bazaar, etc.) and are generally used to keeping entire projects under version control. The standard Go layout (http://golang.org/doc/code.html#Organization) shows us that we should have 3 top-level directories: src/, bin/, and pkg/. Nested inside src/ are the names of top-level repositories like github.com, launchpad.net, etc. Inside those repository directories are more directories containing the actual Go packages. So, how do we manage a project that contains a multitude of versioned software including our own?
The answer: workspaces
In Go, a workspace is a container that the Go tools use to understand where Go source files are, where to place ‘go gettable’ packages, where to build and install Go programs and libraries, and so on. The workspace itself should not be under version control. A common beginner’s mistake is to create a repository with a src/github.com/github-user/project hierarchy to make the Go tools happy, but then realize that the structure prevents the code from being ‘go gettable’ because the root level of the repository contains the src/ directory instead of Go files.
So what’s the best way to start a new Go project? Carefully follow the instructions here: http://golang.org/doc/code.html#Organization
- When creating a new Go project, create the version-controlled directory structure you expect to use in the future, even if you’re not going to use it yet (i.e. cd ~/go_workspace && mkdir -p src/github.com/git-user/go-project)
- In the above pointer, go-project is the root of your repository
- If you publish your code, a developer who runs ‘go get github.com/git-user/go-project’ will be able to use your code