Przejdź do głównej treści
eLearner.app
Moduł 9 · Lekcja 4 z 544/50 w kursie~12 min
Lekcje modułu (4/5)

Moduły Go

Moduł Go to jednostka z możliwością wersjonowania, składająca się z jednego lub większej liczby pakietów. Jest to podstawa nowoczesnego systemu zależności (Go 1.11+): koniec z GOPATH, koniec z obowiązkowym vendor, jawne i powtarzalne zależności.

go.mod: manifest modułu

Code
module example.com/myapp

go 1.22

require (
    github.com/google/uuid v1.6.0
    golang.org/x/time     v0.5.0
)

Trzy główne dyrektywy:

  • module <path> — ścieżka importu modułu. Wszystkie pakiety wewnętrzne są importowane jako example.com/myapp/sub/pkg. Nie musi to być prawdziwy adres URL, ale aby opublikować go za pomocą go get, musi zostać rozwiązany.
  • go <version> — minimalna wymagana wersja Go (używana również do kontrolowania, które funkcje językowe są dozwolone, np. funkcja range-over w wersji 1.23).
  • require — bezpośrednie zależności z ich dokładną wersją.

Inne dyrektywy: replace (zastępuje dep rozwidleniem lub ścieżką lokalną), exclude, retract.

go.sum: plik blokady kryptograficznej

Oprócz go.mod, go.sum zawiera kryptograficzny skrót KAŻDEJ pobranej wersji (w tym zależności przechodnie). Gwarantuje powtarzalność: jeśli ktoś manipuluje opublikowaną wersją, kompilacja zakończy się niepowodzeniem.

Zawsze to zatwierdzaj. Jest aktualizowany automatycznie za pomocą poleceń go.

Podstawowe polecenia

Bash
go mod init example.com/myapp        # create go.mod
go get github.com/google/uuid        # add the dep at its latest version
go get github.com/google/uuid@v1.5.0 # specific version
go get -u ./...                      # upgrade every dep
go mod tidy                          # remove unused deps, add missing ones
go mod download                      # download everything into the cache
go mod why github.com/x/y            # explain why a dep is included
go mod graph                         # full dependency graph

go mod tidy to ten, który uruchamiasz po każdej zmianie importu: gwarantuje, że go.mod odzwierciedla dokładnie faktycznie używane pakiety.

Semantyczne wersjonowanie importu (SIV)

Wersje są zgodne z SemVer: v1.2.3 = MAJOR.MINOR.PATCH. Interesującą częścią jest główna wersja 2+:

  • Główne v0 i v1 → normalna ścieżka: github.com/foo/bar.
  • Major v2 lub nowszy → ścieżka zawiera wersję główną: github.com/foo/bar/v2.
Go
import "github.com/foo/bar/v2"

Umożliwia to jednoczesne importowanie v1 i v2 z tej samej biblioteki (przydatne podczas migracji progresywnych).

Importuj ścieżki i pakiety wewnętrzne

Jeśli Twój moduł to example.com/myapp, podfolder utils/ jest importowany jako:

Go
import "example.com/myapp/utils"

Ścieżka zależy tylko od nazwy zadeklarowanej w go.mod, a nie od lokalizacji na dysku: ten sam kod w innym folderze nadal działa.

Tryb przestrzeni roboczej (wersja 1.18+)

Aby pracować na wielu modułach, które odwołują się do siebie w tym samym czasie (np. biblioteka i aplikacja, która z niej korzysta):

Bash
go work init ./lib ./app

Spowoduje to utworzenie go.work: go build użyje lokalnej wersji ./lib zamiast pobierać opublikowaną. Nie popełniaj go.work (jest to środowisko programistyczne).

Ćwiczenia

Ćwiczenie#go.m9.l4.e1
Próby: 0Ładowanie...

Moduł to example.com/myapp i zawiera podfolder utils. Zaimportuj podpakiet do głównego pakietu, używając pełnej ścieżki.

Ładowanie edytora...
Pokaż wskazówkę

Ścieżka importu to nazwa modułu (z go.mod) plus ścieżka względna folderu.

Rozwiązanie dostępne po 3 próbach

Ćwiczenie#go.m9.l4.e2
Próby: 0Ładowanie...

Zmień pojedynczy import w grupę importu za pomocą składni import (...), importując zarówno fmt, jak i os.

Ładowanie edytora...

Rozwiązanie dostępne po 3 próbach

Quiz#go.m9.l4.e3
Gotowe

Które polecenie usuwa zależności, które nie są już importowane z go.mod i dodaje brakujące?

Go
$ go mod ???
Opcje odpowiedzi