I'm writing a test with AVA and jsdom.
This works:
const rp = require('request-promise-native')
const jsdom = require('jsdom')
const {JSDOM} = jsdom
const url = 'http://localhost:8000'
rp(url).then((body) => {
const options = {
url: url,
resources: 'usable',
runScripts: 'dangerously',
}
let dom = new JSDOM(body, options)
dom.window.document.addEventListener('DOMContentLoaded', () => {
setImmediate(() => {
console.log(dom.serialize()) // works, prints <html><head></head><body><h1>Hello world!</h1></body></html>
})
})
})
An external script adds an h1 to the document body.
// external.js
document.addEventListener('DOMContentLoaded', () => {
document.write('<h1>Hello world!</h1>')
})
This is the markup at http://localhost:8000:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>JSDOM test</title>
<script src="external.js"></script>
</head>
<body>
</body>
</html>
When I try the same thing in a test:
const rp = require('request-promise-native')
const test = require('ava')
const jsdom = require('jsdom')
const {JSDOM} = jsdom
const url = 'http://localhost:8000'
test('Check custom CSS', t => {
return rp(url).then((body) => {
const options = {
url: url,
resources: 'usable',
runScripts: 'dangerously',
}
let dom = new JSDOM(body, options)
dom.window.document.addEventListener('DOMContentLoaded', () => {
setImmediate(() => {
console.log(dom.serialize()) // nothing gets printed
})
})
t.pass('passed')
})
})
console.log
isn't called. I would expect <html><head></head><body><h1>Hello world!</h1></body></html>
to get printed, rather than there being no output.
In summary, I want to:
- Grab the response body from a url
- Create a new jsdom object from it
- Execute the scripts linked to in the response body's head tags
- Let the scripts change the markup
- Print the resulting modified markup
What is the best way of going about doing this?
Here's a minimum working example: https://github.com/cg433n/jsdom-test