云风在skynet中继承了sproto的传输协议,对比protobuf的好处是,能明文看到传输内容,而且skynet不需要protobuf这么功能,所以云风也建议在lua层使用sproto来作为skynet的传输协议。

在examples文件夹中的agent.lua中有用到sproto的例子。下面讲解一下sproto的使用过程和原理:

proto.lua的文件中包含一个实例协议:

 local sprotoparser = require "sprotoparser"

 local proto = {}

 proto.c2s = sprotoparser.parse [[
.package {
type 0 : integer
session 1 : integer
} handshake 1 {
response {
msg 0 : string
}
} get 2 {
request {
what 0 : string
}
response {
result 0 : string
}
} set 3 {
request {
what 0 : string
value 1 : string
}
} quit 4 {} ]] proto.s2c = sprotoparser.parse [[
.package {
type 0 : integer
session 1 : integer
} heartbeat 1 {}
]] return proto

proto.c2s是客户端发送个服务端的协议,proto.s2c是服务端发送客户端的协议。

sproto的协议变量类型有integer、string、boolean。sproto协议也可以实现结构体和数组、字典。

结构体的实现可以仿造.package,结构体开头必须是以“.”开头,"."后面的是结构体的名字,

字典和数组的实现是类似于c指针,例子如下:

 local s2c = [[

 protoName 1 {

   request {

     arg1 0 :integer

     arg2 1 :*value(key)

   }

 }

 ]]

如果服务端要发送玩家拥有的角色信息的数组,key就是角色数组的索引数据类型,如果角色数组的索引是角色id的话,id类型是integer类型,那么key就是“integer”,

value是角色数组的头元素。

sproto协议中也可以加注释:在注释内容前加上“#”符号。

sprotoparser.parse是通过sprotoparser.lua中的parse方法将协议解析成一个table,过程需要用到lpeg的库来进行匹配。笔者到现在还没弄懂这个parse过程,哈哈。。。

首先看看client.lua中的sproto的实现过程,

local sproto = require "sproto"

local host = sproto.new(proto.s2c):host "package"

local request = host:attach(sproto.new(proto.c2s))

sproto.new(proto.s2c):将proto.s2c闯入sproto.lua中,通过c的lsproto.c文件中的newproto方法将协议数据保存在sproto结构体中,sproto协议作为全局变量,一般情况下不需要gc,

最后返回一个sproto的table,具体实现还是要看看sproto.lua文件比较好理解。

host("package")是返回的sproto的table中查找“package”包头,也就是.package结构体,和一些host的方法保存在一个新的table中,这个有点难理解,所以还是看看实现过程。

host:attach(sproto.new(proto.c2s))是通过上一步返回包头协议,绑定在c2s的协议,返回一个负责打包协议的函数体,每次调用该函数时,传入要打包的协议名,参数,和session就可以

得到一个协议结构体,例如:

 send_request("set", { what = "hello", value = "world" })

skynet 学习笔记-sproto模块(2)的更多相关文章

  1. skynet 学习笔记-netpack模块(1)

    int luaopen_netpack(lua_State *L) { luaL_checkversion(L); luaL_Reg l[] = { { "pop", lpop } ...

  2. Python学习笔记—itertools模块

    这篇是看wklken的<Python进阶-Itertools模块小结> 学习itertools模块的学习笔记 在看itertools中各函数的源代码时,刚开始还比较轻松,但后面看起来就比较 ...

  3. Python学习笔记之模块与包

    一.模块 1.模块的概念 模块这一概念很大程度上是为了解决代码的可重用性而出现的,其实这一概念并没有多复杂,简单来说不过是一个后缀为 .py 的 Python 文件而已 例如,我在某个工作中经常需要打 ...

  4. Python3学习笔记25-logging模块

    logging模块,Python自带用来记录日志的模块. 因为工作需要用到关于日志的,最近一直都在看关于日志模块的东西,百度了很多文章,可惜都是看的让人一头雾水,最后运气不错,找到一篇很详细的文章.传 ...

  5. Scikit-Learn模块学习笔记——数据集模块datasets

    scikit-learn 的 datasets 模块包含测试数据相关函数,主要包括三类: datasets.load_*():获取小规模数据集.数据包含在 datasets 里 datasets.fe ...

  6. node 学习笔记 - Modules 模块加载系统 (1)

    本文同步自我的个人博客:http://www.52cik.com/2015/12/11/learn-node-modules-path.html 用了这么久的 require,但却没有系统的学习过 n ...

  7. python学习笔记五 模块上(基础篇)

    模块学习 模块,用一砣代码实现了某个功能的代码集合. 类似于函数式编程和面向过程编程,函数式编程则完成一个功能,其他代码用来调用即可,提供了代码的重用性和代码间的耦合.而对于一个复杂的功能来,可能需要 ...

  8. 网上图书商城项目学习笔记-011Book模块查询(分页)

    一.流程分析 1.图书模块 2.分布分析 二.代码 1.view层 1)list.jsp <%@ page language="java" import="java ...

  9. angular2 学习笔记 ( ngModule 模块 )

    2016-08-25, 当前版本是 RC 5. 参考 : https://angular.cn/docs/ts/latest/guide/ngmodule.html 提醒 : 这系列笔记的 " ...

随机推荐

  1. 洛谷P3200 [HNOI2009]有趣的数列(Catalan数)

    P3200 [HNOI2009]有趣的数列 题目描述 我们称一个长度为2n的数列是有趣的,当且仅当该数列满足以下三个条件: (1)它是从1到2n共2n个整数的一个排列{ai}: (2)所有的奇数项满足 ...

  2. Mac环境下制作ubantu安装盘

    前言:ubantu为Linux发行版之一,此方法亦可制作其他Linux发行版 1.在磁盘工具中将准备好的u盘格式化为Mac OS扩展(日志型),并确保分区的模式是GUID分区 2.官网自行下载uban ...

  3. POJ 3299

    #include <iostream> #include "math.h" double e2h(double e) { return 0.5555*(e-10.0); ...

  4. Hive进阶_开发Hive的自定义函数

    Hive中的自定义函数简介 (1) 在类中创建自定义函数.自定义UDF需要继承'org.apache.hadoop.hive.ql.exec.UDF',实现evaluate函数,evaluate函数支 ...

  5. redis最佳实践

    总结: String类型的value(string/list/set/hash)使用StringRedisTemplate 其他类型的value(string/list/set/hash/object ...

  6. Consul实现服务治理

    .NET Core微服务之基于Consul实现服务治理 https://www.cnblogs.com/edisonchou/p/9124985.html 一.Consul基础介绍 Consul是Ha ...

  7. 批量插入,update

    #####setting 1create table t as select * from all_objects where 1 =2; ###.模拟逐行提交的情况,注意观察执行时间DECLAREB ...

  8. docker jetty启动时报错 failed setting default capabilities.

    docker 容器中jetty启动fail ,查看/var/log/jetty中的日志发现具体错误信息如下: failed setting default capabilities.set_caps( ...

  9. Linux 解压压缩war包

    jar -xvf aaa.war   (jar只能解压war 包到当前目录下) unzip aaa.war -d aaa/   (解压war包到aaa目录下) 打包aaa 下的所有文件为aaa.war ...

  10. CentOS7.2配置本地yum源

    1.检查是否有本地yum源 1)检查是否能连网 ping www.baidu.com 2)检查是否有本地yum源 yum list 2.挂载镜像文件 以上检查,说明确实是内网,也确实没有本地yum源, ...