遊戲伺服器和用戶端的通信有很多種形式,有的用http,有的用websocket,不過最常見的還是socket伺服器,socket 伺服器在遊戲中是最常見的,至于為什麼和怎麼建立,等以後再說,今天先來聊聊伺服器和用戶端交談的協定。協定的定義是服務端和用戶端溝通的結果,形成一緻的資料格式,這樣大家才好解析,知道對方在說什麼,在做什麼。
在最初的時候有的人自定義格式,雖然緊湊,但是可能會存在一些問題,不夠穩定。也有的人用xml,也有人用json,存在的問題就是格式雖然很好,但是網絡包太大,不太适合,問題存在必然就要解決,有沒有一種方案可以解決上面的問題?答案顯而易見,就是今天聊的protobuf。
protobuf 是谷歌開源的跨平台的一種通訊協定,更緊湊,更高效。廢話不多說,進入正文。
1、Java項目引用
pom.xml 中加入以下依賴,版本可以自己根據需要進行選擇
com.google.protobuf protobuf-java 3.6.1
2、protobuf 的檔案定義格式
option java_package ="com.gamwatcher.soulmsg";option java_outer_classname = "SoulMsg";option java_multiple_files = true;message SOUL_UP_OUT{ required int64 uid =1; repeated int64 costuid =2; optional int64 useExp = 3;}
基礎類型
.proto類型 | java類型 | 備注 |
---|---|---|
double | double | |
float | float | |
int32 | int | 使用可變長編碼方式。編碼負數時不夠高效——如果你的字段可能含有負數,那麼請使用sint32。 |
int64 | long | 使用可變長編碼方式。編碼負數時不夠高效——如果你的字段可能含有負數,那麼請使用sint64。 |
unit32 | int[1] | 總是4個位元組。如果數值總是比總是比228大的話,這個類型會比uint32高效。 |
unit64 | long[1] | 總是8個位元組。如果數值總是比總是比256大的話,這個類型會比uint64高效。 |
sint32 | int | 使用可變長編碼方式。有符号的整型值。編碼時比通常的int32高效。 |
sint64 | long | 使用可變長編碼方式。有符号的整型值。編碼時比通常的int64高效。 |
fixed32 | int[1] | |
fixed64 | long[1] | 總是8個位元組。如果數值總是比總是比256大的話,這個類型會比uint64高效。 |
sfixed32 | int | 總是4個位元組。 |
sfixed64 | long | 總是8個位元組。 |
bool | boolean | |
string | String | 一個字元串必須是UTF-8編碼或者7-bit ASCII編碼的文本。 |
bytes | ByteString | 可能包含任意順序的位元組資料 |
特殊字段
英文 | 中文 | 備注 |
---|---|---|
enum | 枚舉(數字從零開始) 作用是為字段指定某”預定義值序列” | enum Type {MAN = 0;WOMAN = 1; OTHER= 3;} |
message | 消息體 | message User{} |
repeated | 數組/集合 | repeated User users = 1 |
import | 導入定義 | import "protos/other_protos.proto" |
// | 注釋 | //用于注釋 |
extend | 擴充 | extend User {} |
package | 包名 | 相當于命名空間,用來防止不同消息類型的明明沖突 |
2、生成java類
下載下傳protoc:https://github.com/protocolbuffers/protobuf/releases
protoc.exe --java_out = ../../src/main/java **.proto
3、使用協定
SOUL_UP_OUT.Builder builder = SOUL_UP_OUT.newBuilder();builder.setUid(1);builder.addAllCostUid(costUidList);builder.setUserExp(1000)builder.build()
4、如何在遊戲項目中使用
正常的協定格式:
len + 加密的 [headMsgId + proto二進制資料]
常用的加密算法:AES和rsa,DES,選擇一個簡單的效率高的,如果遊戲大火了可以換一個稍微複雜的加密算法,小事情,不重要
用戶端解析出根據長度讀出資料長度進行解析。so easy!!!,服務端同樣的規則。用戶端和伺服器通信就是這麼簡單。
總結:protobuf 不過是一個協定格式,省去了我們自定義消息的過程,既然有現成的輪子就沒必要自己造了,況且我們造的還不如别人,先會用,再去了解原理,沒什麼大不了。