在JS中写测试往往让我们甚觉苦恼,众多的Test Framework,Test Runner, Test Assertion, Test Mocking, Testing Utilites,我们该如何选择呢?什么的测试需要借助浏览器,什么样的测试直接在后端可以测试? ES6, ES7编写的代码我们如何运行测试,生成测试报告?怎么样获取代码的测试覆盖率?
本系列文章将尝试抽丝剥茧的方式来让我们逐渐接触和了解JS的测试,为我们在JS项目上TDD,BDD扫除障碍。在这之前,让我们先了解几个基本概念: JavaScript, Node.js, V8引擎。
提到Javascript,大家首先想到的是日常使用的浏览器,现代浏览器包含了各种组件,包括渲染引擎、Javascript引擎等,其中Javascript引擎负责解释执行网页中的Javascript代码。作为Web前端最重要的语言之一,Javascript一直是前端工程师的专利。
而Node.js是一个基于Chrome V8引擎的后端JavaScript运行环境,其采用C++语言编写而成。V8引擎是node的心脏,V8采用JIT——即时编译技术,直接将js代码编译成本地平台的机器码。Node.js还提供了很多系统级的API,如文件操作、网络编程等。
Node.js自写测试断言
我们用最简单的方式来实现自己的assertEqual方法,如index.js:
const add = (a, b) => a + b;
const assertEqual = (actual, expected, message) => {
if(actual != expected) {
message = (message || "Assertion failed") + ", expect [ " + actual +" ], but get[ " + expected + " ]";
if (typeof Error !== "undefined") {
throw new Error(message);
}
throw message;
}
}
assertEqual(add(2,3), 4);
如果你的已经有支持Node.js的环境,可以执行node index.js
查看运行结果。程序会抛出异常且打印出错误堆栈。但是此时我们仅仅能测试一种情况就退出了,如果我们希望测试多种情况并返回错误提示结果,可以小小改造下程序:
const add = (a, b) => a + b;
let results = {
total: 0,
fail: 0
};
const assertEqual = (actual, expected, message) => {
results.total += 1;
if(actual != expected) {
results.fail += 1;
message = (message || "Assertion failed") + ", expect [ " + actual +" ], but get[ " + expected + " ]";
console.log(message);
}
}
assertEqual(add(2,3), 4);
assertEqual(add(6,7), 13);
assertEqual(add(7,7), 10);
console.log("Total " + results.total + " tests, " + results.fail + " failed, "
+ (results.total - results.fail) + " passed.");
运行后,得到的打印结果就有点意思了:
Assertion failed, expect [ 5 ], but get[ 4 ]
Assertion failed, expect [ 14 ], but get[ 10 ]
Total 3 tests, 2 failed, 1 passed.
浏览器的JS测试
上一段介绍的Node.js写的测试,需要有一个Node.js的环境,在浏览器上我们也能很方便执行我们的javascrip代码。但是需要注意的是浏览器(非Chrome)可能不支持const
以及let
关键字。
创建math.js:
function add(a, b) {
return a + b;
}
创建执行测试的index.html文件:
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>Javascript Test examples</title>
<script src="math.js"></script>
<script>
var results = {
total: 0,
fail: 0
};
function assertEqual(actual, expected, message) {
results.total += 1;
if(actual != expected) {
results.fail += 1;
message = (message || "Assertion failed") + ", expect [ " + actual +" ], but get[ " + expected + " ]";
console.log(message);
}
}
assertEqual(add(2,3), 4);
assertEqual(add(6,7), 13);
assertEqual(add(7,7), 10);
console.log("Total " + results.total + " tests, " + results.fail + " failed, "
+ (results.total - results.fail) + " passed.");
</script>
</head>
<body>
</body>
</html>
浏览器打开次index.html文件,打开浏览器的Console可以看到测试结果打印。