Как отлаживать данные в формате Protocol Buffers (Protobuf) в Go?

Ответ

Отладка бинарного формата Protobuf заключается в его преобразовании в человекочитаемый вид. Вот основные способы:

1. Конвертация в текстовый формат

Пакет prototext позволяет преобразовать Protobuf-сообщение в многострочный текстовый формат, который удобно читать.

import "google.golang.org/protobuf/encoding/prototext"

// msg - ваше protobuf-сообщение
textData, err := prototext.MarshalOptions{Multiline: true}.Marshal(msg)
if err != nil {
    // обработка ошибки
}
fmt.Println(string(textData))

2. Конвертация в JSON

JSON — еще один удобный формат для анализа. Пакет protojson решает эту задачу.

import "google.golang.org/protobuf/encoding/protojson"

// msg - ваше protobuf-сообщение
jsonData, err := protojson.MarshalOptions{Multiline: true, Indent: "  "}.Marshal(msg)
if err != nil {
    // обработка ошибки
}
fmt.Println(string(jsonData))

3. Использование утилиты protoc

Если у вас есть бинарные данные в файле или из сетевого трафика, можно использовать компилятор protoc для их декодирования. Для этого нужен .proto файл со схемой.

# my_message.bin содержит бинарные данные
# schema.proto содержит определение MyMessage
protoc --decode=MyMessage schema.proto < my_message.bin

4. Специализированные инструменты

  • grpcurl: Утилита командной строки для взаимодействия с gRPC-сервисами. Позволяет отправлять запросы и просматривать ответы в текстовом виде без написания кода.
  • Postman / Insomnia: Современные API-клиенты поддерживают gRPC, позволяя импортировать .proto файлы и удобно отлаживать запросы/ответы через GUI.

Важно:

  • При отладке всегда проверяйте ошибки, возвращаемые функциями Unmarshal, — они часто указывают на несоответствие данных и схемы.

Ответ 18+ 🔞

Ага, слушай, вот ты пишешь на Go, и тебе надо посмотреть, что там внутри этого бинарного протобуфа творится, а он как шифровка, блядь, одни байты. Ну, хуле, сейчас разберёмся, как его в нормальный вид превратить, чтобы глаза не вытекали.

1. Превращаем в читаемый текст (как в кино про хакеров)

Есть пакетик prototext, который твоё сообщение разжуёт и красиво, с отступами, на экран выплюнет. Всё по полочкам, как в хорошем бардачке.

import "google.golang.org/protobuf/encoding/prototext"

// msg - твой protobuf, который ты из сети или файла вытащил
textData, err := prototext.MarshalOptions{Multiline: true}.Marshal(msg)
if err != nil {
    // Ну тут понятно, если ошибка — значит, где-то накосячил, иди смотри
}
fmt.Println(string(textData)) // И вот она, красота, вся структура как на ладони

2. А можно в JSON, это ж все любят!

Если тебе больше по душе JSON, который каждый фронтендер понимает, то protojson тебе в помощь. Тоже с отступами и переносами, чтоб не одна строка в километр.

import "google.golang.org/protobuf/encoding/protojson"

// Тот же самый msg
jsonData, err := protojson.MarshalOptions{Multiline: true, Indent: "  "}.Marshal(msg)
if err != nil {
    // Опа, опять что-то не так, блядь
}
fmt.Println(string(jsonData)) // Готово, можно хоть в постман копировать

3. Старая добрая консоль, если код писать лень

Сидишь ты такой, а у тебя просто бинарный файл my_message.bin валяется, и есть схема schema.proto. Зачем городить огород? Берёшь protoc и в одну строку всё делаешь!

# my_message.bin — это твои зашифрованные послания
# schema.proto — это инструкция по расшифровке, где лежит MyMessage
protoc --decode=MyMessage schema.proto < my_message.bin

И он тебе прямо в терминале всё красиво выведет. Волшебство, ёпта!

4. Разные приблуды для ленивых (как я)

  • grpcurl: Вообще огонь-утилита. Хочешь потыкать gRPC-сервис палкой, не вставая с кресла? Эта штука умеет. Загрузил .proto — и вперёд, запросы слать, ответы читать. Ни одной строчки кода!
  • Postman / Insomnia: Ну, эти ребята теперь тоже gRPC подвезли. Нажимаешь кнопочки, выбираешь прото-файл, и оп-па — весь трафик как на духу. Для тех, кто любит красивые окошки, а не консоль.

Важное предупреждение, нахуй!

Не забывай проверять ошибки, которые Unmarshal тебе возвращает, а то будешь потом чесать репу, почему данные не парсятся. Он тебе часто прямо говорит: «Чувак, тут в твоей схеме поле int32, а в данных какая-то хуйня лежит, я не могу!». Слушай его, этот err, он не просто так.