# #go #go-modules
Вопрос:
Я использую go1.16.3 с этим файлом инструментов для консолидации зависимостей:
// build tools
package main
import (
_ "github.com/swaggo/swag/cmd/swag"
_ "honnef.co/go/tools/cmd/staticcheck"
)
Запуск go get
в директории проекта загружает и устанавливает пакеты $GOPATH/pkg/mod
, но не устанавливает их двоичные $GOPATH/bin
файлы . Запуск go get
индивидуально для каждого мода (т. Е. go get github.com/swaggo/swag/cmd/swag
) устанавливает как пакеты, так и двоичные файлы.
Есть ли способ установить двоичные файлы для всех модов с помощью одной команды?
Если нет, то как правильно автоматически устанавливать все пакеты и двоичные файлы для всех зависимостей?
Комментарии:
1.
go.mod
указывает модули, которые не являются двоичными файлами, хотя некоторые из них могут соответствоватьmain
пакетам. Путь импортаgithub.com/swaggo/swag/cmd/swag
-это не модуль, этоmain
пакет (также обратите внимание на уведомление об устаревании при запускеgo get
этого пакета). Было бы очень необычно хотеть, чтобы каждый отдельныйmain
пакет из каждой зависимости модуля был установлен. Обычно у вас просто есть команда для установки конкретных двоичных файлов, которые вы хотите.2. Я думаю, что скрипт оболочки является подходящим инструментом для этой проблемы.
3. В этой статье хорошо описано, как удобно спланировать этот процесс: marcofranssen.nl/manage-go-tools-via-go-modules
4. Если вы не хотите синхронизировать сценарий сборки с файлом инструментов, сделайте так, чтобы сценарий устанавливал пакеты на основе
tools.go
путей импорта файлов. Я никогда не видел, чтобы это стало реальной проблемой, так как они меняются очень редко, и это сразу становится очевидным, если у вас не установлен инструмент, который вызывается позже в процессе сборки.5. @Дейв не лично, нет. Если сборка сложна, у меня есть шаг создания файла, который устанавливает инструменты, необходимые для процесса сборки, и управляет этим списком в файле создания. Но YMMV, и нет ни одного «правильного способа» управлять такого рода инструментами.
Ответ №1:
На самом деле нет хорошего способа сделать это в одной команде. Вашим лучшим выбором может быть сценарий, который связывает go list
команду для перечисления всего импорта из инструментов.войдите в go install
команду:
tools=$(go list -f '{{range .Imports}}{{.}} {{end}}' tools.go)
go install $tools
Чтобы объяснить вышесказанное, go list
запросите пакеты и модули. По умолчанию он просто печатает имена пакетов, но его выводом можно управлять с -f
помощью или -json
. go help list
показывает, что все go list
можно распечатать. Синтаксис для -f
такой же, как text/template
.
Итак, здесь go list tools.go
запрашивается пакет, представляющий собой список файлов .go, в данном случае просто tools.go. .Imports
представляет собой отсортированный дедуплицированный список импорта из этого пакета. Мы могли бы просто использовать шаблон {{.Imports}}
, но он печатает скобки в начале и в конце.
$ go list -f '{{.Imports}}' tools.go
[github.com/swaggo/swag/cmd/swag honnef.co/go/tools/cmd/staticcheck]
Поэтому вместо этого мы расширяем диапазон .Imports
, и внутри диапазона мы печатаем каждый импорт ( {{.}}
), за которым следует пробел.
Комментарии:
1. Это облом, что файл tools был решен без исправления этого, но этот подход ^ намного лучше, чем его анализ.
2. @Dave Я согласен с инструментами. идиоматичность-это своего рода неудовлетворение. Я надеюсь, что в будущем мы придумаем что-то лучшее, что также касается частных зависимостей.
3. Еще один вариант-отделить версии инструментов от
go.mod
файла и просто сделать его сценарием оболочки, который устанавливает инструменты в известных версиях:go install github.com/swaggo/swag/cmd/swag@v1.7.1 amp;amp; go install honnef.co/go/tools/cmd/staticcheck@v0.2.0