hjr-MUD遊戲(五):字符串與二進制與protobuf通信

網絡通信時通常我們傳輸字符串或二進制
這裏以websocket爲例,

傳輸字符串在frame->ws中能夠看到每次通信傳輸的內容
傳輸二進制只能看到 Binary Frame

字符串

一般傳輸字符串可以直接傳輸json,協議頭可以採用

{"login":{"username":"' + username + '","password":"' + password + '"}}'

這種方式表明 協議頭爲login數據爲{"username":"' + username + '","password":"' + password + '"},到了後端,直接轉化成JSONArray,然後遍歷既可以取出頭部和數據內容。

二進制

傳輸二進制一般使用protobuf就可以

		byte.writeInt(123);
	    byte.writeBytes("數據");

協議頭爲123 數據爲 數據,然後後端就可以根據協議頭判斷是什麼請求了,byte可以寫類型還有 writeShort等,區別在於字節長度不同,用什麼長度寫,後臺 就要用什麼長度讀。
比如 java ByteBuffer

  int  header = byteBuffer.getInt();

這樣就可以把協議頭讀取出來了,然後再接着讀取byteBuffer,比如轉化protobuf格式。

protobuf

這是谷歌推出的二進制通信工具

  • java
    pom
   <!-- protobuf依賴-->
        <dependency>
            <groupId>com.google.protobuf</groupId>
            <artifactId>protobuf-java</artifactId>
            <version>3.6.0</version>
        </dependency>
        <dependency>
            <groupId>com.googlecode.protobuf-java-format</groupId>
            <artifactId>protobuf-java-format</artifactId>
            <version>1.4</version>
        </dependency>

配置文件

@Configuration
public class ProtobufConfig {
    /**
     * protobuf 序列化
     */
    @Bean
    ProtobufHttpMessageConverter protobufHttpMessageConverter() {
        return new ProtobufHttpMessageConverter();
    }

    /**
     * protobuf 反序列化
     */
    @Bean
    RestTemplate restTemplate(ProtobufHttpMessageConverter protobufHttpMessageConverter) {
        return new RestTemplate(Collections.singletonList(protobufHttpMessageConverter));
    }
}

使用
先新建一個game_msg.proto文件

syntax = "proto3";
package com.xxx.xxx.xxx;

message Msg {
    string type = 1;
    string json = 2;
}

然後下載protoc.exe把文件轉化爲class,在github上下載,不要選帶語言的,那是源碼,選擇windows x64。
添加環境變量,然後運行如下指令

protoc --java_out=./admin/src/main/java ./admin/src/main/java/game_msg.proto
//protoc --java_out=輸出路徑 .proto文件路徑

下面是操作protobuf

     GameMsg.Msg.Builder builder = GameMsg.Msg.newBuilder();    
     builder = builder.mergeFrom(conver(byteBuffer));//byte[]轉protobuf
     builder.build().toByteArray();//protobuf轉byte[]
  

        System.out.println("來自客戶端的消息:" +         builder.getType()+";"+builder.getJson());

    //ByteBuffer 轉化 byte[]必須調用完後flip()纔可以調用此方法
    public static byte[] conver(ByteBuffer byteBuffer){
        int len = byteBuffer.limit() - byteBuffer.position();
        byte[] bytes = new byte[len];

        if(byteBuffer.isReadOnly()){
            return null;
        }else {
            byteBuffer.get(bytes);
        }
        return bytes;
    }
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章