基于TCP的分布式IM架构

IM框架由一个根网关服务器RootServer和一个数据中心DataCenter以及多个分布式服务器集群ChatServerCluster组成;

RootServer:根网关服务器,基于libfdk的高并发TCP服务器fdkrootserver;
DataCenter:在FreeBSD上搭建PostgreSQL;

一个服务器集群ServerCluster, 由
LoginServer(1#), GateServer(1#),
ChatServer(10#),
StateServer(2#), OfflineMsgServer(2#),
给 1M个用户提供正常的聊天服务;
除了登录验证, 不进行任何数据库操作, 在线状态管理全部交给分布式StateServer存储(Key-Value), 跨ChatServer的聊天通过GateServer检索StateServer确定Client的位置, 进行数据转发;
离线消息全部存储到 OfflineMsgServer中。

  1. LoginServer:登陆服务器, 基于libfdk的高并发TCP服务器fdkloginserver, 负责以下两个功能模块:
    • 用户登录验证, 向数据中心请求登陆验证信息;
    • 本集群内的聊天服务器负载平衡。
  2. GateServer:网关服务器, 基于libfdk的高并发TCP服务器fdkgateserver, 负责本集群内所有用户所在ChatServer的定位和查找,以及聊天消息的转发。
  3. ChatServer:聊天服务器, 基于libfdk的高并发TCP服务器fdkchatserver, 设计每一台服务于100K个客户端的聊天逻辑;
  4. StateServer:状态服务器,管理所有用户所在的服务器,由多台memcached组成分布式的位置信息管理 ;
  5. OfflineMsgServer:离线消息服务器,由多台memcached组成分布式的离线信息管理;

1)问题:每个集群的离线消息存储在本地,当客户端登录时,如何完整的获得离线消息?
SpriteRay:当用户B向离线用户A发送消息,ChatServer把B->A的离线消息存储在本地的OfflineMsgServer中,当A登录时,检索完在线用户后,顺带检索一下所有服务器集群,自然会获得所有离线消息,由客户端进行所有消息的排序。

libmemcache和queue.h的冲突

最近前段时间对libmemcache进行封装,准备加入到libfdk中,

由于memcached支持分布式查询,所以需要管理一个memcached服务器的列表,就想到了系统中自带的SLIST的宏,就在/usr/include/sys/queue.h中。

在编译的时候出现了一堆TAILQ的重复定义的错误。

less memcache.h,发现其中一堆从queue.h中截取的TAILQ的定义宏。

所以建议大家在编译的时候注意这个问题。

我的做法是,在memcache.h中加入#include <sys/queue.h>, 并注释掉那段对TAILQ定义的宏。