Библиотека Go-разработчика | Golang
24K subscribers
2.55K photos
48 videos
88 files
5.07K links
Все самое полезное для Go-разработчика в одном канале.

По рекламе: @proglib_adv

Учиться у нас: https://proglib.io/w/32d20779

Для обратной связи: @proglibrary_feeedback_bot

РКН: https://gosuslugi.ru/snet/67a4a8c24689c2151c752af0

#WXSSA
Download Telegram
💡 Замените счётчики на итераторы

В Go давно есть идиоматичный способ обходить коллекции: range. Но многие стандартные типы исторически предлагали только Len() и At(i), и код превращался в ручной счётчик. Анализатор stditerators из golang.org/x/tools находит такие места и предлагает замену.

Типичный паттерн, который можно встретить в Go-проекте:
for i := 0; i < x.Len(); i++ {
use(x.At(i))
}


Это работает, но многословно. Появились итераторы: метод All() у ряда стандартных типов возвращает iter.Seq, по которому можно пройтись через range. stditerators находит старые конструкции и предлагает переписать их вот так:
for elem := range x.All() {
use(elem)
}


Анализатор понимает оба варианта счётчика — классический for i := 0; i < x.Len(); i++ и более новый for i := range x.Len().

Что покрывает

Анализатор работает с конкретными типами из стандартной библиотеки, у которых уже есть метод All(). Это не универсальный «переписыватель» для всего подряд, а точечный инструмент с заранее известным списком поддерживаемых типов.

Как запустить:
go install golang.org/x/tools/gopls@latest


Или через go vet с плагином:
go run golang.org/x/tools/go/analysis/passes/stditerators/cmd/stditerators@latest ./...


В большинстве редакторов с gopls анализатор подсветит проблемное место прямо в коде и предложит автоматический фикс.

📍 Навигация: ВакансииЗадачиСобесы

🐸 Библиотека Go-разработчика

#GoToProduction
Please open Telegram to view this post
VIEW IN TELEGRAM
9
🤔 Разрабатываете ИИ-агентов, но всё ещё не уверены в их стабильности и прогнозируемости?

Мы поговорили с десятками разработчиков ИИ-агентов и сделали отдельный курс по AgentOps.

🧠 На нём вы узнаете:

– как оптимизировать траты на токены;
– как на практике оценить качество работы агента;
– как «докручивать» RAG-системы без потери качества;
– как обеспечить устойчивость агента к сбоям внешних сервисов без падения всей системы и про многое-многое другое.

📅 Старт: 19 мая.

👥 Спикеры — практики с опытом в AI и Data Science в крупных IT-компаниях, таких как Яндекс, Huawei, МТС и др.

Длительность: 6-12 недель в зависимости от тарифа.


🔗 Программа курса и другие подробности
1
🤯 Представьте, что ваш AI-агент работает так же предсказуемо, как обычный микросервис. Звучит утопически, но это именно то, к чему должна прийти разработка в 2026 году.

Основная боль текущих реализаций — полная непредсказуемость поведения. Сегодня агент выполнил задачу за два шага, а завтра ушёл в рекурсию и потратил все лимиты.

Наш обновлённый курс «Разработка AI-агентов» научит, как приручить этот хаос с помощью Python и современных фреймворков. Мы не будем учить «общаться» с нейросетью, мы будем строить из неё надёжный инструмент.

Что вы получите:


— понимание того, как управлять логикой агента на уровне кода;
— навыки работы с LangChain и библиотеками оркестрации;
— готовые паттерны для обработки ошибок и галлюцинаций;
— опыт создания систем, которые реально экономят время.

Есть пара мест со скидкой до завтра, решайтесь 👈🏻
🤩 Дайджест недели

Что прошло уже не вернуть, но стоит ознакомиться с нашей подборкой прошедшей недели.

oaswrap/spec v0.4.0

Патчи с исправлениями безопасности

Эмулятор AWS-сервисов

Entity Component System на Go

📍 Навигация: ВакансииЗадачиСобесы

🐸 Библиотека Go-разработчика

#GoLive
Please open Telegram to view this post
VIEW IN TELEGRAM
⚙️ CLI, который замораживает dev-сервер вместо его убийства

Типичная ситуация: запущен dev-сервер на порту 3000, нужно на полминуты освободить порт под другую задачу. Убиваете процесс и теряете кэши в памяти, состояние билд-вотчера, прогретые соединения. Потом поднимаете всё заново.

Разработчик написал инструмент park, который решает это иначе: замораживает процесс и освобождает порт, а потом возвращает всё как было. Тот же PID, та же память, те же открытые файлы. Процесс не знает, что что-то произошло.

park 3000          # заморозить и освободить порт
# делаем что нужно на порту 3000
park resume 3000 # вернуть всё обратно


Почему Ctrl+Z не работает

Ctrl+Z отправляет SIGSTOP — процесс замирает, но ядро по-прежнему считает порт занятым. Попытка занять его другим процессом даёт Address already in use. SIGSTOP не закрывает сокет.

park решает это через инъекцию close(fd) прямо в работающий процесс без его перезапуска и изменения кода.

Установка:
curl -fsSL https://raw.githubusercontent.com/mr-vaibh/park/main/install.sh | sh


Инсталлятор сам определяет ОС и архитектуру. На macOS автоматически подписывает бинарник с нужными правами для инъекции в процессы.

➡️ Репозиторий

📍 Навигация: ВакансииЗадачиСобесы

🐸 Библиотека Go-разработчика

#GoToProduction
Please open Telegram to view this post
VIEW IN TELEGRAM
👍13
✏️ Автоматизация рутины в Go-проектах

Большинство Go-разработчиков знают про go generate, но редко его используют. А зря — это простой способ убрать ручную работу из цикла разработки.

Что такое go generate и зачем оно нужно

В каждом проекте есть код, который кто-то должен написать руками: моки для тестов, protobuf-файлы, бойлерплейт для новых сущностей. Обычно это делается руками, иногда забывается, иногда делается неправильно.

go generate решает эту проблему. Вы один раз описываете команду прямо в коде, а потом запускаете одну команду и всё генерируется автоматически.

Как это работает

Вы добавляете специальный комментарий в .go-файл:
//go:generate mockgen -source=service.go -destination=mock_service.go -package=service


Потом запускаете:
go generate ./...


Go находит все такие комментарии в проекте и выполняет указанные команды. Всё.

Что можно генерировать

Моки для тестов. Если вы используете mockgen или moq, достаточно добавить комментарий рядом с интерфейсом и мок всегда будет актуальным:
//go:generate moq -out=user_repo_mock.go . UserRepository
type UserRepository interface {
FindByID(id int) (*User, error)
Save(user *User) error
}


Protobuf-файлы. Вместо того чтобы каждый раз вспоминать флаги protoc, достаточно один раз прописать команду:
//go:generate protoc --go_out=. --go-grpc_out=. api.proto


Встраивание ресурсов. Генераторы вроде go-bindata упаковывают статику прямо в бинарник.

Строковые представления для констант. stringer автоматически генерирует метод String() для ваших типов:
//go:generate stringer -type=Status
type Status int

const (
Active Status = iota
Inactive
Banned
)


Практический совет

Добавьте go generate ./... в ваш Makefile или CI-пайплайн. Тогда сгенерированный код всегда будет пересоздаваться при сборке, и никто не забудет обновить моки после изменения интерфейса:
generate:
go generate ./...

build: generate
go build ./...


📍 Навигация: ВакансииЗадачиСобесы

🐸 Библиотека Go-разработчика

#GoDeep
Please open Telegram to view this post
VIEW IN TELEGRAM
👍12
🧑‍💻 Свой diff-драйвер для git

git diff умеет делегировать сравнение файлов внешнему инструменту. Это называется diff-драйвер. Штатный вывод git не всегда читаем особенно для JSON, YAML или OpenAPI-спецификаций. Вместо того чтобы смотреть на кашу из + и -, можно подключить инструмент, который покажет изменения в удобном виде.

Чем это отличается от textconv

Есть более простой способ — textconv. Он конвертирует файл в текст, и git сравнивает уже текст. Но если нужно не просто показать разницу построчно, а сформировать собственный вывод, например, changelog между двумя версиями API, textconv не подойдёт. Тут нужен полноценный драйвер.

Что git передаёт в драйвер

Многие ожидают, что инструмент получит два аргумента: файл «до» и файл «после». На самом деле git передаёт семь:
# при изменении существующего файла
my-diff-tool \
path/to/file.json # 1: путь к файлу в репозитории
/tmp/git-blob-xxx/file.json # 2: "до"
f0a1311ae439... # 3: SHA-1 хэш "до"
100644 # 4: octal mode "до"
/tmp/git-blob-yyy/file.json # 5: "после"
e39975894a72... # 6: SHA-1 хэш "после"
100644 # 7: octal mode "после"


При создании или удалении файла вместо несуществующей версии придёт /dev/null, а неприменимые аргументы заменяются точкой .:
# новый файл
my-diff-tool \
path/to/file.json
/dev/null # файла "до" не было
.
.
/tmp/git-blob-yyy/file.json
5c55e5b99b21...
100644

# удалённый файл
my-diff-tool \
path/to/file.json
/tmp/git-blob-xxx/file.json
6b24e38aa4aa...
100644
/dev/null # файла "после" нет
.
.


Пример драйвера:
#!/usr/bin/env bash

# diff-драйвер для OpenAPI-спецификаций через oasdiff

if [[ "$2" == "/dev/null" ]]; then
echo "$1 was added"
exit 0
elif [[ "$5" == "/dev/null" ]]; then
echo "$1 was deleted"
exit 0
fi

oasdiff changelog "$2" "$5" --color always


Аргументы $2 и $5 это пути к временным файлам «до» и «после», которые git уже подготовил.

Как подключить драйвер

В .gitattributes указываем, для каких файлов его использовать:
*.yaml diff=oasdiff


В .git/config или глобальном ~/.gitconfig регистрируем сам драйвер:
[diff "oasdiff"]
command = /path/to/oasdiff-driver.sh


После этого git diff будет вызывать скрипт для всех .yaml-файлов вместо стандартного построчного сравнения.

Diff-драйвер нужен, когда стандартный вывод git бесполезен. Написать его несложно: достаточно bash-скрипта, который принимает семь аргументов и знает, что делать с /dev/null для новых и удалённых файлов. Всё остальное берёт на себя git.

➡️ Источник

📍 Навигация: ВакансииЗадачиСобесы

🐸 Библиотека Go-разработчика

#GoToProduction
Please open Telegram to view this post
VIEW IN TELEGRAM
9👍2
🔒 internal: Go защищает архитектуру вашего проекта

Когда проект растёт, рано или поздно кто-то импортирует не то, что нужно. Репозиторий тянет сервис, хендлер лезет напрямую в базу и архитектура начинает разваливаться. Go решает это на уровне компилятора.

Что такое internal

Папка internal это встроенный механизм Go для ограничения импортов. Любой пакет внутри internal/ можно импортировать только из кода, который находится в родительском модуле этой папки. Всё остальное компилятор просто не пропустит.

Типичная структура проекта:
myapp/
├── cmd/
│ └── main.go
├── internal/
│ ├── service/
│ │ └── user.go
│ └── repository/
│ └── user.go
└── pkg/
└── utils/


Код в cmd/ может импортировать internal/service и internal/repository. А вот внешний пакет или другой модуль нет. Go выдаст ошибку компиляции:
imports myapp/internal/service: use of internal package not allowed


Можно вкладывать internal глубже

internal работает не только на уровне корня проекта. Его можно положить внутрь любого пакета:
myapp/
├── payment/
│ ├── internal/
│ │ └── processor/
│ └── payment.go


internal это не соглашение, а правило, которое компилятор применяет сам.

📍 Навигация: ВакансииЗадачиСобесы

🐸 Библиотека Go-разработчика

#GoDeep
Please open Telegram to view this post
VIEW IN TELEGRAM
16❤‍🔥5👍5🔥1🌚1
👀 Go-фреймворк для серверного UI без React и npm

Doors это бэкенд-фреймворк для веб-приложений на Go. Он позволяет строить реактивный UI без JS-фреймворков, без гидратации и без npm. Весь бизнес-логика живёт на сервере, браузер работает только как тонкий клиент для отображения.

Стандартный стек Go + React требует писать и поддерживать два слоя: API на Go и фронт на JS. Это дублирование типов, синхронизация состояния, сборка, зависимости. Htmx даёт частичные обновления страницы, но не даёт нормального реактивного состояния и контроля из Go.

Doors убирает API-слой полностью. Сервер держит живое состояние каждой вкладки пользователя, а браузер просто синхронизирует изменения DOM.

Как это работает

При загрузке страницы сервер создаёт экземпляр сессии и отдаёт cookie. Дальше между клиентом и сервером держится лёгкое соединение через короткие HTTP-запросы с поддержкой QUIC.

Пользователь что-то делает и событие летит на Go-обработчик. Сервер считает изменения и отдаёт конкретные обновления DOM.

Два ключевых примитива:

Door — динамический контейнер в HTML. Умеет обновляться, заменяться, удаляться. Каждый Door имеет свой жизненный цикл и локальный context, который можно использовать как хук при размонтировании.

Beam — реактивное состояние на сервере. SourceBeam хранит мутабельное значение, производные Beam считаются из него. Обновления гарантированно консистентны по дереву контейнеров.

Пример запуска:
import "github.com/doors-dev/doors"

func main() {
app := doors.New()
// регистрация страниц и обработчиков
app.Run(":8080")
}


➡️ Репозиторий

📍 Навигация: ВакансииЗадачиСобесы

🐸 Библиотека Go-разработчика

#GoToProduction
Please open Telegram to view this post
VIEW IN TELEGRAM
❤‍🔥8👍53🌚1
🌐 Топ-вакансий для Go-разработчиков за неделю

Senior Go Developer — удаленно по Москве

Golang Middle/Senior Developer — до 420 000 ₽, удаленно кроме РФ, РБ и Израиля

Junior Бэкенд-разработчик — от 80 000 до 120 000 ₽ в офис в Тамбове

➡️ Еще больше топовых вакансий — в нашем канале Go jobs

🐸 Библиотека Go-разработчика

#GoWork
Please open Telegram to view this post
VIEW IN TELEGRAM
🤩 Тесты с реальными сервисами без моков

Мокать базу данных — занятие неблагодарное. Каждое изменение схемы тянет за собой правки в моках, а уверенности в корректности поведения всё равно нет. Настоящий тест это тест против реального PostgreSQL, Redis или любого другого сервиса.

ory/dockertest
решает эту задачу: библиотека поднимает Docker-контейнеры прямо из Go-теста и убирает их по завершении.

Как это работает:
func TestPostgres(t *testing.T) {
pool := dockertest.NewPoolT(t, "")

postgres := pool.RunT(t, "postgres",
dockertest.WithTag("14"),
dockertest.WithEnv([]string{
"POSTGRES_PASSWORD=secret",
"POSTGRES_DB=testdb",
}),
)

hostPort := postgres.GetHostPort("5432/tcp")

err := pool.Retry(t.Context(), 30*time.Second, func() error {
db, err := sql.Open("pgx", "postgres://postgres:secret@"+hostPort+"/testdb")
if err != nil {
return err
}
return db.Ping()
})
if err != nil {
t.Fatalf("не удалось подключиться: %v", err)
}
}


Контейнер поднимается, тест выполняется, контейнер удаляется. Всё через t.Cleanup, без лишнего кода.

Установка:
go get github.com/ory/dockertest/v4


➡️ Репозиторий

📍 Навигация: ВакансииЗадачиСобесы

🐸 Библиотека Go-разработчика

#GoToProduction
Please open Telegram to view this post
VIEW IN TELEGRAM
👍16😁2
🖼 Работа с изображениями в терминале

gowall это CLI-инструмент на Go, который перекрашивает изображение под любую заданную цветовую схему. Вы отдаёте ему картинку и говорите «сделай в стиле Gruvbox». Он берёт доминирующие цвета и заменяет их на цвета из нужной палитры.

Изначально gowall создавался именно для перекраски обоев, но со временем оброс другими возможностями. Сейчас это целый набор утилит для обработки изображений из командной строки.

Помимо перекраски есть OCR — извлечение текста из изображений и PDF. Поддерживает 9+ провайдеров, в том числе визуальные языковые модели и гибридные методы.

Работает через Unix pipes и вписывается в любые скрипты и пайплайны.

Пример использования

Перекрасить обои под тему Nord:
gowall convert wallpaper.png --theme nord


Посмотреть все доступные темы:
gowall list


Извлечь цветовую палитру из изображения:
gowall palette photo.jpg


Сжать изображение:
gowall compress image.png


Что нового в v0.2.4

Четыре дня назад вышел свежий релиз. Главное: улучшенное удаление фона и новый набор утилит для работы с цветом.

Вместо того чтобы искать обои под нужную палитру, можно взять любую картинку и перекрасить за одну команду.

📍 Навигация: ВакансииЗадачиСобесы

🐸 Библиотека Go-разработчика

#GoToProduction
Please open Telegram to view this post
VIEW IN TELEGRAM
1
25 апреля в Санкт-Петербурге пройдет Я.Субботник по Go: митап для тех, кто строит и масштабирует сервисы на Go

Встречаемся в питерском офисе Яндекса или на онлайн-трансляции, чтобы обсудить все, что волнует Go-сообщество.

В программе выступлений:

Владимир Тельбухов, руководитель группы разработки Городских сервисов, расскажет, как построить устойчивую систему в интеграциях с внешними сервисами

Иван Похабов, разработчик Yandex Cloud, разберет, как устроен GoBGP, какие баги в нём встречаются и как их исправляют в production

Сергей Толмачев, разработчик Yandex Infrastructure, разберет S3 Inventory, основываясь на практическом опыте внедрения

Имран Турсунов, разработчик Персональных сервисов, сделает практический разбор observability

Все, кто будет очно, после докладов смогут принять участие в круглых столах и квизе по Go. А чтобы посетить экскурсию по офису перед началом мероприятия, офлайн-участникам нужна будет предварительная регистрация.

▶️ Подробности и регистрация
👍2🌚1