您的位置:首页 > 数据库 > Mongodb

oci批量提取oracle数据写入mongodb或写成bson文件

2018-01-19 12:09 288 查看
项目需要,将oracle中上亿的数据表数据提取到mongdb,通过api单条插入,效率极低。通过第三方工具data-integration导入,效率还不够高。最终只能根据需求编写程序。

最初思路是解析oracle导出的dump二进制文件,在转换为bson二进制导入mongodb,但是根据测试,效率依旧较低。发现oracle与mongodb都采用批处理,效率算数有进步,最终决定采用编写程序实现。以下是在centos测试机器1万批量测得,鉴于代码未继续优化以及主机性能不强,后续效率还待测试:



在oracle导入mongodb时,通过oci批量提取数据,调用mongc driver批量写入mongddb,大幅提升效率,120万批量处理速度约21845条/s。代码还可继续优化,如使用oracle分页技术分多进程,理论提高页数倍,如有更好方式,也请分享,谢谢。以下为100万批量处理时速度记录:



oci程序中批量提取函数OCIDefineArrayOfStruct只能绑定静态数据,通过malloc开辟连续空间实现静态数组即可。以下为测试代码,后续请自行改进(需具备oci、mongodb、mongodb c driver、bson知识):

ToBson.h:

/**
* @file  ToBson.h
* @brief 导出ORACLE数据表或JSON文件为SBON文件、查看BSON文件工具
* @author   wangcc3
* @date     2018-1-5
* @version  001
* @copyright Copyright (c) 2018,AsiaInfo(FzOcs)
*/
#ifndef _TO_BSON_H_
#define _TO_BSON_H_

#include <string>
#include <oci.h>
#include <bson.h>
#include <bcon.h>
#include <mongoc.h>

namespace BM35 {

using namespace std;

// 地址对齐
#define ALIGNMENT 8
#define ADDRPADDING(p, a) (uintptr_t)(((uintptr_t)a - ((uintptr_t)p % (uintptr_t)a)) % (uintptr_t)a)
#define ADDRALIGN(p, a) (char *)(((uintptr_t)p + ((uintptr_t)a - 1))&~((uintptr_t)a -1))

// 默认最大行数
#define _MAX_ROW_NUMS_ 1000000

/*
typedef unsigned char  ub1;
typedef   signed char  sb1;
typedef unsigned short    ub2;
typedef   signed short    sb2;
typedef unsigned int  ub4;
typedef   signed int  sb4;
typedef         ub4      duword;
typedef         sb4      dsword;
typedef         dsword   dword;
*/

// oracle句柄结构体
typedef struct _oci_env_
{
OCIEnv      *envhp;
OCIError    *errhp;
OCISvcCtx   *svchp;
OCIServer   *srvhp;
OCISession	*usrhp;
OCIStmt	    *smthp;
OCIParam    *paramhp;
} OCI_ENV;

// 字段信息
class OracleField {
public:
char *colName;
char *colPoint;
int	colScale;
int colOffset;
ub2 colType;
ub2 colDefineType;
ub2 coLen;
ub4 colNameLen;
OCIDefine *ociDefine;
};

// 配置结构体
class OCI_CONF
{
public:
int flag;
long rownum;
long long begin;
long long end;
string table;
string sql;
string bfile; //可空
string jfile;
string tns;
string user;
string passwd;
string mongouri;
string mongodb;
string mongocollection;

void init() {
flag = 0;
rownum = 0;
begin = -1;
end = -1;
table = "";
sql = "";
bfile = ""; //可空
jfile = "";
passwd = "";
user = "";
tns = "";
mongouri = "";
mongodb = "";
mongocollection = "";
}
};

class ToBson
{

public:

ToBson();
~ToBson();

// 运行入口
bool run(string & sJsonFile);

// 运行入口
bool run(OCI_CONF & conf);

// 获得错误信息
string getErrInfo();

private:

// 运行
bool run();

// 输出容器配置信息
void printConf(vector<OCI_CONF>::iterator vIter);

// 关闭BSON文件
void closeFile();

/* flag: 1ORACLETOBSON  2JSONTOBSON  3BSONTOJSON 4READBSON 5BSONNUMS 6ORACLETOMONGODB
* 解析配置文件config.json:
{"note":"遍历完所有flag=1 or 6的配置时,tns、user、passwd三个字段必须存在,字段实际生效按第一次出现配置"}
{"note":"遍历完所有flag=6的配置时,uri、mdb二个字段必须存在,字段实际生效按第一次出现配置"}
{"note":"flag: 1ORACLETOBSON  2JSONTOBSON  3BSONTOJSON 4READBSON 5BSONNUMS 6ORACLETOMONGODB"}
{"flag":1,"tns":"SiC","user":"comm","passwd":"comm","table":"TEST9","bfile":"./TEST9.bson","sql":"","note":"bfile,[sql/table] can empty"}
{"flag":1,"table":"TEST10","bfile":"./TEST10.bson"}
{"flag":2,"bfile":"./test.bson","jfile":"./test.json","begin":0,"end":4,"note":"write 0-4 line json to bson file,default all"}
{"flag":3,"bfile":"./test.bson","jfile":"./test.json","begin":0,"end":4,"note":"write 0-4 line bson to json file,default all"}
{"flag":4,"bfile":"./TEST9.bson","begin":0,"end":4,"note":"read 0-4 line bson file info,default first 10 line"}
{"flag":5,"bfile":"./TEST9.bson","note":"get bson file line nums"}
{"flag":6,"table":"TEST9","uri":"mongodb://192.168.1.123:20000/","mdb":"mongodb","collection":"TEST9","note":"read oracle to mongodb"}
*/
bool ParseConfig(string sJsonFile);

// 获得SQL表名
bool getTableName(char * sql, string &strOut, bool onlyTable = true);

// 端口ORACLE连接
bool closeOracle();

// 端口MONGODB连接
bool closeMongodb();

// 将JSON文件写成BSON文件
bool writeBson(string sJsonFile, string sBsonFile, long lBegin = -1, long lEnd = -1);

// 将BSON文件写成JSON文件
bool writeJson(string sBsonFile, string sJsonFile, long lBegin = -1, long lEnd = -1);

// 初始化参数
bool initParameter(const string tableName = "",
const string fileName = "",
const long maxRowNum = _MAX_ROW_NUMS_);

// 初始化MONGODB参数
bool initMongodb(const string database = "",
const string table = "");

// 设置SQL语句
bool setSql(string sSql);

// 连接ORACLE
bool connectOracle(text *dnName,text *userName, text *passWord);

// 连接MONGODB
bool connectMongodb(const string &uri);

// 打开MONGODB数据库
bool useDB(const string &databaseName);

// 使用MONGODB数据表
bool useTable(const string &tableName);

// 插入MONGODB
bool insert(string & sJsonDoc);

// 将表数据写成BSON文件
bool writeTableInfo();

// 写入BSON文件
bool writeBson(bson_t * bsonDoc, FILE *fp);

// 检测ORACLE错误
bool checkErr(OCIError *pErr, sword lSattus);

// 打开BSON文件
bool openFile(const char * sFileName);

// 读取BSON文件信息
bool readBson(string sBsonFile, long lBegin = -1, long lEnd = -1);

// 获得ORACLE定义类型
ub2 getDefineType(ub2 iType);

// 获得缓存列偏移量
int getOffset(int col);

// 获得BSON文件记录数
long getBsonNum(string sBsonFile);

// 获得当前系统时间
string getTime();

// 去除换行
string trimNewline(char * str);

private:

bool bIsSetSql;
bool isOracle;
bool isMongodb;
bool isWriteMongo;
bool isInitDb;
char sTnsName[32];
char sUserName[32];
char sPassWord[32];
char sTableName[32];
char sErr[512] = {0};
char sqlText[512];
char rowNum[32];
string sSqlTable;
string sSqlRow;
string sBsonFile;
string errMsg;
string nowTable;
string mDatabaseName;
string mTableName;
string mUri;
char *pBuf;
char *pBufPoint;
text *colName;
FILE *fp;
bson_t * docBson;
mongoc_client_t      *mClient;
mongoc_database_t    *mDatabase;
mongoc_collection_t  *mCollection;
mongoc_bulk_operation_t *bulk;
OCIDefine *dfnhp;
OracleField *pOracleField;
int iRowLen;
ub2 coLen;
ub4 colNum;
ub4 colnameLen;
ub4 rrows;
ub4 psz;
sb4 para_status;
sb4 status;
long lMaxRowNum;
long lBufSize;
long long lNowRow;
long bsonNums;
bson_t bsonDoc;
bson_error_t  bson_error;
OCI_ENV stOciEnv;
vector<OCI_CONF> vConf;
vector<OCI_CONF>::iterator vIter;

};

}

#endif //_TO_BSON_H_


ToBson.cpp:

/**
* @file  ToBson.cpp
* @brief 导出ORACLE数据表或JSON文件为SBON文件、查看BSON文件工具
* @author   wangcc3
* @date     2018-1-5
* @version  001
* @copyright Copyright (c) 2018,AsiaInfo(FzOcs)
*/

#include <time.h>
#include <iostream>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include "ToBson.h"

namespace BM35 {

ToBson::ToBson() {

fp = NULL;
docBson = NULL;
errMsg = "NO ERROR";
sSqlRow = "";
bIsSetSql = false;
isInitDb = false;
mDatabaseName = "";
mTableName = "";
mUri = "";
mCollection = NULL;
mDatabase = NULL;
mClient = NULL;
bulk = NULL;
pOracleField = NULL;
pBuf = NULL;
bson_init(&bsonDoc);
memset(sTableName, 0, sizeof(sTableName));
memset(sqlText, 0, sizeof(sqlText));
memset(sTnsName, 0, sizeof(sTnsName));
memset(sUserName, 0, sizeof(sUserName));
memset(sPassWord, 0, sizeof(sPassWord));
}

ToBson::~ToBson() {

if(pOracleField) {
for(int i = 0; i <colNum; i++) {
if(pOracleField[i].colName) {
delete [] pOracleField[i].colName;
pOracleField[i].colName = NULL;
}
}
delete[] pOracleField;
pOracleField = NULL;
}

if(pBuf) {
delete[] pBuf;
pBuf = NULL;
}

closeFile();
bson_destroy(&bsonDoc);
}

bool ToBson::initMongodb(const string database, const string table) {

if(database.empty() && mDatabaseName.empty()) {
errMsg = "Mongodb database is empty";
return false;
}

if(!database.empty()) {
if(!isInitDb) {
useDB(database);
} else if(database.compare(mDatabaseName)) {
if(!useDB(database))
return false;
}
} else
if(!useDB(mDatabaseName))
return false;

if(!table.empty()) {
useTable(table);
} else if(!nowTable.empty()) {
useTable(nowTable);
} else {
errMsg = "Mongodb table is empty";
return false;
}

return true;
}

bool ToBson::initParameter(const string tableName,
const string fileName,
const long maxRowNum) {

nowTable = "";
if(!tableName.empty()) {
strcpy(sTableName, tableName.c_str());
nowTable = sTableName;
} else if(bIsSetSql) {
if(!getTableName(sqlText, nowTable)) {
errMsg = "Parsing sql failure when getting the table name";
return false;
}
} else {
errMsg = "Parameter tableName and sql is empty";
return false;
}

if(!fileName.empty())
sBsonFile = fileName;
else
sBsonFile = "./" + nowTable + ".bson";

lMaxRowNum = maxRowNum;
return true;
}

void ToBson::printConf(vector<OCI_CONF>::iterator vIter) {

cout<<endl;
cout<<"Config Info:"<<endl;
cout<<"flag="<<vIter->flag<<endl;
cout<<"table="<<vIter->table<<endl;
cout<<"jfile="<<vIter->jfile<<endl;
cout<<"bfile="<<vIter->bfile<<endl;
cout<<"rownum="<<vIter->rownum<<endl;
cout<<"sql="<<vIter->sql<<endl;
cout<<"begin="<<vIter->begin<<endl;
cout<<"end="<<vIter->end<<endl;
cout<<endl;
}

string ToBson::trimNewline(char * str) {
string _str = str;
if(!_str.empty() )
{
_str.erase(_str.find_last_not_of('\r') + 1);
_str.erase(_str.find_last_not_of('\n') + 1);
}
return _str;
}

bool ToBson::run(OCI_CONF & conf) {

vConf.clear();
if(conf.flag == 1 || conf.flag == 6) {
if(conf.tns.empty() ||
conf.user.empty() ||
conf.passwd.empty()) {
errMsg = "Parameter of tns or user or passed is empty";
return false;
}
strcpy(sTnsName, conf.tns.c_str());
strcpy(sUserName, conf.user.c_str());
strcpy(sPassWord, conf.passwd.c_str());
isOracle = true;

if(conf.flag == 6) {
if(conf.mongodb.empty() ||
conf.mongouri.empty()) {
errMsg = "Parameter of muri or mdb is empty";
return false;
}
mDatabaseName = conf.mongodb;
mTableName = conf.mongocollection;
mUri = conf.mongouri;
isMongodb = true;
} else
isMongodb = false;
} else
isOracle = false;

vConf.push_back(conf);
return run();
}

bool ToBson::run(string & sJsonFile) {

if(!ParseConfig(sJsonFile))
return false;
return run();
}

bool ToBson::run() {

long count = 0;

if(isOracle) {
// check environment
//export NLS_LANG=AMERICAN_AMERICA.ZHS16GBK
//Chinese: export NLS_LANG=AMERICAN_AMERICA.UTF8
if(getenv("NLS_LANG") == NULL)
{
errMsg = "Set env NLS_LANG first";
return false;
}

if(!connectOracle((text *)sTnsName, (text *)sUserName, (text *)sPassWord))
return false;

if(isMongodb)
if(!connectMongodb(mUri))
return false;
}

cout<<endl;
for (vIter=vConf.begin(); vIter!=vConf.end(); vIter++) {
if(vIter->flag == 1 ||
vIter->flag == 6) {
if(!isOracle) {
errMsg = "Can't connect oracle";
cout<<getErrInfo()<<endl;
printConf(vIter);
continue;
}
if((vIter->flag == 6) && !isMongodb) {
errMsg = "Can't connect mongodb";
cout<<getErrInfo()<<endl;
printConf(vIter);
continue;
}
if(!vIter->sql.empty())
setSql(vIter->sql);
if(!vIter->rownum)
vIter->rownum = _MAX_ROW_NUMS_;
if(!initParameter(vIter->table,vIter->bfile,vIter->rownum)) {
cout<<getErrInfo()<<endl;
printConf(vIter);
continue;
}
if(vIter->flag == 6) {
if(!initMongodb(vIter->mongodb, vIter->mongocollection)) {
cout<<getErrInfo()<<endl;
printConf(vIter);
continue;
}
isWriteMongo = true;
} else
isWriteMongo = false;

cout<<"Begin time:"<<getTime()<<endl;
if(!writeTableInfo()) {
cout<<getErrInfo()<<endl;
printConf(vIter);
continue;
}
cout<<"End time:"<<getTime()<<endl<<endl;
} else if(vIter->flag == 2) {
if(!writeBson(vIter->jfile, vIter->bfile, vIter->begin, vIter->end)) {
cout<<getErrInfo()<<endl;
printConf(vIter);
continue;
}
} else if(vIter->flag == 3) {
if(!writeJson(vIter->bfile, vIter->jfile, vIter->begin, vIter->end)) {
cout<<getErrInfo()<<endl;
printConf(vIter);
continue;
}
} else if(vIter->flag == 4) {
if(!readBson(vIter->bfile,vIter->begin,vIter->end)) {
cout<<getErrInfo()<<endl;
printConf(vIter);
continue;
}
} else if(vIter->flag == 5) {
cout<<"file "<<vIter->bfile<<" record nums="<<getBsonNum(vIter->bfile)<<endl<<endl;
}
count++;
}

cout<<endl<<"Total finish "<<count<<" config tasks"<<endl<<endl;

if(isOracle) {
if(!closeOracle())
return false;

if(isMongodb)
if(!closeMongodb())
return false;
}

return true;
}

bool ToBson::closeMongodb() {

if(mCollection)
mongoc_collection_destroy (mCollection);

if(mDatabase)
mongoc_database_destroy (mDatabase);

if(mClient)
mongoc_client_destroy (mClient);

mongoc_cleanup ();
return true;
}

string ToBson::getErrInfo() {
return errMsg;
}

bool ToBson::getTableName(char * sql, string &strOut, bool onlyTable) {

if(!sql || !strlen(sql)) {
errMsg = "sql is empty";
return false;
}
string strSql= sql;
string find_begin = "from";
size_t begin_postion;
begin_postion = strSql.find(find_begin);
if(onlyTable) {
string find_end = "where";
size_t end_postion = strSql.find(find_end);
if (end_postion != string::npos)
strOut = strSql.substr(begin_postion+5, end_postion-begin_postion-6);
else
strOut = strSql.substr(begin_postion+5);
} else {
if (begin_postion != string::npos)
strOut = strSql.substr(begin_postion+5);
else
return false;
}
return true;
}

string ToBson::getTime() {

char year[5] = {0};
char month[3] = {0};
char day[3] = {0};
char hour[3] = {0};
char min[3] = {0};
char second[3] = {0};
char nowTime[20] = {0};
//string cNowTime = "";
time_t timep;
struct tm *p;

time(&timep);
p = localtime(&timep);

sprintf(year,"%d",1900 + p->tm_year);

if(p->tm_mon < 10)
sprintf(month, "0%d", 1 + p->tm_mon);
else
sprintf(month, "%d", 1 + p->tm_mon);

if(p->tm_mday < 10)
sprintf(day, "0%d", p->tm_mday);
else
sprintf(day, "%d", p->tm_mday);

if(p->tm_hour < 10)
sprintf(hour,"0%d",p->tm_hour);
else
sprintf(hour,"%d",p->tm_hour);

if(p->tm_min < 10)
sprintf(min, "0%d", p->tm_min);
else
sprintf(min, "%d", p->tm_min);

if(p->tm_sec < 10)
sprintf(second,"0%d",p->tm_sec);
else
sprintf(second,"%d",p->tm_sec);

sprintf(nowTime, "%s/%s/%s %s:%s:%s",year, month, day, hour, min, second);

//cNowTime = cNowTime + year + month + day + hour + min + second;

return string(nowTime);
}

bool ToBson::connectMongodb(const string &uri) {

if(uri.empty()) {
errMsg = "Mongodb database connect uri is empty";
return false;
}
mongoc_init();
mClient = mongoc_client_new(uri.c_str());
if(!mClient) {
errMsg = "Create mongodb client failed!\n";
return false;
}

return true;
}

bool ToBson::useDB(const string &databaseName) {

if(databaseName.empty()) {
errMsg = "databaseName is empty\n";
return false;
}

if(mCollection) {
mongoc_collection_destroy(mCollection);
mCollection = NULL;
}

if(mDatabase) {
mongoc_database_destroy(mDatabase);
mDatabase = NULL;
}

mDatabase = mongoc_client_get_database(mClient, databaseName.c_str());
if(!mDatabase) {
errMsg = "Mongodb get database failed";
return false;
}

isInitDb = true;
return true;
}

bool ToBson::insert(string & sJsonDoc) {

docBson = bson_new_from_json ((const uint8_t*)sJsonDoc.c_str(), -1, &bson_error);

if (!docBson) {
errMsg = bson_error.message;
return false;
}

if(!mongoc_collection_insert(mCollection,
MONGOC_INSERT_NONE,
docBson, NULL, &bson_error)) {
errMsg = bson_error.message;
return false;
}

bson_destroy (docBson);

return true;
}

bool ToBson::useTable(const string &tableName) {

if(tableName.empty()) {
errMsg = "Mogndb tableName is empty\n";
return false;
}
if(mCollection) {
mongoc_collection_destroy(mCollection);
mCollection = NULL;
}

if(mDatabaseName.empty()) {
errMsg = "Mongodb database is null, use useDB to init database instacne";
return false;
}

mCollection = mongoc_client_get_collection(mClient,
mDatabaseName.c_str(),
tableName.c_str());
if(!mCollection) {
errMsg = "Mongodb get collection failed";
return false;
}

return true;
}

bool ToBson::connectOracle(text *dnName,text *userName, text *passWord) {

OCIEnvCreate(&stOciEnv.envhp, OCI_DEFAULT, (dvoid *) 0, 0, 0, 0, (size_t) 0, (dvoid **) 0);
OCIHandleAlloc((dvoid *) stOciEnv.envhp, (dvoid **)&stOciEnv.errhp, OCI_HTYPE_ERROR, 0, (dvoid **) 0);
OCIHandleAlloc((dvoid *) stOciEnv.envhp, (dvoid **)&stOciEnv.srvhp, OCI_HTYPE_SERVER, 0, (dvoid **) 0);
if(OCIServerAttach(stOciEnv.srvhp, stOciEnv.errhp, (text *) dnName, strlen((char *) dnName), OCI_DEFAULT) != OCI_SUCCESS) {
errMsg = "Connection database failure";
return false;
}
OCIHandleAlloc((dvoid *) stOciEnv.envhp, (dvoid **) &stOciEnv.svchp, OCI_HTYPE_SVCCTX, (size_t) 0, (dvoid **) 0);
OCIAttrSet((dvoid *) stOciEnv.svchp, OCI_HTYPE_SVCCTX, (dvoid *) stOciEnv.srvhp, (ub4) 0, OCI_ATTR_SERVER, (OCIError *) stOciEnv.errhp);
OCIHandleAlloc((dvoid *) stOciEnv.envhp, (dvoid **) &stOciEnv.usrhp, OCI_HTYPE_SESSION, (size_t) 0, (dvoid **) 0);
OCIAttrSet((dvoid *) stOciEnv.usrhp, OCI_HTYPE_SESSION, (dvoid *) userName, (ub4) strlen((char *) userName), (ub4) OCI_ATTR_USERNAME, stOciEnv.errhp);
OCIAttrSet((dvoid *) stOciEnv.usrhp, OCI_HTYPE_SESSION, (dvoid *) passWord, (ub4) strlen((char *) passWord), (ub4) OCI_ATTR_PASSWORD, stOciEnv.errhp);
OCIAttrSet((dvoid *) stOciEnv.svchp, OCI_HTYPE_SVCCTX, (dvoid *) stOciEnv.usrhp, (ub4) 0, OCI_ATTR_SESSION, (OCIError *) stOciEnv.errhp);
if(OCISessionBegin(stOciEnv.svchp, stOciEnv.errhp, stOciEnv.usrhp, OCI_CRED_RDBMS, OCI_DEFAULT) != OCI_SUCCESS) {
errMsg = "Setting up user session failure";
return false;
}

if(!checkErr(stOciEnv.errhp, OCIHandleAlloc((dvoid *) stOciEnv.envhp, (dvoid **) &stOciEnv.smthp, OCI_HTYPE_STMT, (size_t) 0, (dvoid **) 0 )))
return false;
return true;
}

bool ToBson::openFile(const char * sFileName) {

if(!sFileName) {
errMsg = "File is null";
return false;
}

if((fp=fopen(sFileName,"w+"))==NULL) {
errMsg = "Fail to open file";
return false;
}
return true;
}

void ToBson::closeFile() {

if(fp) {
fclose(fp);
fp = NULL;
}
}

bool ToBson::ParseConfig(string sJsonFile) {

if(sJsonFile.empty()) {
errMsg = "Config file path is empty";
return false;
}
vConf.clear();
OCI_CONF tmpConf;
tmpConf.init();
string key;
uint32_t len=0;
bson_json_reader_t *reader;
bson_error_t error;
bson_t doc = BSON_INITIALIZER;
int b;
bson_iter_t iter;
char errInfo[256] = { 0 };

if (!(reader = bson_json_reader_new_from_file (sJsonFile.c_str(), &error))) {
sprintf(errInfo, "Fail to open the json config file:%s", error.message);
errMsg = errInfo;
return false;
}

while ((b = bson_json_reader_read (reader, &doc, &error))) {
if (b < 0) {
//continue;
sprintf(errInfo, "Parsing json file failure:%s", error.message);
errMsg = errInfo;
return false;
}

if (bson_iter_init(&iter, &doc)) {
while(bson_iter_next(&iter)) {
key = bson_iter_key(&iter);
if(BSON_ITER_HOLDS_UTF8(&iter)) {
if(!key.compare("tns")) {
if(!strlen(sTnsName))
strcpy(sTnsName, bson_iter_utf8(&iter,&len));
} else if(!key.compare("user")) {
if(!strlen(sUserName))
strcpy(sUserName, bson_iter_utf8(&iter,&len));
} else if(!key.compare("passwd")) {
if(!strlen(sPassWord))
strcpy(sPassWord, bson_iter_utf8(&iter,&len));
} else if(!key.compare("table")) {
tmpConf.table = bson_iter_utf8(&iter,&len);
} else if(!key.compare("sql")) {
tmpConf.sql = bson_iter_utf8(&iter,&len);
} else if(!key.compare("bfile")) {
tmpConf.bfile = bson_iter_utf8(&iter,&len);
} else if(!key.compare("jfile")) {
tmpConf.jfile = bson_iter_utf8(&iter,&len);
} else if(!key.compare("uri")) {
if(mUri.empty())
mUri = bson_iter_utf8(&iter,&len);
} else if(!key.compare("mdb")) {
tmpConf.mongodb = bson_iter_utf8(&iter,&len);
if(mDatabaseName.empty())
mDatabaseName = tmpConf.mongodb;
} else if(!key.compare("collection")) {
tmpConf.mongocollection = bson_iter_utf8(&iter,&len);
} else
continue;
} else if(BSON_ITER_HOLDS_INT64(&iter)) {
if(!key.compare("flag")) {
tmpConf.flag = bson_iter_int64(&iter);
} else if(!key.compare("rownum")) {
tmpConf.rownum = bson_iter_int64(&iter);
} else if(!key.compare("begin")) {
tmpConf.begin = bson_iter_int64(&iter);
} else if(!key.compare("end")) {
tmpConf.end = bson_iter_int64(&iter);
} else
continue;
} else if(BSON_ITER_HOLDS_INT32(&iter)) {
if(!key.compare("flag")) {
tmpConf.flag = bson_iter_int32(&iter);
} else if(!key.compare("rownum")) {
tmpConf.rownum = bson_iter_int32(&iter);
} else if(!key.compare("begin")) {
tmpConf.begin = bson_iter_int32(&iter);
} else if(!key.compare("end")) {
tmpConf.end = bson_iter_int32(&iter);
} else
continue;
} else {
errMsg = "Conf file data type error";
}
}
if(tmpConf.flag == 1 ||
tmpConf.flag == 2 ||
tmpConf.flag == 3 ||
tmpConf.flag == 4 ||
tmpConf.flag == 5 ||
tmpConf.flag == 6) {
vConf.push_back(tmpConf);
tmpConf.init();
}

} else {
errMsg = "init bson iter error!";
return false;
//continue;
}
bson_reinit (&doc);
}

bson_json_reader_destroy (reader);
bson_destroy (&doc);

if(vConf.empty()) {
errMsg = "Conf vector are empty, initialization failed";
return false;
}

if(strlen(sTnsName) &&
strlen(sUserName) &&
strlen(sPassWord))
isOracle = true;
else
isOracle = false;

if(mUri.empty() ||
mDatabaseName.empty())
isMongodb = false;
else
isMongodb = true;

return true;
}

bool ToBson::writeJson(string sBsonFile, string sJsonFile, long lBegin, long lEnd) {

if(sBsonFile.empty()) {
errMsg = "The parameter sBsonFile is empty";
return false;
}

if(sJsonFile.empty()) {
errMsg = "The parameter sJsonFile is empty";
return false;
}

FILE *jsonfp;
char errInfo[256] = { 0 };
bson_reader_t *reader;
const bson_t *b;
bson_error_t error;
long lCount = 0;

if(!(reader = bson_reader_new_from_file(sBsonFile.c_str(), &error))) {
sprintf(errInfo, "Fail to open the bson file:%s", error.message);
errMsg = errInfo;
return false;
}

if((jsonfp=fopen(sJsonFile.c_str(),"w+"))==NULL) {
errMsg = "Fail to open the bson file";
return false;
}

while((b = bson_reader_read (reader, NULL))) {

if(lEnd >= 0) {
if(lCount >= lEnd)
break;
}

if(lBegin > lCount) {
lCount ++;
continue;
}

fprintf(jsonfp, "%s\n", bson_as_json (b, NULL));
lCount ++;
}
fclose(jsonfp);
bson_reader_destroy (reader);
return true;
}

bool ToBson::writeBson(string sJsonFile, string sBsonFile, long lBegin,long lEnd) {

//参数 /ccw/test.json   /ccw/test.bson
if(sJsonFile.empty() || sBsonFile.empty()) {
errMsg = "Parameter jsonfile or bsonfile is empty";
return false;
}

FILE *bsonfp;
bson_json_reader_t *reader;
bson_error_t error;
bson_t doc = BSON_INITIALIZER;
int b;
char errInfo[256] = { 0 };
long lCount = 0;

if((bsonfp=fopen(sBsonFile.c_str(),"w+"))==NULL) {
errMsg = "Fail to open the bson file";
return false;
}

if (!(reader = bson_json_reader_new_from_file (sJsonFile.c_str(), &error))) {
sprintf(errInfo, "Fail to open the json file:%s", error.message);
errMsg = errInfo;
return false;
}

while ((b = bson_json_reader_read (reader, &doc, &error))) {
if (b < 0) {
sprintf(errInfo, "Parsing json file failure:%s", error.message);
errMsg = errInfo;
return false;
}

if(lEnd >= 0) {
if(lCount >= lEnd)
break;
}

if(lBegin > lCount) {
lCount ++;
continue;
}

if (fwrite (bson_get_data(&doc), 1, doc.len, bsonfp) != doc.len) {
errMsg = "Write file failure";
return false;
}

lCount ++;
bson_reinit (&doc);
}

bson_json_reader_destroy (reader);
bson_destroy (&doc);
fclose(bsonfp);
return true;
}

bool ToBson::writeBson(bson_t * bsonDoc, FILE *fp) {

if(!fp) {
errMsg = "File pointers are not initialized";
return false;
}

if (fwrite(bson_get_data(bsonDoc), 1, bsonDoc->len, fp) != bsonDoc->len) {
errMsg = "Invocation of fwrite() error, write file failure";
return false;
}

return true;
}

long ToBson::getBsonNum(string sBsonFile) {

if(sBsonFile.empty()) {
errMsg = "Parameter sBsonFile is empty";
return -1;
}
char errInfo[256] = { 0 };
bson_reader_t *reader;
bson_error_t error;
long lCount = 0;
if(!(reader = bson_reader_new_from_file(sBsonFile.c_str(), &error))) {
sprintf(errInfo, "Fail to open the bson file:%s", error.message);
errMsg = errInfo;
return -1;
}

while(bson_reader_read (reader, NULL)) {
lCount ++;
}

bson_reader_destroy (reader);
return lCount;
}

bool ToBson::readBson(string sBsonFile,long lBegin,long lEnd) {

if(sBsonFile.empty()) {
errMsg = "The parameter sBsonFile is empty";
return false;
}
char errInfo[256] = { 0 };
bson_reader_t *reader;
const bson_t *b;
bson_error_t error;
char *str;
long lCount = 0;
if(!(reader = bson_reader_new_from_file(sBsonFile.c_str(), &error))) {
sprintf(errInfo, "Fail to open the bson file:%s", error.message);
errMsg = errInfo;
return false;
}

while((b = bson_reader_read (reader, NULL))) {

if((lBegin < 0) && (lEnd < 0)) {
if(lCount >= 10)
break;
}

if(lEnd >= 0) {
if(lCount >= lEnd)
break;
}

if(lBegin > lCount) {
lCount ++;
continue;
}

str = bson_as_json (b, NULL);
cout<<str<<endl;
bson_free (str);
lCount ++;
}

bson_reader_destroy (reader);
return true;
}

bool ToBson::setSql(string sSql) {

bIsSetSql = false;
if(sSql.empty()) {
errMsg = "sql is empty in setSql()";
return false;
}
sprintf(sqlText, "%s" , sSql.c_str());
bIsSetSql = true;
return true;
}

ub2 ToBson::getDefineType(ub2 iType) {

ub2 type;
switch(iType) {
case SQLT_AFC:
case SQLT_VCS:
case SQLT_CHR:
case SQLT_UIN:
case SQLT_INT:
case SQLT_FLT:
case SQLT_NUM:
case SQLT_RDD:
type = SQLT_STR;
break;
case SQLT_DAT:
type = SQLT_ODT;
break;
//    case SQLT_FLT:
//    case SQLT_NUM:
//        type = SQLT_VNU;
//        break;
default:
type = iType;
break;
}
return type;
}

int ToBson::getOffset(int col) {

if(col <= 0 )
return 0;

int offset = 0;
int i = 0;
for(i = col -1; i >= 0; i--) {
offset += (pOracleField[i].coLen + ALIGNMENT -1 + 1);
}
return offset;
}

bool ToBson::writeTableInfo() {

if(!bIsSetSql && !strlen(sTableName)) {
errMsg = "TableName or sql statement is not set!";
return false;
}

if(!bIsSetSql) {
sSqlRow.clear();
sprintf(sqlText, "select * from %s" ,sTableName);
sSqlRow = sSqlRow + "select count(*) from " + sTableName;
} else {
if(!getTableName(sqlText, sSqlTable, false)) {
errMsg = "Parsing sql failure when getting the table name";
return false;
}
sSqlRow = "select count(*) from " + sSqlTable;
}

if(!checkErr(stOciEnv.errhp, OCIStmtPrepare(stOciEnv.smthp, stOciEnv.errhp, (text *)sSqlRow.c_str(), (ub4)sSqlRow.length(), OCI_NTV_SYNTAX, OCI_DEFAULT)))
return false;

if(!checkErr(stOciEnv.errhp, OCIStmtExecute(stOciEnv.svchp, stOciEnv.smthp, stOciEnv.errhp, 0, 0, NULL, NULL, OCI_DEFAULT)))
return false;

para_status = OCIDefineByPos(stOciEnv.smthp, &dfnhp, stOciEnv.errhp, 1, (dvoid*)rowNum, sizeof(rowNum) + 1, SQLT_STR, 0, 0, 0, OCI_DEFAULT);
if (para_status != OCI_SUCCESS) {
checkErr(stOciEnv.errhp,para_status);
return false;
}

para_status = OCIStmtFetch(stOciEnv.smthp, stOciEnv.errhp, 1, OCI_FETCH_NEXT, OCI_DEFAULT);
if (para_status == OCI_NO_DATA) {
errMsg = "Get rowNum error";
return false;
}

cout<<"["<<nowTable<<"]Total row nums="<<rowNum<<endl;

lNowRow = atol(rowNum);
if(!lNowRow)
return true;
if(lNowRow < lMaxRowNum)
lMaxRowNum = lNowRow;

if(!checkErr(stOciEnv.errhp, OCIStmtPrepare(stOciEnv.smthp, stOciEnv.errhp, (text *)sqlText, (ub4)strlen((const char *) sqlText), OCI_NTV_SYNTAX, OCI_DEFAULT)))
return false;

if(!checkErr(stOciEnv.errhp, OCIStmtExecute(stOciEnv.svchp, stOciEnv.smthp, stOciEnv.errhp, 0, 0, NULL, NULL, OCI_DEFAULT)))
return false;

OCIAttrGet((dvoid*)stOciEnv.smthp, OCI_HTYPE_STMT, (dvoid*)&colNum, (ub4 *)0, OCI_ATTR_PARAM_COUNT, stOciEnv.errhp);

pOracleField = new OracleField[colNum];
if(!pOracleField) {
errMsg = "Allocation field list memory failure";
return false;
}

int i = 0;
iRowLen = 0;
for (i=0; i< colNum; i++) {
para_status = OCIParamGet(stOciEnv.smthp, OCI_HTYPE_STMT, stOciEnv.errhp, (void **) &stOciEnv.paramhp, (ub4)i+1);
OCIAttrGet((dvoid*)stOciEnv.paramhp, OCI_DTYPE_PARAM, (dvoid**)&colName, &pOracleField[i].colNameLen, OCI_ATTR_NAME, stOciEnv.errhp);
pOracleField[i].colName = new char[pOracleField->colNameLen+1];
if(!pOracleField[i].colName) {
errMsg = "Allocation field name memory failure";
return false;
}
strncpy(pOracleField[i].colName, (char*)colName, pOracleField[i].colNameLen);
pOracleField[i].colName[pOracleField[i].colNameLen] = '\0';
OCIAttrGet((dvoid*)stOciEnv.paramhp, OCI_DTYPE_PARAM, (dvoid *)&pOracleField[i].colScale, 0, OCI_ATTR_SCALE, stOciEnv.errhp);
OCIAttrGet((dvoid*)stOciEnv.paramhp, OCI_DTYPE_PARAM, (dvoid*)&pOracleField[i].colType, 0, OCI_ATTR_DATA_TYPE, stOciEnv.errhp);
OCIAttrGet((dvoid*)stOciEnv.paramhp, OCI_DTYPE_PARAM, (dvoid*)&pOracleField[i].coLen, 0, OCI_ATTR_DATA_SIZE, stOciEnv.errhp);

if(pOracleField[i].colType == SQLT_LNG ||
pOracleField[i].colType == SQLT_LBI ||
pOracleField[i].colType == SQLT_LVC ||
pOracleField[i].colType == SQLT_LVB ||
pOracleField[i].colType == SQLT_CLOB ||
pOracleField[i].colType == SQLT_BLOB) {
errMsg = "Type unsupport";
return false;
}

pOracleField[i].colDefineType = getDefineType(pOracleField[i].colType);
pOracleField[i].colOffset = getOffset(i);
iRowLen = iRowLen + pOracleField[i].coLen + (ALIGNMENT -1) + 1;
}
iRowLen = iRowLen + ((ALIGNMENT - (iRowLen % ALIGNMENT)) % ALIGNMENT);
lBufSize = iRowLen * lMaxRowNum;
pBuf = new char[lBufSize];
if(pBuf == NULL) {
errMsg = "Allocation buf memory failure";
return false;
}
memset(pBuf, 0, lBufSize);

for(i=0; i< colNum; i++) {
pBufPoint = pBuf + pOracleField[i].colOffset;
pOracleField[i].colPoint = ADDRALIGN(pBufPoint,ALIGNMENT);

para_status = OCIDefineByPos(stOciEnv.smthp, &pOracleField[i].ociDefine, stOciEnv.errhp, i+1, (dvoid*)pOracleField[i].colPoint, (sb4)(pOracleField[i].coLen + 1), pOracleField[i].colDefineType, 0, 0, 0, OCI_DEFAULT);
if(!checkErr(stOciEnv.errhp, para_status))
return false;

para_status=OCIDefineArrayOfStruct(pOracleField[i].ociDefine, stOciEnv.errhp, (ub4)iRowLen, 0, (ub4)0, 0);
if(!checkErr(stOciEnv.errhp, para_status))
return false;
}

if(!isWriteMongo) {
if(!openFile(sBsonFile.c_str()))
return false;
}

lNowRow = 0;
char tmpStr[32] = {0};
ub4 buf_size = 32;
psz = sizeof(ub4);
long j = 0;

while(true) {

status = OCIStmtFetch(stOciEnv.smthp, stOciEnv.errhp, lMaxRowNum, OCI_FETCH_NEXT, OCI_DEFAULT);

if(!checkErr(stOciEnv.errhp, OCIAttrGet((dvoid *)stOciEnv.smthp, (ub4)OCI_HTYPE_STMT, (dvoid *)&rrows, (ub4 *)&psz, (ub4)OCI_ATTR_ROWS_FETCHED, stOciEnv.errhp))) {
errMsg = "Rows fetched of OCIAttrGet() failed";
return false;
}

if(!rrows)
break;

if(isWriteMongo) {
bulk = mongoc_collection_create_bulk_operation(mCollection, true, NULL);
if(!bulk) {
errMsg = "Create bulk failed";
return false;
}
}

for(j = 0; j < rrows; j++) {
bson_reinit(&bsonDoc);
for(i = 0; i < colNum; i++) {
pBufPoint = pOracleField[i].colPoint + j*iRowLen;
//printf("value=%x\n",pBufPoint);
switch(pOracleField[i].colType) {
case SQLT_AFC:
case SQLT_VCS:
case SQLT_CHR:
case SQLT_RDD:
BSON_APPEND_UTF8(&bsonDoc, pOracleField[i].colName, pBufPoint);
break;
case SQLT_DAT:
para_status = OCIDateToText(stOciEnv.errhp,
(OCIDate*)pBufPoint,
(oratext*)"yyyymmddhh24miss",
strlen("yyyymmddhh24miss"),
(oratext*)"American",
strlen("American"),
&buf_size,
(oratext*)tmpStr);
if(!checkErr(stOciEnv.errhp, para_status))
cout<<"Use Func OCIDateToText() failed"<<endl;
if(strcmp(tmpStr, "00000000000000"))
BSON_APPEND_UTF8(&bsonDoc, pOracleField[i].colName, tmpStr);
tmpStr[0] = '\0';
break;
case SQLT_FLT:
case SQLT_NUM:
if(strlen(pBufPoint)) {
if(pOracleField[i].colScale != 0)
BSON_APPEND_DOUBLE(&bsonDoc, pOracleField[i].colName, atof(pBufPoint));
else
BSON_APPEND_INT64(&bsonDoc, pOracleField[i].colName, atoll(pBufPoint));
}
break;
case SQLT_UIN:
case SQLT_INT:
if(strlen(pBufPoint))
BSON_APPEND_INT64(&bsonDoc, pOracleField[i].colName, atoll(pBufPoint));
break;
case SQLT_BLOB:
case SQLT_BIN:
cout<<"type nosupper"<<endl;
errMsg = "type nosupper";
break;
default:
cout<<"other type nosupper"<<endl;
errMsg = "other type nosupper";
break;
}
pBufPoint[0] = '\0';
}

if(isWriteMongo) {
mongoc_bulk_operation_insert(bulk, &bsonDoc);
} else {
if(!writeBson(&bsonDoc,fp))
return false;
}
}

if(isWriteMongo) {
if (!mongoc_bulk_operation_execute(bulk, NULL, &bson_error)) {
errMsg = bson_error.message;
mongoc_bulk_operation_destroy(bulk);
return false;
}
mongoc_bulk_operation_destroy(bulk);
}

lNowRow = lNowRow + rrows;

// When rrows is less than lMaxRowNum, also return OCI_NO_DATA
if(status == OCI_NO_DATA)
break;
}

closeFile();

if(pOracleField) {
for(int i = 0; i <colNum; i++) {
if(pOracleField[i].colName) {
delete [] pOracleField[i].colName;
pOracleField[i].colName = NULL;
}
}
delete[] pOracleField;
pOracleField = NULL;
}

if(pBuf) {
delete[] pBuf;
pBuf = NULL;
}

cout <<"["<<nowTable<<"]Rows has been processed="<<lNowRow<<endl;

return true;
}

bool ToBson::checkErr(OCIError *pErr, sword lSattus) {

sb4 iErrCode = 0;
switch (lSattus) {
case OCI_SUCCESS:
strcpy(sErr, "OCI_SUCCESS");
break;
case OCI_SUCCESS_WITH_INFO:
strcpy(sErr, "OCI_SUCCESS_WITH_INFO");
break;
case OCI_NO_DATA:
strcpy(sErr, "OCI_NO_DATA");
break;
case OCI_ERROR:
OCIErrorGet((dvoid *) pErr, (ub4) 1, (text *) NULL, &iErrCode, (text *) sErr, (ub4) sizeof(sErr), (ub4) OCI_HTYPE_ERROR);
break;
case OCI_NEED_DATA:
strcpy(sErr, "OCI_NEED_DATA");
break;
case OCI_INVALID_HANDLE:
strcpy(sErr, "OCI_INVALID_HANDLE");
break;
case OCI_STILL_EXECUTING:
strcpy(sErr, "OCI_STILL_EXECUTING");
break;
case OCI_CONTINUE:
strcpy(sErr, "OCI_CONTINUE");
break;
default:
break;
}
if(OCI_SUCCESS != lSattus && OCI_SUCCESS_WITH_INFO != lSattus) {
errMsg = sErr;
return false;
}
return true;
}

bool ToBson::closeOracle() {

if(stOciEnv.smthp) {
if(!checkErr(stOciEnv.errhp, OCIHandleFree(stOciEnv.smthp, OCI_HTYPE_STMT)))
return false;
stOciEnv.smthp = NULL;
}

if(stOciEnv.svchp && stOciEnv.errhp && stOciEnv.usrhp) {
if(!checkErr(stOciEnv.errhp,OCISessionEnd(stOciEnv.svchp, stOciEnv.errhp, stOciEnv.usrhp, OCI_DEFAULT)))
return false;
}

if (stOciEnv.usrhp) {
if(!checkErr(stOciEnv.errhp, OCIHandleFree(stOciEnv.usrhp, OCI_HTYPE_SESSION)))
return false;
stOciEnv.usrhp = NULL;
}

if (stOciEnv.srvhp && stOciEnv.errhp) {
if (!checkErr(stOciEnv.errhp, OCIServerDetach(stOciEnv.srvhp, stOciEnv.errhp, OCI_DEFAULT)))
return false;
}

if (stOciEnv.srvhp) {
if (!checkErr(stOciEnv.errhp, OCIHandleFree(stOciEnv.srvhp, OCI_HTYPE_SERVER)))
return false;
stOciEnv.srvhp = NULL;
}

if(stOciEnv.svchp) {
if (!checkErr(stOciEnv.errhp, OCIHandleFree(stOciEnv.svchp, OCI_HTYPE_SVCCTX)))
return false;
stOciEnv.svchp = NULL;
}

if (stOciEnv.errhp) {
if (!checkErr(stOciEnv.errhp, OCIHandleFree(stOciEnv.errhp, OCI_HTYPE_ERROR)))
return false;
stOciEnv.errhp = NULL;
}

if (stOciEnv.envhp) {
if (!checkErr(stOciEnv.errhp,OCIHandleFree(stOciEnv.envhp, OCI_HTYPE_ENV)))
return false;
stOciEnv.envhp = NULL;
}
return true;
}

}

using namespace std;
using namespace BM35;

int main(int argc, char *argv[])
{
string confFile;
string strYN;
string rowNum;
string bFile;
string jFile;
string table;
string end;
string start;
string sql;
string tns;
string user;
string passwd;
string mDb;
string mUri;
string mCollection;
OCI_CONF conf;
conf.init();
for (int c; (c = getopt(argc, argv, "f:hHr:b:j:t:e:s:q:p:u:n:d:c:i:")) != EOF;) {
switch (c) {
case 'f':
confFile = optarg;
break;
case 'r':
rowNum = optarg;
break;
case 'i':
mUri = optarg;
break;
case 'd':
mDb = optarg;
break;
case 'c':
mCollection = optarg;
break;
case 'p':
passwd = optarg;
break;
case 'u':
user = optarg;
break;
case 'n':
tns = optarg;
break;
case 'b':
bFile = optarg;
break;
case 'j':
jFile = optarg;
break;
case 'q':
sql = optarg;
break;
case 't':
table = optarg;
break;
case 'e':
end = optarg;
break;
case 's':
start = optarg;
break;
case '?':
case 'h':
case 'H':
cout<<"Usage: ToBson  \n";
cout<<"   -f confFile [default ./ToBson.json]\n";
cout<<"      or 1,2,3,4,5 6[1ORACLETOBSON 2JSONTOBSON 3BSONTOJSON 4READBSON 5BSONNUMS 6ORACLETOMONGODB]\n";
cout<<"   -r rownum \n";
cout<<"   -p passwd \n";
cout<<"   -u user \n";
cout<<"   -n tns \n";
cout<<"   -b bfile \n";
cout<<"   -j jfile \n";
cout<<"   -q sql \n";
cout<<"   -s start \n";
cout<<"   -e end \n";
cout<<"   -t table \n";
cout<<"   -i uri \n";
cout<<"   -d mongoDb \n";
cout<<"   -c collection \n";
cout<<"   -h printf help\n";
cout<<"   example:ToBson -f ./ToBson.json \n";
cout<<"           ToBson -f 4 -b ./test9.bson\n";
cout<<"           ToBson -f 1 -u comm -p comm -n SiC -t test9\n";
cout<<"           ToBson -f 6 -u comm -p comm -n SiC -t test9 -d mongodb -i mongodb://192.168.1.123:20000/\n";
cout<<"   more detail reference file ToBson.json \n";
exit(-1);
break;
default:
break;
}
}

ToBson toBson;
if(confFile.empty()) {
cout<<"Using ./ToBson.json file to run(y/n):"<<endl;
cin>>strYN;
if(!strYN.compare("Y") ||
!strYN.compare("y"))
confFile = "./ToBson.json";
else
return 0;
} else if(!confFile.compare("1") ||
!confFile.compare("2") ||
!confFile.compare("3") ||
!confFile.compare("4") ||
!confFile.compare("5") ||
!confFile.compare("6")) {
conf.flag = atoi(confFile.c_str());
if(!rowNum.empty())
conf.rownum = atol(rowNum.c_str());
if(!end.empty())
conf.end = atoll(end.c_str());
if(!start.empty())
conf.begin = atoll(start.c_str());
conf.bfile = bFile;
conf.jfile = jFile;
conf.table = table;
conf.sql = sql;
conf.tns = tns;
conf.user = user;
conf.passwd = passwd;
conf.mongouri = mUri;
conf.mongocollection = mCollection;
conf.mongodb = mDb;

if(!toBson.run(conf)){
cout<<toBson.getErrInfo()<<endl;
return -1;
}
return 0;
}

if(!toBson.run(confFile)){
cout<<toBson.getErrInfo()<<endl;
return -1;
}
return 0;
}


 ToBson.json:

{"note":"遍历完所有flag=1 or 6的配置时,tns、user、passwd三个字段必须存在,字段实际生效按第一次出现配置"}
{"note":"遍历完所有flag=6的配置时,uri、mdb二个字段必须存在,字段实际生效按第一次出现配置"}
{"note":"flag: 1ORACLETOBSON  2JSONTOBSON  3BSONTOJSON 4READBSON 5BSONNUMS 6ORACLETOMONGODB"}
{"flag":1,"tns":"SiC","user":"comm","passwd":"comm","table":"TEST9","bfile":"./TEST9.bson","sql":"","note":"bfile,[sql/table] can empty"}
{"flag":1,"table":"TEST10","bfile":"./TEST10.bson"}
{"flag":2,"bfile":"./test.bson","jfile":"./test.json","begin":0,"end":4,"note":"write 0-4 line json to bson file,default all"}
{"flag":3,"bfile":"./test.bson","jfile":"./test.json","begin":0,"end":4,"note":"write 0-4 line bson to json file,default all"}
{"flag":4,"bfile":"./TEST9.bson","begin":0,"end":4,"note":"read 0-4 line bson file info,default first 10 line"}
{"flag":5,"bfile":"./TEST9.bson","note":"get bson file line nums"}
{"flag":6,"table":"TEST9","uri":"mongodb://192.168.1.123:20000/","mdb":"mongodb","collection":"TEST9","note":"read oracle to mongodb"}

ToBson.json_bak:

{"flag":6,"tns":"SiC","user":"comm","passwd":"comm","table":"TEST","uri":"mongodb://192.168.1.127:27017/","mdb":"mongodb","rownum":1200000}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息