Gaea源码阅读(五):C客户端

转载地址:http://blog.csdn.net/m_vptr/article/details/9245763

除了Java客户端外,Gaea还提供了C语言和.NET实现。


基本都是相同的,只是序列化/反序列化用C语言重新实现了。你可能会注意到一个特别的文件:Debug/conf/struct.conf ,这个文件曾经让我很迷惑。


实际上,gaea还提供了一个编译过的可执行文件FileScan,源代码位于src/structScan目录下,入口main被重命名为了mainY。


struct.conf就是通过FileScan按如下命令生成的,

FileScan -f 定义实体类的文件


FileScan.structScan扫描结构体定义文件,可识别struct、typedef定义。

结果保存到std::map<std::string, scanStructInfo*> structMap;

然后writeConfig保存到struct.conf中


产生的struct.conf每行一个结构体

ExceptionProtocol,-1300746967,32,0;fromIP,char,-139515017,16,1;errorCode,int,824862661,0,0;ErrorMsg,char,931829677,24,1;toIP,char,1461299386,8,1;

 

[cpp]  view plain  copy
  1. typedef struct {  
  2.     int errorCode;  
  3.     char *toIP;  
  4.     char *fromIP;  
  5.     char *ErrorMsg;  
  6. } ExceptionProtocol;  

一行一个实体,第一个分号之4个字段,后面的都是5个字段。


读取格式:

fieldname

typeId

//非首跳过

offset

isPointer


Client执行流程

//GeeaClientTest

[cpp]  view plain  copy
  1. int main(int argc, char *argv[]) {  
  2.     GaeaClientTest *ha = new GaeaClientTest();  
  3.     std::string configFile="/项目路径/c-gaea/Debug/conf/gaea.config";  
  4.     std::string s1 = "//项目路径/c-gaea/Debug/conf/struct.conf";  
  5.     std::string logFile = "//项目路径/c-gaea/Debug/conf/gaea.log"  
  6.     gaea::GaeaClientConfig().init(configFile,s1,logFile);  
  7.     ha->NewsServiceTest();}  
//首先加载配置以及实体类

gaea.config通过tinyxpath解析,然后注册实体类。

[cpp]  view plain  copy
  1. //structHelper.registerStruct  
  2.         sfi->typeId = atoi(c);  
  3.         key = malloc(sizeof(int));  
  4.         *key = sfi->typeId;  
  5.   
  6.         //扫描字段  
  7.         while{  
  8.             byteArrayPutData(value, sfi, sfiSize);  
  9.             ++cursor;  
  10.         }  
  11.   
  12.         //注册结构体id -> 结构体信息  
  13.         objc_hash_add(&structInfoMap, key, value);  


//客户端调用

ps->invoke("getNewsByCateID",NULL,0);


//构造RequestProtocol

[cpp]  view plain  copy
  1. //serviceProxy.  
  2.     RequestProtocol requestProtocol;  
  3.     requestProtocol.lookup = lookup;  
  4.     requestProtocol.methodName = methodName;  
  5.     requestProtocol.paraList = paraList;  
  6.     std::string sdpEntityType = "RequestProtocol";  
  7.   
  8.     Protocol sendP(sid, config->getServiceId(), Request, UnCompress, GAEABinary, Java, &requestProtocol, sdpEntityType.c_str());  
  9.   
  10. receiveP = server->request(sendP);  

//server.request

         char*data = p.getBytes(dataLen);


//Protocol.getBytes

         char*sdpData = Serialize(sdpEntityType, sdpEntity, &serDataLen);


//序列化Protocol

[cpp]  view plain  copy
  1. int typeId = GetTypeId(type);  
  2. serializerInfo info = { outArray:&retArray, hashcode:1000, refObjArray:&refObjArray };  
  3.   
  4. serializer sr = getSerializer(typeId, obj); //函数指针  
  5. sr(typeId, &info, obj); //提取typeId类型的obj对象信息,存到info中  

//默认getSerilizer返回structSeralizer

[cpp]  view plain  copy
  1. array *structInfo = objc_hash_value_for_key(structInfoMap, &typeId);  
  2.   
  3. for (i = 1; i < fieldLen; ++i) {  
  4.     newObj = obj + sfi->offset;  
  5.     if (sfi->isPointe == 1) {  
  6.         if (sfi->typeId == SERIALIZE_VOID_N) {  
  7.             t = *(int*) (obj + sfi->offset + sizeof(void*));  
  8.             sr = getSerializer(t, *(void**) newObj);  
  9.         } else {  
  10.             t = sfi->typeId;  
  11.             sr = getSerializer(sfi->typeId, *(void**) newObj);  
  12.         }  
  13.         if (sr != nullSerializer && sr != enumSerializer) {  
  14.             byteArrayPutData(info->outArray, &t, 4);  
  15.         }  
  16.         sr(t, info, *(void**) newObj);  
  17.     } else {  
  18.         sr = getSerializer(sfi->typeId, newObj);  
  19.         if (sr != nullSerializer && sr != enumSerializer) {  
  20.             byteArrayPutData(info->outArray, &sfi->typeId, 4);  
  21.         }  
  22.         sr(sfi->typeId, info, newObj);  
  23.     }  
  24.     ++sfi;  
  25. }  

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值