протобуф нужен сетевой заголовок пакета? - PullRequest
8 голосов
/ 15 ноября 2011

Я использую protobuf для сетевой программы C / S, использующей TCP.

вот мои шаги для клиента:

1, упаковать данные в «protobuf»

2, получить размер в байтах пакета и построить рамку с префиксом длины

3, запишите кадр + пакет в сокет

и затем сервер:

1, прочитайте длину префикса кадра из сокета и получите длину N

2, прочитать N байтов из сокета и заполнить данные в экземпляре protobuf

3, получить "значения" из protobuf по "ключу" s

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

Ответы [ 2 ]

6 голосов
/ 16 ноября 2011

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

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

Лично я склонен делать вид, что последовательность данных является частью последовательности repeated - то есть префикс с «полем 1, строка» (он же 0a) и длиной в кодировке «varint». Это означает, что весь сетевой поток является допустимым потоком protobuf. Впрочем, это может быть только мой ОКР.

В некоторые реализации могут быть включены функции, помогающие с этим. Например, protobuf-net (одна из версий .NET) имеет методы SerializeWithLengthPrefix / DeserializeWithLengthPrefix, что позволяет библиотеке делать это за вас (предлагая широкий выбор форматов на ваш выбор).

3 голосов
/ 15 ноября 2011

Я не знаю, подходит ли это для вашего назначения, но я рассмотрю одну из «реализаций rpc», уже написанных для языка (языков), который вы хотите поддерживать.

http://code.google.com/p/protobuf/wiki/ThirdPartyAddOns#RPC_Implementations

например. У меня были хорошие результаты в Java со встроенной поддержкой Netty для отправки MessageLite экземпляров заданного типа: http://docs.jboss.org/netty/3.2/guide/html/architecture.html#d0e1979

(я уверен, что ваш заголовок длины будет работать нормально, но фреймворки, такие как Netty, добавят поддержку таких вещей, как асинхронный «дуплексный» ввод-вывод, SSL, аутентификация и т. Д., Относительно легко)

НТН

...