Setting Up and Organizing Your Go Workspace
A well-organized Go workspace is crucial for efficient development. This guide covers both traditional GOPATH-based workspaces and modern module-based approaches.
Modern Go Workspace (Recommended)
Since Go 1.11, the recommended approach is to use Go modules, which don't require a specific workspace structure. However, understanding workspace organization is still important.
Basic Module Structure
myproject/
├── go.mod # Module definition and dependencies
├── go.sum # Dependency checksums
├── main.go # Main application entry point
├── README.md # Project documentation
├── .gitignore # Git ignore file
├── cmd/ # Command-line applications
│ └── server/ # Server binary
│ └── main.go
├── internal/ # Private application code
│ ├── auth/ # Authentication package
│ └── db/ # Database package
├── pkg/ # Public libraries
│ ├── models/ # Data models
│ └── utils/ # Utility functions
├── api/ # API definitions
│ └── openapi.yaml
├── configs/ # Configuration files
│ └── config.yaml
├── docs/ # Documentation
│ └── api.md
└── tests/ # Integration and e2e tests
└── api_test.go
Creating a New Module
# Create project directory
mkdir myproject
cd myproject
# Initialize module
go mod init github.com/username/myproject
# Create basic structure
mkdir cmd internal pkg api configs docs tests
Traditional GOPATH Workspace
While modules are preferred, understanding GOPATH is important for maintaining legacy code.
GOPATH Structure
$GOPATH/
├── bin/ # Compiled executables
├── pkg/ # Compiled package objects
└── src/ # Source code
└── github.com/
└── username/
└── project/
├── main.go
└── package/
Setting Up GOPATH
# Add to ~/.bashrc or ~/.zshrc
export GOPATH=$HOME/go
export PATH=$PATH:$GOPATH/bin
# Create directory structure
mkdir -p $GOPATH/{bin,pkg,src}
Project Organization Best Practices
1. Package Organization
// Bad: Mixed concerns in one package
package utils
func ValidateUser() {} // Authentication
func FormatDate() {} // Formatting
func QueryDatabase() {} // Database
// Good: Separated concerns
package auth
func ValidateUser() {}
package format
func FormatDate() {}
package db
func Query() {}
2. Internal Packages
Use the internal
directory to prevent packages from being imported by other projects:
myproject/
├── internal/ # Private code
│ └── auth/
│ └── auth.go
└── pkg/ # Public code
└── utils/
└── utils.go
3. Command Applications
Separate main packages into the cmd
directory:
cmd/
├── api/
│ └── main.go # API server
└── cli/
└── main.go # CLI tool
4. Vendor Management
When using vendored dependencies:
myproject/
├── vendor/ # Vendored dependencies
│ └── github.com/
│ └── pkg/
└── go.mod
# Vendor dependencies
go mod vendor
# Build using vendored dependencies
go build -mod=vendor
Module Management
Creating and Updating Modules
# Initialize a new module
go mod init example.com/myproject
# Add a dependency
go get github.com/pkg/errors
# Update dependencies
go get -u ./...
# Tidy dependencies
go mod tidy
Working with Multiple Modules
Go 1.18+ supports workspace mode for multiple modules:
workspace/
├── go.work
├── moduleA/
│ ├── go.mod
│ └── main.go
└── moduleB/
├── go.mod
└── lib.go
# Initialize workspace
go work init ./moduleA ./moduleB
# Add module to workspace
go work use ./moduleC
Development Tools Integration
VS Code Setup
// .vscode/settings.json
{
"go.useLanguageServer": true,
"go.lintTool": "golangci-lint",
"go.formatTool": "goimports",
"go.testOnSave": true
}
GoLand Setup
- Set GOROOT:
Settings → Go → GOROOT
- Enable Go modules:
Settings → Go → Go Modules
- Configure formatters:
Settings → Go → Formatting
Testing Organization
Test File Structure
package/
├── file.go # Source file
├── file_test.go # Unit tests
├── file_internal_test.go # Internal tests
└── testdata/ # Test fixtures
└── sample.json
Test Types Organization
// file_test.go
package mypackage_test // Black box testing
// file_internal_test.go
package mypackage // White box testing
Documentation
Project Documentation
docs/
├── README.md # Project overview
├── CONTRIBUTING.md # Contribution guidelines
├── ARCHITECTURE.md # Architecture design
└── api/
└── api.md # API documentation
Package Documentation
// Package auth provides authentication functionality.
package auth
// User represents an authenticated user.
type User struct {
ID string
Roles []string
}
Common Issues and Solutions
1. Module Path Issues
# Wrong module path
go mod init myproject
# Correct module path
go mod init github.com/username/myproject
2. Dependency Conflicts
# View module dependencies
go mod graph
# Clean up dependencies
go mod tidy
# Verify dependencies
go mod verify
3. GOPATH vs Module Mode
# Force module mode
export GO111MODULE=on
# Force GOPATH mode
export GO111MODULE=off
# Auto detection (default)
export GO111MODULE=auto
Next Steps
- Learn about Go modules in detail
- Explore Go tools for development
- Study project structure best practices
- Understand dependency management