介绍
目前许多NoSql的数据库开始踊跃出现,作为性能比较出色的Nosql DB,Redis还是不错的选择,并且Redis 支持多种数据结构 SortSet,SET ,LIST, 并且在1.3.4版本支持SortSet的RANK功能,如果您想要计算排名服务不妨试试它、
Redis 官方网站:
http://code.google.com/p/redis/
以下是Redis 服务器端代码的分析
目前许多NoSql的数据库开始踊跃出现,作为性能比较出色的Nosql DB,Redis还是不错的选择,并且Redis 支持多种数据结构 SortSet,SET ,LIST, 并且在1.3.4版本支持SortSet的RANK功能,如果您想要计算排名服务不妨试试它、
Redis 官方网站:
http://code.google.com/p/redis/
以下是Redis 服务器端代码的分析
- //Title: Redis 深入分析之服务器篇
- //author: liuzheng
- //注意: 本篇文章仅供参考
- main(int argc, char **argv)
- {
- //一 加载配置
- loadServerConfig();
- ///二 配置项
- maxidletime,port,bindaddr,verbosity,logfile,dbnum,maxclients,maxmemory,masterhost,masterport,replstate,masterauth,glueoutputbuf,shareobjects,rdbcompression
- sharingpoolsize,daemonize,appendonly,appendfsyncm,requirepass,pidfile,dbfilename
- //三 初始化服务器
- initServer();
- //1.赋值server 属性
- //2.创建定时器,1ms执行一次
- aeCreateTimeEvent(server.el, 1, serverCron, NULL, NULL); //这个是个定时器链表
- //long long aeCreateTimeEvent(aeEventLoop *eventLoop, long long milliseconds,
- //aeTimeProc *proc, void *clientData,
- //aeEventFinalizerProc *finalizerProc)
- //3.server Crontab
- serverCron();
- //1.log数据库信息
- //2.log client connections
- //3.Show info about connections of clients
- //4.Close connections of timedout clients
- //5.1 Check if a background saving or AOF rewrite in progress terminated,
- //5.2 If there is not a background saving in progress check if we have to save now
- if (server.dirty >= sp->changes && now-server.lastsave > sp->seconds)
- rdbSaveBackground(server.dbfilename)-> rdbSave(server.dbfilename);
- //1.创建 "temp-%d.rdb"
- //2.
- for (j = 0; j < server.dbnum; j++) {
- redisDb *db = server.db+j;
- //1.保存类型
- //2.保存大小
- //遍历 DB 写入每个 entry
- //写入方式
- // 1.写入原始值-一般为string类型
- // 2.将内存值转换为string写入
- }
- //写入文件数据结构为
- //DB_TYPE,DB_LEN,Entry_type,Entry_len,Entry_object_string......
- //DB_TYPE,DB_LEN,Entry_type,Entry_len,Entry_object_string......
- //...16个DB
- //这里只有发生变化就会触发
- server.dirty++;
- //但是mset 使用的是如下算法
- server.dirty += (c->argc-1)/2;
- //6. Try to expire a few timed out keys
- //7. Check if we should connect to a MASTER ,SYNC
- syncWithMaster(void);
- //1.valid and auth
- //2.按块(1024)读取数据库文件
- while(可以读到数据)
- {
- nread = read(fd,buf,(dumpsize < 1024)?dumpsize:1024); #
- nwritten = write(dfd,buf,nread);
- nwritten.to(temp_file);
- }
- rename(temp_file,server.dbfilename);
- emptyDb();
- rdbLoad(server.dbfilename);
- //四 Load File to memory
- if (server.appendonly) {
- if (loadAppendOnlyFile(server.appendfilename) == REDIS_OK)
- redisLog(REDIS_NOTICE,"DB loaded from append only file");
- } else {
- if (rdbLoad(server.dbfilename) == REDIS_OK)
- redisLog(REDIS_NOTICE,"DB loaded from disk");
- }
- //五 侦听client事件
- aeCreateFileEvent(server.el, server.fd, AE_READABLE,acceptHandler, NULL) == AE_ERR)
- //aeCreateFileEvent(aeEventLoop *eventLoop, int fd, int mask,aeFileProc *proc, void *clientData)
- //六 开启所有侦听事件
- aeMain();
- //七 清楚完成事件
- aeDeleteEventLoop(server.el);
- }
- //Redis 数据结构介绍
- //DB struct
- //创建数据库
- server.db = zmalloc(sizeof(redisDb)*server.dbnum);
- for (j = 0; j < server.dbnum; j++) {
- server.db[j].dict = dictCreate(&hashDictType,NULL);
- server.db[j].expires = dictCreate(&setDictType,NULL);
- server.db[j].id = j;
- }
- /* Create a new hash table */
- dict *dictCreate(dictType *type, void *privDataPtr)
- {
- dict *ht = _dictAlloc(sizeof(*ht));
- _dictInit(ht,type,privDataPtr);
- return ht;
- }
- /* Initialize the hash table */
- int _dictInit(dict *ht, dictType *type,void *privDataPtr)
- {
- _dictReset(ht);
- ht->type = type;
- ht->privdata = privDataPtr;
- return DICT_OK;
- }
- /* Resize the table to the minimal size that contains all the elements,
- * but with the invariant of a USER/BUCKETS ration near to <= 1 */
- static void _dictReset(dict *ht)
- {
- ht->table = NULL;
- ht->size = 0;
- ht->sizemask = 0;
- ht->used = 0;
- }
- typedef struct dictEntry {
- void *key;
- void *val;
- struct dictEntry *next;
- } dictEntry;
- typedef struct dictType {
- unsigned int (*hashFunction)(const void *key);
- void *(*keyDup)(void *privdata, const void *key);
- void *(*valDup)(void *privdata, const void *obj);
- int (*keyCompare)(void *privdata, const void *key1, const void *key2);
- void (*keyDestructor)(void *privdata, void *key);
- void (*valDestructor)(void *privdata, void *obj);
- } dictType;
- typedef struct dict {
- dictEntry **table;
- dictType *type;
- unsigned long size;
- unsigned long sizemask;
- unsigned long used;
- void *privdata;
- } dict;
- typedef struct redisDb {
- dict *dict;
- dict *expires;
- int id;
- } redisDb;
- ///
- //Save Struct
- appendServerSaveParams(60*60,1); /* save after 1 hour and 1 change */
- appendServerSaveParams(300,100); /* save after 5 minutes and 100 changes */
- appendServerSaveParams(60,10000); /* save after 1 minute and 10000 changes */
- static void appendServerSaveParams(time_t seconds, int changes) {
- server.saveparams = zrealloc(server.saveparams,sizeof(struct saveparam)*(server.saveparamslen+1));
- server.saveparams[server.saveparamslen].seconds = seconds;
- server.saveparams[server.saveparamslen].changes = changes;
- server.saveparamslen++;
- }
- static void resetServerSaveParams() {
- zfree(server.saveparams);
- server.saveparams = NULL;
- server.saveparamslen = 0;
- }


1373

被折叠的 条评论
为什么被折叠?



