說實話,作為前端來說,單元測試,並不是一種必須的技能,但是確實一種可以讓你加法的技能
之前我一個庫添加了單元測試,加完之后感悟頗深,所以寫下這篇文章來記錄
環境搭建
一般來說,普通的庫,如果沒有添加 babel 的話,在 test 里面,也是不能使用 es6 的語法的
總結來說 test 文件的兼容性是和普通文件一樣的
正常 JS
這個搭建環境就有關於 babel 的搭建
npm i -D @babel/core @babel/preset-env @types/jest babel-jest jest
添加文件 babel.config.js
:
module.exports = {
presets: [
['@babel/preset-env', {targets: {node: 'current'}}],
'@babel/preset-typescript',
],
plugins: ["@babel/plugin-proposal-class-properties"]
};
如果有特效的語法需求,則需要添加其他的 babel 包,如:
npm i -D @babel/plugin-proposal-class-properties
在 package.json
中添加
"jest": {
"testMatch": \[
"<rootDir>/test/?(\*.)(spec|test).{js,jsx,ts,tsx}"
\],
"transform": {
"^.+\\\\.\[t|j\]s?$": "babel-jest"
},
"transformIgnorePatterns": \[
"<rootDir>/node\_modules/(?!(lodash-es|other-es-lib))"
\],
"testEnvironment": "jsdom",
"moduleFileExtensions": \[
"web.js",
"js",
"web.ts",
"ts",
"web.tsx",
"tsx",
"json",
"web.jsx",
"jsx",
"node"
\]
}
typescript
如果你使用的是 typescript,那么就不需要添加 babel,只需要如下三個庫即可
@types/jest ts-jest jest
在 package.json
中:
將
"transform": {
"^.+\\\\.\[t|j\]s?$": "babel-jest"
},
改為:
"transform": {
"^.+\\\\.\[t|j\]s?$": "ts-jest"
},
即可
關於 jest 參數
testMatch
[array
]
(默認值:[ "**/__tests__/**/*.[jt]s?(x)", "**/?(*.)+(spec|test).[jt]s?(x)" ]
)
Jest用於檢測測試文件的全局模式。 默認情況下,它會在__tests__文件夾內查找.js,.jsx,.ts和.tsx文件,以及帶有.test或.spec后綴的任何文件。 (例如,Component.test.js或Component.spec.js)。 它還會找到名為test.js或spec.js的文件。
transform
[object<string, pathToTransformer | [pathToTransformer, object]>]
默認值:undefined
從正則表達式到轉換器路徑的映射。 轉換器是提供同步功能以轉換源文件的模塊。 例如,如果您希望能夠在模塊或測試中使用節點尚不支持的新語言功能,則可以插入許多將JavaScript的未來版本編譯為當前版本的編譯器之一。 示例:請參見examples / typescript示例或[webpack教程](https:// jestjs。 io / docs / zh-Hans / webpack)
transformIgnorePatterns
[array
]
默認值︰["node_modules"]
轉換前與所有源文件路徑匹配的regexp模式字符串數組。 如果測試路徑與任何模式匹配,則將不會對其進行轉換。
testEnvironment
[string]
默認值︰"jsdom"
將用於測試的測試環境。 Jest中的默認環境是通過jsdom的類似於瀏覽器的環境。 如果要構建節點服務,則可以使用node選項來使用類似節點的環境。
moduleFileExtensions
[array
]
Default:["js", "json", "jsx", "ts", "tsx", "node"]
模塊使用的文件擴展名數組。 如果您需要模塊而未指定文件擴展名,則這些是Jest將按從左到右的順序查找的擴展名。
以上說明來自於 jest 官網
實戰
此處以我的庫 storage 來舉例
首先想要測試就要窮舉所以可能出現的情況
describe('Normal setting', () => {
test('set value', () => {
localStorage.clear();
const ins = storage.set('gre', '123456');
expect(ins.value).toBe('123456');
expect(ins.status).toBe(0);
expect(ins.key).toBe(preId + 'gre');
})
})
此處可以看做一個 localStorage 的 setItem;
expect 的作用是驗證 代碼的數據
和你想要得到的數據
是否相同,
如果相同,那么就代表測試通過,反正則未通過;
expect 后面跟着的方法很多,具體可以去官網查看:
官網傳送門
測試結果
使用命令來運行 test 文件:
"test": "jest --coverage"
test 的結果如下:
coverage
選項的作用是生成文檔,來記錄此次的測試結果,
而結果文檔基本生成在根文件目錄下的 coverage
目錄下,如圖:
在 lcov-report 目錄下,可直接在瀏覽器內運行 index.html ,這個文件的運行結果和 test 結果相同;
還有更加有用的東西:
運行 index.ts.html,可以看到一個類似於 git 提交的一個東西:
可以看到你的 test 代碼中,哪些代碼是運行到的,哪些是未運行到的,
再根據此文件的結果來優化另外的代碼;
結語
如果簡單的測試,其實是一個很容易的技能,但是各種情景都是不一樣的,比如有項目里加入了 react 和 redux 等等,光是配置都是比較麻煩的,所以后面還需要自己努力,去接觸各種各樣的情況
此文中使用的項目鏈接:
https://github.com/Grewer/storage-DAO