您的位置:首页 > 其它

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

2013-07-05 11:17 183 查看
除了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;

typedef struct {
int errorCode;
char *toIP;
char *fromIP;
char *ErrorMsg;
} ExceptionProtocol;


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

读取格式:

fieldname

typeId

//非首跳过

offset

isPointer

Client执行流程

//GeeaClientTest

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

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

//structHelper.registerStruct
sfi->typeId = atoi(c);
key = malloc(sizeof(int));
*key = sfi->typeId;

//扫描字段
while{
byteArrayPutData(value, sfi, sfiSize);
++cursor;
}

//注册结构体id -> 结构体信息
objc_hash_add(&structInfoMap, key, value);


//客户端调用
ps->invoke("getNewsByCateID",NULL,0);

//构造RequestProtocol

//serviceProxy.
RequestProtocol requestProtocol;
requestProtocol.lookup = lookup;
requestProtocol.methodName = methodName;
requestProtocol.paraList = paraList;
std::string sdpEntityType = "RequestProtocol";

Protocol sendP(sid, config->getServiceId(), Request, UnCompress, GAEABinary, Java, &requestProtocol, sdpEntityType.c_str());

receiveP = server->request(sendP);


//server.request

char*data = p.getBytes(dataLen);

//Protocol.getBytes

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

//序列化Protocol

int typeId = GetTypeId(type);
serializerInfo info = { outArray:&retArray, hashcode:1000, refObjArray:&refObjArray };

serializer sr = getSerializer(typeId, obj); //函数指针
sr(typeId, &info, obj); //提取typeId类型的obj对象信息,存到info中


//默认getSerilizer返回structSeralizer

array *structInfo = objc_hash_value_for_key(structInfoMap, &typeId);

for (i = 1; i < fieldLen; ++i) {
newObj = obj + sfi->offset;
if (sfi->isPointe == 1) {
if (sfi->typeId == SERIALIZE_VOID_N) {
t = *(int*) (obj + sfi->offset + sizeof(void*));
sr = getSerializer(t, *(void**) newObj);
} else {
t = sfi->typeId;
sr = getSerializer(sfi->typeId, *(void**) newObj);
}
if (sr != nullSerializer && sr != enumSerializer) {
byteArrayPutData(info->outArray, &t, 4);
}
sr(t, info, *(void**) newObj);
} else {
sr = getSerializer(sfi->typeId, newObj);
if (sr != nullSerializer && sr != enumSerializer) {
byteArrayPutData(info->outArray, &sfi->typeId, 4);
}
sr(sfi->typeId, info, newObj);
}
++sfi;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: