每秒更新一次数据库的问题
发布于 9 年前 作者 nyrf 6231 次浏览 最后一次编辑是 8 年前 来自 问答

现在有个需求,物品价格是每秒自动下降10,一直降到0,这时所有用户看到的价格都在不停下降更新,试了在客户端设置每秒请求服务器一次,然后更新表中的价格-10,但发现这个好像读写数据库有点太频繁,不知道大家有啥好点的办法?

32 回复

计算时间不就好了

来自酷炫的 CNodeMD

@liygheart 计算时间好像不行,比如原来这个物品价格100,每秒下降10,过了1秒,用户打开看到价格应该是90,用户2打开看到的也应该是90. 但在服务器端要怎么设置呢,,感觉客户端用个js计算下时间差就可以了,但,,数据库也要更新的,有个偷懒的方法,就是只在客户端计算,然后某个用户买了后,把这个价格直接丢给服务器去更新。。

@nyrf 我的意思就是你说的这样

来自酷炫的 CNodeMD

卖家希望尽量卖高的价格 买家希望尽量以低价抢到

@liygheart 不过这样存在一个问题,用户就可以直接在客户端修改价格了,比如起始价100,直接post一个10的价格给服务器,对,可以在提交后在服务器再计算一次,测试了下,始终有一点误差。不知道还有没有别的办法

@nyrf 把初始时间和初始价格和减少的速度都存表,然后再以提交时间为准计算一遍

@nyrf 客户提交时在服务器端进行一次时间差计算,就算用户提交了10,服务器里肯定要再重新计算一次,交易肯定不能以客户提交的数据为主

你这规则是1秒减10,有时候客户提交浏览器,或者网络卡了一下估计2,3秒就过去了,还是要以服务器为主

如果我是客户的话,肯定会等到减到几十块的时候再提交

来自酷炫的 CNodeMD

在服务器计算,每秒更新一次,最好放内存。用socket.io每秒广播一次。客户拼网速 自豪地采用 CNodeJS ionic

有多少用户?百万级?

考虑过用缓存吗

@zouzhenxing 我也考虑在服务器计算,然后用socket.io广播,不过在服务器上计算每秒把价格更新一次,没想到啥好方法,不能像在客户端那样用settimeout,请问下能提供个思路不,谢谢

@jiangliqin 缓存想过,不过现在主要是在服务器端每秒更新一次,然后广播出去,只是服务器上我没找到啥好方法,想用redis,不知道redis有没有每秒自动更新一次的功能

@jingsam 一两万用户量吧,不是很大

这个有点像闪拍,但又不是,主要就是这个价格是每秒在不停下降,闪拍好实现,用户提交价格,服务器接收更新,广播出去,这个,暂时想不到什么办法在服务器端每秒更新一次价格

@nyrf redis读写性能肯定高于数据库啊,而且redis也有广播机制

@jiangliqin redis不是很熟,不知道redis有没有自动每秒更新一次的功能,看文档好像没有,

@nyrf 自动每秒更新可以设置啊,在存记录的同时增加个定时每秒更新的机制

@jiangliqin redis里有?我再去看看文档。

@nyrf 建议先做测试,可能最简单直接的方法就能符合你的需求

这个一典型多线程问题啊。 @nyrf 使用 ChildProcess.fork 开启一个新线程,每一秒更新内存中的数据,然后广播。 浏览器端使用webwork开线程接收。

@zouzhenxing 这的确是个办法,我去试下,谢谢

@nyrf 不用谢,注意,在改变价格的线程中不要做广播。具体为什么在朴灵的书中说得很清楚。setTimeout()必须用一个单独线程为执行,才有可能保证每秒运行一次,但不完全保证。除非你用一个独立核心来运行这个线程。

@zouzhenxing 暂时我的处理方式是,另开一线程,在线程中每秒更新价格,这个线程在只有这个物件在刚开卖时启动,启动后把物品status栏设置为sale,线程中价格每秒下降10,达到0后,商品下架。不过有个问题,如果中间有人购买了,这时这个线程还在跑,价格还是在下降。

@nyrf 在商品中你需要一个状态,或者用一个promise对象来控制商品。当为0或己卖时,线程停止更新数据,直到下一个商品上线。 From Noder

nodejs的优势就在于简化了java中的多线程协调问题。搞这种功能,node有优势。 From Noder

@zouzhenxing 我的想法是,在用户A点购买时,这时,价格就应该停止更新了,我想的是,用户A点购买后,传递个参数过去,线程拿到这个参数,就直接退出更新价格

@zouzhenxing 谢谢,我node还是菜鸟,不知道node线程能不能暂停和继续。

@nyrf 你只要把settimeout停了就可以了 From Noder

@zouzhenxing 嗯,对哦,好的,继续测试下,谢谢

@zouzhenxing 不好意思,再问下,我发现在setTImeout中改变价格,这时更新数据也要耗费时间,那这个时候是不是会出现不是每秒更新的情况了

@nyrf 所以你的商品数据要放到内存中,这样才可能保证你真的一秒更改。对于客户端来说,他接到数据的时间就看网络延时或你服务器广播的速度了。

@zouzhenxing 嗯,看来是要放内存了,不知道直接用mongodb会不会好点

回到顶部