Содержание

Введение в управление зависимостями в Go

Почти любой реальный проект использует чужой код: HTTP-роутер, драйвер PostgreSQL, библиотеку для UUID, YAML-парсер, Telegram SDK. Такой внешний код называется зависимостью.

Управление зависимостями отвечает на практические вопросы:

  • какие пакеты нужны проекту;
  • какие версии этих пакетов используются;
  • где их скачать;
  • как другой разработчик получит те же версии;
  • как удалить то, что больше не используется.

В Go для этого используется система Go Modules.

Модуль

Модуль - это корень Go-проекта с файлом go.mod. Обычно один репозиторий содержит один модуль.

Создать модуль:

go mod init github.com/username/weather-cli

После этого появится go.mod:

module github.com/username/weather-cli go 1.22

module задает module path. Если проект будет опубликован на GitHub, обычно используют путь репозитория. Для учебного локального проекта можно использовать условный путь, но лучше сразу привыкать к реальному формату.

Import path

Пакеты внутри модуля импортируются относительно module path:

github.com/username/weather-cli/internal/config

Если в go.mod написано:

module github.com/username/weather-cli

а пакет лежит в:

internal/config

то import будет:

import "github.com/username/weather-cli/internal/config"

Если module path выбран случайно, импорты тоже станут случайными. Поэтому имя модуля лучше выбирать внимательно.

go.mod

go.mod хранит:

  • имя модуля;
  • версию Go;
  • прямые зависимости;
  • иногда indirect dependencies;
  • replace directives, если они нужны локально.

Пример:

module github.com/username/books-api go 1.22 require ( github.com/go-chi/chi/v5 v5.0.12 github.com/google/uuid v1.6.0 )

Этот файл нужно коммитить. Без него другой человек не поймет, какие зависимости нужны проекту.

go.sum

go.sum хранит checksums зависимостей. Он помогает Go проверить, что скачанный код совпадает с ожидаемым.

go.sum тоже нужно коммитить. Это не временный файл и не lock-файл в привычном смысле, но он важен для воспроизводимости и безопасности.

Добавление зависимости

Чтобы добавить зависимость:

go get github.com/google/uuid

После этого можно импортировать пакет:

import "github.com/google/uuid" id := uuid.NewString()

Go обновит go.mod и go.sum.

Часто зависимость добавляется автоматически при:

go mod tidy

если импорт уже есть в коде.

Версии

Go Modules используют semantic versioning:

v1.2.3
  • 1 - major;
  • 2 - minor;
  • 3 - patch.

Patch обычно содержит исправления. Minor добавляет функциональность без ломания совместимости. Major может ломать API.

Для major version v2+ в Go меняется import path:

import "github.com/go-chi/chi/v5"

Это не случайность. Go делает major version частью пути, чтобы разные major versions могли сосуществовать.

Обновление зависимости

Обновить до последней совместимой версии:

go get github.com/google/uuid@latest

Указать конкретную версию:

go get github.com/go-chi/chi/v5@v5.0.12

После обновления запускайте тесты:

go test ./...

Даже minor update может изменить поведение в деталях.

Удаление зависимости

Чтобы удалить зависимость:

  1. Удалите import из кода.
  2. Удалите использование пакета.
  3. Выполните:
go mod tidy

tidy удалит неиспользуемые зависимости из go.mod и go.sum.

go mod tidy

go mod tidy приводит файлы модуля в соответствие с кодом:

  • добавляет зависимости, которые импортируются;
  • удаляет зависимости, которые больше не нужны;
  • обновляет go.sum.

Эту команду полезно запускать перед commit.

Indirect dependencies

В go.mod можно увидеть:

require github.com/some/package v1.2.3 // indirect

Indirect dependency нужна не вашему коду напрямую, а одной из ваших зависимостей. Обычно не нужно редактировать такие строки руками.

replace

replace позволяет временно заменить модуль локальным путем или другим источником:

replace github.com/example/lib => ../lib

Это удобно для локальной разработки нескольких модулей, но будьте осторожны: случайный replace на путь вроде /Users/alice/lib сломает проект у других людей.

Чеклист

  1. В корне проекта есть go.mod.
  2. Module path выбран осознанно.
  3. go.mod и go.sum закоммичены.
  4. Зависимости добавляются через go get или go mod tidy.
  5. Неиспользуемые зависимости удаляются через go mod tidy.
  6. После обновления зависимостей запускаются тесты.
  7. replace не содержит локальных путей перед публикацией.

Следующий шаг после статьи

Закрепите тему во вводном проекте без регистрации, а затем переходите к курсам.

Продолжить изучение

Выбери следующую статью по маршруту или углубись в смежную тему.

Похожие статьи