Node.js 单元测试:workflow

Talk is cheap, show me the code!

是否还记得小明在《 Node.js 单元测试之我要写测试》里引用的这句话么,不过引用了之后,小明就像跑路了一般再也没见其 code……其实呀,不知道大家有没有关注最近比较火 minggeJs, 稍微联想下你就知道小明最近在忙啥了 O(∩_∩)O~~

虽说小明现在还写不出 minggeJs 这样的前端库,不过,小明想说的是:当你准备开源一个库的时候,一定要写单元测试;当你要使用一个开源库的时候,单元测试的覆盖率是衡量质量的最重要标准之一

好了,扯了这么多闲话之后,明哥(不对,是小明……)接下来介绍一下在项目里单元测试整个流程是如何的。

Node.js 专属之 npm scripts

起初,小明将 Mocha 和 istanbul 装在全局命令下,然后每个项目都使用全局的命令,后来发现多人合作时会因为版本不一致而报错,因此果断将 Mocha 之类的装在项目的node_modules/ 下:

npm install mocha istanbul --save-dev

然后只需要执行下面两条命令即可:

# 执行单测./node_modules/.bin/mocha test/*.test.js --timeout 20000# 收集覆盖率报告./node_modules/.bin/istanbul cover ./node_modules/.bin/_mocha -- -u exports --reporter spec --timeout 20000

然而每次都执行这么长的命令让隔壁(座位)的老王实在看不下去了,于是就告诉小明 npm scripts 的用法。只需要在 package.json 里定义几个命令即可:

"scripts": {  "test": "./node_modules/.bin/mocha 'test/*.test.js' --timeout 20000",  "cov": "./node_modules/.bin/istanbul cover ./node_modules/.bin/_mocha -- -u exports 'test/*.test.js' --timeout 20000"}

如此之后,每次写完代码,小明只需要执行 npm run test/cov 即可,省事了很多。

不知道诸位有没有注意到,小明在 'test/*.test.js' 上故意加了一个引号,这一点也是小明被坑了之后才发现的:执行 shell 命令时,如果参数中包含如 test/*.test.js 这种 glob 模式,对应的 shell 会自动解析掉,但是不同的 shell 对 glob 的实现又不一致,因此就会出现匹配文件出错的问题,当加了引号之后,shell 会把参数原封不动的交给 Mocha(或者其他工具)来解析,这样才能保持不同 shell 的一致性。

当然,npm scripts 还有很多对于 Node.js 开发者很便利的功能,请参阅文末的相关链接。

构建利器 makefile

随着代码的积累,小明写的单测也越来越多,有时候可能只需要运行某一个测试文件,所以小明希望能通过命令行参数将需要测试的单个文件传进去,这时候 npm scripts 就显得捉襟见肘了。于是小明继续秉持着「有问题找老王」的原则,老王毫不犹豫的给小明推荐了makefile.

关于 makefile 的介绍,网上有很多的资料,小明的简单理解就是:makefile 就是将某个流程(如编译、打包、构建等)包含的所有相关命令集成到一个 make 命令下,极大的方便开发者。具体到目前的场景,可以参照如下的示例:

test := './test/*.test.js'timeout := 20000mocha := ./node_modules/.bin/mochaistanbul := ./node_modules/.bin/istanbulcoverageMocha := ./node_modules/.bin/_mocha

test:	echo '开始运行单测'	$(mocha) --timeout $(timeout) $(test)	echo '单测运行结束'

cov:	$(istanbul) cover $(coverageMocha) -- -u exports $(test) --timeout $(timeout)

# 区分命令和文件名称.PHONY: test

在项目里定义了如上的 makefile 文件后,只需要执行 make test 就可以跑单元测试了,并且上面提到的传参数的问题也可以迎刃而解:make test test=test/util.test.js. 相对于 npm scriptsmakefile 借助 shell 脚本的能力要强大灵活很多,然而一个不太好的消息是:windows 并不支持 makefile……

持续集成

在经过了上面的这些步骤之后,小明在本地已经可以完美的执行单元测试了,然而在跟小伙伴们合作的过程中,小明发现有的同学并不是很关注这个事情,单元测试没跑通过就将代码 push 到了远程仓库,这时候就需要其他同学来帮忙擦屁股,很是不方便。

于是,老王就告诉了小明持续集成这个东西,所谓持续集成,简单来讲就是:在代码 push 之后,对代码进行一系列的构建,比如 lint 检测、单元测试、部署等,借此提高代码的质量以及多人合作开发效率。而在 Node.js 领域,这方面比较优秀的工具就是 travis-ci 了,小明也顺便体验了一下 travis-ci, 按照其三步走的接入流程的确是非常之方便。

然而,小明平时开发的仓库大部分都是托管在内部的,没法使用面向 GitHub 的 travis-ci, 这一次小明决定不再去问老王了,程序员嘛,造轮子的功能还是要有的。于是,在一个多月的开发后,小明基于内部的其他服务做出了一个八九不离十的持续集成系统,名曰 UITest-ci:

这个系统可以运行单测、执行 lint、可以生成覆盖率报表、可以通知开发者集成结果、同时提供徽章服务,近乎完美。之后有时间了再详细介绍这个系统的设计和实现吧 :)

总结

至此,小明介绍了单元测试各个部分的相关概念以及整个工作流程是如何的,接下来,我们会面对项目中更具体的一些单测问题,比如:如何用 supertest 做接口测试、如何测试私有方法、如何针对命令行工具做单测等等。敬请期待~

相关链接

相关文章

Node.js 单元测试:我要写测试

本文转自:http://taobaofed.org/blog/2015/12/29/nodejs-unit-tests-workflow/

作者: 大果

时间: 2025-01-02 10:20:33

Node.js 单元测试:workflow的相关文章

Node.js 单元测试:我要写测试

小明是一个前端工程师,近期因为个人兴趣以及工作上的需要,开始做 Node.js 相关的项目.一个多月过去了,小明基于 Koa 搭出了自己的第一个 Node.js web 应用,在这个过程中,小明也遇到了很多的问题: 如何在上线时保证代码完全没问题? 每次增加功能时如何保证之前的功能是可用的? 随着代码增多,没有勇气和信心去重构代码 面对以上这些问题,小明作为一个前端工程师,惯性思维就是每次部署前先在页面上到处点点,然而一个机智的程序员怎么能把大好时间浪费在这些重复劳动上呢,于是小明就去咨询了组里

玩转Node.js单元测试

代码部署之前,进行一定的单元测试是十分必要的,这样能够有效并且持续保证代码质量.而实践表明,高质量的单元测试还可以帮助我们完善自己的代码.这篇博客将通过一些简单的测试案例,介绍几款Node.js测试模块: Mocha和Should,SuperTest.本文侧重于解释原理,各个模块的详细使用案例以后单独再聊. 为啥需要单元测试? 所谓单元测试,就是对某个函数或者API进行正确性验证.来看个简单的例子add1.js: function add(a, b) { return a + b; } 没错,我

我的Node.js学习之路(四)--单元测试_node.js

通过NPM安装: npm install nodeunit -g 支持命令行,浏览器运行. 各种断言. 在node.js下模块化对于方法导出exports, 如果是对象导出module.exports,模块儿是单元测试的基础,看下面的node.js代码: var fs = require('fs'), global=require('./global.js'); var utils = { startWith: function(s1, s) { if (s == null || s == "&

Node.js的UnitTest单元测试

在专业化的软件开发过程中,无论什么平台语言,现在都需要UnitTest单元测试. Node.js有built-in的Assert. 今天让我们来看一下Node.js的单元测试.在这儿我们使用nodeunit, 通过NPM安装: npm install nodeunit -g 支持命令行,浏览器运行. 各种断言. 在node.js下模块化对于方法导出exports, 如果是对象导出module.exports,模块儿是单元测试的基础,看下面的node.js代码: var fs = require(

当IoC遇见了Node.js

没有IoC的年代 一个简单的例子: var Engine = require('./engine'); var Wheel = require('./wheel'); var Car = function() { this.engine = new Engine(); this.wheel = new Wheel(); } Car.prototype.run = function() { this.engine.run(); this.wheel.run(); console.log('run

使用Node.js完成的第一个项目的实践总结

项目简介 这是一个资产管理项目,主要的目的就是实现对资产的无纸化管理.通过为每个资产生成二维码,来联合移动终端完成对资产的审核等.这个项目既提供了Web端的管理界面也提供移动端(Andorid)的资产审核.派发等相关功能. 我们用Node.js构建该项目的Web端以及移动端的Serveice API. 项目主框架:Express 简介 Express 是一个非常流行的node.js的web框架.基于connect(node中间件框架).提供了很多便于处理http请求等web开发相关的扩展. Ex

CodePipeline 持续集成/持续交付快速入门-- Node.js篇

本文演示如何使用Codepipeline构建一个Node.js项目并部署到ECS. 资源准备和限制 申请开通AliyunCodePipelineDefaultRole 服务 创建一台ECS(经典网络或VPC均可) 创建一个OSS的bucket 部署目标机器的操作系统:目前支持Ubutu 16.04, 14.04, Centos 7.3, 7.2, 6.8, Alinux 17.1操作系统. 源码地址:目前支持git协议的代码仓库. 在"用户证书"处根据项目配置设置用户凭证,比如gith

Node.js面试题之2017

本文讲的是Node.js面试题之2017, 为了保证可读性,本文采用意译而非直译. 问题 什么是错误优先的回调函数? 如何避免回调地狱? 什么是Promise? 用什么工具保证一致的代码风格?为什么要这样? 什么是Stub?举例说明 什么是测试金字塔?举例说明 最喜欢哪个HTTP框架?为什么? Cookies如何防范XSS攻击? 如何保证依赖的安全性? 答案 1. 什么是错误优先的回调函数? 错误优先的回调函数(Error-First Callback)用于同时返回错误和数据.第一个参数返回错误

最受欢迎的5款Node.js端到端测试框架

笔者在本文中会结合自身实践和 GitHub 趋势对比最受欢迎的 Node.js E2E 测试解决方案,期望对大家的技术选型有帮助 测试,尤其是自动化测试在现代 WEB 工程中有着非常重要的角色,与交付过程集成良好的自动化测试流程可以在新版发布时帮你快速回归产品功能,也可以充当产品文档.测试因粒度不同又可以分为单元测试.接口测试.功能测试.在 WEB 领域,功能测试亦称为端到端测试(End to End Test,简称 E2E 测试),笔者在本文中会结合自身实践和 GitHub 趋势对比最受欢迎的