support simple json tars2json

This commit is contained in:
ruanshudong 2019-11-30 20:01:04 +08:00
parent 26771398b7
commit bf07a8015a
6 changed files with 2195 additions and 334 deletions

768
servant/tup/TarsJson.h Normal file
View File

@ -0,0 +1,768 @@
#ifndef __TARS_JSON_H__
#define __TARS_JSON_H__
#include <iostream>
#include <cassert>
#include <vector>
#include <map>
#include <string>
#include <stdexcept>
#include <string.h>
#include "util/tc_json.h"
#include "util/tc_common.h"
namespace tars
{
class JsonInput
{
public:
static void readJson(Bool& b, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeBoolean)
{
b = JsonValueBooleanPtr::dynamicCast(p)->value;
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'Bool' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
static void readJson(Char& c, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeNum)
{
c = (char)JsonValueNumPtr::dynamicCast(p)->value;
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'Char' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
static void readJson(UInt8& n, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeNum)
{
n = (UInt8)JsonValueNumPtr::dynamicCast(p)->value;
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'Uint8' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
static void readJson(Short& n, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeNum)
{
n = (Short)JsonValueNumPtr::dynamicCast(p)->value;
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'Short' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
static void readJson(UInt16& n, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeNum)
{
n = (UInt16)JsonValueNumPtr::dynamicCast(p)->value;
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'Uint16' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
static void readJson(Int32& n, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeNum)
{
n = (Int32)JsonValueNumPtr::dynamicCast(p)->value;
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'Int32' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
static void readJson(UInt32& n, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeNum)
{
n = (UInt32)JsonValueNumPtr::dynamicCast(p)->value;
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'UInt32' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
static void readJson(Int64& n, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeNum)
{
n = (Int64)JsonValueNumPtr::dynamicCast(p)->value;
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'Int64' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
static void readJson(Float& n, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeNum)
{
n = (Float)JsonValueNumPtr::dynamicCast(p)->value;
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'Float' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
static void readJson(Double& n, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeNum)
{
n = JsonValueNumPtr::dynamicCast(p)->value;
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'Double' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
static void readJson(std::string& s, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeString)
{
s = JsonValueStringPtr::dynamicCast(p)->value;
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'string' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
static void readJson(char *buf, const UInt32 bufLen, UInt32 & readLen, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeString)
{
JsonValueStringPtr pString=JsonValueStringPtr::dynamicCast(p);
if((UInt32)pString->value.size()>bufLen)
{
char s[128];
snprintf(s, sizeof(s), "invalid char * size, size: %u", (UInt32)pString->value.size());
throw TC_Json_Exception(s);
}
memcpy(buf,pString->value.c_str(),pString->value.size());
readLen = (UInt32)pString->value.size();
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'char *' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename V, typename Cmp, typename Alloc>
static void readJson(std::map<string, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
auto iter=pObj->value.begin();
for(;iter!=pObj->value.end();++iter)
{
std::pair<string, V> pr;
pr.first=iter->first;
readJson(pr.second,iter->second);
m.insert(pr);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'map' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename V, typename Cmp, typename Alloc>
static void readJson(std::map<bool, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
auto iter=pObj->value.begin();
for(;iter!=pObj->value.end();++iter)
{
std::pair<bool, V> pr;
pr.first=TC_Common::strto<bool>(iter->first);
readJson(pr.second,iter->second);
m.insert(pr);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'map' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename V, typename Cmp, typename Alloc>
static void readJson(std::map<Char, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
auto iter=pObj->value.begin();
for(;iter!=pObj->value.end();++iter)
{
std::pair<Char, V> pr;
pr.first=TC_Common::strto<Int32>(iter->first);
readJson(pr.second,iter->second);
m.insert(pr);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'map' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename V, typename Cmp, typename Alloc>
static void readJson(std::map<UInt8, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
auto iter=pObj->value.begin();
for(;iter!=pObj->value.end();++iter)
{
std::pair<UInt8, V> pr;
pr.first=TC_Common::strto<UInt8>(iter->first);
readJson(pr.second,iter->second);
m.insert(pr);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'map' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename V, typename Cmp, typename Alloc>
static void readJson(std::map<Short, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
auto iter=pObj->value.begin();
for(;iter!=pObj->value.end();++iter)
{
std::pair<Short, V> pr;
pr.first=TC_Common::strto<Short>(iter->first);
readJson(pr.second,iter->second);
m.insert(pr);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'map' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename V, typename Cmp, typename Alloc>
static void readJson(std::map<UInt16, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
auto iter=pObj->value.begin();
for(;iter!=pObj->value.end();++iter)
{
std::pair<UInt16, V> pr;
pr.first=TC_Common::strto<UInt16>(iter->first);
readJson(pr.second,iter->second);
m.insert(pr);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'map' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename V, typename Cmp, typename Alloc>
static void readJson(std::map<Int32, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
auto iter=pObj->value.begin();
for(;iter!=pObj->value.end();++iter)
{
std::pair<Int32, V> pr;
pr.first=TC_Common::strto<Int32>(iter->first);
readJson(pr.second,iter->second);
m.insert(pr);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'map' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename V, typename Cmp, typename Alloc>
static void readJson(std::map<UInt32, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
auto iter=pObj->value.begin();
for(;iter!=pObj->value.end();++iter)
{
std::pair<UInt32, V> pr;
pr.first=TC_Common::strto<UInt32>(iter->first);
readJson(pr.second,iter->second);
m.insert(pr);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'map' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename V, typename Cmp, typename Alloc>
static void readJson(std::map<Int64, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
auto iter=pObj->value.begin();
for(;iter!=pObj->value.end();++iter)
{
std::pair<Int64, V> pr;
pr.first=TC_Common::strto<Int64>(iter->first);
readJson(pr.second,iter->second);
m.insert(pr);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'map' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename V, typename Cmp, typename Alloc>
static void readJson(std::map<Float, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
auto iter=pObj->value.begin();
for(;iter!=pObj->value.end();++iter)
{
std::pair<Float, V> pr;
pr.first=TC_Common::strto<Float>(iter->first);
readJson(pr.second,iter->second);
m.insert(pr);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'map' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename V, typename Cmp, typename Alloc>
static void readJson(std::map<Double, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
auto iter=pObj->value.begin();
for(;iter!=pObj->value.end();++iter)
{
std::pair<Double, V> pr;
pr.first=TC_Common::strto<Double>(iter->first);
readJson(pr.second,iter->second);
m.insert(pr);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'map' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename K, typename V, typename Cmp, typename Alloc>
static void readJson(std::map<K, V, Cmp, Alloc>& m, const JsonValuePtr & p, bool isRequire = true)
{
char s[128];
snprintf(s, sizeof(s), "map key is not Basic type. map key is only string|bool|num");
throw TC_Json_Exception(s);
}
template<typename T, typename Alloc>
static void readJson(std::vector<T, Alloc>& v, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeArray)
{
JsonValueArrayPtr pArray=JsonValueArrayPtr::dynamicCast(p);
v.resize(pArray->value.size());
for(size_t i=0;i<pArray->value.size();++i)
{
readJson(v[i],pArray->value[i]);
}
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'vector' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
/// 读取结构数组
template<typename T>
static void readJson(T* v, const UInt32 len, UInt32 & readLen, const JsonValuePtr & p, bool isRequire = true)
{
if(NULL != p.get() && p->getType() == eJsonTypeArray)
{
JsonValueArrayPtr pArray=JsonValueArrayPtr::dynamicCast(p);
if(pArray->value.size()>len)
{
char s[128];
snprintf(s, sizeof(s), "read 'T *' invalid size, size: %u", (uint32_t)pArray->value.size());
throw TC_Json_Exception(s);
}
for(size_t i=0;i<pArray->value.size();++i)
{
readJson(v[i],pArray->value[i]);
}
readLen=pArray->value.size();
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'T *' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
template<typename T>
static void readJson(T& v, const JsonValuePtr & p, bool isRequire = true, typename detail::disable_if<detail::is_convertible<T*, TarsStructBase*>, void ***>::type dummy = 0)
{
Int32 n = 0;
readJson(n, p, isRequire);
v = (T) n;
}
/// 读取结构
template<typename T>
static void readJson(T& v, const JsonValuePtr & p, bool isRequire = true, typename detail::enable_if<detail::is_convertible<T*, TarsStructBase*>, void ***>::type dummy = 0)
{
if(NULL != p.get() && p->getType() == eJsonTypeObj)
{
JsonValueObjPtr pObj=JsonValueObjPtr::dynamicCast(p);
v.readFromJson(pObj);
}
else if (isRequire)
{
char s[128];
snprintf(s, sizeof(s), "read 'Char' type mismatch, get type: %d.", p->getType());
throw TC_Json_Exception(s);
}
}
};
class JsonOutput
{
public:
static JsonValueBooleanPtr writeJson(Bool b)
{
JsonValueBooleanPtr p = new JsonValueBoolean();
p->value=b;
return p;
}
static JsonValueNumPtr writeJson(Char n)
{
return (new JsonValueNum(n,true));
}
static JsonValueNumPtr writeJson(UInt8 n)
{
return (new JsonValueNum(n,true));
}
static JsonValueNumPtr writeJson(Short n)
{
return (new JsonValueNum(n,true));
}
static JsonValueNumPtr writeJson(UInt16 n)
{
return (new JsonValueNum(n,true));
}
static JsonValueNumPtr writeJson(Int32 n)
{
return (new JsonValueNum(n,true));
}
static JsonValueNumPtr writeJson(UInt32 n)
{
return (new JsonValueNum(n,true));
}
static JsonValueNumPtr writeJson(Int64 n)
{
return (new JsonValueNum((double)n,true));
}
static JsonValueNumPtr writeJson(Float n)
{
return (new JsonValueNum(n));
}
static JsonValueNumPtr writeJson(Double n)
{
return (new JsonValueNum(n));
}
static JsonValueStringPtr writeJson(const std::string& s)
{
return (new JsonValueString(s));
}
static JsonValueStringPtr writeJson(const char *buf, const UInt32 len)
{
return (new JsonValueString(string(buf,len)));
}
template<typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<string, V, Cmp, Alloc>& m)
{
JsonValueObjPtr pObj=new JsonValueObj();
typedef typename std::map<string, V, Cmp, Alloc>::const_iterator IT;
for (IT i = m.begin(); i != m.end(); ++i)
{
pObj->value[i->first]=writeJson(i->second);
}
return pObj;
}
template<typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<Bool, V, Cmp, Alloc>& m)
{
JsonValueObjPtr pObj=new JsonValueObj();
typedef typename std::map<Bool, V, Cmp, Alloc>::const_iterator IT;
for (IT i = m.begin(); i != m.end(); ++i)
{
pObj->value[TC_Common::tostr(i->first)]=writeJson(i->second);
}
return pObj;
}
template<typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<Char, V, Cmp, Alloc>& m)
{
JsonValueObjPtr pObj=new JsonValueObj();
typedef typename std::map<Char, V, Cmp, Alloc>::const_iterator IT;
for (IT i = m.begin(); i != m.end(); ++i)
{
pObj->value[TC_Common::tostr((Int32)i->first)]=writeJson(i->second);
}
return pObj;
}
template<typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<UInt8, V, Cmp, Alloc>& m)
{
JsonValueObjPtr pObj=new JsonValueObj();
typedef typename std::map<UInt8, V, Cmp, Alloc>::const_iterator IT;
for (IT i = m.begin(); i != m.end(); ++i)
{
pObj->value[TC_Common::tostr(i->first)]=writeJson(i->second);
}
return pObj;
}
template<typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<Short, V, Cmp, Alloc>& m)
{
JsonValueObjPtr pObj=new JsonValueObj();
typedef typename std::map<Short, V, Cmp, Alloc>::const_iterator IT;
for (IT i = m.begin(); i != m.end(); ++i)
{
pObj->value[TC_Common::tostr(i->first)]=writeJson(i->second);
}
return pObj;
}
template<typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<UInt16, V, Cmp, Alloc>& m)
{
JsonValueObjPtr pObj=new JsonValueObj();
typedef typename std::map<UInt16, V, Cmp, Alloc>::const_iterator IT;
for (IT i = m.begin(); i != m.end(); ++i)
{
pObj->value[TC_Common::tostr(i->first)]=writeJson(i->second);
}
return pObj;
}
template<typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<Int32, V, Cmp, Alloc>& m)
{
JsonValueObjPtr pObj=new JsonValueObj();
typedef typename std::map<Int32, V, Cmp, Alloc>::const_iterator IT;
for (IT i = m.begin(); i != m.end(); ++i)
{
pObj->value[TC_Common::tostr(i->first)]=writeJson(i->second);
}
return pObj;
}
template<typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<UInt32, V, Cmp, Alloc>& m)
{
JsonValueObjPtr pObj=new JsonValueObj();
typedef typename std::map<UInt32, V, Cmp, Alloc>::const_iterator IT;
for (IT i = m.begin(); i != m.end(); ++i)
{
pObj->value[TC_Common::tostr(i->first)]=writeJson(i->second);
}
return pObj;
}
template<typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<Int64, V, Cmp, Alloc>& m)
{
JsonValueObjPtr pObj=new JsonValueObj();
typedef typename std::map<Int64, V, Cmp, Alloc>::const_iterator IT;
for (IT i = m.begin(); i != m.end(); ++i)
{
pObj->value[TC_Common::tostr(i->first)]=writeJson(i->second);
}
return pObj;
}
template<typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<Float, V, Cmp, Alloc>& m)
{
JsonValueObjPtr pObj=new JsonValueObj();
typedef typename std::map<Float, V, Cmp, Alloc>::const_iterator IT;
for (IT i = m.begin(); i != m.end(); ++i)
{
pObj->value[TC_Common::tostr(i->first)]=writeJson(i->second);
}
return pObj;
}
template<typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<Double, V, Cmp, Alloc>& m)
{
JsonValueObjPtr pObj=new JsonValueObj();
typedef typename std::map<Double, V, Cmp, Alloc>::const_iterator IT;
for (IT i = m.begin(); i != m.end(); ++i)
{
pObj->value[TC_Common::tostr(i->first)]=writeJson(i->second);
}
return pObj;
}
template<typename K, typename V, typename Cmp, typename Alloc>
static JsonValueObjPtr writeJson(const std::map<K, V, Cmp, Alloc>& m)
{
char s[128];
snprintf(s, sizeof(s), "map key is not Basic type. map key is only string|bool|num");
throw TC_Json_Exception(s);
}
template<typename T, typename Alloc>
static JsonValueArrayPtr writeJson(const std::vector<T, Alloc>& v)
{
JsonValueArrayPtr pArray=new JsonValueArray();
typedef typename std::vector<T, Alloc>::const_iterator IT;
for (IT i = v.begin(); i != v.end(); ++i)
pArray->value.push_back(writeJson(*i));
return pArray;
}
template<typename T>
static JsonValueArrayPtr writeJson(const T *v, const UInt32 len)
{
JsonValueArrayPtr pArray=new JsonValueArray();
for (size_t i = 0; i < len; ++i)
{
pArray->value.push_back(writeJson(v[i]));
}
return pArray;
}
template<typename T>
static JsonValueNumPtr writeJson(const T& v, typename detail::disable_if<detail::is_convertible<T*, TarsStructBase*>, void ***>::type dummy = 0)
{
return writeJson((Int32) v);
}
template<typename T>
static JsonValueObjPtr writeJson(const T& v, typename detail::enable_if<detail::is_convertible<T*, TarsStructBase*>, void ***>::type dummy = 0)
{
return v.writeToJson();
}
};
////////////////////////////////////////////////////////////////////////////////////////////////////
}
#endif

View File

@ -23,13 +23,14 @@
void usage()
{
cout << "Usage : tars2cpp [OPTION] tarsfile" << endl;
cout << " --coder=Demo::interface1;Demo::interface2 create interface encode and decode api" << endl;
// cout << " --coder=Demo::interface1;Demo::interface2 create interface encode and decode api" << endl;
cout << " --dir=DIRECTORY generate source file to DIRECTORY(生成文件到目录DIRECTORY,默认为当前目录)" << endl;
cout << " --check-default=<true,false> 如果optional字段值为默认值不打包(默认打包)" << endl;
cout << " --unjson 不生成json编解码" << endl;
cout << " --os 只生成tars文件中结构体编解码的程序段" << endl;
cout << " --include=\"dir1;dir2;dir3\" 设置tars文件搜索路径" << endl;
cout << " --unknown 生成处理tars数据流中的unkown field的代码" << endl;
cout << " --tarsMaster 生成获取主调信息的选项" << endl;
cout << " --tarsMaster 生成获取主调信息的选项" << endl;
cout << " --currentPriority use current path first." << endl;
cout << " tars2cpp support type: bool byte short int long float double vector map" << endl;
exit(0);
@ -75,17 +76,17 @@ int main(int argc, char* argv[])
usage();
}
bool bCoder = option.hasParam("coder");
vector<string> vCoder;
if(bCoder)
{
vCoder = tars::TC_Common::sepstr<string>(option.getValue("coder"), ";", false);
if(vCoder.size() == 0)
{
usage();
return 0;
}
}
// bool bCoder = option.hasParam("coder");
// vector<string> vCoder;
// if(bCoder)
// {
// vCoder = tars::TC_Common::sepstr<string>(option.getValue("coder"), ";", false);
// if(vCoder.size() == 0)
// {
// usage();
// return 0;
// }
// }
Tars2Cpp t2c;
@ -102,6 +103,14 @@ int main(int argc, char* argv[])
t2c.setOnlyStruct(option.hasParam("os"));
//默认支持json
t2c.setJsonSupport(true);
if (option.hasParam("unjson"))
{
t2c.setJsonSupport(false);
}
t2c.setTarsMaster(option.hasParam("tarsMaster"));
try
@ -119,7 +128,7 @@ int main(int argc, char* argv[])
{
g_parse->parse(vTars[i]);
t2c.createFile(vTars[i], vCoder);
t2c.createFile(vTars[i]);//, vCoder);
}
}
catch(exception& e)

View File

@ -29,6 +29,7 @@
Tars2Cpp::Tars2Cpp()
: _checkDefault(false)
, _onlyStruct(false)
, _bJsonSupport(true)
, _namespace("tars")
, _unknownField(false)
, _tarsMaster(false)
@ -36,6 +37,105 @@ Tars2Cpp::Tars2Cpp()
}
string Tars2Cpp::writeToJson(const TypeIdPtr& pPtr) const
{
ostringstream s;
if (EnumPtr::dynamicCast(pPtr->getTypePtr()))
{
s << TAB << "p->value[\"" << pPtr->getId() << "\"] = " + _namespace + "::JsonOutput::writeJson((" + _namespace + "::Int32)"
<< pPtr->getId() << ");" << endl;
}
else if (pPtr->getTypePtr()->isArray())
{
s << TAB << "p->value[\"" << pPtr->getId() << "\"] = " + _namespace + "::JsonOutput::writeJson((const "
<< tostr(pPtr->getTypePtr()) << " *)" << pPtr->getId() << "Len" << ");" << endl;
}
else if (pPtr->getTypePtr()->isPointer())
{
s << TAB << "p->value[\"" << pPtr->getId() << "\"] = " + _namespace + "::JsonOutput::writeJson((const "
<< tostr(pPtr->getTypePtr()) << " )" << pPtr->getId() << "Len" << ");" << endl;
}
else
{
MapPtr mPtr = MapPtr::dynamicCast(pPtr->getTypePtr());
VectorPtr vPtr = VectorPtr::dynamicCast(pPtr->getTypePtr());
// 对于json 不检测默认值
if (true || !_checkDefault || pPtr->isRequire() || (!pPtr->hasDefault() && !mPtr && !vPtr))
{
s << TAB << "p->value[\"" << pPtr->getId() << "\"] = " + _namespace + "::JsonOutput::writeJson("
<< pPtr->getId() << ");" << endl;
}
else
{
string sDefault = pPtr->def();
BuiltinPtr bPtr = BuiltinPtr::dynamicCast(pPtr->getTypePtr());
if (bPtr && bPtr->kind() == Builtin::KindString)
{
sDefault = "\"" + tars::TC_Common::replace(pPtr->def(), "\"", "\\\"") + "\"";
}
if (mPtr || vPtr)
{
s << TAB << "if (" << pPtr->getId() << ".size() > 0)" << endl;
}
else if (bPtr && (bPtr->kind() == Builtin::KindFloat || bPtr->kind() == Builtin::KindDouble))
{
s << TAB << "if (!tars::TC_Common::equal(" << pPtr->getId() << "," << sDefault << "))" << endl;
}
else
{
s << TAB << "if (" << pPtr->getId() << " != " << sDefault << ")" << endl;
}
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "p->value[\"" << pPtr->getId() << "\"] = " + _namespace + "::JsonOutput::writeJson("
<< pPtr->getId() << ");" << endl;
DEL_TAB;
s << TAB << "}" << endl;
}
}
return s.str();
}
string Tars2Cpp::readFromJson(const TypeIdPtr& pPtr, bool bIsRequire) const
{
ostringstream s;
// if (EnumPtr::dynamicCast(pPtr->getTypePtr()))
// {
// s << TAB << _namespace + "::JsonInput::readJson((" + _namespace + "::Int32&)" << pPtr->getId() << ",pObj->value[\"" << pPtr->getId() << "\"]";
// }
// else
if (pPtr->getTypePtr()->isArray())
{
s << TAB << _namespace + "::JsonInput::readJson(" << pPtr->getId() << "Len" << ",pObj->value[\"" << pPtr->getId() << "\"]" << getSuffix(pPtr);
}
else if (pPtr->getTypePtr()->isPointer())
{
#if 0
s << TAB << pPtr->getId() <<" = ("<<tostr(pPtr->getTypePtr())<<")_is.cur();"<<endl;
s << TAB << "_is.read("<< pPtr->getId()<<", _is.left(), "<< pPtr->getId() << "Len";
#endif
s << TAB << "not support";
}
else
{
s << TAB << _namespace + "::JsonInput::readJson(" << pPtr->getId() << ",pObj->value[\"" << pPtr->getId() << "\"]";
}
s << ", " << ((pPtr->isRequire() && bIsRequire) ? "true" : "false") << ");" << endl;
#if 0
if(pPtr->getTypePtr()->isPointer())
s << TAB <<"_is.mapBufferSkip("<<pPtr->getId() << "Len);"<<endl;
#endif
return s.str();
}
string Tars2Cpp::writeTo(const TypeIdPtr& pPtr) const
{
ostringstream s;
@ -581,6 +681,55 @@ string Tars2Cpp::generateH(const StructPtr& pPtr, const string& namespaceId) con
DEL_TAB;
s << TAB << "}" << endl;
if (_bJsonSupport)
{
s << TAB << "tars::JsonValueObjPtr writeToJson() const" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "tars::JsonValueObjPtr p = new tars::JsonValueObj();" << endl;
for (size_t j = 0; j < member.size(); j++)
{
s << writeToJson(member[j]);
}
s << TAB << "return p;" << endl;
DEL_TAB;
s << TAB << "}" << endl;
s << TAB << "string writeToJsonString() const" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "return tars::TC_Json::writeValue(writeToJson());" << endl;
DEL_TAB;
s << TAB << "}" << endl;
s << TAB << "void readFromJson(const tars::JsonValuePtr & p, bool isRequire = true)" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "resetDefautlt();" << endl;
s << TAB << "if(NULL == p.get() || p->getType() != tars::eJsonTypeObj)" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "char s[128];" << endl;
s << TAB << "snprintf(s, sizeof(s), \"read 'struct' type mismatch, get type: %d.\", (p.get() ? p->getType() : 0));" << endl;
s << TAB << "throw tars::TC_Json_Exception(s);" << endl;
DEL_TAB;
s << TAB << "}" << endl;
s << TAB << "tars::JsonValueObjPtr pObj=tars::JsonValueObjPtr::dynamicCast(p);" << endl;
for (size_t j = 0; j < member.size(); j++)
{
s << readFromJson(member[j]);
}
DEL_TAB;
s << TAB << "}" << endl;
s << TAB << "void readFromJsonString(const string & str)" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "readFromJson(tars::TC_Json::getValue(str));" << endl;
DEL_TAB;
s << TAB << "}" << endl;
}
s << TAB << "ostream& display(ostream& _os, int _level=0) const" << endl;
s << TAB << "{" << endl;
INC_TAB;
@ -624,7 +773,7 @@ string Tars2Cpp::generateH(const StructPtr& pPtr, const string& namespaceId) con
}
if (_unknownField)
{
s << TAB << "std::string sUnknownField; //¹¤¾ß´ø--unknown²ÎÊý×Ô¶¯Éú³É×Ö¶Î,´æ·Åδ֪tagÊý¾Ý." << endl;
s << TAB << "std::string sUnknownField;" << endl;
}
DEL_TAB;
s << TAB << "};" << endl;
@ -661,6 +810,32 @@ string Tars2Cpp::generateH(const StructPtr& pPtr, const string& namespaceId) con
DEL_TAB;
s << TAB << "}" << endl;
//定义 << >>
if (_bJsonSupport)
{
//重载 <<
s << TAB << "inline ostream& operator<<(ostream & os,const " << pPtr->getId() << "&r)" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "os << r.writeToJsonString();" << endl;
s << TAB << "return os;" << endl;
DEL_TAB;
s << TAB << "}" << endl;
//重载 >>
s << TAB << "inline istream& operator>>(istream& is," << pPtr->getId() << "&l)" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "std::istreambuf_iterator<char> eos;" << endl;
s << TAB << "std::string s(std::istreambuf_iterator<char>(is), eos);" << endl;
s << TAB << "l.readFromJsonString(s);" << endl;
s << TAB << "return is;" << endl;
DEL_TAB;
s << TAB << "}" << endl;
}
vector<string> key = pPtr->getKey();
//定义<
if (key.size() > 0)
@ -2344,6 +2519,7 @@ void Tars2Cpp::generateH(const ContextPtr &pPtr) const
s << "#include <string>" << endl;
s << "#include <vector>" << endl;
s << "#include \"tup/Tars.h\"" << endl;
if (_bJsonSupport) s << "#include \"tup/TarsJson.h\"" << endl;
s << "using namespace std;" << endl;
@ -2381,24 +2557,24 @@ void Tars2Cpp::generateH(const ContextPtr &pPtr) const
tars::TC_File::save2file(fileH, s.str());
}
void Tars2Cpp::createFile(const string& file, const vector<string>& vsCoder)
void Tars2Cpp::createFile(const string& file)//, const vector<string>& vsCoder)
{
std::vector<ContextPtr> contexts = g_parse->getContexts();
for (size_t i = 0; i < contexts.size(); i++)
{
if (file == contexts[i]->getFileName())
{
if (vsCoder.size() == 0)
{
// if (vsCoder.size() == 0)
// {
generateH(contexts[i]);
}
else
{
for (size_t j = 0; j < vsCoder.size(); j++)
{
generateCoder(contexts[i], vsCoder[j]);
}
}
// }
// else
// {
// for (size_t j = 0; j < vsCoder.size(); j++)
// {
// generateCoder(contexts[i], vsCoder[j]);
// }
// }
}
}
}
@ -2426,332 +2602,332 @@ StructPtr Tars2Cpp::findStruct(const ContextPtr& pPtr, const string& id)
return NULL;
}
////////////////////////////////
//for coder generating
////////////////////////////////
string Tars2Cpp::generateCoder(const NamespacePtr& pPtr, const string& sInterface) const
{
ostringstream s;
vector<InterfacePtr>& is = pPtr->getAllInterfacePtr();
vector<StructPtr>& ss = pPtr->getAllStructPtr();
vector<EnumPtr>& es = pPtr->getAllEnumPtr();
vector<ConstPtr>& cs = pPtr->getAllConstPtr();
s << endl;
s << TAB << "namespace " << pPtr->getId() << endl;
s << TAB << "{" << endl;
INC_TAB;
for (size_t i = 0; i < cs.size(); i++)
{
s << generateH(cs[i]) << endl;
}
for (size_t i = 0; i < es.size(); i++)
{
s << generateH(es[i]) << endl;
}
for (size_t i = 0; i < ss.size(); i++)
{
s << generateH(ss[i], pPtr->getId()) << endl;
}
s << endl;
for (size_t i = 0; i < is.size(); i++)
{
if (pPtr->getId() + "::" + is[i]->getId() == sInterface)
{
s << generateCoder(is[i]) << endl;
s << endl;
}
}
DEL_TAB;
s << "}";
s << endl << endl;
return s.str();
}
string Tars2Cpp::generateCoder(const InterfacePtr& pPtr) const
{
ostringstream s;
vector<OperationPtr>& vOperation = pPtr->getAllOperationPtr();
//生成编解码类
s << TAB << "// encode and decode for client" << endl;
s << TAB << "class " << pPtr->getId() << "Coder" << endl;
s << TAB << "{" << endl;
s << TAB << "public:" << endl << endl;
INC_TAB;
s << TAB << "typedef map<string, string> TARS_CONTEXT;" << endl << endl;
s << TAB << "enum enumResult" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "eTarsServerSuccess = 0," << endl;
s << TAB << "eTarsPacketLess = 1," << endl;
s << TAB << "eTarsPacketErr = 2," << endl;
s << TAB << "eTarsServerDecodeErr = -1," << endl;
s << TAB << "eTarsServerEncodeErr = -2," << endl;
s << TAB << "eTarsServerNoFuncErr = -3," << endl;
s << TAB << "eTarsServerNoServantErr = -4," << endl;
s << TAB << "eTarsServerQueueTimeout = -6," << endl;
s << TAB << "eTarsAsyncCallTimeout = -7," << endl;
s << TAB << "eTarsProxyConnectErr = -8," << endl;
s << TAB << "eTarsServerUnknownErr = -99," << endl;
DEL_TAB;
s << TAB << "};" << endl << endl;
for (size_t i = 0; i < vOperation.size(); i++)
{
s << generateCoder(vOperation[i]) << endl;
}
DEL_TAB;
s << TAB << "protected:" << endl << endl;
INC_TAB;
s << TAB << "static " + _namespace + "::Int32 fetchPacket(const string & in, string & out)" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "if(in.length() < sizeof(" + _namespace + "::Int32)) return eTarsPacketLess;" << endl;
s << TAB << "" + _namespace + "::Int32 iHeaderLen;" << endl;
s << TAB << "memcpy(&iHeaderLen, in.c_str(), sizeof(" + _namespace + "::Int32));" << endl;
s << TAB << "iHeaderLen = ntohl(iHeaderLen);" << endl;
s << TAB << "if(iHeaderLen < (" + _namespace + "::Int32)sizeof(" + _namespace + "::Int32) || iHeaderLen > 100000000) return eTarsPacketErr;" << endl;
s << TAB << "if((" + _namespace + "::Int32)in.length() < iHeaderLen) return eTarsPacketLess;" << endl;
s << TAB << "out = in.substr(sizeof(" + _namespace + "::Int32), iHeaderLen - sizeof(" + _namespace + "::Int32)); " << endl;
s << TAB << "return 0;" << endl;
DEL_TAB;
s << TAB << "}" << endl;
s << endl;
s << TAB << "static string encodeBasePacket(const string & sServantName, const string & sFuncName, const vector<char> & buffer, "
<< "const map<string, string>& context = TARS_CONTEXT())" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << _namespace + "::TarsOutputStream<" + _namespace + "::BufferWriter> os;" << endl;
s << TAB << "os.write(1, 1);" << endl;
s << TAB << "os.write(0, 2);" << endl;
s << TAB << "os.write(0, 3);" << endl;
s << TAB << "os.write(0, 4);" << endl;
s << TAB << "os.write(sServantName, 5);" << endl;
s << TAB << "os.write(sFuncName, 6);" << endl;
s << TAB << "os.write(buffer, 7);" << endl;
s << TAB << "os.write(60, 8);" << endl;
s << TAB << "os.write(context, 9);" << endl;
s << TAB << "os.write(map<string, string>(), 10);" << endl;
s << TAB << _namespace + "::Int32 iHeaderLen;" << endl;
s << TAB << "iHeaderLen = htonl(sizeof(" + _namespace + "::Int32) + os.getLength());" << endl;
s << TAB << "string s;" << endl;
s << TAB << "s.append((const char*)&iHeaderLen, sizeof(" + _namespace + "::Int32));" << endl;
s << TAB << "s.append(os.getBuffer(), os.getLength());" << endl;
s << TAB << "return s;" << endl;
DEL_TAB;
s << TAB << "}" << endl;
s << endl;
s << TAB << "static " + _namespace + "::Int32 decodeBasePacket(const string & in, " + _namespace + "::Int32 & iServerRet, vector<char> & buffer)" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << _namespace + "::TarsInputStream<" + _namespace + "::BufferReader> is;" << endl;
s << TAB << "is.setBuffer(in.c_str(), in.length());" << endl;
s << TAB << "is.read(iServerRet, 5, true);" << endl;
s << TAB << "is.read(buffer, 6, true);" << endl;
s << TAB << "return 0;" << endl;
DEL_TAB;
s << TAB << "}" << endl;
s << endl;
DEL_TAB;
s << TAB << "};" << endl;
return s.str();
}
string Tars2Cpp::generateCoder(const OperationPtr& pPtr) const
{
ostringstream s;
vector<ParamDeclPtr>& vParamDecl = pPtr->getAllParamDeclPtr();
//编码函数
s << TAB << "//encode & decode function for '" << pPtr->getId() << "()'" << endl << endl;
s << TAB << "static string encode_" << pPtr->getId() << "(const string & sServantName, ";
for (size_t i = 0; i < vParamDecl.size(); i++)
{
if (!vParamDecl[i]->isOut())
{
s << generateH(vParamDecl[i]) << ",";
}
}
s << endl;
s << TAB << " const map<string, string>& context = TARS_CONTEXT())" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "try" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << _namespace + "::TarsOutputStream<" + _namespace + "::BufferWriter> _os;" << endl;
for (size_t i = 0; i < vParamDecl.size(); i++)
{
if (vParamDecl[i]->isOut()) continue;
s << writeTo(vParamDecl[i]->getTypeIdPtr());
}
// ////////////////////////////////
// //for coder generating
// ////////////////////////////////
// string Tars2Cpp::generateCoder(const NamespacePtr& pPtr, const string& sInterface) const
// {
// ostringstream s;
// vector<InterfacePtr>& is = pPtr->getAllInterfacePtr();
// vector<StructPtr>& ss = pPtr->getAllStructPtr();
// vector<EnumPtr>& es = pPtr->getAllEnumPtr();
// vector<ConstPtr>& cs = pPtr->getAllConstPtr();
// s << endl;
// s << TAB << "namespace " << pPtr->getId() << endl;
// s << TAB << "{" << endl;
// INC_TAB;
// for (size_t i = 0; i < cs.size(); i++)
// {
// s << generateH(cs[i]) << endl;
// }
// for (size_t i = 0; i < es.size(); i++)
// {
// s << generateH(es[i]) << endl;
// }
// for (size_t i = 0; i < ss.size(); i++)
// {
// s << generateH(ss[i], pPtr->getId()) << endl;
// }
// s << endl;
// for (size_t i = 0; i < is.size(); i++)
// {
// if (pPtr->getId() + "::" + is[i]->getId() == sInterface)
// {
// s << generateCoder(is[i]) << endl;
// s << endl;
// }
// }
// DEL_TAB;
// s << "}";
// s << endl << endl;
// return s.str();
// }
// string Tars2Cpp::generateCoder(const InterfacePtr& pPtr) const
// {
// ostringstream s;
// vector<OperationPtr>& vOperation = pPtr->getAllOperationPtr();
// //生成编解码类
// s << TAB << "// encode and decode for client" << endl;
// s << TAB << "class " << pPtr->getId() << "Coder" << endl;
// s << TAB << "{" << endl;
// s << TAB << "public:" << endl << endl;
// INC_TAB;
// s << TAB << "typedef map<string, string> TARS_CONTEXT;" << endl << endl;
// s << TAB << "enum enumResult" << endl;
// s << TAB << "{" << endl;
// INC_TAB;
// s << TAB << "eTarsServerSuccess = 0," << endl;
// s << TAB << "eTarsPacketLess = 1," << endl;
// s << TAB << "eTarsPacketErr = 2," << endl;
// s << TAB << "eTarsServerDecodeErr = -1," << endl;
// s << TAB << "eTarsServerEncodeErr = -2," << endl;
// s << TAB << "eTarsServerNoFuncErr = -3," << endl;
// s << TAB << "eTarsServerNoServantErr = -4," << endl;
// s << TAB << "eTarsServerQueueTimeout = -6," << endl;
// s << TAB << "eTarsAsyncCallTimeout = -7," << endl;
// s << TAB << "eTarsProxyConnectErr = -8," << endl;
// s << TAB << "eTarsServerUnknownErr = -99," << endl;
// DEL_TAB;
// s << TAB << "};" << endl << endl;
// for (size_t i = 0; i < vOperation.size(); i++)
// {
// s << generateCoder(vOperation[i]) << endl;
// }
// DEL_TAB;
// s << TAB << "protected:" << endl << endl;
// INC_TAB;
// s << TAB << "static " + _namespace + "::Int32 fetchPacket(const string & in, string & out)" << endl;
// s << TAB << "{" << endl;
// INC_TAB;
// s << TAB << "if(in.length() < sizeof(" + _namespace + "::Int32)) return eTarsPacketLess;" << endl;
// s << TAB << "" + _namespace + "::Int32 iHeaderLen;" << endl;
// s << TAB << "memcpy(&iHeaderLen, in.c_str(), sizeof(" + _namespace + "::Int32));" << endl;
// s << TAB << "iHeaderLen = ntohl(iHeaderLen);" << endl;
// s << TAB << "if(iHeaderLen < (" + _namespace + "::Int32)sizeof(" + _namespace + "::Int32) || iHeaderLen > 100000000) return eTarsPacketErr;" << endl;
// s << TAB << "if((" + _namespace + "::Int32)in.length() < iHeaderLen) return eTarsPacketLess;" << endl;
// s << TAB << "out = in.substr(sizeof(" + _namespace + "::Int32), iHeaderLen - sizeof(" + _namespace + "::Int32)); " << endl;
// s << TAB << "return 0;" << endl;
// DEL_TAB;
// s << TAB << "}" << endl;
// s << endl;
// s << TAB << "static string encodeBasePacket(const string & sServantName, const string & sFuncName, const vector<char> & buffer, "
// << "const map<string, string>& context = TARS_CONTEXT())" << endl;
// s << TAB << "{" << endl;
// INC_TAB;
// s << TAB << _namespace + "::TarsOutputStream<" + _namespace + "::BufferWriter> os;" << endl;
// s << TAB << "os.write(1, 1);" << endl;
// s << TAB << "os.write(0, 2);" << endl;
// s << TAB << "os.write(0, 3);" << endl;
// s << TAB << "os.write(0, 4);" << endl;
// s << TAB << "os.write(sServantName, 5);" << endl;
// s << TAB << "os.write(sFuncName, 6);" << endl;
// s << TAB << "os.write(buffer, 7);" << endl;
// s << TAB << "os.write(60, 8);" << endl;
// s << TAB << "os.write(context, 9);" << endl;
// s << TAB << "os.write(map<string, string>(), 10);" << endl;
// s << TAB << _namespace + "::Int32 iHeaderLen;" << endl;
// s << TAB << "iHeaderLen = htonl(sizeof(" + _namespace + "::Int32) + os.getLength());" << endl;
// s << TAB << "string s;" << endl;
// s << TAB << "s.append((const char*)&iHeaderLen, sizeof(" + _namespace + "::Int32));" << endl;
// s << TAB << "s.append(os.getBuffer(), os.getLength());" << endl;
// s << TAB << "return s;" << endl;
// DEL_TAB;
// s << TAB << "}" << endl;
// s << endl;
// s << TAB << "static " + _namespace + "::Int32 decodeBasePacket(const string & in, " + _namespace + "::Int32 & iServerRet, vector<char> & buffer)" << endl;
// s << TAB << "{" << endl;
// INC_TAB;
// s << TAB << _namespace + "::TarsInputStream<" + _namespace + "::BufferReader> is;" << endl;
// s << TAB << "is.setBuffer(in.c_str(), in.length());" << endl;
// s << TAB << "is.read(iServerRet, 5, true);" << endl;
// s << TAB << "is.read(buffer, 6, true);" << endl;
// s << TAB << "return 0;" << endl;
// DEL_TAB;
// s << TAB << "}" << endl;
// s << endl;
// DEL_TAB;
// s << TAB << "};" << endl;
// return s.str();
// }
// string Tars2Cpp::generateCoder(const OperationPtr& pPtr) const
// {
// ostringstream s;
// vector<ParamDeclPtr>& vParamDecl = pPtr->getAllParamDeclPtr();
// //编码函数
// s << TAB << "//encode & decode function for '" << pPtr->getId() << "()'" << endl << endl;
// s << TAB << "static string encode_" << pPtr->getId() << "(const string & sServantName, ";
// for (size_t i = 0; i < vParamDecl.size(); i++)
// {
// if (!vParamDecl[i]->isOut())
// {
// s << generateH(vParamDecl[i]) << ",";
// }
// }
// s << endl;
// s << TAB << " const map<string, string>& context = TARS_CONTEXT())" << endl;
// s << TAB << "{" << endl;
// INC_TAB;
// s << TAB << "try" << endl;
// s << TAB << "{" << endl;
// INC_TAB;
// s << TAB << _namespace + "::TarsOutputStream<" + _namespace + "::BufferWriter> _os;" << endl;
// for (size_t i = 0; i < vParamDecl.size(); i++)
// {
// if (vParamDecl[i]->isOut()) continue;
// s << writeTo(vParamDecl[i]->getTypeIdPtr());
// }
s << TAB << "return encodeBasePacket(sServantName, \"" << pPtr->getId() << "\", _os.getByteBuffer(), context);" << endl;
// s << TAB << "return encodeBasePacket(sServantName, \"" << pPtr->getId() << "\", _os.getByteBuffer(), context);" << endl;
DEL_TAB;
s << TAB << "}" << endl;
s << TAB << "catch (" + _namespace + "::TarsException & ex)" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "return \"\";" << endl;
DEL_TAB;
s << TAB << "}" << endl;
DEL_TAB;
s << TAB << "}" << endl;
s << endl;
//解码函数
s << TAB << "static " + _namespace + "::Int32 decode_" << pPtr->getId() << "(const string & in ";
// DEL_TAB;
// s << TAB << "}" << endl;
// s << TAB << "catch (" + _namespace + "::TarsException & ex)" << endl;
// s << TAB << "{" << endl;
// INC_TAB;
// s << TAB << "return \"\";" << endl;
// DEL_TAB;
// s << TAB << "}" << endl;
// DEL_TAB;
// s << TAB << "}" << endl;
// s << endl;
// //解码函数
// s << TAB << "static " + _namespace + "::Int32 decode_" << pPtr->getId() << "(const string & in ";
if (pPtr->getReturnPtr()->getTypePtr())
{
s << ", " << tostr(pPtr->getReturnPtr()->getTypePtr()) << " & _ret ";
}
for (size_t i = 0; i < vParamDecl.size(); i++)
{
if(!vParamDecl[i]->isOut())
continue;
// if (pPtr->getReturnPtr()->getTypePtr())
// {
// s << ", " << tostr(pPtr->getReturnPtr()->getTypePtr()) << " & _ret ";
// }
// for (size_t i = 0; i < vParamDecl.size(); i++)
// {
// if(!vParamDecl[i]->isOut())
// continue;
s << ", " << generateH(vParamDecl[i]);
}
s << ")" << endl;
// s << ", " << generateH(vParamDecl[i]);
// }
// s << ")" << endl;
s << TAB << "{" << endl;
// s << TAB << "{" << endl;
INC_TAB;
s << TAB << "try" << endl;
s << TAB << "{" << endl;
// INC_TAB;
// s << TAB << "try" << endl;
// s << TAB << "{" << endl;
INC_TAB;
s << TAB << "string out;" << endl;
s << TAB << _namespace + "::Int32 iRet = 0;" << endl;
s << TAB << "if((iRet = fetchPacket(in, out)) != 0) return iRet;" << endl;
// INC_TAB;
// s << TAB << "string out;" << endl;
// s << TAB << _namespace + "::Int32 iRet = 0;" << endl;
// s << TAB << "if((iRet = fetchPacket(in, out)) != 0) return iRet;" << endl;
s << TAB << _namespace + "::TarsInputStream<" + _namespace + "::BufferReader> _is;" << endl;
s << TAB << _namespace + "::Int32 iServerRet=0;" << endl;
s << TAB << "vector<char> buffer;" << endl;
s << TAB << "decodeBasePacket(out, iServerRet, buffer);" << endl;
s << TAB << "if(iServerRet != 0) return iServerRet;" << endl;
// s << TAB << _namespace + "::TarsInputStream<" + _namespace + "::BufferReader> _is;" << endl;
// s << TAB << _namespace + "::Int32 iServerRet=0;" << endl;
// s << TAB << "vector<char> buffer;" << endl;
// s << TAB << "decodeBasePacket(out, iServerRet, buffer);" << endl;
// s << TAB << "if(iServerRet != 0) return iServerRet;" << endl;
s << TAB << "_is.setBuffer(buffer);" << endl;
// s << TAB << "_is.setBuffer(buffer);" << endl;
if (pPtr->getReturnPtr()->getTypePtr())
{
s << readFrom(pPtr->getReturnPtr());
}
// if (pPtr->getReturnPtr()->getTypePtr())
// {
// s << readFrom(pPtr->getReturnPtr());
// }
for (size_t i = 0; i < vParamDecl.size(); i++)
{
if (vParamDecl[i]->isOut())
{
s << readFrom(vParamDecl[i]->getTypeIdPtr());
}
}
// for (size_t i = 0; i < vParamDecl.size(); i++)
// {
// if (vParamDecl[i]->isOut())
// {
// s << readFrom(vParamDecl[i]->getTypeIdPtr());
// }
// }
s << TAB << "return 0;" << endl;
// s << TAB << "return 0;" << endl;
DEL_TAB;
s << TAB << "}" << endl;
s << TAB << "catch (" + _namespace + "::TarsException & ex)" << endl;
s << TAB << "{" << endl;
INC_TAB;
s << TAB << "return eTarsPacketErr;" << endl;
DEL_TAB;
s << TAB << "}" << endl;
// DEL_TAB;
// s << TAB << "}" << endl;
// s << TAB << "catch (" + _namespace + "::TarsException & ex)" << endl;
// s << TAB << "{" << endl;
// INC_TAB;
// s << TAB << "return eTarsPacketErr;" << endl;
// DEL_TAB;
// s << TAB << "}" << endl;
DEL_TAB;
s << TAB << "}" << endl;
// DEL_TAB;
// s << TAB << "}" << endl;
s << endl;
// s << endl;
return s.str();
}
// return s.str();
// }
void Tars2Cpp::generateCoder(const ContextPtr& pPtr, const string& sInterface) const
{
cout << "Interface:" << sInterface << endl;
string n = tars::TC_File::excludeFileExt(tars::TC_File::extractFileName(pPtr->getFileName())) + "Coder";
// void Tars2Cpp::generateCoder(const ContextPtr& pPtr, const string& sInterface) const
// {
// cout << "Interface:" << sInterface << endl;
// string n = tars::TC_File::excludeFileExt(tars::TC_File::extractFileName(pPtr->getFileName())) + "Coder";
string fileH = _baseDir + "/" + n + ".h";
// string fileH = _baseDir + "/" + n + ".h";
string define = tars::TC_Common::upper("__" + n + "_h_");
// string define = tars::TC_Common::upper("__" + n + "_h_");
ostringstream s;
// ostringstream s;
s << g_parse->printHeaderRemark();
// s << g_parse->printHeaderRemark();
s << "#ifndef " << define << endl;
s << "#define " << define << endl;
s << endl;
s << "#include <map>" << endl;
s << "#include <string>" << endl;
s << "#include <vector>" << endl;
s << "#include \"tup/Tars.h\"" << endl;
// s << "#ifndef " << define << endl;
// s << "#define " << define << endl;
// s << endl;
// s << "#include <map>" << endl;
// s << "#include <string>" << endl;
// s << "#include <vector>" << endl;
// s << "#include \"tup/Tars.h\"" << endl;
s << "using namespace std;" << endl;
// s << "using namespace std;" << endl;
vector<string> include = pPtr->getIncludes();
for (size_t i = 0; i < include.size(); i++)
{
s << "#include \"" << g_parse->getHeader()
<< tars::TC_Common::replace(tars::TC_File::extractFileName(include[i]), ".h", "Coder.h") << "\"" << endl;
}
// vector<string> include = pPtr->getIncludes();
// for (size_t i = 0; i < include.size(); i++)
// {
// s << "#include \"" << g_parse->getHeader()
// << tars::TC_Common::replace(tars::TC_File::extractFileName(include[i]), ".h", "Coder.h") << "\"" << endl;
// }
vector<NamespacePtr> namespaces = pPtr->getNamespaces();
// vector<NamespacePtr> namespaces = pPtr->getNamespaces();
s << endl;
// s << endl;
for (size_t i = 0; i < namespaces.size(); i++)
{
s << generateCoder(namespaces[i], sInterface) << endl;
}
// for (size_t i = 0; i < namespaces.size(); i++)
// {
// s << generateCoder(namespaces[i], sInterface) << endl;
// }
s << endl;
s << "#endif" << endl;
// s << endl;
// s << "#endif" << endl;
tars::TC_File::makeDirRecursive(_baseDir, 0755);
tars::TC_File::save2file(fileH, s.str());
// tars::TC_File::makeDirRecursive(_baseDir, 0755);
// tars::TC_File::save2file(fileH, s.str());
return;
}
// return;
// }

View File

@ -38,7 +38,7 @@ public:
*
* @param file
*/
void createFile(const string &file, const vector<string> &vsCoder);
void createFile(const string &file);//, const vector<string> &vsCoder);
/**
*
@ -51,6 +51,11 @@ public:
*/
void setCheckDefault(bool bCheck) { _checkDefault = bCheck; }
/**
* json支持
*/
void setJsonSupport(bool bJsonSupport) { _bJsonSupport = bJsonSupport; }
/**
* struct
*/
@ -70,6 +75,22 @@ public:
//下面是编解码的源码生成
protected:
/**
* json
* @param pPtr
*
* @return string
*/
string writeToJson(const TypeIdPtr& pPtr) const;
/**
* json
* @param pPtr
*
* @return string
*/
string readFromJson(const TypeIdPtr& pPtr, bool bIsRequire = true) const;
/**
*
* @param pPtr
@ -403,19 +424,19 @@ protected:
*/
StructPtr findStruct(const ContextPtr &pPtr,const string &id);
/**
*
*
* @param pPtr
* @param interface
*/
void generateCoder(const ContextPtr &pPtr,const string &interface) const;
// /**
// *
// * 生成接口编解码代码
// * @param pPtr
// * @param interface
// */
// void generateCoder(const ContextPtr &pPtr,const string &interface) const;
string generateCoder(const NamespacePtr &pPtr,const string & sInterface) const;
// string generateCoder(const NamespacePtr &pPtr,const string & sInterface) const;
string generateCoder(const InterfacePtr &pPtr) const;
// string generateCoder(const InterfacePtr &pPtr) const;
string generateCoder(const OperationPtr &pPtr) const;
// string generateCoder(const OperationPtr &pPtr) const;
string generateInitValue(const TypeIdPtr &pPtr) const;
@ -428,6 +449,8 @@ private:
bool _onlyStruct;
bool _bJsonSupport;
std::string _namespace ;
bool _unknownField;

259
util/include/util/tc_json.h Normal file
View File

@ -0,0 +1,259 @@
#ifndef __TC_JSON_H
#define __TC_JSON_H
#include <string>
#include <unordered_map>
#include <map>
#include <vector>
#include <list>
#include <assert.h>
#include <stdio.h>
#include <sstream>
#include "util/tc_autoptr.h"
using namespace std;
namespace tars
{
/////////////////////////////////////////////////
// 说明: json编解码的公共库
// Author : zhangcunli@tencent.com
/////////////////////////////////////////////////
/**
*
*/
struct TC_Json_Exception : public TC_Exception
{
TC_Json_Exception(const string &buffer) : TC_Exception(buffer){};
~TC_Json_Exception() throw(){};
};
enum eJsonType
{
eJsonTypeString,
eJsonTypeNum,
eJsonTypeObj,
eJsonTypeArray,
eJsonTypeBoolean,
eJsonTypeNull,
};
/*
* json字符串用到的
*/
class BufferJsonReader
{
const char * _buf; ///< 缓冲区
size_t _buf_len; ///< 缓冲区长度
size_t _cur; ///< 当前位置
public:
BufferJsonReader () :_buf(NULL),_buf_len(0), _cur(0) {}
void reset() { _cur = 0;}
void setBuffer(const char * buf, size_t len)
{
_buf = buf;
_buf_len = len;
_cur = 0;
}
void setBuffer(const std::vector<char> &buf)
{
_buf = buf.data();
_buf_len = buf.size();
_cur = 0;
}
const size_t &getCur() const { return _cur; }
const char * getPoint() const { return _buf+_cur; }
const char &read() { check(); _cur ++; return *(_buf+_cur-1); }
const char &get() const { check(); return *(_buf+_cur); }
const char &getBack() const { assert(_cur>0); return *(_buf+_cur-1); }
void back() { assert(_cur>0); _cur--; }
void check() const
{
if (_cur + 1 > _buf_len)
{
char s[64];
snprintf(s, sizeof(s), "buffer overflow when peekBuf, over %u.", (uint32_t)_buf_len);
throw TC_Json_Exception(s);
}
}
bool hasEnd() const { return _cur >= _buf_len; }
};
class JsonValue;
class JsonValueObj;
class JsonValueArray;
class JsonValueString;
class JsonValueBoolean;
class JsonValueNum;
class JsonValueNull;
typedef TC_AutoPtr<JsonValue> JsonValuePtr;
typedef TC_AutoPtr<JsonValueObj> JsonValueObjPtr;
typedef TC_AutoPtr<JsonValueNum> JsonValueNumPtr;
typedef TC_AutoPtr<JsonValueArray> JsonValueArrayPtr;
typedef TC_AutoPtr<JsonValueString> JsonValueStringPtr;
typedef TC_AutoPtr<JsonValueBoolean> JsonValueBooleanPtr;
typedef TC_AutoPtr<JsonValueNull> JsonValueNullPtr;
/*
* json类型的基类
*/
class JsonValue : public TC_HandleBase
{
public:
virtual eJsonType getType() const = 0;
virtual void write(ostream& ostr) const;
virtual void read(BufferJsonReader & reader, char c) = 0;
virtual ~JsonValue() { }
public:
static JsonValuePtr createJsonValue(BufferJsonReader & reader);
static uint32_t getHex(BufferJsonReader & reader);
static bool isspace(char c);
static void writeString(const string &str, ostream& ostr);
protected:
JsonValue(){};
};
/*
* json类型 string类型 "dd\ndfd"
*/
class JsonValueString : public JsonValue
{
public:
JsonValueString(const string & s):value(s)
{
}
JsonValueString()
{
}
eJsonType getType() const { return eJsonTypeString; }
virtual void write(ostream& ostr) const;
virtual void read(BufferJsonReader & reader, char c);
virtual ~JsonValueString() { }
string value;
};
/*
* json类型 number类型 1.5e8
*/
class JsonValueNum : public JsonValue
{
public:
JsonValueNum(double d,bool b=false):value(d),isInt(b)
{
}
JsonValueNum()
{
isInt=false;
value=0.0f;
}
eJsonType getType() const { return eJsonTypeNum; }
virtual void write(ostream& ostr) const;
virtual void read(BufferJsonReader & reader, char c);
virtual ~JsonValueNum(){}
public:
double value;
bool isInt;
};
/*
* json类型 object类型 {"aa","bb"}
*/
class JsonValueObj: public JsonValue
{
public:
eJsonType getType() const { return eJsonTypeObj; }
virtual void write(ostream& ostr) const;
virtual void read(BufferJsonReader & reader, char c);
const JsonValuePtr &get(const char *name);
virtual ~JsonValueObj();
public:
unordered_map<string, JsonValuePtr> value;
};
/*
* json类型 array类型 ["aa","bb"]
*/
class JsonValueArray: public JsonValue
{
public:
eJsonType getType() const { return eJsonTypeArray; }
void push_back(const JsonValuePtr & p) { value.push_back(p); }
virtual void write(ostream& ostr) const;
virtual void read(BufferJsonReader & reader, char c = 0);
virtual ~JsonValueArray();
public:
vector<JsonValuePtr> value;
};
/*
* json类型 boolean类型 true
*/
class JsonValueBoolean : public JsonValue
{
public:
eJsonType getType() const { return eJsonTypeBoolean; }
bool getValue() const { return value; }
virtual void write(ostream& ostr) const;
virtual void read(BufferJsonReader & reader,char c);
virtual ~JsonValueBoolean(){}
public:
bool value;
};
/*
* json类型 null类型 "dd\ndfd"
*/
class JsonValueNull : public JsonValue
{
public:
JsonValueNull() { }
eJsonType getType() const { return eJsonTypeNull; }
virtual void write(ostream& ostr) const;
virtual void read(BufferJsonReader & reader, char c);
virtual ~JsonValueNull() { }
};
/*
* json的类static
*/
class TC_Json
{
public:
//json类型到字符串的转换
static string writeValue(const JsonValuePtr &p);
//解析成智能指针
static JsonValuePtr getValue(const string & str);
};
}
#endif

626
util/src/tc_json.cpp Normal file
View File

@ -0,0 +1,626 @@
#include "util/tc_json.h"
#include <math.h>
#include <sstream>
#include <iostream>
#include <iomanip>
#include "util/tc_common.h"
namespace tars
{
#define FILTER_SPACE while(isspace((int)c)) {c=reader.read();}
//json里面定义的空白字符
bool JsonValue::isspace(char c)
{
if(c == ' ' || c == '\t' || c == '\r' || c == '\n')
return true;
return false;
}
uint32_t JsonValue::getHex(BufferJsonReader & reader)
{
uint32_t iCode=0;
char c;
for(int iLoop=0;iLoop<4;iLoop++)
{
c=reader.read();
if(c>='a'&&c<='f')
iCode=iCode*16+c-'a'+10;
else if(c>='A'&&c<='F')
iCode=iCode*16+c-'A'+10;
else if(c>='0'&&c<='9')
iCode=iCode*16+c-'0';
else
{
char s[64];
snprintf(s, sizeof(s), "get string error3(\\u)[pos:%u]", (uint32_t)reader.getCur());
throw TC_Json_Exception(s);
}
}
return iCode;
}
void JsonValue::writeString(const string &str, ostream& ostr)
{
ostr << "\"";
std::string::const_iterator it(str.begin()), itEnd(str.end());
for (; it != itEnd; ++it)
{
switch(*it)
{
case '"':
ostr << "\\\"";
break;
case '\\':
ostr << "\\\\";
break;
case '/':
ostr << "\\/";
break;
case '\b':
ostr << "\\b";
break;
case '\f':
ostr << "\\f";
break;
case '\n':
ostr << "\\n";
break;
case '\r':
ostr << "\\r";
break;
case '\t':
ostr << "\\t";
break;
default:
{
if((unsigned char)(*it)<0x20)
{
char buf[16];
snprintf(buf,sizeof(buf),"\\u%04x",(unsigned char)*it);
ostr << string(buf,6);
}
else
{
ostr << *it;
}
break;
}
}
}
ostr << "\"";
}
void JsonValue::write(ostream& ostr) const
{
switch(getType())
{
case eJsonTypeString:
dynamic_cast<const JsonValueString*>(this)->write(ostr);
break;
case eJsonTypeNum:
dynamic_cast<const JsonValueNum*>(this)->write(ostr);
break;
case eJsonTypeObj:
dynamic_cast<const JsonValueObj*>(this)->write(ostr);
break;
case eJsonTypeArray:
dynamic_cast<const JsonValueArray*>(this)->write(ostr);
break;
case eJsonTypeBoolean:
dynamic_cast<const JsonValueBoolean*>(this)->write(ostr);
break;
case eJsonTypeNull:
dynamic_cast<const JsonValueNull*>(this)->write(ostr);
break;
default:
assert(false);
}
}
JsonValuePtr JsonValue::createJsonValue(BufferJsonReader & reader)
{
char c = reader.read();
FILTER_SPACE;
JsonValue* obj = NULL;
switch(c)
{
case '{':
obj = new JsonValueObj();
break;
case '[':
obj = new JsonValueArray();
break;
case '"':
obj = new JsonValueString();
break;
case 'T':
case 't':
case 'F':
case 'f':
obj = new JsonValueBoolean();
break;
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
case '8':
case '9':
case '-':
obj = new JsonValueNum();
break;
case 'n':
case 'N':
obj = new JsonValueNull();
break;
default:
char s[64];
snprintf(s, sizeof(s), "buffer overflow when peekBuf, over %u.", (uint32_t)reader.getCur());
throw TC_Json_Exception(s);
}
obj->read(reader, c);
return obj;
}
void JsonValueString::write(ostream& ostr) const
{
writeString(value, ostr);
}
void JsonValueString::read(BufferJsonReader & reader, char head)
{
const char * pChar=reader.getPoint();
uint32_t i=0;
while(1)
{
char c = reader.read();
if(c == '\\')
{
value.append(pChar,i);
pChar=pChar+i+2;
i=0;
c=reader.read();
switch(c)
{
case '\\':
case '\"':
case '/':
value.append(1, c);
break;
case 'b':
value.append(1,'\b');
break;
case 'f':
value.append(1,'\f');
break;
case 'n':
value.append(1,'\n');
break;
case 'r':
value.append(1,'\r');
break;
case 't':
value.append(1,'\t');
break;
case 'u':
// }
// if(c == '\\' || c == '\"' || c == '/')
// value.append(1,c);
// else if(c == 'b')
// value.append(1,'\b');
// else if(c == 'f')
// value.append(1,'\f');
// else if(c == 'n')
// value.append(1,'\n');
// else if(c == 'r')
// value.append(1,'\r');
// else if(c == 't')
// value.append(1,'\t');
// else if(c == 'u')
{
uint32_t iCode=getHex(reader);
if (iCode < 0x00080)
{
value.append(1,(char)(iCode & 0xFF));
}
else if (iCode < 0x00800)
{
value.append(1,(char)(0xC0 + ((iCode >> 6) & 0x1F)));
value.append(1,(char)(0x80 + (iCode & 0x3F)));
}
else if (iCode < 0x10000)
{
value.append(1,(char)(0xE0 + ((iCode >> 12) & 0x0F)));
value.append(1,(char)(0x80 + ((iCode >> 6) & 0x3F)));
value.append(1,(char)(0x80 + (iCode & 0x3F)));
}
else
{
value.append(1,(char)(0xF0 + ((iCode >> 18) & 0x07)));
value.append(1,(char)(0x80 + ((iCode >> 12) & 0x3F)));
value.append(1,(char)(0x80 + ((iCode >> 6) & 0x3F)));
value.append(1,(char)(0x80 + (iCode & 0x3F)));
}
pChar+=4;
}
}
}
else if(c==head)
break;
else
i++;
}
value.append(pChar,i);
}
void JsonValueNum::write(ostream& ostr) const
{
if (!isInt)
{
ostr << TC_Common::tostr(value);
}
else
{
ostr << (int64_t)value;
}
}
void JsonValueNum::read(BufferJsonReader & reader, char head)
{
bool bOk=true;
bool bFloat=false;
bool bExponential=false;
bool bNegative=false;
bool bExponentialNegative=false;
int64_t iInt=0;
double dFloat=0;
double dFloatRat=0;
int64_t iExponential=0;
if(head == '-')
{
bOk=false;
bNegative=true;
}
else
iInt=head-0x30;
char c;
bool bNeedBack=false;
while(1)
{
if(reader.hasEnd())
break;
c=reader.read();
if(c>=0x30 && c<=0x39)
{
bOk=true;
if(bExponential)
iExponential=iExponential*10+c-0x30;
else if(bFloat)
{
dFloat=dFloat+dFloatRat*(c-0x30);
dFloatRat=dFloatRat*0.1;
}
else
iInt=iInt*10+c-0x30;
}
else if(c == '.' && !bFloat && !bExponential && bOk)
{
bOk=false;
bFloat=true;
dFloatRat=0.1;
}
else if((c == 'e' || c == 'E') && !bExponential && bOk)
{
bOk=false;
bExponential=true;
iExponential=0;
if(reader.hasEnd())
break;
c=reader.read();
if(c == '-')
bExponentialNegative=true;
else if(c == '+')
bExponentialNegative=false;
else if(c>=0x30 && c<=0x39)
{
bOk=true;
bExponential=(bool)(c-0x30);
}
else
{
bNeedBack=true;
break;
}
}
else
{
bNeedBack=true;
break;
}
}
if(!bOk)
{
char s[64];
snprintf(s, sizeof(s), "get num error[pos:%u]", (uint32_t)reader.getCur());
throw TC_Json_Exception(s);
}
if(bNeedBack)
reader.back();
if(bExponentialNegative)
iExponential=0-iExponential;
double dResult=(iInt+dFloat)*pow(10,iExponential);
if(bNegative)
dResult=0-dResult;
this->value=dResult;
}
JsonValueObj::~JsonValueObj()
{
// for(auto it = value.begin(); it != value.end(); ++it)
// {
// delete it->second;
// }
// value.clear();
}
const JsonValuePtr& JsonValueObj::get(const char *name)
{
auto it = value.find(name);
if(it == value.end())
{
char s[64];
snprintf(s, sizeof(s), "get obj error(key is not exists)[key:%s]", name);
throw TC_Json_Exception(s);
}
return it->second;
}
void JsonValueObj::write(ostream& ostr) const
{
ostr << "{ ";
auto it = value.begin(); //unordered_map<string, JsonValuePtr>::const_iterator it(value.begin()), it_end(value.end());
while (it != value.end())
{
writeString(it->first, ostr);
ostr << ": " ;
it->second->write(ostr);
if(++it != value.end())
{
ostr << ", ";
}
}
ostr << " }";
}
void JsonValueObj::read(BufferJsonReader & reader, char cc)
{
bool bFirst=true;
while(1)
{
char c=reader.read();
FILTER_SPACE;
if(c == '}' && bFirst)
{
return;
}
bFirst=false;
if(c != '"')
{
char s[64];
snprintf(s, sizeof(s), "get obj error(key is not string)[pos:%u]", (uint32_t)reader.getCur());
throw TC_Json_Exception(s);
}
JsonValueString vs;
vs.read(reader, c);
c=reader.read();
FILTER_SPACE;
if(c != ':')
{
char s[64];
snprintf(s, sizeof(s), "get obj error(: not find)[pos:%u]", (uint32_t)reader.getCur());
throw TC_Json_Exception(s);
}
value.insert(make_pair(vs.value, JsonValue::createJsonValue(reader)));
c=reader.read();
FILTER_SPACE;
if(c == ',') continue;
if(c == '}')
{
return;
}
char s[64];
snprintf(s, sizeof(s), "get obj error(, not find)[pos:%u]", (uint32_t)reader.getCur());
throw TC_Json_Exception(s);
}
}
JsonValueArray::~JsonValueArray()
{
// for(auto it = value.begin(); it != value.end(); ++it)
// {
// delete *it;
// }
// value.clear();
}
void JsonValueArray::write(ostream& ostr) const
{
ostr << "[ ";
auto it = value.begin(); //vector<JsonValuePtr>::const_iterator it(value.begin()), it_end(value.end());
while (it != value.end())
{
(*it)->write(ostr);
if (++it != value.end())
{
ostr << ", ";
}
}
ostr << " ]";
}
void JsonValueArray::read(BufferJsonReader & reader, char cc)
{
bool bFirst=true;
while(1)
{
char c;
if(bFirst)
{
c=reader.read();
FILTER_SPACE;
if(c == ']')
{
return;
}
reader.back();
}
bFirst=false;
this->push_back(JsonValue::createJsonValue(reader));
c=reader.read();
FILTER_SPACE;
if(c == ',')
continue;
if(c == ']')
return;
char s[64];
snprintf(s, sizeof(s), "get vector error(, not find )[pos:%u]", (uint32_t)reader.getCur());
throw TC_Json_Exception(s);
}
}
void JsonValueBoolean::write(ostream& ostr) const
{
if(value)
ostr << "true";
else
ostr << "false";
}
//为了提高效率和代码好写就先这么写了
void JsonValueBoolean::read(BufferJsonReader & reader, char c)
{
bool bOk=false;
// bool bValue;
if(c=='t'||c=='T')
{
c=reader.read();
if(c=='r'||c=='R')
{
c=reader.read();
if(c=='u'||c=='U')
{
c=reader.read();
if(c=='e'||c=='E')
{
value=true;
bOk=true;
}
}
}
}
else if(c=='f'||c=='F')
{
c=reader.read();
if(c=='a'||c=='A')
{
c=reader.read();
if(c=='l'||c=='L')
{
c=reader.read();
if(c=='s'||c=='S')
{
c=reader.read();
if(c=='e'||c=='E')
{
value=false;
bOk=true;
}
}
}
}
}
if(!bOk)
{
char s[64];
snprintf(s, sizeof(s), "get bool error[pos:%u]", (uint32_t)reader.getCur());
throw TC_Json_Exception(s);
}
}
void JsonValueNull::write(ostream& ostr) const
{
ostr << "null";
}
void JsonValueNull::read(BufferJsonReader & reader, char c)
{
assert(c=='n' || c=='N');
bool bOk=false;
c=reader.read();
if(c=='u'||c=='U')
{
c=reader.read();
if(c=='l'||c=='L')
{
c=reader.read();
if(c=='l'||c=='L')
{
bOk=true;
}
}
}
if(!bOk)
{
char s[64];
snprintf(s, sizeof(s), "get NULL error[pos:%u]", (uint32_t)reader.getCur());
throw TC_Json_Exception(s);
}
}
string TC_Json::writeValue(const JsonValuePtr& p)
{
ostringstream ostr;
p->write(ostr);
return ostr.str();
}
JsonValuePtr TC_Json::getValue(const string & str)
{
BufferJsonReader reader;
reader.setBuffer(str.c_str(),str.length());
return JsonValue::createJsonValue(reader);
}
}