Mongodb源码分析
MongoDB提供了auto-sharding 功能。因为其是auto-sharding,即mongodb通过mongos(一个自动分片模块,用于构建一个大规模的可扩展的数据库集群,这个集群可以并入动态增加的机器)自动建立一个水平扩展的数据库集群系统,将数据库分表存储在sharding的各个节点上。
一个mongodb集群包括一些shards(包括一些mongod进程),mongos路由进程,一个或多个config服务器
下面是一些相关词汇说明:
Shards : 每一个shard包括一个或多个服务和存储数据的mongod进程(mongod是MongoDB数据的核心进程)典型的每个shard开启多个服务来提高服务的可用性。这些服务/mongod进程在shard中组成一个复制集Chunks: Chunk是一个来自特殊集合中的一个数据范围,(collection,minKey,maxKey)描叙一个chunk,它介于minKey和maxKey范围之间。例如chunks 的maxsize大小是100M,如果一个文件达到或超过这个范围时,会被切分到2个新的chunks中。当一个shard的数据过量时,chunks将会被迁移到其他的shards上。同样,chunks也可以迁移到其他的shards上
Config Servers : Config服务器存储着集群的metadata信息,包括每个服务器,每个shard的基本信息和chunk信息Config服务器主要存储的是chunk信息。每一个config服务器都复制了完整的chunk信息。
今天要介绍的源码主要是Mongos的主入口函数的执行流程,首先我们打开Mongos的项目(可通过打开源码dbdb_10.sln加载所有项目),如下图:
注:如果要调试mongos,需要设置一个mongod进程和一个Config Server,形如:
d:mongodb>bin>mongod --dbpath d:mongodbdb --port 27012
d:mongodb>bin>mongod --configsvr --dbpath d:mongodbdb --port 27022
然后在vs2010中配置相应的boost路径信息及启动参数信息,如下图:
下面开始正文。首先打开mongos项目中的server.cpp文件,找到下面方法:
int main(int argc, char* argv[]) {
try {
return _main(argc, argv);
}
catch(DBException& e) {
cout << "uncaught exception in mongos main:" << endl;
cout << e.toString() << endl;
}
catch(std::exception& e) {
cout << "uncaught exception in mongos main:" << endl;
cout << e.what() << endl;
}
catch(...) {
cout << "uncaught exception in mongos main" << endl;
}
return 20;
}
该方法是mongos的主函数,代码很简,它主要是try方式执行_main方法,下面是_main的执行流程:
int _main(int argc, char* argv[]) {
static StaticObserver staticObserver;
mongosCommand = argv[0];
//声明options信息描述对象
po::options_description options("General options");
po::options_description sharding_options("Sharding options");
po::options_description hidden("Hidden options");
po::positional_options_description positional;CmdLine::addGlobalOptions( options , hidden );
//添加sharding选项描述信息
sharding_options.add_options()
( "configdb" , po::value<string>() , "1 or 3 comma separated config servers" )
( "test" , "just run unit tests" )
( "upgrade" , "upgrade meta data version" )
( "chunkSize" , po::value<int>(), "maximum amount of data per chunk" )
( "ipv6", "enable IPv6 support (disabled by default)" )
( "jsonp","allow JSONP access via http (has security implications)" )
;options.add(sharding_options);
.....
在完成option描述信息的初始化操作之后,下面就开始对启动命令行参数进行分析和执行了,如下:
.....
// parse options
po::variables_map params;
//对argc,argv进行分析并转换成params,以便下面使用
if ( ! CmdLine::store( argc , argv , options , hidden , positional , params ) )
return 0;// The default value may vary depending on compile options, but for mongos
// we want durability to be disabled.
cmdLine.dur = false;
//如果是help
if ( params.count( "help" ) ) {
cout << options << endl;
return 0;
}
//如果是版本信息
if ( params.count( "version" ) ) {
printShardingVersionInfo();
return 0;
}
//如要设置chunkSize
if ( params.count( "chunkSize" ) ) {
Chunk::MaxChunkSize = params["chunkSize"].as<int>() * 1024 * 1024;
}......
//必选项,设置configdb信息
if ( ! params.count( "configdb" ) ) {
out() << "error: no args for --configdb" << endl;
return 4;
}vector<string> configdbs;
//对参数configdb进行分割 (以,分割 )
splitStringDelim( params["configdb"].as<string>() , &configdbs , , );
//mongodb强制为1或3,具体原因不明
if ( configdbs.size() != 1 && configdbs.size() != 3 ) {
out() << "need either 1 or 3 configdbs" << endl;
return 5;
}// we either have a seeting were all process are in localhost or none is
for ( vector<string>::const_iterator it = configdbs.begin() ; it != configdbs.end() ; ++it ) {
try {
// 根据地址参数实例化HostAndPort对象,如地址不合法则抛出异常
HostAndPort configAddr( *it );if ( it == configdbs.begin() ) {
grid.setAllowLocalHost( configAddr.isLocalHost() );
补充:软件开发 , C语言 ,