В сценариях применения сетевой связи и обмена данными в предыдущих проектах наиболее часто используемой технологией является json или xml. Благодаря гибким преимуществам JSON все больше и больше предприятий выбирают JSON в качестве формата обмена данными. В настоящее время JSON стал основным в отрасли. JSON достаточно прост в использовании и подходит для большинства сценариев. Но сегодня я представляю шедевр Google protobuf как формат обмена данными. Давайте посмотрим.
Githubадрес:GitHub - protocolbuffers/protobuf: Protocol Buffers - Google's data interchange format
官网адрес:Overview | Protocol Buffers Documentation
Protobuf (Protocol Buffers) — это легкий и эффективный формат обмена данными, разработанный Google. Он используется для сериализации, десериализации и передачи структурированных данных. По сравнению с текстовыми форматами, такими как XML и JSON, Protobuf имеет меньший объем данных, более высокую скорость анализа и более высокую масштабируемость. В то же время это независимый от языка, платформы и расширяемый формат сериализации. Это позволяет разработчикам определять структурированные данные в файле .proto, а затем использовать этот файл для создания исходного кода, который может записывать и читать данные из разных потоков данных.
Основная идея Protobuf — использование протоколов для определения структуры и кодирования данных. Протокол — это текстовый файл, определяющий структуру сообщения. Сообщения состоят из полей, каждое из которых имеет имя, тип и необязательное значение по умолчанию. Затем используйте декодер, предоставленный Protobuf, для создания соответствующего кода для сериализации и десериализации данных. Поскольку Protobuf основан на двоичном кодировании, его можно использовать на разных языках.
Protobuf поддерживает следующие типы данных:
Protobuf использует двоичный формат данных, который более компактен и быстрее читается и пишется, чем текстовые форматы. Он также предоставляет язык определения интерфейса (IDL), позволяющий легко определить структуру данных, подлежащих сериализации.
Файлы Protobuf сохраняются с расширением .proto. Файл .proto написан в формате IDL Protobuf и содержит всю информацию о структуре данных. Данные моделируются как «сообщения», которые представляют собой пары имя/значение. Вот пример простого сообщения Protobuf в файле .proto:
// обозначение Protobuf Версия есть версия 3 (последняя версия)
syntax = "proto3";
// обозначениеprotobufимя пакета,Предотвращение дублирования названий классов
package com.shamee.protobuf;
// В каком пакете хранятся сгенерированные файлы?
option java_package = "com.shamee.protos";
// Создать имя класса,если необозначение,Имя файла будет автоматически преобразовано в верблюжий регистр.
option java_outer_classname = "PersonProtos";
// Определяет класс Person
message Person {
// Следующее из значений (=1 =2) Как сериализация после двоичного кодирования поля из уникальной метки
// поэтому соотношение 1-15 16 Это будет на один байт меньше, поэтому попробуйте использовать 1-15 Перейдите к изображению общих полей.
int32 id = 1;
string name = 2;
string email = 3;
string address = 4;
}
В этом примере сообщение клиента содержит четыре поля: идентификатор, имя, адрес электронной почты и адрес. Каждое поле имеет указание его типа, а также метку, указывающую, является ли оно обязательным, необязательным или повторяющимся.
Файл .proto можно скомпилировать в различные языки программирования с помощью Protoc, компилятора Protobuf. Компилятор генерирует исходный код на языке программирования, указанном разработчиком. Исходный код включает классы и методы для записи, чтения и управления типами сообщений, определенными в файле .proto.
Если у вас есть данные для хранения или передачи, вы можете создавать экземпляры сгенерированных классов и заполнять их своими данными. Эти экземпляры затем сериализуются в двоичный формат. Когда данные считываются, двоичный формат десериализуется обратно в экземпляр класса, созданный из файла .proto. Это дает вам легкий доступ к структурированным данным.
Формат двоичных данных, создаваемый Protobuf, не зависит от платформы и может использоваться для обмена данными между различными системами, приложениями или сервисами, даже если они реализованы на разных языках программирования или работают на разных платформах.
Определенный выше .proto можно скомпилировать на разные языки с помощью компилятора Protobbuf (Protoc).
скачатькомпилироватьустройство:Release Protocol Buffers v25.3 · protocolbuffers/protobuf · GitHub
Команда компиляции выглядит следующим образом: скомпилируйте файл .proto в JavaScript:
protoc --js_out=import_style=commonjs,binary: .customers.proto
Скомпилировано на языке Java:
protoc --java_out=./my_dist .customers.proto
Вышеуказанное знакомит с основным содержанием protobuf, а также с написанием и компиляцией простого синтаксиса. Далее мы воспользуемся им и интегрируем в наш Springboot.
<dependency>
<groupId>com.google.protobuf</groupId>
<artifactId>protobuf-java</artifactId>
<version>3.6.1</version>
</dependency>
<!-- В то же время добавьте плагин maven для компиляции protobuf для генерации java-файлов. -->
<build>
<extensions>
<extension>
<groupId>kr.motd.maven</groupId>
<artifactId>os-maven-plugin</artifactId>
<version>1.5.0.Final</version>
</extension>
</extensions>
<plugins>
<plugin>
<groupId>org.xolstice.maven.plugins</groupId>
<artifactId>protobuf-maven-plugin</artifactId>
<version>0.5.0</version>
<configuration>
<protocArtifact>
com.google.protobuf:protoc:3.1.0:exe:${os.detected.classifier}
</protocArtifact>
<!--значение по умолчанию,protoПуть к исходному файлу-->
<protoSourceRoot>${project.basedir}/src/main/resources/proto</protoSourceRoot>
<pluginId>grpc-java</pluginId>
<!--да Очистить ли указанный выше каталог конфигурацииoutputDirectory-->
<clearOutputDirectory>false</clearOutputDirectory>
</configuration>
<executions>
<execution>
<goals>
<goal>compile</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
<version>3.3.0</version>
<configuration>
<excludes>
<exclude>**/*.proto</exclude>
</excludes>
</configuration>
</plugin>
</plugins>
</build>
Определите два файла прототипов: один для получения данных запроса интерфейса Person.proto и один для ответа на Response.proto.
Person.proto:
syntax = "proto3";
package proto.shamee;
// В каком пакете хранятся сгенерированные файлы?
option java_package = "proto.shamee";
// Создать имя класса,если необозначение,Имя файла будет автоматически преобразовано в верблюжий регистр.
option java_outer_classname = "PersonProto";
// Определяет класс Person
message Person {
// Следующее из значений (=1 =2) Как сериализация после двоичного кодирования поля из уникальной метки
// поэтому соотношение 1-15 16 Это будет на один байт меньше, поэтому попробуйте использовать 1-15 Перейдите к изображению общих полей.
int32 id = 1;
string name = 2;
string email = 3;
string address = 4;
}
Response.proto:
syntax = "proto3";
package proto.shamee;
option java_package = "proto.shamee";
option java_outer_classname = "ResponseProto";
message Response {
int32 code = 1;
string message = 2;
string data = 3;
}
После завершения определения вы можете напрямую установить mvn, чтобы сгенерировать соответствующий прототип Java-кода.
@Configuration
public class ProtobufConfig {
/**
* protobuf сериализация
*/
@Bean
ProtobufHttpMessageConverter protobufHttpMessageConverter() {
return new ProtobufHttpMessageConverter();
}
/**
* protobuf противоположныйсериализация */
@Bean
RestTemplate restTemplate(ProtobufHttpMessageConverter protobufHttpMessageConverter) {
return new RestTemplate(Collections.singletonList(protobufHttpMessageConverter));
}
}
Поскольку protobuf передает данные на основе двоичных потоков, здесь необходимо указать протокол x-protobuf.
@RestController
@RequestMapping("/test")
public class TestController {
@PostMapping(value = "/index", produces = "application/x-protobuf")
public ResponseProto.Response index(@RequestBody PersonProto.Person person){
return ResponseProto.Response.newBuilder()
.setCode(200)
.setMessage("OK")
.setData("hello:" + person.getName()).build();
}
}
Затем вы можете запустить проект Springboot.
При доступе сюда вам необходимо определить тип содержимого заголовка, а параметры передаются и доступны как двоичные данные. Данные нашего запроса:
Доступ к конфигурации заголовка:
возвращаться:
На данный момент мы просто выучили protobuf и можем спокойно перекусывать в полночь.
protobuf по-прежнему имеет некоторые проблемы во всей интеграции. Например, если номера версий ptobuf слишком сильно различаются, компиляция не пройдет. Конечно, у protobuf есть и недостатки:
Protobuf — отличный формат сериализации, но он не идеален. При выборе формата сериализации необходимо учитывать всесторонние соображения, основанные на реальных потребностях. Если вам нужен эффективный, компактный и масштабируемый формат сериализации, Protobuf — хороший выбор. Но если вам нужно представлять сложные концепции, быть универсальными или не требующими пояснений, вам необходимо рассмотреть другие форматы сериализации.