JSDOM - 文档未定义
JSDOM - Document is not defined
我创建了一个非常简单的页面,它只显示一条消息,因为我正在尝试测试 JSDOM 以使用 document
。但是,我收到以下错误。
首先,我在网上看了无数的例子,加上Stack Overflow上的问题,但是连最简单的例子我都解决不了。作为旁注,我是 Javascript.
的新手
到目前为止我的代码如下:
根目录
--->index.html
--->module.js
--->包-lock.json
--->package.json
--->测试
--->--->messageTest.js
不同的文件如下:
index.html
<!doctype html>
<head>
<meta charset="utf-8">
<title>jsdom Unit Test</title>
</head>
<body>
<p id='msg'>Hello, World!</p>
<script src="module.js"></script>
</body>
</html>
module.js
function updateMsg(newMsg) {
document.getElementById('msg').innerHTML = newMsg;
}
updateMsg("Changing message");
module.exports = updateMsg;
package.json
{
"name": "message-example",
"version": "1.0.0",
"description": "Testing how to use the JSDOM",
"main": "module.js",
"scripts": {
"test": "mocha"
},
"author": "",
"license": "ISC",
"devDependencies": {
"chai": "^4.2.0",
"jsdom": "^15.1.1",
"mocha": "^6.2.0",
"mocha-jsdom": "^2.0.0",
"rewire": "^4.0.1",
"sinon": "^7.3.2"
}
}
messageTest.js
var updateMsg = require('../module.js');
const expect = require('chai').expect
const { JSDOM } = require('jsdom');
describe('updateMsg', function () {
before(function() {
return JSDOM.fromFile('index.html')
.then((dom) => {
global.window = dom.window;
global.document = window.document;
});
})
it ('updates the innerHTML of element with id "msg"', function () {
expect(document.getElementById('msg').innerHTML).to.equal('Hello, World!');
updateMsg('The new msg!');
expect(document.getElementById('msg').innerHTML).to.equal('The new msg!');
});
});
如果我 运行 使用 npm test
进行测试,我会在 module.js 的 document.getElementByID...
步骤得到 ReferenceError: document is not defined
错误 文件。
如果我删除 updateMsg("Changing message")
,我的测试显然 运行 没问题。
你在那个例子中有几个问题:
您正在混合 jsdom window 和全局节点上下文。避免分配给 global
(因为这样更容易犯错误),不要 require()
您想要 运行 的脚本在您的虚拟 window.
jsdom 默认阻止 运行ning on-page 脚本,所以你的 module.js 既不加载也不执行。你必须提供 { resources: "usable", runScripts: "outside-only" }
参数来解决这个问题(确保你阅读了 jsdom README 中的安全隐患)。
您没有等待 load
事件,因此您的测试是 运行 在 jsdom 有机会加载脚本之前。
工作代码看起来像这样:
const expect = require("chai").expect;
const { JSDOM } = require("jsdom");
describe("updateMsg", function() {
let jsdom;
before(async function() {
jsdom = await JSDOM.fromFile("index.html", {
resources: "usable",
runScripts: "dangerously"
});
await new Promise(resolve =>
jsdom.window.addEventListener("load", resolve)
);
});
it('updates the innerHTML of element with id "msg"', function() {
expect(jsdom.window.document.getElementById("msg").innerHTML).to.equal(
"Hello, World!"
);
jsdom.window.updateMsg("The new msg!");
expect(jsdom.window.document.getElementById("msg").innerHTML).to.equal(
"The new msg!"
);
});
});
您还需要从 module.js 中删除模块行,module
在浏览器中不存在。
我创建了一个非常简单的页面,它只显示一条消息,因为我正在尝试测试 JSDOM 以使用 document
。但是,我收到以下错误。
首先,我在网上看了无数的例子,加上Stack Overflow上的问题,但是连最简单的例子我都解决不了。作为旁注,我是 Javascript.
的新手到目前为止我的代码如下:
根目录
--->index.html
--->module.js
--->包-lock.json
--->package.json
--->测试
--->--->messageTest.js
不同的文件如下:
index.html
<!doctype html>
<head>
<meta charset="utf-8">
<title>jsdom Unit Test</title>
</head>
<body>
<p id='msg'>Hello, World!</p>
<script src="module.js"></script>
</body>
</html>
module.js
function updateMsg(newMsg) {
document.getElementById('msg').innerHTML = newMsg;
}
updateMsg("Changing message");
module.exports = updateMsg;
package.json
{
"name": "message-example",
"version": "1.0.0",
"description": "Testing how to use the JSDOM",
"main": "module.js",
"scripts": {
"test": "mocha"
},
"author": "",
"license": "ISC",
"devDependencies": {
"chai": "^4.2.0",
"jsdom": "^15.1.1",
"mocha": "^6.2.0",
"mocha-jsdom": "^2.0.0",
"rewire": "^4.0.1",
"sinon": "^7.3.2"
}
}
messageTest.js
var updateMsg = require('../module.js');
const expect = require('chai').expect
const { JSDOM } = require('jsdom');
describe('updateMsg', function () {
before(function() {
return JSDOM.fromFile('index.html')
.then((dom) => {
global.window = dom.window;
global.document = window.document;
});
})
it ('updates the innerHTML of element with id "msg"', function () {
expect(document.getElementById('msg').innerHTML).to.equal('Hello, World!');
updateMsg('The new msg!');
expect(document.getElementById('msg').innerHTML).to.equal('The new msg!');
});
});
如果我 运行 使用 npm test
进行测试,我会在 module.js 的 document.getElementByID...
步骤得到 ReferenceError: document is not defined
错误 文件。
如果我删除 updateMsg("Changing message")
,我的测试显然 运行 没问题。
你在那个例子中有几个问题:
您正在混合 jsdom window 和全局节点上下文。避免分配给
global
(因为这样更容易犯错误),不要require()
您想要 运行 的脚本在您的虚拟 window.jsdom 默认阻止 运行ning on-page 脚本,所以你的 module.js 既不加载也不执行。你必须提供
{ resources: "usable", runScripts: "outside-only" }
参数来解决这个问题(确保你阅读了 jsdom README 中的安全隐患)。您没有等待
load
事件,因此您的测试是 运行 在 jsdom 有机会加载脚本之前。
工作代码看起来像这样:
const expect = require("chai").expect;
const { JSDOM } = require("jsdom");
describe("updateMsg", function() {
let jsdom;
before(async function() {
jsdom = await JSDOM.fromFile("index.html", {
resources: "usable",
runScripts: "dangerously"
});
await new Promise(resolve =>
jsdom.window.addEventListener("load", resolve)
);
});
it('updates the innerHTML of element with id "msg"', function() {
expect(jsdom.window.document.getElementById("msg").innerHTML).to.equal(
"Hello, World!"
);
jsdom.window.updateMsg("The new msg!");
expect(jsdom.window.document.getElementById("msg").innerHTML).to.equal(
"The new msg!"
);
});
});
您还需要从 module.js 中删除模块行,module
在浏览器中不存在。