免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
楼主: linux_c_py_php
打印 上一主题 下一主题

[C++] [如何用状态机思想降低Server端开发复杂度? (GIT分支提供http server的实现框架示例) [复制链接]

论坛徽章:
4
水瓶座
日期:2013-09-06 12:27:30摩羯座
日期:2013-09-28 14:07:46处女座
日期:2013-10-24 14:25:01酉鸡
日期:2014-04-07 11:54:15
41 [报告]
发表于 2012-10-21 13:51 |只看该作者
这得提一下, 公司里是有公共开发框架的, 并且全部依赖公司其他库, 协议也是公司定死的协议(二进制协议头), 这个框架就只提供了两种工作方式:

1, 单线程epoll模式, 程序员填回调函数, 框架负责帮你解析出一个请求回调你的函数, 并给你发送应答的接口, 也就是一问一答, 必须立即响应.
2, 多线程模式, 一个线程一个连接, 愿意怎么阻塞就怎么阻塞.

在腾讯实习的时候, 腾讯的公共库框架我也读过, 当前公司的不读我也知道怎么回事. 要表达的意思就是, 这种轮询的实现方式或者状态机的使用一般是没人用的, 大家更擅长简单朴素的方案: 读入, 拆包, 解析, 写出, 这个过程我相信10个程序员9个都会, 这个比例绝对可信(否则谁聘他, 啥也干不了), 但你说nginx/lighttpd这种工作模式10个7,8个都会, 这一点我绝对不能赞同.

我在CU发个贴, 问我有个服务端, 想做Mysql查询, 耗时30秒, 怎么设计? 答案会是什么, 用脚趾头都猜得到, 是吧 :wink:

zylthinking 发表于 2012-10-21 13:28
其实这个所谓单线程服务器的思路, 随便抓十个人, 估计有7,8 个人知道。 具体不同也就是细节方面而已, 也 ...

论坛徽章:
0
42 [报告]
发表于 2012-10-21 14:34 |只看该作者
赞同传输层和业务逻辑层分离,所有业务逻辑均以event方式触发,各个消息模块间是异步(回掉式)消息模型。

不过,我的思路与你不同,业务逻辑是进程,而不是线程,业务逻辑以一个命名唯一的object存在(我称为service),可以存在于一个或多个进程中。
此外,系统中存在多个你所说的“代理”服务器(我称为gate),业务逻辑进程可以动态分布在不同的进程以及物理服务器上,调用时消息定位以其name为标识(类似域名的概念),在同一进程下直接转发,不同进程同一物理服务器则gate直接转发,不同物理服务器则经过2个gate跳转。
gate之间以TCP/IP互联,service和gate之间本机用sharememory,异地用TCP/IP。

另外,复杂的逻辑业务,能用好用对多线程非常困难,大量的锁极有可能死锁或者锁碰撞严重,退化到单线程都不如,因此对此部分一律我一律要求单线程异步消息。

论坛徽章:
0
43 [报告]
发表于 2012-10-21 14:42 |只看该作者
另外,推荐一个大牛正在开发中的项目,C + lua 的,估计颇合这里很多人的口味
https://github.com/cloudwu/skynet

论坛徽章:
5
狮子座
日期:2013-08-20 10:12:24午马
日期:2013-11-23 18:04:102015年辞旧岁徽章
日期:2015-03-03 16:54:152015亚冠之德黑兰石油
日期:2015-06-29 18:11:1115-16赛季CBA联赛之新疆
日期:2024-02-21 10:00:53
44 [报告]
发表于 2012-10-21 14:43 |只看该作者
回复 43# liuspring6


    这个就是我之前回帖所说的“云风正在做这事儿”………………

论坛徽章:
5
狮子座
日期:2013-08-20 10:12:24午马
日期:2013-11-23 18:04:102015年辞旧岁徽章
日期:2015-03-03 16:54:152015亚冠之德黑兰石油
日期:2015-06-29 18:11:1115-16赛季CBA联赛之新疆
日期:2024-02-21 10:00:53
45 [报告]
发表于 2012-10-21 14:45 |只看该作者
回复 42# liuspring6


    复杂的逻辑业务,脚本+coroutine是非常合适的。直接写业务逻辑,业务需要的异步操作全部在底层作为基础件委托好。而且还方便改,效率也不低(数量级上Lua比C慢20倍左右,基本上可以接受)

论坛徽章:
0
46 [报告]
发表于 2012-10-21 14:50 |只看该作者
回复 44# starwing83


    没错,前面说就是他的skynet,不过我也实现了一个,思路与他的不太一样,我个人比较排斥过多的线程,所以我以2 + N 线程模型(网络 + 逻辑 ,N基本不用,除了非常特别的需求),逻辑业务还是以进程方式封装。当然比不上云风那种大牛的版本,不过我试过,在3年前的笔记本(俺的开发机),10W次RPC调用,如果最优状态(都在一台物理机上),还是能达到13秒内完成,基本也能满足大部分场合了

论坛徽章:
4
水瓶座
日期:2013-09-06 12:27:30摩羯座
日期:2013-09-28 14:07:46处女座
日期:2013-10-24 14:25:01酉鸡
日期:2014-04-07 11:54:15
47 [报告]
发表于 2012-10-21 15:34 |只看该作者
看你的意思就是说, 你的Plugin都是独立运行的服务进程, 主框架永远像一个反向代理, 请求转给服务进程, 从服务进程拿到结果后发回客户端, 其实和web server +fcgi是一样的, 具体进程间通信用SOCKET/UNIX-DOMAIN-SOCKET/ShareMemory queue, 都是细节.

其实这一切方案或者说实现手法都是建立在能够开发一个优秀的Server个体基础上形成的, 集群也是单机联接起来的, 基础功与架构能力是关键.

liuspring6 发表于 2012-10-21 14:34
赞同传输层和业务逻辑层分离,所有业务逻辑均以event方式触发,各个消息模块间是异步(回掉式)消息模型。
...

论坛徽章:
0
48 [报告]
发表于 2012-10-21 16:02 |只看该作者
回复 47# linux_c_py_php


差不过就这意思,术业有专攻,让每个模块做尽可能少的事,这样bug比较少,开发速度也快。

论坛徽章:
1
双子座
日期:2013-11-14 17:43:24
49 [报告]
发表于 2012-10-22 11:51 |只看该作者
本帖最后由 star_in_sky 于 2012-10-22 11:58 编辑

LZ提出的在异步框架内处理阻塞式的业务(这里的例子中是MySQL的阻塞式查询)的方法,确实
非常漂亮。

我虽然不熟悉Linux下面的epoll事件循环模型;但是我仔细研究过Windows下面的IOCP模型,
也设计过一个状态机,来实现了一个网络通讯协议。

因为IOCP模型实际上包含了信号通知机制,所以通过使用状态机可以很好解决异步I/O数据包的
处理问题:其实不仅仅包括网络I/O,磁盘I/O也可以统一在这个IOCP模型下面。
所以,在处理异步I/O的问题上面,我同意LZ的观点:状态机能够降低Server端的复杂读。

但是,如果服务端整合了业务逻辑,如果业务模块的状态比较复杂(业务的状态变化往往有前后关联,
先后顺序),状态机还能否降低Server端的开发复杂度,我就表示怀疑了(因为在这样的情况下面,
更多时候需要兼顾健壮性,容错处理,性能问题,负载问题,维护问题,事情就没有那么简单了)。


论坛徽章:
0
50 [报告]
发表于 2012-10-22 11:59 |只看该作者
本帖最后由 aaxron 于 2012-10-22 12:01 编辑

epool + 线程池吧,设置合理的池大小

阻塞的就用线程,一个请求一个线程,简单明了

非阻塞就直接处理.



您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP