现在业务需要这样一个功能:
需要一个类似定时任务的一个功能,比如用户开始某一个任务,假设时间限制30分钟。不管用户是否完成该任务,到
30
分钟(1800
秒)后更新该任务状态或更新该任务对应的其它业务数据。不要访问触发有效期判断。
注册定时器:
参数:
- 回调时间:精确到秒。比如
10s
,10s
后执行回调url
接口。 - 回调
url
接口; - 回调参数:
json
字符串;
要求:
- 回调时间相对当前时间精确到秒,
且只回调一次
。 - 可以在回调前注销某一个回调定时器,让它别回调了。
不知道现在有什么好的办法来实现以上类似定时任务的功能?谢谢。
现在目前后台服务器是LNMP
环境,外加Redis
。
Redis
只会简单的存取操作,不会太复杂的。所以下面这个答案也没怎么看明白。不知道还有没有好一点解决方案,谢谢。
参考回答一:
依你目前的架构,这种需求,把回调参数扔
Redis
里,然后在一个sorted set
里把key
和回调时间记上,再>通过pub/sub
通知执行回调的服务。执行回调的服务,收到通知之后就去
sorted set
里取最早的一个回调数据,然后等时间到了就执行回调。然后继续取下一个回调数据。取消的逻辑:把回调在
Redis
里的key
删掉,这样回调执行者取不到数据就不会执行了嘛。你的回调执行者当然不能依托于
php-fpm
那种东西了。单独起一个进程专门执行,PHP
可以做到的。当然你也可以用其它语言来实现。
参考回答二:
光看你那个例子,任务的功能:可以在创建任务的时候产生一个任务开始时间,然后利用
lnmp
里的linux
crontab
功能,定时每秒执行一次你的URL API
,逻辑全部放在API
里,比如api
中先用sql
查询一遍是否有超时的任务,超时就停止,并执行你说的其他业务逻辑,这个你应该目前就非常清楚了。当然除了sql
还有优化空间,但是目前我建议你根据实际情况选择最简单的方案
laravel框架有一个命令, 可以完全满足你的要求.
原理就像你说问题下面的说明.
会向redis里面添加一个json数据, 以及你要执行任务的时间.
json数据包括你要执行的任务及参数.
php artisan queue:listen
这个命令后在后台每秒查询一次redis队列, 有需要执行的任务就取出来执行.