ソシャゲにおける
サーバとクライアントの
決めごと
自己紹介
@peto_tn
エンジニア
Java,Obj-C,C#を経てPHPとか
ソシャゲ
必ずクライアント(アプリ)とサーバの
通信が発生
通信する為には色々と取り決めが必要
決めること
ネットワークプロトコル
(HTTP, TCP/UDP)
データ形式
(XML, JSON, MessagePack, RPC)
ゲーム用プロトコル
(ゲーム用通信プロトコル)
プロトコルの管理方法
(仕様書, バージョン管理, 共通化保障)
セキュリティ
(SSL/TLS, 暗号化, 難読化)
決めること
ネットワークプロトコル
(HTTP, TCP/UDP)
データ形式
(XML, JSON, MessagePack, RPC)
ゲーム用プロトコル
(ゲーム用通信プロトコル)
プロトコルの管理方法
(仕様書, バージョン管理, 共通化保障)
セキュリティ
(SSL/TLS, 暗号化, 難読化)
ネットワークプロトコル
基本HTTPで片付く
リアルタイム通信が必要な場合はUDPを
(3G回線遅い)
UDPは不正確でいいデータのみに絞る
(現状リアルタイムは作ってません)
決めること
ネットワークプロトコル
(HTTP, TCP/UDP)
データ形式
(XML, JSON, MessagePack, RPC)
ゲーム用プロトコル
(ゲーム用通信プロトコル)
プロトコルの管理方法
(仕様書, バージョン管理, 共通化保障)
セキュリティ
(SSL/TLS, 暗号化, 難読化)
データ形式
選択肢は色々
XMLか JSONか MessagePackか?
RPCという手も?
独自シリアライズ作るか?
データ形式
 XML : 肥大化して遅くなりがち
 JSON : 可読性よい。割りと小さい
 MessagePack : バイナリ。小さく速い
 RPC : どうしても使いたかったら
 独自シリアライズ : 大変
MessagePackおすすめです
データ形式
<?xml version="1.0" encoding="UTF-8" ?>
<user_id>123456</user_id>
<name>hogehoge</name>
<age>20</age>
{"user_id":123456,
"name":"hogehoge",
"age":20}
83 a7 75 73 65 72 5f 69 64 ce 00 01 e2 40
a4 6e 61 6d 65 a8 68 6f 67 65 68 6f 67 65 a3
61 67 65 14 0a
XML
102 byte
JSON
51 byte
50%削減
MessagePack
34 byte
67%削減
データ形式
1通信  1リクエスト
1通信  複数リクエスト
一度に複数リクエストの方がよい
実装は複雑になる
データ形式
1通信  1リクエスト
Client Server
ユーザ情報
リクエスト
ユーザ情報
レスポンス
フレンド情報
リクエスト
フレンド情報
レスポンス
データ形式
1通信  複数リクエスト
Client Server
ユーザ情報
リクエスト
ユーザ情報
レスポンス
フレンド情報
リクエスト
フレンド情報
レスポンス
決めること
ネットワークプロトコル
(HTTP, TCP/UDP)
データ形式
(XML, JSON, MessagePack, RPC)
ゲーム用プロトコル
(ゲーム用通信プロトコル)
プロトコルの管理方法
(仕様書, バージョン管理, 共通化保障)
セキュリティ
(SSL/TLS, 暗号化, 難読化)
ゲーム用プロトコル
ユーザID, パスワード, ユーザ名
ゲームで必要なデータを設計
ログイン
アイテムID, 使用個数アイテム使用
ユーザID, フレンドIDフレンド申請
ゲーム用プロトコル
リクエストとレスポンス
フレンド一覧
取得
リクエスト
ユーザID
レスポンス
フレンド一覧
ゲーム用プロトコル
共通の定数
フレンド状態
0: フレンド未登録
1: フレンド申請中
2: フレンド登録済
ゲーム用プロトコル
全レスポンスの共通項目
リクエストの成否/エラー情報
メンテナンス情報
通信エラー
コード1000
OK
メンテナンス中
OK
決めること
ネットワークプロトコル
(HTTP, TCP/UDP)
データ形式
(XML, JSON, MessagePack, RPC)
ゲーム用プロトコル
(ゲーム用の通信プロトコル)
プロトコルの管理方法
(仕様書, バージョン管理, 共通化保障)
セキュリティ
(SSL/TLS, 暗号化, 難読化)
プロトコルの管理方法
クライアント/サーバで共有し参照する
資料
Excel, SpreadSheet etc.
概要 コマンド名 リクエスト レスポンス
ログイン login int: user_id
string: password
int: result
プロトコルの管理方法
Client Server
userid : 1234
password : hoge
user_id
が送られて
来ていない!
ログインする
からデータ
送るよ
プロトコルの管理方法
サーバ/クライアント両方に対して
確実にデータ構造を保障したい
共通の定義を記述し、サーバ用、クライ
アント用に自動コンバート/反映させる
プロトコルの管理方法
プロトコル
サーバ クライアント
プロトコルのコンバート
プロトコルの管理方法
{
“request”: {
“user_id”: {“type”: “int”, “comment”: “ユーザーID"}
},
"response": {
"result": {"type": "int", "comment": "結果"}
}
}
public class UserReq {
public int userId;
}
public class UserRes {
public int result;
}
public class MessageUserRequest {
public int UserId { get; set; }
}
public class MessageUserResponse {
public override int Result { get; set; }
}
定数のコンバート
プロトコルの管理方法
STATE_SEND_REQUEST,0,,フレンド未登録,
STATE_RECV_REQUEST,1,,申請中,
STATE_ACCEPTED,2,,フレンド登録済,
public final class ConstFriend {
public static final int STATE_SEND_REQUEST = 0;
public static final int STATE_RECV_REQUEST = 1;
public static final int STATE_ACCEPTED = 2;
}
public static class ConstFriend {
public const int STATE_SEND_REQUEST = 0;
public const int STATE_RECV_REQUEST = 1;
public const int STATE_ACCEPTED = 2;
}
マスタのコンバート
プロトコルの管理方法
id name rarity type
1 ゴブリン 1 1
2 ドラゴン 2 2
INSERT INTO `data_monsters` (`id`, `name`,
`rarity`, `type`) VALUES
(1, ‘ゴブリン’, 1, 1),
(2, ‘ドラゴン’, 2, 2);
1,ゴブリン,1,1
2,ドラゴン,2,2
DB
配信用
アセット
プロトコルの管理方法
クライアントとサーバのソースは
同一リポジトリに置いたほうが楽
リポジトリが肥大化してやばいなら、
別途安全な反映方法を検討する必要あり
プロトコルもバージョン管理へ
決めること
ネットワークプロトコル
(HTTP, TCP/UDP)
データ形式
(XML, JSON, MessagePack, RPC)
ゲーム用プロトコル
(ゲーム用の通信プロトコル)
プロトコルの管理方法
(仕様書, バージョン管理, 共通化保障)
セキュリティ
(SSL/TLS, 暗号化, 難読化)
セキュリティ
全ての通信に暗号化、難読化
アカウント、課金周りは細心の注意を!
SSL/TLS、各種暗号化
それでも不正はある
不正対策は十分行う
その他
アセットの配布方法
セッションの保持方法
などなど
最後に
色々ちゃんと決めとかないと死ぬ
変な決め方をしても死ぬ
ゲームにあった最適なものを採用!
ありがとうございました

ソシャゲにおけるサーバとクライアントの決めごと