queue-fun —— nodejs下基于Promise的队列控制模块。
工作告一段落,闲来无事,写了一个在nodejs实现“半阻塞”的控制程序。
一直以来,nodejs以单线程非阻塞,高并发的特性而闻名。搞这个“半阻塞”是东西,有什么用呢?
场景一:
现在的web应用可有都是一个这样的结构:
http服务(node) > 接口(业务逻辑) > 数据库
很多时候,瓶颈一般出现在业务层,或者数据层。更多的可能是某一个业务的处理,拉下整个系统的性能。
当用户或一些不怀好意的人,故意大量调用这些处理逻辑,好吧,你nodejs是非阻塞的,这一大波处理请求就一窝蜂冲到到业务层,很可能导致整个系统性能下降,或者瘫痪。
如果这个时候,node层就把这些耗资源的请求,排好队,控制好并发,甚至分用户排成队,配置好不同身份的用户并发量。是不是很好。
场景二:
应用中,可能会有一些无需即时处理的同一类业务,处理前都需要收集一次资源,处理业务,处理后再清理一次。高消耗工作主要在收集或是清理上。
这个时候,我们可将要处理的业务暂存到队列中,当队列数量到达一个值或是某个时间点时,我们一次性处理完队列中的任务。在消耗上,只做一次“收集”、“清理”的操作。
可见,如果在小型的项目中如果node方便实现类似线程池的功能,对整个项目的稳定性及工作效率是有很大贡献的。
现在说一说我写的这一个“半阻塞”的东西,为什么要基于Promise;
如果你用过q.js或了解EC6,应该对Promise有所了解,不然还请先了解下。
我的想法是,并不需要把整个业务的后续处理全都放到队列中去,而只是将高消耗的那一部分放入队列,利用Promise的异部处理机制来处理后续的操作。
在编写代码的时候你几乎可以忘记队列的存在,但是他就在那里默默的工作着,代码可读性和灵活性没有丝毫影响。
queue-fun
queue-fun 是基于Promise的 运行队列控制类。
使用场景
- 巨量同逻辑业务平稳处理
- 间歇性高并发系统
- 控制单用户占用资源过高
队列
queue-fun.Queue(q)
初始化队列控制 参数q可传
- 无参数 队列使用内置的实现的Promise;
- q/ES6原生Promise 插入队列方法:
pushunshiftgojump返回对应的promise
实例化队列 new queue-fun.Queue()(runMax, con)
- runMax 并行运行队列方法的最大个数
- con 配置队列 开始 结束 事件,运行单元的 成功,失败 事件及配置执行单元出错的 重试 机制。
var queue = new queue-fun.Queue()(100,{
"event_succ":function(){} //成功
,"event_err":function(){} //失败
,"event_begin":function(){} //队列开始
,"event_end":function(){} //队列完成
,"event_add":function(){} //有执行项添加进执行单元后执行,注意go及jump不会触发
,"retryON":0 //队列单元出错重试次数
,"retryType":0 //重试模式true/false(优先/搁置)执行
})`
API
queue.push(promisefun, args[], con)
向队列中尾部添加运行单元 fun: promise function args: 传入的参数 con 默认值
{
'event_succ':null //一般没用,某些情况下,可能比then要方便
,'event_err':null //一般没用,某些情况下,可能比then要方便
,'Queue_event':true //默认会执行队列定义的回调
}
queue.unshift(promisefun, args[], con) 同push 向队列中头部添加运行单元
queue.go(promisefun, args[], con) 同push,添加后会启动队列.
queue.jump(promisefun, args[], con) 同unshift,添加后启动队列.
setMax(newMax)
修改并行数
queue.start()
启动队列
queue.stop()
暂停队列
queue.clear()
清空队列
demo
var queuefun = require('queue-fun'); //引入
//初始化Promise异步队列类
var Queue = queuefun.Queue();
//实列化最大并发为2的运行队列
var queue1 = new Queue(2,{
"event_succ":function(data){console.log('queue-succ:',data)} //成功
,"event_err":function(err){console.log('queue-succ:',data)} //失败
});
var q = queuefun.Q; //模块中简单实现了Q的基本功能,可以一试,
//定义一个Promise风格的异步方法
function testfun(i){
var deferred = q.defer();
setTimeout(function(){
if(i\ && i % 3 == 0){
deferred.reject(new Error("err " + i))
}else{
deferred.resolve(i)
}
},(Math.random() * 2000)>>0)
return deferred.promise;
}
//向队列添加运行单元
queue1.push(testfun,[1]) //添加运行项
queue1.go(testfun,[2]) //添加并自动启动队列
queue1.go(testfun,[3],{Queue_event:0}) //添加不会触发队列 回调的运行项.
queue1.go(testfun,[4]).then(
function(data){console.log('done-succ:',data)},
function(err){console.log('done-err:',err)}
)
queue1.go(testfun,[5],{
event_succ:function(data){console.log('conf-succ:',data)},
event_err:function(err){console.log('conf-err:',err)}
})
关于内置Promise实现类queuefun.Q
实现了Promises/A+规范及done,spread,fail;
API模仿Q;
模拟实现了 q.defer,q.Promise,q.all,q.any,q.nfcall,q.nfapply,q.denodeify 等函数.
.toPromis(obj).then()
如果你习惯了.then风格写代码,你可以尝试用toPromis将普通函数/语句包装一下,让他可以获得then方法,及捕获错误。
var add = function(a,b){return a+b;}
q.toPromis(function(){return add(a+b)})
.then(console.log,console.error)
待完善
- 集群支持
- 内存溢出隐患处理
- 其它Promise实现类的支持
安装:npm install quque-fun
github: https://github.com/cnwhy/queue-fun
queue-fun —— nodejs下基于Promise的队列控制模块。的更多相关文章
- dsp下基于双循环缓冲队列的视频采集和显示记录
对最近在设计的视频采集和显示缓冲机制做一个记录,以便以后使用. 视频采集和显示缓冲机制,其实是参考了Linux下v4L2的驱动机制,其采用输入多缓冲frame,输出多缓冲的切换机制.简单的就是ping ...
- atitit. java queue 队列体系and自定义基于数据库的队列总结o7t
atitit. java queue 队列体系and自定义基于数据库的队列总结o7t 1. 阻塞队列和非阻塞队列 1 2. java.util.Queue接口, 1 3. ConcurrentLink ...
- atitit. java queue 队列体系and自己定义基于数据库的队列总结o7t
atitit. java queue 队列体系and自己定义基于数据库的队列总结o7t 1. 堵塞队列和非堵塞队列 1 2. java.util.Queue接口. 1 3. ConcurrentLin ...
- windows下基于sublime text3的nodejs环境搭建
第一步:先安装sublime text3.详细教程可自行百度,这边不具体介绍了. 第二步.安装nodejs插件,有两种方式 第一种方式:直接下载https://github.com/tanepiper ...
- 分布式学习(一)——基于ZooKeeper的队列爬虫
zookeeper 一直琢磨着分布式的东西怎么搞,公司也没有相关的项目能够参与,所以还是回归自己的专长来吧--基于ZooKeeper的分布式队列爬虫,由于没什么人能够一起沟通分布式的相关知识,下面的小 ...
- 基于promise用于浏览器和node.js的http客户端的axios
axios 是一个基于Promise 用于浏览器和 nodejs 的 HTTP 客户端,它本身具有以下特征: 从浏览器中创建 XMLHttpRequest 从 node.js 发出 http 请求 支 ...
- 【360开源】thinkjs:基于Promise的Node.js MVC框架 (转)
thinkjs是360奇舞团开源的一款Node.js MVC框架,该框架底层基于Promise来实现,很好的解决了Node.js里异步回调的问题.360奇舞团(奇虎75Team),是奇虎360公司We ...
- webpack+babel项目在IE下报Promise未定义错误引出的思考
低版本浏览器引起的问题 最近开发一个基于webpack+babel+react的项目,一般本地是在chrome浏览上面开发,chrome浏览器开发因为支持大部分新的js特性,所以一般不怎么需要poly ...
- 教你如何使用Java手写一个基于链表的队列
在上一篇博客[教你如何使用Java手写一个基于数组的队列]中已经介绍了队列,以及Java语言中对队列的实现,对队列不是很了解的可以我上一篇文章.那么,现在就直接进入主题吧. 这篇博客主要讲解的是如何使 ...
随机推荐
- java中的substring用法
String str="我是中国人"; str = str.substring(0, 2) +"_"+str.substring(3, 4); 结果:str=& ...
- 21、HierarchyViewer使用记录
1.是啥 HierachyViewer是一种能够方便开发人员了解activity中的布局信息的工具. 2.异常 HierachyViewer在未root过的设备或者低版本的设备是无法使用的 3.怎么办 ...
- [转载]关于android SDK安装Failed to fetch URL http://dl-ssl.google.com/android/repository/addons_list-1.xml出错
原文地址为:http://blog.csdn.net/springsky_/article/details/7442388 因为入行移动测试,所以很多测试环境的搭建.从中遇到了和这个GG同样的问题.怕 ...
- IEEE 802.11 标准列表
IEEE 802.11 标准列表 IEEE 802.11,1997年,原始标准(2Mbit/s,播在2.4GHz). IEEE 802.11a,1999年,物理层补充(54Mbit/s,播在5GHz) ...
- Noip模拟考第三题——饥饿游戏
饥饿游戏 (hungry.pas/c/cpp) [问题描述] Chanxer饿了,但是囊中羞涩,于是他去参加号称免费吃到饱的“饥饿游戏”. 这个游戏的规则是这样的,举办者会摆出一排 个食物,希望你能够 ...
- DXGI_FORMAT_R8G8B8A8_UNORM_SRGB
这个类型的resource 后面多个SRGB 表示SRGB空间是指gamma 矫正系数为2.2的色彩空间,这个问题我没有问别人,是我自己是上网查的,我觉得我不是个女人了......我又level up ...
- sigaction 函数
本文主要参考<unix环境高级编程> sigaction函数的功能是检查或修改与指定信号相关联的处理动作(可同时两种操作). int sigaction(int signo,con ...
- Codis集群的搭建与使用
一.简介 Codis是一个分布式的Redis解决方案,对于上层的应用来说,连接Codis Proxy和连接原生的Redis Server没有明显的区别(不支持的命令列表),上层应用可以像使用单机的Re ...
- mybatis处理查询map列表属性为null的问题,而导致查询map无该key对象
1.常规处理方法(数据库以mysql为例) IFNULL(m.last_use_time,) ) ) as last_lat if判断是否为null,设置一个默认值. 2.前台jsp页面处理,判断是否 ...
- Sqli-labs less 53
Less-53 和less51是一样的,只是这里的mysql错误不会在前台显示,但是对于stacked injection是一样的利用方式 http://127.0.0.1/sqli-labs/Les ...