Install Go, write hello world, understand go run vs go build.
Go Modules & go.mod
A module is a project. It's a folder with a go.mod file at the top, which tells
the compiler:
- the module's path (its import name)
- the Go version it targets
- every dependency and its exact version
You'll work with modules from day one. They replace the older GOPATH workflow that
existed before Go 1.11.
Starting a module
mkdir hello && cd hello
go mod init example.com/hello
That creates a single file:
// go.mod
module example.com/hello
go 1.23
The path can be anything you want — but pick something that uniquely identifies you,
typically a domain or git URL like github.com/yourname/project.
Adding a dependency
go get github.com/google/uuid
Two things happen:
go.modgets arequire github.com/google/uuid v1.x.yline.- A
go.sumfile is created (or updated) — it pins cryptographic hashes of the dependency's contents so nobody can swap the code under you.
After the go get, go.mod looks like:
module example.com/hello
go 1.23
require github.com/google/uuid v1.6.0
You don't edit go.sum by hand. Treat it like a lockfile.
Useful module commands
| Command | What it does |
| ------------------ | ----------------------------------------------------- |
| go mod init PATH | Start a new module. |
| go get PKG | Add or upgrade a dependency. |
| go mod tidy | Remove unused deps and add missing ones. |
| go mod download | Download deps without building. |
| go mod why PKG | Explain why this dependency exists. |
| go mod graph | Print the dep graph. |
Versioning rule of thumb
Go modules follow semantic versioning strictly:
v0.x.y— unstable, anything can change.v1.x.y— stable; minor and patch versions never break callers.v2.x.yand above — must have/v2(or/v3, …) appended to the import path. This is a one-off rule unique to Go and it prevents accidental upgrades.
import "github.com/some/pkg/v2"
Minimum Version Selection
When two dependencies require different versions of the same library, Go does not pick "the latest". It picks the minimum version that satisfies every requirement in the graph. This is called MVS. The upshot: builds are reproducible without a lockfile resolver, and adding a dependency rarely cascades into surprise upgrades.
If you want a newer version, ask for it explicitly: go get pkg@v1.5.0.