Skip to main content
eLearner.app
Module 10 · Lesson 1 of 546/50 in the course~10 min
Module lessons (1/5)

Naming conventions and style

Go has strong and non-negotiable naming and style conventions: the official formatter gofmt (and its superset goimports) decides indentation, spacing, and import order. Discussing style is considered off-topic: you run gofmt -w and move on. This frees up energy for more interesting problems.

Visibility: uppercase or lowercase

There are no public/private keywords. The first letter of the name determines visibility:

  • Uppercase → exported outside the package (User, Login, MaxRetries).
  • Lowercase → private to the package (user, parseLine, defaultTimeout).

This applies to: types, functions, methods, variables, constants, struct fields.

Go
type User struct {
    Name  string  // exported
    email string  // private to the package
}

A "private" struct field is not serialized by encoding/json (see Module 8), and it is not accessible from tests in pkg_test.

CamelCase, never snake_case

No underscores in multi-word names:

  • HTTPClient, userName, parseRequest
  • Http_Client, user_name, parse_request

Acronyms go all uppercase (or all lowercase, if in private scope):

  • URL, ID, HTML, JSON, parseURL, userID
  • Url, Id, Html, Json, parseUrl, userId
Go
type APIResponse struct {
    UserID  int
    HTMLURL string
}

Short names for short scopes

Go style favors brevity at equal clarity in narrow scopes:

Go
// idiomatic
for i, v := range items { ... }
for k, v := range m { ... }

if err := f(); err != nil { ... }

func (s *Server) Serve(w http.ResponseWriter, r *http.Request) { ... }

Established conventions:

  • i, j, k for loop indices.
  • v for values, k for keys.
  • r for *Request/io.Reader, w for Writer/ResponseWriter.
  • err for errors.
  • ctx for context.Context.
  • Method receivers: 1–2 consistent letters across the whole type (s *Server, u *User). Never this or self.

The wider the scope, the more descriptive the name must become: a local count is fine, but an exported Count variable should tell you what it counts.

No "I" prefix on interfaces, no "Impl" suffix

Go
// idiomatic
type Reader interface { ... }
type fileReader struct { ... } // concrete implementation

// not idiomatic
type IReader interface { ... }
type ReaderImpl struct { ... }

Small interfaces often take the -er suffix: Reader, Writer, Stringer, Closer. It echoes the fact that they describe a behavior (a single method, ideally).

Package names

A package has a single name, short, all lowercase, no underscores:

  • bytes, http, os, userauth
  • userAuth, user_auth, UserAuth

The package name is the usage prefix of its symbols: bytes.Buffer, http.Client. So user.User is redundant: better to rename the type (user.Account) or the package.

gofmt is not up for debate

gofmt enforces:

  • Indentation with tabs (not spaces).
  • Brace { on the same line as the signature.
  • Imports in groups separated by a blank line; goimports also adds missing imports.
  • Spaces around operators.

Always run before committing:

Bash
go fmt ./...
goimports -w .
go vet ./...

Linters (staticcheck, golangci-lint) add extra rules (unused variables, shadowing, useless comparisons, ...).

Exercises

Exercise#go.m10.l1.e1
Attempts: 0Loading…

Rinomina la struct Http_Client in HTTPClient (e il campo Url in URL) seguendo le convenzioni Go sugli acronimi.

Loading editor…

Solution available after 3 attempts

Exercise#go.m10.l1.e2
Attempts: 0Loading…

Inverti la visibilità: rendi Username esportato (maiuscolo) e password privato (minuscolo).

Loading editor…

Solution available after 3 attempts

Quiz#go.m10.l1.e3
Ready

Quale di questi nomi è idiomatico in Go per un tipo esportato 'server HTTP'?

Go
type ??? struct {}
Answer options