关于 HTTP 服务器实现的小白级别的问题

2021-03-10 16:32:00 +08:00
 fireleaves

我也是一个后端开发,但是做的都是和客户端直接建立长连接的,例如 TCP 或者 Web socket 。所以对 HTTP 的服务端的实现方式有点好奇。

主要问题在于,如果一个 HTTP 请求是需要去数据库取数据的或者耗时较长的,那么服务器怎么异步的处理这个请求呢?还是说不管请求是什么类型的,都同步的处理完,然后再返回?

举个栗子:

客户端发起登录,服务器收到请求需要去数据库中获取玩家数据。

对于长链接,可以在收到客户端请求之后,发起数据库操作,流程就此中止,服务器可以在此时处理其他请求,异步等数据库返回结果,再回调完成登录的后续处理,返回给客户端下行协议。

HTTP 好像不能把请求缓存起来,等待后边数据库触发之后再处理。是可以缓存再处理而我不知道呢?还是大家用 Redis 等查询耗时低的数据库解决呢?

纯小白,还请大家不吝赐教去。

2468 次点击
所在节点    程序员
23 条回复
lidongyo
2021-03-10 16:38:45 +08:00
所以类似场景都一般不用 HTTP
fireleaves
2021-03-10 16:40:15 +08:00
@lidongyo 那对于网站来说,像登录这种请求,都是先建立好长链接吗? Web socket ?
j0hnj
2021-03-10 16:40:19 +08:00
这种一般是先请求创建一个任务,服务端返回一个任务 ID,之后客户端轮询这个任务 ID,直到任务完成
fireleaves
2021-03-10 16:41:22 +08:00
@j0hnj 牛啊,这种方式可以的
lidongyo
2021-03-10 16:47:04 +08:00
@j0hnj 楼主钻牛角尖,非得从现代回到远古时期
hello2060
2021-03-10 16:50:15 +08:00
@fireleaves 登录应该就是同步的啊,登陆能用多久,没有异步的登录吧
clayyj1210
2021-03-10 16:51:52 +08:00
你可以从长连接的角度来看 HTTP,每次 HTTP 请求①相当于长连接中的客户端请求,HTTP 请求到服务器端之后流程中止,中止之后(如果业务场景允许,就是等待长时间的操作;如果业务场景不允许,那可能就是返回失败或者采用别的方式如 Redis 来减小时间)。
这时候客户端可以发起其它的 HTTP 请求②,不过这两个 HTTP 请求是相互独立的,没有采用相同的 TCP 链接。
当前面的中止结束之后,通过 HTTP 请求①链接将数据返回。
HTTP 请求②的处理同理返回。
fireleaves
2021-03-10 16:58:59 +08:00
@lidongyo 我是真的不懂呀,不知道网站那种的 HTTP 请求是怎么实现的
fireleaves
2021-03-10 17:02:26 +08:00
@clayyj1210 理解了,就是类似于#4 的那种任务 ID,不断轮询,直到服务器完成的时候在某次的轮询中下行结果
baiyi
2021-03-10 17:05:34 +08:00
对于 HTTP 协议本身来说是有异步这个响应结果的,它的 202 Accepted 状态码的响应就是告诉客户端请求已经接受了,但还没有处理,并且不保证在处理的过程中是否一定能成功。

从这个角度来说,只用 HTTP 就需要服务端再提供一个查询的接口,客户端在请求结束后不断的查询请求的处理状态。

还有一种情况是你的处理结果可以分批次传输,比如去数据库读取数据需要较长时间,那么就分别读取,分批次交给客户端,这时是可以在一个 HTTP 连接中完成的,通过 chunked 传输编码,让客户端和服务端保持长连接。
kikione
2021-03-10 17:35:52 +08:00
异步的话,不是应该有个回调地址么
yamasa
2021-03-10 17:39:39 +08:00
楼上哥们儿说的很好了。我们的服务里 chunked transfer encoding 和异步接口轮询两种做法都涉及了。
acmore
2021-03-10 17:54:11 +08:00
一种简单的异步任务 HTTP 请求方案:

1. 第一次请求返回 202 Accepted 和一个 Job ID;
2. 之后轮询这个 Job ID,直到拿到结果为止;
YokitCoder
2021-03-10 17:59:07 +08:00
HTTP 一般不处理耗时较长的请求,非要处理一个是可以采用 redis 缓存加快查询结果,另一个就是借助 js 的 ajax 异步处理。
ikas
2021-03-10 19:11:26 +08:00
依赖的是操作系统 IO 的支持,想真的搞明白就看下 IO 模型,http 只不过是个上层应用协议
also24
2021-03-10 19:41:27 +08:00
关键词:
1 、长连接
2 、轮询
3 、长轮询
FucUrFrd
2021-03-10 21:48:48 +08:00
Oltp 大部分 200ms 以下,而 http nginx 尽量配成 10s 超时
fireleaves
2021-03-10 22:47:57 +08:00
@baiyi 感谢
fireleaves
2021-03-10 22:48:58 +08:00
@also24 老哥稳,我去了解一下。
laowudxf
2021-03-11 08:43:04 +08:00
比如我用 php 开发后台,就比较简单了,php-fpm 有个连接池,比如可以同时处理 10 个请求,其他的框架的话我知道有些是非阻塞类型的框架这种阻塞操作也不会影响下一个请求。

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/760378

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX