blog/rails/node_modules/jsdom/README.md
2011-12-02 23:24:03 -08:00

278 lines
No EOL
9.2 KiB
Markdown

# jsdom
A javascript implementation of the W3C DOM.
## Install
npm install jsdom
or
git clone http://github.com/tmpvar/jsdom.git
cd jsdom
npm link
## Human contact
see: [mailing list][]
[mailing list]: http://groups.google.com/group/jsdom
## Easymode
Bootstrapping a DOM is generally a difficult process involving many error prone steps. We didn't want jsdom to fall into the same trap and that is why a new method, `jsdom.env()`, has been added in jsdom 0.2.0 which should make everyone's lives easier.
with URL
// Count all of the links from the nodejs build page
var jsdom = require("jsdom");
jsdom.env("http://nodejs.org/dist/", [
'http://code.jquery.com/jquery-1.5.min.js'
],
function(errors, window) {
console.log("there have been", window.$("a").length, "nodejs releases!");
});
or with raw html
// Run some jQuery on a html fragment
var jsdom = require('jsdom');
jsdom.env('<p><a class="the-link" href="http://jsdom.org>JSDOM\'s Homepage</a></p>', [
'http://code.jquery.com/jquery-1.5.min.js'
],
function(errors, window) {
console.log("contents of a.the-link:", window.$("a.the-link").text());
});
or with a configuration object
// Print all of the news items on hackernews
var jsdom = require('jsdom');
jsdom.env({
html: 'http://news.ycombinator.com/',
scripts: [
'http://code.jquery.com/jquery-1.5.min.js'
],
done: function(errors, window) {
var $ = window.$;
console.log('HN Links');
$('td.title:not(:last) a').each(function() {
console.log(' -', $(this).text());
});
}
});
or with raw javascript source
// Print all of the news items on hackernews
var jsdom = require('jsdom');
var fs = require('fs');
var jquery = fs.readFileSync("./jquery-1.6.2.min.js").toString();
jsdom.env({
html: 'http://news.ycombinator.com/',
src: [
jquery
],
done: function(errors, window) {
var $ = window.$;
console.log('HN Links');
$('td.title:not(:last) a').each(function() {
console.log(' -', $(this).text());
});
}
});
### How it works
`jsdom.env` is built for ease of use, which is rare in the world of the DOM! Since the web has some absolutely horrible javascript on it, as of jsdom 0.2.0 `jsdom.env` will not process external resources (scripts, images, etc). If you want to process the javascript use one of the methods below (`jsdom.jsdom` or `jsdom.jQueryify`)
jsdom.env(html, [scripts], [config], callback)
- `html` (**required**)
May be a url, html fragment, or file
- `scripts` (**optional**)
May contain files or urls
- `callback` (**required**)
Takes 2 arguments:
- `errors` : array of errors
- `window` : a brand new window
_example:_ jsdom.env(html, function(`errors`, `window`) {})
If you would like to specify a configuration object
jsdom.env({ /* config */ })
- config.html : see `html` above
- config.scripts : see `scripts` above
- config.src : An array of javascript strings that will be evaluated against the resulting document. Similar to `scripts`, but it accepts javascript instead of paths/urls.
- config.done : see `callback` above
- config.document :
- referer : the new document will have this referer
- cookie : manually set a cookie value i.e. `'key=value; expires=Wed, Sep 21 2011 12:00:00 GMT; path=/'`
- config.features : see `Flexibility` section below. **Note**: the default feature set for jsdom.env does _not_ include fetching remote javascript and executing it. This is something that you will need to **carefully** enable yourself.
## For the hardcore
If you want to spawn a document/window and specify all sorts of options this is the section for you. This section covers the `jsdom.jsdom` method:
var jsdom = require("jsdom").jsdom,
doc = jsdom(markup, level, options),
window = doc.createWindow();
- `markup` is an html/xml document to be parsed. You can also pass `null` or an undefined value to get a basic document with empty head and body tags. Document fragments are also supported (including `""`), and will behave as sanely as possible (eg. the resulting document will lack the `head`, `body` and `documentElement` properties if the corresponding elements aren't included).
- `level` is `null` (which means level3) by default, but you can pass another level if you'd like.
var jsdom = require('jsdom'),
doc = jsdom.jsdom('<html><body></body></html>', jsdom.dom.level1.core)
- `options` see the **Flexibility** section below
### Flexibility
One of the goals of jsdom is to be as minimal and light as possible. This section details how
someone can change the behavior of `Document`s on the fly. These features are baked into
the `DOMImplementation` that every `Document` has, and may be tweaked in two ways:
1. When you create a new `Document` using the jsdom builder (`require('jsdom').jsdom()`)
var jsdom = require('jsdom').jsdom,
doc = jsdom("<html><body></body></html>", null, {
features: {
FetchExternalResources : ['img']
}
});
Do note, that this will only affect the document that is currently being created. All other documents
will use the defaults specified below (see: Default Features)
2. Previous to creating any documents you can modify the defaults for all future documents
require('jsdom').defaultDocumentFeatures = {
FetchExternalResources : ['script'],
ProcessExternalResources : false,
MutationEvents : false,
QuerySelector : false
}
#### Default Features
Default features are extremely important for jsdom as they lower the configuration requirement and present developers a set of consistent default behaviors. The following sections detail the available features, their defaults, and the values that jsdom uses.
`FetchExternalResources`
_Default_: ['script']
_Allowed_: ['script', 'img', 'css', 'frame', 'link'] or false
Enables/Disables fetching files over the filesystem/http
`ProcessExternalResources`
_default_: ['script']
_allowed_: ['script'] or false
Disabling this will disable script execution (currently only javascript).
`MutationEvents`
_default_: '2.0'
_allowed_ : '2.0' or false
Initially enabled to be up to spec. Disable this if you do not need mutation events and want jsdom to be a bit more efficient.
**Note**: `ProcessExternalResources` requires this to be enabled
`QuerySelector`
_default_ : false
_allowed_ : true
This feature is backed by [sizzle][] but currently causes problems with some libraries. Enable this if you want `document.querySelector` and friends, but be aware that many libraries feature detect for this, and it may cause you a bit of trouble.
[sizzle]:http://sizzlejs.com/
# More Examples
## Creating a document-less window
var jsdom = require("jsdom"),
window = jsdom.createWindow();
console.log(window.document);
// output: undefined
## Creating a document
var jsdom = require("jsdom"),
doc = new (jsdom.dom.level1.core.Document)();
console.log(doc.nodeName);
// outputs: #document
## Creating a browser-like BOM/DOM/Window
var jsdom = require("./lib/jsdom").jsdom,
document = jsdom("<html><head></head><body>hello world</body></html>"),
window = document.createWindow();
console.log(window.document.innerHTML);
// output: '<html><head></head><body>hello world</body></html>'
console.log(window.innerWidth)
// output: 1024
console.log(typeof window.document.getElementsByClassName);
// outputs: function
## jQueryify
var jsdom = require("jsdom"),
window = jsdom.jsdom().createWindow();
jsdom.jQueryify(window, 'http://code.jquery.com/jquery-1.4.2.min.js' , function() {
window.$('body').append('<div class="testing">Hello World, It works</div>');
console.log(window.$('.testing').text());
});
# Test Compliance:
level1/core 531/531 100%
level1/html 238/238 100%
level1/svg 527/527 100%
level2/core 283/283 100%
level2/html 687/687 100%
level2/style 4/4 100%
level2/extra 4/4 100%
level3/xpath 93/93 100%
window/index 5/5 100%
window/script 8/8 100%
window/frame 14/14 100%
sizzle/index 12/15 80%
jsdom/index 63/63 100%
--------------------------------------
TOTALS: 3/2472 failed; 99% success
TIME: 16730ms
## Running the tests
First you'll want to `npm install -g nodeunit` then `npm install --dev`
Using `test/runner` you can slice and dice which tests your want to run from different levels. Usage is as follows:
test/runner --help
Run the jsdom test suite
Options:
-s, --suites suites that you want to run. ie: -s level1/core,1/html,html [string]
-f, --fail-fast stop on the first failed test
-h, --help show the help
-t, --tests choose the test cases to run. ie: -t jquery