08-27-周三_17-09-29

This commit is contained in:
2025-08-27 17:10:05 +08:00
commit 86df397d8f
12735 changed files with 1145479 additions and 0 deletions

5
node_modules/CSSselect/.travis.yml generated vendored Normal file
View File

@@ -0,0 +1,5 @@
language: node_js
node_js:
- 0.8
- "0.10"
- 0.11

11
node_modules/CSSselect/LICENSE generated vendored Normal file
View File

@@ -0,0 +1,11 @@
Copyright (c) Felix Böhm
All rights reserved.
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
THIS IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS,
EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

57
node_modules/CSSselect/README.md generated vendored Normal file
View File

@@ -0,0 +1,57 @@
#CSSselect [![Build Status](https://secure.travis-ci.org/fb55/CSSselect.png?branch=master)](http://travis-ci.org/fb55/CSSselect)
a CSS selector compiler/engine
##What?
CSSselect turns CSS selectors into functions that tests if elements match them. When searching for elements, testing is executed "from the top", similar to how browsers execute CSS selectors.
In its default configuration, CSSselect queries the DOM structure of the [`domhandler`](https://github.com/fb55/domhandler) module.
##API
```js
var CSSselect = require("CSSselect");
```
####`CSSselect(query, elems)`
- `query` can be either a function or a string. If it's a string, the string is compiled as a CSS selector.
- `elems` can be either an array of elements, or a single element. If it is an element, its children will be used (so we're working with an array again).
Queries `elems`, returns an array containing all matches.
Aliases: `CSSselect.selectAll(query, elems)`, `CSSselect.iterate(query, elems)`.
####`CSSselect.compile(query)`
Compiles the query, returns the function.
####`CSSselect.is(elem, query)`
Tests whether or not an element is matched by `query`. `query` can be either a CSS selector or a function.
####`CSSselect.selectOne(query, elems)`
Arguments are the same as for `CSSselect(query, elems)`. Only returns the first match, or `null` if there was no match.
##Why?
The common approach of executing CSS selectors (used eg. by [`Sizzle`](https://github.com/jquery/sizzle), [`nwmatcher`](https://github.com/dperini/nwmatcher/) and [`qwery`](https://github.com/ded/qwery)) is to execute every component of the selector in order, from left to right. The selector `a b` for example will first look for `a` elements, then search these for `b` elements.
While this works, it has some downsides: Children of `a`s will be checked multiple times, first, to check if they are also `a`s, then, for every superior `a` once, if they are `b`s. Using [Big O notation](http://en.wikipedia.org/wiki/Big_O_notation), that would be `O(n^2)`.
The far more efficient approach is to first look for `b` elements, then check if they have superior `a` elements: Using big O notation again, that would be `O(n)`.
And that's exactly what CSSselect does.
##How?
By stacking functions!
_//TODO: Better explanation. For now, if you're interested, have a look at the source code._
---
License: BSD-like

67
node_modules/CSSselect/browser_functions.js generated vendored Normal file
View File

@@ -0,0 +1,67 @@
function isTag(elem){
return elem.nodeType === 1;
}
function getChildren(elem){
return Array.prototype.slice.call(elem.childNodes, 0);
}
function getParent(elem){
return elem.parentElement;
}
module.exports = {
isTag: isTag,
getSiblings: function(elem){
var parent = getParent(elem);
return parent && getChildren(parent);
},
getChildren: getChildren,
getParent: getParent,
getAttributeValue: function(elem, name){
return elem.attributes[name].value;
},
hasAttrib: function(elem, name){
return name in elem.attributes;
},
getName: function(elem){
return elem.tagName.toLowerCase();
},
findOne: function findOne(test, arr){
var elem = null;
for(var i = 0, l = arr.length; i < l && !elem; i++){
if(test(arr[i])){
elem = arr[i];
} else {
var childs = getChildren(arr[i]);
if(childs && childs.length > 0){
elem = findOne(test, childs);
}
}
}
return elem;
},
findAll: function findAll(test, elems){
var result = [];
for(var i = 0, j = elems.length; i < j; i++){
if(!isTag(elems[i])) continue;
if(test(elems[i])) result.push(elems[i]);
var childs = getChildren(elems[i]);
if(childs) result = result.concat(findAll(test, childs));
}
return result;
},
//https://github.com/ded/qwery/blob/master/pseudos/qwery-pseudos.js#L47-54
getText: function getText(elem) {
var str = "",
childs = getChildren(elem);
if(!childs) return str;
for(var i = 0; i < childs.length; i++){
if(isTag(childs[i])) str += elem.textContent || elem.innerText || getText(childs[i]);
}
return str;
}
};

54
node_modules/CSSselect/index.js generated vendored Normal file
View File

@@ -0,0 +1,54 @@
"use strict";
module.exports = CSSselect;
var Pseudos = require("./lib/pseudos.js"),
DomUtils = require("domutils"),
findOne = DomUtils.findOne,
findAll = DomUtils.findAll,
getChildren = DomUtils.getChildren,
removeSubsets = DomUtils.removeSubsets,
falseFunc = require("./lib/basefunctions.js").falseFunc,
compile = require("./lib/compile.js"),
compileUnsafe = compile.compileUnsafe;
function getSelectorFunc(searchFunc){
return function select(query, elems, options){
if(typeof query !== "function") query = compileUnsafe(query, options);
if(!Array.isArray(elems)) elems = getChildren(elems);
else elems = removeSubsets(elems);
return searchFunc(query, elems);
};
}
var selectAll = getSelectorFunc(function selectAll(query, elems){
return (query === falseFunc || !elems || elems.length === 0) ? [] : findAll(query, elems);
});
var selectOne = getSelectorFunc(function selectOne(query, elems){
return (query === falseFunc || !elems || elems.length === 0) ? null : findOne(query, elems);
});
function is(elem, query, options){
return (typeof query === "function" ? query : compile(query, options))(elem);
}
/*
the exported interface
*/
function CSSselect(query, elems, options){
return selectAll(query, elems, options);
}
CSSselect.compile = compile;
CSSselect.filters = Pseudos.filters;
CSSselect.pseudos = Pseudos.pseudos;
CSSselect.selectAll = selectAll;
CSSselect.selectOne = selectOne;
CSSselect.is = is;
//legacy methods (might be removed)
CSSselect.parse = compile;
CSSselect.iterate = selectAll;

178
node_modules/CSSselect/lib/attributes.js generated vendored Normal file
View File

@@ -0,0 +1,178 @@
var DomUtils = require("domutils"),
hasAttrib = DomUtils.hasAttrib,
getAttributeValue = DomUtils.getAttributeValue,
falseFunc = require("./basefunctions.js").falseFunc;
//https://github.com/slevithan/XRegExp/blob/master/src/xregexp.js#L469
var reChars = /[-[\]{}()*+?.,\\^$|#\s]/g;
/*
attribute selectors
*/
var attributeRules = {
__proto__: null,
equals: function(next, data){
var name = data.name,
value = data.value;
if(data.ignoreCase){
value = value.toLowerCase();
return function equalsIC(elem){
var attr = getAttributeValue(elem, name);
return attr != null && attr.toLowerCase() === value && next(elem);
};
}
return function equals(elem){
return getAttributeValue(elem, name) === value && next(elem);
};
},
hyphen: function(next, data){
var name = data.name,
value = data.value,
len = value.length;
if(data.ignoreCase){
value = value.toLowerCase();
return function hyphenIC(elem){
var attr = getAttributeValue(elem, name);
return attr != null &&
(attr.length === len || attr.charAt(len) === "-") &&
attr.substr(0, len).toLowerCase() === value &&
next(elem);
};
}
return function hyphen(elem){
var attr = getAttributeValue(elem, name);
return attr != null &&
attr.substr(0, len) === value &&
(attr.length === len || attr.charAt(len) === "-") &&
next(elem);
};
},
element: function(next, data){
var name = data.name,
value = data.value;
if(/\s/.test(value)){
return falseFunc;
}
value = value.replace(reChars, "\\$&");
var pattern = "(?:^|\\s)" + value + "(?:$|\\s)",
flags = data.ignoreCase ? "i" : "",
regex = new RegExp(pattern, flags);
return function element(elem){
var attr = getAttributeValue(elem, name);
return attr != null && regex.test(attr) && next(elem);
};
},
exists: function(next, data){
var name = data.name;
return function exists(elem){
return hasAttrib(elem, name) && next(elem);
};
},
start: function(next, data){
var name = data.name,
value = data.value,
len = value.length;
if(len === 0){
return falseFunc;
}
if(data.ignoreCase){
value = value.toLowerCase();
return function startIC(elem){
var attr = getAttributeValue(elem, name);
return attr != null && attr.substr(0, len).toLowerCase() === value && next(elem);
};
}
return function start(elem){
var attr = getAttributeValue(elem, name);
return attr != null && attr.substr(0, len) === value && next(elem);
};
},
end: function(next, data){
var name = data.name,
value = data.value,
len = -value.length;
if(len === 0){
return falseFunc;
}
if(data.ignoreCase){
value = value.toLowerCase();
return function endIC(elem){
var attr = getAttributeValue(elem, name);
return attr != null && attr.substr(len).toLowerCase() === value && next(elem);
};
}
return function end(elem){
var attr = getAttributeValue(elem, name);
return attr != null && attr.substr(len) === value && next(elem);
};
},
any: function(next, data){
var name = data.name,
value = data.value;
if(value === ""){
return falseFunc;
}
if(data.ignoreCase){
var regex = new RegExp(value.replace(reChars, "\\$&"), "i");
return function anyIC(elem){
var attr = getAttributeValue(elem, name);
return attr != null && regex.test(attr) && next(elem);
};
}
return function any(elem){
var attr = getAttributeValue(elem, name);
return attr != null && attr.indexOf(value) >= 0 && next(elem);
};
},
not: function(next, data){
var name = data.name,
value = data.value;
if(value === ""){
return function notEmpty(elem){
return !!getAttributeValue(elem, name) && next(elem);
};
} else if(data.ignoreCase){
value = value.toLowerCase();
return function notIC(elem){
var attr = getAttributeValue(elem, name);
return attr != null && attr.toLowerCase() !== value && next(elem);
};
}
return function not(elem){
return getAttributeValue(elem, name) !== value && next(elem);
};
}
};
module.exports = {
compile: function(next, data){
return attributeRules[data.action](next, data);
},
rules: attributeRules
};

8
node_modules/CSSselect/lib/basefunctions.js generated vendored Normal file
View File

@@ -0,0 +1,8 @@
module.exports = {
trueFunc: function trueFunc(){
return true;
},
falseFunc: function falseFunc(){
return false;
}
};

84
node_modules/CSSselect/lib/compile.js generated vendored Normal file
View File

@@ -0,0 +1,84 @@
/*
compiles a selector to an executable function
*/
module.exports = compile;
module.exports.compileUnsafe = compileUnsafe;
var parse = require("CSSwhat"),
DomUtils = require("domutils"),
isTag = DomUtils.isTag,
Rules = require("./general.js"),
sortRules = require("./sort.js"),
BaseFuncs = require("./basefunctions.js"),
trueFunc = BaseFuncs.trueFunc,
falseFunc = BaseFuncs.falseFunc;
function compile(selector, options){
var next = compileUnsafe(selector, options);
return function base(elem){
return isTag(elem) && next(elem);
};
}
function compileUnsafe(selector, options){
return parse(selector, options)
.map(compileRules)
.reduce(reduceRules, falseFunc);
}
function compileRules(arr){
if(arr.length === 0) return falseFunc;
return sortRules(arr).reduce(function(func, rule){
if(func === falseFunc) return func;
return Rules[rule.type](func, rule);
}, trueFunc);
}
function reduceRules(a, b){
if(b === falseFunc || a === trueFunc){
return a;
}
if(a === falseFunc || b === trueFunc){
return b;
}
return function combine(elem){
return a(elem) || b(elem);
};
}
//:not and :has have to compile selectors
//doing this in lib/pseudos.js would lead to circular dependencies,
//so we add them here
var Pseudos = require("./pseudos.js"),
filters = Pseudos.filters,
isParent = Pseudos.pseudos.parent,
existsOne = DomUtils.existsOne,
getChildren = DomUtils.getChildren;
filters.not = function(next, select){
var func = compileUnsafe(select);
if(func === falseFunc) return next;
if(func === trueFunc) return falseFunc;
return function(elem){
return !func(elem) && next(elem);
};
};
filters.has = function(next, selector){
var func = compile(selector);
if(func === falseFunc) return falseFunc;
if(func === trueFunc) return function(elem){
return isParent(elem) && next(elem);
};
return function has(elem){
return next(elem) && existsOne(func, getChildren(elem));
};
};

80
node_modules/CSSselect/lib/general.js generated vendored Normal file
View File

@@ -0,0 +1,80 @@
var DomUtils = require("domutils"),
isTag = DomUtils.isTag,
getParent = DomUtils.getParent,
getChildren = DomUtils.getChildren,
getSiblings = DomUtils.getSiblings,
getName = DomUtils.getName;
/*
all available rules
*/
module.exports = {
__proto__: null,
attribute: require("./attributes.js").compile,
pseudo: require("./pseudos.js").compile,
//tags
tag: function(next, data){
var name = data.name;
return function tag(elem){
return getName(elem) === name && next(elem);
};
},
//traversal
descendant: function(next){
return function descendant(elem){
var found = false;
while(!found && (elem = getParent(elem))){
found = next(elem);
}
return found;
};
},
parent: function(next){
return function parent(elem){
return getChildren(elem).some(next);
};
},
child: function(next){
return function child(elem){
var parent = getParent(elem);
return !!parent && next(parent);
};
},
sibling: function(next){
return function sibling(elem){
var siblings = getSiblings(elem);
for(var i = 0; i < siblings.length; i++){
if(isTag(siblings[i])){
if(siblings[i] === elem) break;
if(next(siblings[i])) return true;
}
}
return false;
};
},
adjacent: function(next){
return function adjacent(elem){
var siblings = getSiblings(elem),
lastElement;
for(var i = 0; i < siblings.length; i++){
if(isTag(siblings[i])){
if(siblings[i] === elem) break;
lastElement = siblings[i];
}
}
return !!lastElement && next(lastElement);
};
},
universal: function(next){
return next;
}
};

84
node_modules/CSSselect/lib/nth-check.js generated vendored Normal file
View File

@@ -0,0 +1,84 @@
var BaseFuncs = require("./basefunctions.js"),
trueFunc = BaseFuncs.trueFunc,
falseFunc = BaseFuncs.falseFunc;
module.exports = function nthCheck(formula){
return compile(parse(formula));
};
module.exports.parse = parse;
module.exports.compile = compile;
//following http://www.w3.org/TR/css3-selectors/#nth-child-pseudo
//[ ['-'|'+']? INTEGER? {N} [ S* ['-'|'+'] S* INTEGER ]?
var re_nthElement = /^([+\-]?\d*n)?\s*(?:([+\-]?)\s*(\d+))?$/;
/*
parses a nth-check formula, returns an array of two numbers
*/
function parse(formula){
formula = formula.trim().toLowerCase();
if(formula === "even"){
return [2, 0];
} else if(formula === "odd"){
return [2, 1];
} else {
var parsed = formula.match(re_nthElement);
if(!parsed){
throw new SyntaxError("n-th rule couldn't be parsed ('" + formula + "')");
}
var a;
if(parsed[1]){
a = parseInt(parsed[1], 10);
if(!a){
if(parsed[1].charAt(0) === "-") a = -1;
else a = 1;
}
} else a = 0;
return [
a,
parsed[3] ? parseInt((parsed[2] || "") + parsed[3], 10) : 0
];
}
}
/*
returns a function that checks if an elements index matches the given rule
highly optimized to return the fastest solution
*/
function compile(parsed){
var a = parsed[0],
b = parsed[1] - 1;
//when b <= 0, a*n won't be possible for any matches when a < 0
//besides, the specification says that no element is matched when a and b are 0
if(b < 0 && a <= 0) return falseFunc;
//when a is in the range -1..1, it matches any element (so only b is checked)
if(a ===-1) return function(pos){ return pos <= b; };
if(a === 0) return function(pos){ return pos === b; };
//when b <= 0 and a === 1, they match any element
if(a === 1) return b < 0 ? trueFunc : function(pos){ return pos >= b; };
//when a > 0, modulo can be used to check if there is a match
var bMod = b % a;
if(bMod < 0) bMod += a;
if(a > 1){
return function(pos){
return pos >= b && pos % a === bMod;
};
}
a *= -1; //make `a` positive
return function(pos){
return pos <= b && pos % a === bMod;
};
}

338
node_modules/CSSselect/lib/pseudos.js generated vendored Normal file
View File

@@ -0,0 +1,338 @@
/*
pseudo selectors
---
they are available in two forms:
* filters called when the selector
is compiled and return a function
that needs to return next()
* pseudos get called on execution
they need to return a boolean
*/
var DomUtils = require("domutils"),
isTag = DomUtils.isTag,
getText = DomUtils.getText,
getParent = DomUtils.getParent,
getChildren = DomUtils.getChildren,
getSiblings = DomUtils.getSiblings,
hasAttrib = DomUtils.hasAttrib,
getName = DomUtils.getName,
getAttribute= DomUtils.getAttributeValue,
getNCheck = require("./nth-check.js"),
checkAttrib = require("./attributes.js").rules.equals,
BaseFuncs = require("./basefunctions.js"),
trueFunc = BaseFuncs.trueFunc,
falseFunc = BaseFuncs.falseFunc;
//helper methods
function getFirstElement(elems){
for(var i = 0; elems && i < elems.length; i++){
if(isTag(elems[i])) return elems[i];
}
}
function getAttribFunc(name, value){
var data = {name: name, value: value};
return function attribFunc(next){
return checkAttrib(next, data);
};
}
function getChildFunc(next){
return function(elem){
return !!getParent(elem) && next(elem);
};
}
var filters = {
contains: function(next, text){
if(
(text.charAt(0) === "\"" || text.charAt(0) === "'") &&
text.charAt(0) === text.substr(-1)
){
text = text.slice(1, -1);
}
return function contains(elem){
return getText(elem).indexOf(text) >= 0 && next(elem);
};
},
//location specific methods
//first- and last-child methods return as soon as they find another element
"first-child": function(next){
return function firstChild(elem){
return getFirstElement(getSiblings(elem)) === elem && next(elem);
};
},
"last-child": function(next){
return function lastChild(elem){
var siblings = getSiblings(elem);
for(var i = siblings.length - 1; i >= 0; i--){
if(siblings[i] === elem) return next(elem);
if(isTag(siblings[i])) break;
}
return false;
};
},
"first-of-type": function(next){
return function firstOfType(elem){
var siblings = getSiblings(elem);
for(var i = 0; i < siblings.length; i++){
if(isTag(siblings[i])){
if(siblings[i] === elem) return next(elem);
if(getName(siblings[i]) === getName(elem)) break;
}
}
return false;
};
},
"last-of-type": function(next){
return function lastOfType(elem){
var siblings = getSiblings(elem);
for(var i = siblings.length-1; i >= 0; i--){
if(isTag(siblings[i])){
if(siblings[i] === elem) return next(elem);
if(getName(siblings[i]) === getName(elem)) break;
}
}
return false;
};
},
"only-of-type": function(next){
return function onlyOfType(elem){
var siblings = getSiblings(elem);
for(var i = 0, j = siblings.length; i < j; i++){
if(isTag(siblings[i])){
if(siblings[i] === elem) continue;
if(getName(siblings[i]) === getName(elem)) return false;
}
}
return next(elem);
};
},
"only-child": function(next){
return function onlyChild(elem){
var siblings = getSiblings(elem);
for(var i = 0; i < siblings.length; i++){
if(isTag(siblings[i]) && siblings[i] !== elem) return false;
}
return next(elem);
};
},
"nth-child": function(next, rule){
var func = getNCheck(rule);
if(func === falseFunc) return func;
if(func === trueFunc) return getChildFunc(next);
return function nthChild(elem){
var siblings = getSiblings(elem);
for(var i = 0, pos = 0; i < siblings.length; i++){
if(isTag(siblings[i])){
if(siblings[i] === elem) break;
else pos++;
}
}
return func(pos) && next(elem);
};
},
"nth-last-child": function(next, rule){
var func = getNCheck(rule);
if(func === falseFunc) return func;
if(func === trueFunc) return getChildFunc(next);
return function nthLastChild(elem){
var siblings = getSiblings(elem);
for(var pos = 0, i = siblings.length - 1; i >= 0; i--){
if(isTag(siblings[i])){
if(siblings[i] === elem) break;
else pos++;
}
}
return func(pos) && next(elem);
};
},
"nth-of-type": function(next, rule){
var func = getNCheck(rule);
if(func === falseFunc) return func;
if(func === trueFunc) return getChildFunc(next);
return function nthOfType(elem){
var siblings = getSiblings(elem);
for(var pos = 0, i = 0; i < siblings.length; i++){
if(isTag(siblings[i])){
if(siblings[i] === elem) break;
if(getName(siblings[i]) === getName(elem)) pos++;
}
}
return func(pos) && next(elem);
};
},
"nth-last-of-type": function(next, rule){
var func = getNCheck(rule);
if(func === falseFunc) return func;
if(func === trueFunc) return getChildFunc(next);
return function nthLastOfType(elem){
var siblings = getSiblings(elem);
for(var pos = 0, i = siblings.length - 1; i >= 0; i--){
if(siblings[i] === elem) break;
if(getName(siblings[i]) === getName(elem)) pos++;
}
return func(pos) && next(elem);
};
},
//jQuery extensions (others follow as pseudos)
checkbox: getAttribFunc("type", "checkbox"),
file: getAttribFunc("type", "file"),
password: getAttribFunc("type", "password"),
radio: getAttribFunc("type", "radio"),
reset: getAttribFunc("type", "reset"),
image: getAttribFunc("type", "image"),
submit: getAttribFunc("type", "submit")
};
//while filters are precompiled, pseudos get called when they are needed
var pseudos = {
root: function(elem){
return !getParent(elem);
},
empty: function(elem){
return !getChildren(elem).some(function(elem){
return isTag(elem) || elem.type === "text";
});
},
//forms
//to consider: :target, :enabled
selected: function(elem){
if(hasAttrib(elem, "selected")) return true;
else if(getName(elem) !== "option") return false;
//the first <option> in a <select> is also selected
var parent = getParent(elem);
if(!parent || getName(parent) !== "select") return false;
var siblings = getChildren(parent),
sawElem = false;
for(var i = 0; i < siblings.length; i++){
if(isTag(siblings[i])){
if(siblings[i] === elem){
sawElem = true;
} else if(!sawElem){
return false;
} else if(hasAttrib(siblings[i], "selected")){
return false;
}
}
}
return sawElem;
},
disabled: function(elem){
return hasAttrib(elem, "disabled");
},
enabled: function(elem){
return !hasAttrib(elem, "disabled");
},
checked: function(elem){
return hasAttrib(elem, "checked") || pseudos.selected(elem);
},
//jQuery extensions
//:parent is the inverse of :empty
parent: function(elem){
return !pseudos.empty(elem);
},
header: function(elem){
var name = getName(elem);
return name === "h1" ||
name === "h2" ||
name === "h3" ||
name === "h4" ||
name === "h5" ||
name === "h6";
},
button: function(elem){
var name = getName(elem);
return name === "button" ||
name === "input" &&
getAttribute(elem, "type") === "button";
},
input: function(elem){
var name = getName(elem);
return name === "input" ||
name === "textarea" ||
name === "select" ||
name === "button";
},
text: function(elem){
var attr;
return getName(elem) === "input" && (
!(attr = getAttribute(elem, "type")) ||
attr.toLowerCase() === "text"
);
}
};
function verifyArgs(func, name, subselect){
if(subselect === null){
if(func.length > 1){
throw new SyntaxError("pseudo-selector :" + name + " requires an argument");
}
} else {
if(func.length === 1){
throw new SyntaxError("pseudo-selector :" + name + " doesn't have any arguments");
}
}
}
module.exports = {
compile: function(next, data){
var name = data.name,
subselect = data.data;
if(typeof filters[name] === "function"){
verifyArgs(filters[name], name, subselect);
return filters[name](next, subselect);
} else if(typeof pseudos[name] === "function"){
var func = pseudos[name];
verifyArgs(func, name, subselect);
return function pseudoArgs(elem){
return func(elem, subselect) && next(elem);
};
} else {
throw new SyntaxError("unmatched pseudo-class :" + name);
}
},
filters: filters,
pseudos: pseudos
};

59
node_modules/CSSselect/lib/sort.js generated vendored Normal file
View File

@@ -0,0 +1,59 @@
module.exports = sortByProcedure;
/*
sort the parts of the passed selector,
as there is potential for optimization
(some types of selectors are faster than others)
*/
var ATTRIBUTE = 1;
var procedure = {
__proto__: null,
universal: 5, //should be last so that it can be ignored
tag: 3, //very quick test
attribute: ATTRIBUTE,
pseudo: 0, //can be pretty expensive (especially :has)
//everything else shouldn't be moved
descendant: -1,
child: -1,
parent: -1,
sibling: -1,
adjacent: -1
};
var attributes = {
__proto__: null,
exists: 8,
equals: 7,
not: 6,
start: 5,
end: 4,
any: 3,
hyphen: 2,
element: 1
};
function sortByProcedure(arr){
for(var i = 1; i < arr.length; i++){
var procNew = procedure[arr[i].type];
if(procNew < 0) continue;
for(var j = i - 1; j >= 0; j--){
if(
procNew > procedure[arr[j].type] || !(
procNew === ATTRIBUTE &&
procedure[arr[j].type] === ATTRIBUTE &&
attributes[arr[i].action] <= attributes[arr[j].action]
)
) break;
var tmp = arr[j + 1];
arr[j + 1] = arr[j];
arr[j] = tmp;
}
}
return arr;
}

11
node_modules/CSSselect/node_modules/domutils/LICENSE generated vendored Normal file
View File

@@ -0,0 +1,11 @@
Copyright (c) Felix Böhm
All rights reserved.
Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
THIS IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS,
EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

14
node_modules/CSSselect/node_modules/domutils/index.js generated vendored Normal file
View File

@@ -0,0 +1,14 @@
var DomUtils = module.exports;
[
require("./lib/stringify"),
require("./lib/traversal"),
require("./lib/manipulation"),
require("./lib/querying"),
require("./lib/legacy"),
require("./lib/helpers")
].forEach(function(ext){
Object.keys(ext).forEach(function(key){
DomUtils[key] = ext[key].bind(DomUtils);
});
});

View File

@@ -0,0 +1,31 @@
// removeSubsets
// Given an array of nodes, remove any member that is contained by another.
exports.removeSubsets = function(nodes) {
var idx = nodes.length, node, ancestor, replace;
// Check if each node (or one of its ancestors) is already contained in the
// array.
while (--idx > -1) {
node = ancestor = nodes[idx];
// Temporarily remove the node under consideration
nodes[idx] = null;
replace = true;
while (ancestor) {
if (nodes.indexOf(ancestor) > -1) {
replace = false;
nodes.splice(idx, 1);
break;
}
ancestor = ancestor.parent;
}
// If the node has been found to be unique, re-insert it.
if (replace) {
nodes[idx] = node;
}
}
return nodes;
};

View File

@@ -0,0 +1,87 @@
var ElementType = require("domelementtype");
var isTag = exports.isTag = ElementType.isTag;
exports.testElement = function(options, element){
for(var key in options){
if(!options.hasOwnProperty(key));
else if(key === "tag_name"){
if(!isTag(element) || !options.tag_name(element.name)){
return false;
}
} else if(key === "tag_type"){
if(!options.tag_type(element.type)) return false;
} else if(key === "tag_contains"){
if(isTag(element) || !options.tag_contains(element.data)){
return false;
}
} else if(!element.attribs || !options[key](element.attribs[key])){
return false;
}
}
return true;
};
var Checks = {
tag_name: function(name){
if(typeof name === "function"){
return function(elem){ return isTag(elem) && name(elem.name); };
} else if(name === "*"){
return isTag;
} else {
return function(elem){ return isTag(elem) && elem.name === name; };
}
},
tag_type: function(type){
if(typeof type === "function"){
return function(elem){ return type(elem.type); };
} else {
return function(elem){ return elem.type === type; };
}
},
tag_contains: function(data){
if(typeof data === "function"){
return function(elem){ return !isTag(elem) && data(elem.data); };
} else {
return function(elem){ return !isTag(elem) && elem.data === data; };
}
}
};
function getAttribCheck(attrib, value){
if(typeof value === "function"){
return function(elem){ return elem.attribs && value(elem.attribs[attrib]); };
} else {
return function(elem){ return elem.attribs && elem.attribs[attrib] === value; };
}
}
function combineFuncs(a, b){
return function(elem){
return a(elem) || b(elem);
};
}
exports.getElements = function(options, element, recurse, limit){
var funcs = Object.keys(options).map(function(key){
var value = options[key];
return key in Checks ? Checks[key](value) : getAttribCheck(key, value);
});
return funcs.length === 0 ? [] : this.filter(
funcs.reduce(combineFuncs),
element, recurse, limit
);
};
exports.getElementById = function(id, element, recurse){
if(!Array.isArray(element)) element = [element];
return this.findOne(getAttribCheck("id", id), element, recurse !== false);
};
exports.getElementsByTagName = function(name, element, recurse, limit){
return this.filter(Checks.tag_name(name), element, recurse, limit);
};
exports.getElementsByTagType = function(type, element, recurse, limit){
return this.filter(Checks.tag_type(type), element, recurse, limit);
};

View File

@@ -0,0 +1,77 @@
exports.removeElement = function(elem){
if(elem.prev) elem.prev.next = elem.next;
if(elem.next) elem.next.prev = elem.prev;
if(elem.parent){
var childs = elem.parent.children;
childs.splice(childs.lastIndexOf(elem), 1);
}
};
exports.replaceElement = function(elem, replacement){
var prev = replacement.prev = elem.prev;
if(prev){
prev.next = replacement;
}
var next = replacement.next = elem.next;
if(next){
next.prev = replacement;
}
var parent = replacement.parent = elem.parent;
if(parent){
var childs = parent.children;
childs[childs.lastIndexOf(elem)] = replacement;
}
};
exports.appendChild = function(elem, child){
child.parent = elem;
if(elem.children.push(child) !== 1){
var sibling = elem.children[elem.children.length - 2];
sibling.next = child;
child.prev = sibling;
child.next = null;
}
};
exports.append = function(elem, next){
var parent = elem.parent,
currNext = elem.next;
next.next = currNext;
next.prev = elem;
elem.next = next;
next.parent = parent;
if(currNext){
currNext.prev = next;
if(parent){
var childs = parent.children;
childs.splice(childs.lastIndexOf(currNext), 0, next);
}
} else if(parent){
parent.children.push(next);
}
};
exports.prepend = function(elem, prev){
var parent = elem.parent;
if(parent){
var childs = parent.children;
childs.splice(childs.lastIndexOf(elem), 0, prev);
}
if(elem.prev){
elem.prev.next = prev;
}
prev.parent = parent;
prev.prev = elem.prev;
prev.next = elem;
elem.prev = prev;
};

View File

@@ -0,0 +1,94 @@
var isTag = require("domelementtype").isTag;
module.exports = {
filter: filter,
find: find,
findOneChild: findOneChild,
findOne: findOne,
existsOne: existsOne,
findAll: findAll
};
function filter(test, element, recurse, limit){
if(!Array.isArray(element)) element = [element];
if(typeof limit !== "number" || !isFinite(limit)){
limit = Infinity;
}
return find(test, element, recurse !== false, limit);
}
function find(test, elems, recurse, limit){
var result = [], childs;
for(var i = 0, j = elems.length; i < j; i++){
if(test(elems[i])){
result.push(elems[i]);
if(--limit <= 0) break;
}
childs = elems[i].children;
if(recurse && childs && childs.length > 0){
childs = find(test, childs, recurse, limit);
result = result.concat(childs);
limit -= childs.length;
if(limit <= 0) break;
}
}
return result;
}
function findOneChild(test, elems){
for(var i = 0, l = elems.length; i < l; i++){
if(test(elems[i])) return elems[i];
}
return null;
}
function findOne(test, elems){
var elem = null;
for(var i = 0, l = elems.length; i < l && !elem; i++){
if(!isTag(elems[i])){
continue;
} else if(test(elems[i])){
elem = elems[i];
} else if(elems[i].children.length > 0){
elem = findOne(test, elems[i].children);
}
}
return elem;
}
function existsOne(test, elems){
for(var i = 0, l = elems.length; i < l; i++){
if(
isTag(elems[i]) && (
test(elems[i]) || (
elems[i].children.length > 0 &&
existsOne(test, elems[i].children)
)
)
){
return true;
}
}
return false;
}
function findAll(test, elems){
var result = [];
for(var i = 0, j = elems.length; i < j; i++){
if(!isTag(elems[i])) continue;
if(test(elems[i])) result.push(elems[i]);
if(elems[i].children.length > 0){
result = result.concat(findAll(test, elems[i].children));
}
}
return result;
}

View File

@@ -0,0 +1,93 @@
var ElementType = require("domelementtype"),
isTag = ElementType.isTag;
module.exports = {
getInnerHTML: getInnerHTML,
getOuterHTML: getOuterHTML,
getText: getText
};
function getInnerHTML(elem){
return elem.children ? elem.children.map(getOuterHTML).join("") : "";
}
//boolean attributes without a value (taken from MatthewMueller/cheerio)
var booleanAttribs = {
__proto__: null,
async: true,
autofocus: true,
autoplay: true,
checked: true,
controls: true,
defer: true,
disabled: true,
hidden: true,
loop: true,
multiple: true,
open: true,
readonly: true,
required: true,
scoped: true,
selected: true
};
var emptyTags = {
__proto__: null,
area: true,
base: true,
basefont: true,
br: true,
col: true,
frame: true,
hr: true,
img: true,
input: true,
isindex: true,
link: true,
meta: true,
param: true,
embed: true
};
function getOuterHTML(elem){
switch(elem.type){
case ElementType.Text:
return elem.data;
case ElementType.Comment:
return "<!--" + elem.data + "-->";
case ElementType.Directive:
return "<" + elem.data + ">";
case ElementType.CDATA:
return "<!CDATA " + getInnerHTML(elem) + "]]>";
}
var ret = "<" + elem.name;
if("attribs" in elem){
for(var attr in elem.attribs){
if(elem.attribs.hasOwnProperty(attr)){
ret += " " + attr;
var value = elem.attribs[attr];
if(value == null){
if( !(attr in booleanAttribs) ){
ret += "=\"\"";
}
} else {
ret += "=\"" + value + "\"";
}
}
}
}
if (elem.name in emptyTags && elem.children.length === 0) {
return ret + " />";
} else {
return ret + ">" + getInnerHTML(elem) + "</" + elem.name + ">";
}
}
function getText(elem){
if(Array.isArray(elem)) return elem.map(getText).join("");
if(isTag(elem) || elem.type === ElementType.CDATA) return getText(elem.children);
if(elem.type === ElementType.Text) return elem.data;
return "";
}

View File

@@ -0,0 +1,24 @@
var getChildren = exports.getChildren = function(elem){
return elem.children;
};
var getParent = exports.getParent = function(elem){
return elem.parent;
};
exports.getSiblings = function(elem){
var parent = getParent(elem);
return parent ? getChildren(parent) : [elem];
};
exports.getAttributeValue = function(elem, name){
return elem.attribs && elem.attribs[name];
};
exports.hasAttrib = function(elem, name){
return hasOwnProperty.call(elem.attribs, name);
};
exports.getName = function(elem){
return elem.name;
};

View File

@@ -0,0 +1,103 @@
{
"_args": [
[
{
"name": "domutils",
"raw": "domutils@1.4",
"rawSpec": "1.4",
"scope": null,
"spec": ">=1.4.0 <1.5.0",
"type": "range"
},
"F:\\tmp\\gitbook\\node_modules\\CSSselect"
]
],
"_from": "domutils@>=1.4.0 <1.5.0",
"_id": "domutils@1.4.3",
"_inCache": true,
"_installable": true,
"_location": "/CSSselect/domutils",
"_npmUser": {
"email": "me@feedic.com",
"name": "feedic"
},
"_npmVersion": "1.4.6",
"_phantomChildren": {},
"_requested": {
"name": "domutils",
"raw": "domutils@1.4",
"rawSpec": "1.4",
"scope": null,
"spec": ">=1.4.0 <1.5.0",
"type": "range"
},
"_requiredBy": [
"/CSSselect"
],
"_resolved": "https://registry.npmjs.org/domutils/-/domutils-1.4.3.tgz",
"_shasum": "0865513796c6b306031850e175516baf80b72a6f",
"_shrinkwrap": null,
"_spec": "domutils@1.4",
"_where": "F:\\tmp\\gitbook\\node_modules\\CSSselect",
"author": {
"email": "me@feedic.com",
"name": "Felix Boehm"
},
"bugs": {
"url": "https://github.com/FB55/domutils/issues"
},
"dependencies": {
"domelementtype": "1"
},
"description": "utilities for working with htmlparser2's dom",
"devDependencies": {
"domhandler": "2",
"htmlparser2": "~3.3.0",
"jshint": "~2.3.0",
"mocha": "~1.15.1"
},
"directories": {
"test": "tests"
},
"dist": {
"shasum": "0865513796c6b306031850e175516baf80b72a6f",
"tarball": "https://registry.npmjs.org/domutils/-/domutils-1.4.3.tgz"
},
"homepage": "https://github.com/FB55/domutils",
"jshintConfig": {
"eqeqeq": true,
"eqnull": true,
"globals": {
"describe": true,
"it": true
},
"node": true,
"proto": true,
"quotmark": "double",
"trailing": true,
"undef": true,
"unused": true
},
"keywords": [
"dom",
"htmlparser2"
],
"main": "index.js",
"maintainers": [
{
"email": "me@feedic.com",
"name": "feedic"
}
],
"name": "domutils",
"optionalDependencies": {},
"readme": "ERROR: No README data found!",
"repository": {
"type": "git",
"url": "git://github.com/FB55/domutils.git"
},
"scripts": {
"test": "mocha test/tests/**.js && jshint index.js test/**/*.js lib/*.js"
},
"version": "1.4.3"
}

View File

@@ -0,0 +1 @@
utilities for working with htmlparser2's dom

View File

@@ -0,0 +1,6 @@
var makeDom = require("./utils").makeDom;
var markup = Array(21).join(
"<?xml><tag1 id='asdf'> <script>text</script> <!-- comment --> <tag2> text </tag1>"
);
module.exports = makeDom(markup);

View File

@@ -0,0 +1,29 @@
var makeDom = require("../utils").makeDom;
var assert = require("assert");
describe("helpers", function() {
describe("removeSubsets", function() {
var removeSubsets = require("../..").removeSubsets;
var dom = makeDom("<div><p><span></span></p><p></p></div>")[0];
it("removes identical trees", function() {
var matches = removeSubsets([dom, dom]);
assert.equal(matches.length, 1);
});
it("Removes subsets found first", function() {
var matches = removeSubsets([dom, dom.children[0].children[0]]);
assert.equal(matches.length, 1);
});
it("Removes subsets found last", function() {
var matches = removeSubsets([dom.children[0], dom]);
assert.equal(matches.length, 1);
});
it("Does not remove unique trees", function() {
var matches = removeSubsets([dom.children[0], dom.children[1]]);
assert.equal(matches.length, 2);
});
});
});

View File

@@ -0,0 +1,119 @@
var DomUtils = require("../..");
var fixture = require("../fixture");
var assert = require("assert");
// Set up expected structures
var expected = {
idAsdf: fixture[1],
tag2: [],
typeScript: []
};
for (var idx = 0; idx < 20; ++idx) {
expected.tag2.push(fixture[idx*2 + 1].children[5]);
expected.typeScript.push(fixture[idx*2 + 1].children[1]);
}
describe("legacy", function() {
describe("getElements", function() {
var getElements = DomUtils.getElements;
it("returns the node with the specified ID", function() {
assert.deepEqual(
getElements({ id: "asdf" }, fixture, true, 1),
[expected.idAsdf]
);
});
it("returns empty array for unknown IDs", function() {
assert.deepEqual(getElements({ id: "asdfs" }, fixture, true), []);
});
it("returns the nodes with the specified tag name", function() {
assert.deepEqual(
getElements({ tag_name:"tag2" }, fixture, true),
expected.tag2
);
});
it("returns empty array for unknown tag names", function() {
assert.deepEqual(
getElements({ tag_name : "asdfs" }, fixture, true),
[]
);
});
it("returns the nodes with the specified tag type", function() {
assert.deepEqual(
getElements({ tag_type: "script" }, fixture, true),
expected.typeScript
);
});
it("returns empty array for unknown tag types", function() {
assert.deepEqual(
getElements({ tag_type: "video" }, fixture, true),
[]
);
});
});
describe("getElementById", function() {
var getElementById = DomUtils.getElementById;
it("returns the specified node", function() {
assert.equal(
expected.idAsdf,
getElementById("asdf", fixture, true)
);
});
it("returns `null` for unknown IDs", function() {
assert.equal(null, getElementById("asdfs", fixture, true));
});
});
describe("getElementsByTagName", function() {
var getElementsByTagName = DomUtils.getElementsByTagName;
it("returns the specified nodes", function() {
assert.deepEqual(
getElementsByTagName("tag2", fixture, true),
expected.tag2
);
});
it("returns empty array for unknown tag names", function() {
assert.deepEqual(
getElementsByTagName("tag23", fixture, true),
[]
);
});
});
describe("getElementsByTagType", function() {
var getElementsByTagType = DomUtils.getElementsByTagType;
it("returns the specified nodes", function() {
assert.deepEqual(
getElementsByTagType("script", fixture, true),
expected.typeScript
);
});
it("returns empty array for unknown tag types", function() {
assert.deepEqual(
getElementsByTagType("video", fixture, true),
[]
);
});
});
describe("getOuterHTML", function() {
var getOuterHTML = DomUtils.getOuterHTML;
it("Correctly renders the outer HTML", function() {
assert.equal(
getOuterHTML(fixture[1]),
"<tag1 id=\"asdf\"> <script>text</script> <!-- comment --> <tag2> text </tag2></tag1>"
);
});
});
describe("getInnerHTML", function() {
var getInnerHTML = DomUtils.getInnerHTML;
it("Correctly renders the inner HTML", function() {
assert.equal(
getInnerHTML(fixture[1]),
" <script>text</script> <!-- comment --> <tag2> text </tag2>"
);
});
});
});

View File

@@ -0,0 +1,9 @@
var htmlparser = require("htmlparser2");
exports.makeDom = function(markup) {
var handler = new htmlparser.DomHandler(),
parser = new htmlparser.Parser(handler);
parser.write(markup);
parser.done();
return handler.dom;
};

91
node_modules/CSSselect/package.json generated vendored Normal file
View File

@@ -0,0 +1,91 @@
{
"_args": [
[
{
"name": "CSSselect",
"raw": "CSSselect@~0.4.0",
"rawSpec": "~0.4.0",
"scope": null,
"spec": ">=0.4.0 <0.5.0",
"type": "range"
},
"F:\\tmp\\gitbook\\node_modules\\gitbook-plugin-multipart\\node_modules\\cheerio"
]
],
"_from": "CSSselect@>=0.4.0 <0.5.0",
"_id": "CSSselect@0.4.1",
"_inCache": true,
"_installable": true,
"_location": "/CSSselect",
"_npmUser": {
"email": "me@feedic.com",
"name": "feedic"
},
"_npmVersion": "1.4.2",
"_phantomChildren": {
"domelementtype": "1.3.1"
},
"_requested": {
"name": "CSSselect",
"raw": "CSSselect@~0.4.0",
"rawSpec": "~0.4.0",
"scope": null,
"spec": ">=0.4.0 <0.5.0",
"type": "range"
},
"_requiredBy": [
"/gitbook-plugin-multipart/cheerio"
],
"_resolved": "https://registry.npmjs.org/CSSselect/-/CSSselect-0.4.1.tgz",
"_shasum": "f8ab7e1f8418ce63cda6eb7bd778a85d7ec492b2",
"_shrinkwrap": null,
"_spec": "CSSselect@~0.4.0",
"_where": "F:\\tmp\\gitbook\\node_modules\\gitbook-plugin-multipart\\node_modules\\cheerio",
"author": {
"email": "me@feedic.com",
"name": "Felix Boehm"
},
"bugs": {
"url": "https://github.com/fb55/CSSselect/issues"
},
"dependencies": {
"CSSwhat": "0.4",
"domutils": "1.4"
},
"deprecated": "the module is now available as 'css-select'",
"description": "a CSS selector compiler/engine",
"devDependencies": {
"cheerio-soupselect": "*",
"expect.js": "*",
"htmlparser2": "*",
"mocha": "*"
},
"directories": {},
"dist": {
"shasum": "f8ab7e1f8418ce63cda6eb7bd778a85d7ec492b2",
"tarball": "https://registry.npmjs.org/CSSselect/-/CSSselect-0.4.1.tgz"
},
"homepage": "https://github.com/fb55/CSSselect",
"keywords": [
"css",
"selector"
],
"license": "BSD-like",
"maintainers": [
{
"email": "me@feedic.com",
"name": "feedic"
}
],
"name": "CSSselect",
"optionalDependencies": {},
"readme": "ERROR: No README data found!",
"repository": {
"type": "git",
"url": "git://github.com/fb55/CSSselect.git"
},
"scripts": {
"test": "mocha"
},
"version": "0.4.1"
}

31
node_modules/CSSselect/test/api.js generated vendored Normal file
View File

@@ -0,0 +1,31 @@
var CSSselect = require(".."),
htmlparser = require("htmlparser2"),
assert = require("assert");
function makeDom(markup) {
var handler = new htmlparser.DomHandler(),
parser = new htmlparser.Parser(handler);
parser.write(markup);
parser.done();
return handler.dom;
}
describe("API", function() {
describe("removes duplicates", function() {
it("between identical trees", function() {
var dom = makeDom("<div></div>")[0];
var matches = CSSselect("div", [dom, dom]);
assert.equal(matches.length, 1, "Removes duplicate matches");
});
it("between a superset and subset", function() {
var dom = makeDom("<div><p></p></div>")[0];
var matches = CSSselect("p", [dom, dom.children[0]]);
assert.equal(matches.length, 1, "Removes duplicate matches");
});
it("betweeen a subset and superset", function() {
var dom = makeDom("<div><p></p></div>")[0];
var matches = CSSselect("p", [dom.children[0], dom]);
assert.equal(matches.length, 1, "Removes duplicate matches");
});
});
});

2
node_modules/CSSselect/test/mocha.opts generated vendored Normal file
View File

@@ -0,0 +1,2 @@
--check-leaks
--reporter spec

117
node_modules/CSSselect/test/nth-check.js generated vendored Normal file
View File

@@ -0,0 +1,117 @@
var nthCheck = require("../lib/nth-check.js"),
assert = require("assert");
var invalid = ["-", "asdf", "2n+-0", "2+0", "- 1n", "-1 n"];
function parseInvalid(){
invalid.forEach(function(formula){
assert.throws(function(){
nthCheck.parse(formula);
},
SyntaxError,
formula
);
});
}
var valid = {
"1": [ 0, 1 ],
"2": [ 0, 2 ],
"3": [ 0, 3 ],
"5": [ 0, 5 ],
" 1 ": [ 0, 1 ],
" 5 ": [ 0, 5 ],
"+2n + 1": [ 2, 1 ],
"-1": [ 0, -1 ],
"-1n + 3": [ -1, 3 ],
"-1n+3": [ -1, 3 ],
"-n+2": [ -1, 2 ],
"-n+3": [ -1, 3 ],
"0n+3": [ 1, 3 ],
"1n": [ 1, 0 ],
"1n+0": [ 1, 0 ],
"2n": [ 2, 0 ],
"2n + 1": [ 2, 1 ],
"2n+1": [ 2, 1 ],
"3n": [ 3, 0 ],
"3n+0": [ 3, 0 ],
"3n+1": [ 3, 1 ],
"3n+2": [ 3, 2 ],
"3n+3": [ 3, 3 ],
"3n-1": [ 3, -1 ],
"3n-2": [ 3, -2 ],
"3n-3": [ 3, -3 ],
even: [ 2, 0 ],
n: [ 1, 0 ],
"n+2": [ 1, 2 ],
odd: [ 2, 1 ],
//surprisingly, neither sizzle, qwery or nwmatcher cover these cases
"-4n+13": [-4, 13],
"-2n + 12": [-2, 12]
};
function parseValid(){
Object.keys(valid).forEach(function(formula){
assert.deepEqual(nthCheck.parse(formula), valid[formula], formula);
});
}
function testValid(){
Object.keys(valid).forEach(function(formula){
testFormula(valid[formula], formula);
});
}
var LIMIT = 1e3;
var valArray = (function(){
var elems = [];
for(var i = 0; i <= LIMIT; i++) elems.push(i);
return elems;
}());
function testFormula(formula, name){
var filtered = valArray.filter(nthCheck.compile(formula)),
iterated = stupidNth(formula);
try {
assert.deepEqual(filtered, iterated, name);
} catch(e){
e.expected = JSON.stringify(iterated) + " " + name;
e.actual = JSON.stringify(filtered) + " " + name;
throw e;
}
}
function stupidNth(formula, limit){
var a = formula[0],
b = formula[1];
if(a === 0 && b > 0) return [b - 1];
/*
var result = [];
for(var i = b; a > 0 ? i <= limit : i >= 1; i += a){
if(i > 0) result.push(i - 1);
}
return result.sort();
*/
//taken from qwery
return valArray.filter(function(val){
for(var i = b, l = valArray.length; ((a > 0) ? (i <= l) : (i >= 1)); i += a){
if(val === valArray[i - 1]) return true;
}
});
}
describe("nth-checks", function(){
describe("parser", function(){
it("parse invalid", parseInvalid);
it("parse valid", parseValid);
});
it("check values", testValid);
});

22
node_modules/CSSselect/test/nwmatcher/LICENSE generated vendored Normal file
View File

@@ -0,0 +1,22 @@
Copyright (c) 2007-2013 Diego Perini (http://www.iport.it)
Permission is hereby granted, free of charge, to any person
obtaining a copy of this software and associated documentation
files (the "Software"), to deal in the Software without
restriction, including without limitation the rights to use,
copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the
Software is furnished to do so, subject to the following
conditions:
The above copyright notice and this permission notice shall be
included in all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
OTHER DEALINGS IN THE SOFTWARE.

467
node_modules/CSSselect/test/nwmatcher/index.js generated vendored Normal file
View File

@@ -0,0 +1,467 @@
/*
taken from https://github.com/dperini/nwmatcher/blob/master/test/scotch/test.js
*/
var DomUtils = require("htmlparser2").DomUtils,
helper = require("../tools/helper.js"),
assert = require("assert"),
path = require("path"),
document = helper.getDocument(path.join(__dirname, "test.html")),
CSSselect = helper.CSSselect;
//Prototype's `$` function
function getById(element){
if(arguments.length === 1){
if(typeof element === "string"){
return DomUtils.getElementById(element, document);
}
return element;
}
else return Array.prototype.map.call(arguments, function(elem){
return getById(elem);
});
}
//NWMatcher methods
var select = function(query, doc){
if(arguments.length === 1 || typeof doc === "undefined") doc = document;
else if(typeof doc === "string") doc = select(doc);
return CSSselect(query, doc);
}, match = CSSselect.is;
var validators = {
assert: assert,
assertEqual: assert.equal,
assertEquivalent: assert.deepEqual,
refute: function refute(a, msg){
assert(!a, msg);
},
assertThrowsException: function(){} //not implemented
};
var runner = {
__name: "",
addGroup: function(name){
this.__name = name;
return this;
},
addTests: function(_, tests){
if(this.__name){
describe(this.__name, run);
this.__name = "";
} else run();
function run(){
Object.keys(tests).forEach(function(name){
it(name, function(){
tests[name].call(validators);
});
});
}
}
}
var RUN_BENCHMARKS = false;
//The tests...
(function(runner){
runner.addGroup("Basic Selectors").addTests(null, {
"*": function(){
//Universal selector
var results = [], nodes = document.getElementsByTagName("*"), index = 0, length = nodes.length, node;
//Collect all element nodes, excluding comments (IE)
for(; index < length; index++){
if((node = nodes[index]).tagName !== "!"){
results[results.length] = node;
}
}
this.assertEquivalent(select("*"), results, "Comment nodes should be ignored.");
},
"E": function(){
//Type selector
var results = [], index = 0, nodes = document.getElementsByTagName("li");
while((results[index] = nodes[index++])){}
results.length--;
// this.assertEquivalent(select("li"), results); //TODO
this.assertEqual(select("strong", getById("fixtures"))[0], getById("strong"));
this.assertEquivalent(select("nonexistent"), []);
},
"#id": function(){
//ID selector
this.assertEqual(select("#fixtures")[0], getById("fixtures"));
this.assertEquivalent(select("nonexistent"), []);
this.assertEqual(select("#troubleForm")[0], getById("troubleForm"));
},
".class": function(){
//Class selector
this.assertEquivalent(select(".first"), getById('p', 'link_1', 'item_1'));
this.assertEquivalent(select(".second"), []);
},
"E#id": function(){
this.assertEqual(select("strong#strong")[0], getById("strong"));
this.assertEquivalent(select("p#strong"), []);
},
"E.class": function(){
var secondLink = getById("link_2");
this.assertEquivalent(select('a.internal'), getById('link_1', 'link_2'));
this.assertEqual(select('a.internal.highlight')[0], secondLink);
this.assertEqual(select('a.highlight.internal')[0], secondLink);
this.assertEquivalent(select('a.highlight.internal.nonexistent'), []);
},
"#id.class": function(){
var secondLink = getById('link_2');
this.assertEqual(select('#link_2.internal')[0], secondLink);
this.assertEqual(select('.internal#link_2')[0], secondLink);
this.assertEqual(select('#link_2.internal.highlight')[0], secondLink);
this.assertEquivalent(select('#link_2.internal.nonexistent'), []);
},
"E#id.class": function(){
var secondLink = getById('link_2');
this.assertEqual(select('a#link_2.internal')[0], secondLink);
this.assertEqual(select('a.internal#link_2')[0], secondLink);
this.assertEqual(select('li#item_1.first')[0], getById("item_1"));
this.assertEquivalent(select('li#item_1.nonexistent'), []);
this.assertEquivalent(select('li#item_1.first.nonexistent'), []);
}
});
runner.addGroup("Attribute Selectors").addTests(null, {
"[foo]": function(){
this.assertEquivalent(select('[href]', document.body), select('a[href]', document.body));
this.assertEquivalent(select('[class~=internal]'), select('a[class~="internal"]'));
this.assertEquivalent(select('[id]'), select('*[id]'));
this.assertEquivalent(select('[type=radio]'), getById('checked_radio', 'unchecked_radio'));
this.assertEquivalent(select('[type=checkbox]'), select('*[type=checkbox]'));
this.assertEquivalent(select('[title]'), getById('with_title', 'commaParent'));
this.assertEquivalent(select('#troubleForm [type=radio]'), select('#troubleForm *[type=radio]'));
this.assertEquivalent(select('#troubleForm [type]'), select('#troubleForm *[type]'));
},
"E[foo]": function(){
this.assertEquivalent(select('h1[class]'), select('#fixtures h1'), "h1[class]");
this.assertEquivalent(select('h1[CLASS]'), select('#fixtures h1'), "h1[CLASS]");
this.assertEqual(select('li#item_3[class]')[0], getById('item_3'), "li#item_3[class]");
this.assertEquivalent(select('#troubleForm2 input[name="brackets[5][]"]'), getById('chk_1', 'chk_2'));
//Brackets in attribute value
this.assertEqual(select('#troubleForm2 input[name="brackets[5][]"]:checked')[0], getById('chk_1'));
//Space in attribute value
this.assertEqual(select('cite[title="hello world!"]')[0], getById('with_title'));
//Namespaced attributes
// this.assertEquivalent(select('[xml:lang]'), [document.documentElement, getById("item_3")]);
// this.assertEquivalent(select('*[xml:lang]'), [document.documentElement, getById("item_3")]);
},
'E[foo="bar"]': function(){
this.assertEquivalent(select('a[href="#"]'), getById('link_1', 'link_2', 'link_3'));
this.assertThrowsException(/Error/, function(){
select('a[href=#]');
});
this.assertEqual(select('#troubleForm2 input[name="brackets[5][]"][value="2"]')[0], getById('chk_2'));
},
'E[foo~="bar"]': function(){
this.assertEquivalent(select('a[class~="internal"]'), getById('link_1', 'link_2'), "a[class~=\"internal\"]");
this.assertEquivalent(select('a[class~=internal]'), getById('link_1', 'link_2'), "a[class~=internal]");
this.assertEqual(select('a[class~=external][href="#"]')[0], getById('link_3'), 'a[class~=external][href="#"]');
},/*
'E[foo|="en"]': function(){
this.assertEqual(select('*[xml:lang|="es"]')[0], getById('item_3'));
this.assertEqual(select('*[xml:lang|="ES"]')[0], getById('item_3'));
},*/
'E[foo^="bar"]': function(){
this.assertEquivalent(select('div[class^=bro]'), getById('father', 'uncle'), 'matching beginning of string');
this.assertEquivalent(select('#level1 *[id^="level2_"]'), getById('level2_1', 'level2_2', 'level2_3'));
this.assertEquivalent(select('#level1 *[id^=level2_]'), getById('level2_1', 'level2_2', 'level2_3'));
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level1 *[id^=level2_]');
}, 1000);
}, 500);
}
},
'E[foo$="bar"]': function(){
this.assertEquivalent(select('div[class$=men]'), getById('father', 'uncle'), 'matching end of string');
this.assertEquivalent(select('#level1 *[id$="_1"]'), getById('level2_1', 'level3_1'));
this.assertEquivalent(select('#level1 *[id$=_1]'), getById('level2_1', 'level3_1'));
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level1 *[id$=_1]');
}, 1000);
}, 500);
}
},
'E[foo*="bar"]': function(){
this.assertEquivalent(select('div[class*="ers m"]'), getById('father', 'uncle'), 'matching substring');
this.assertEquivalent(select('#level1 *[id*="2"]'), getById('level2_1', 'level3_2', 'level2_2', 'level2_3'));
this.assertThrowsException(/Error/, function(){
select('#level1 *[id*=2]');
});
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level1 *[id*=2]');
}, 1000);
}, 500);
}
},
// *** these should throw SYNTAX_ERR ***
'E[id=-1]': function(){
this.assertThrowsException(/Error/, function(){
select('#level1 *[id=-1]');
});
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level1 *[id=9]');
}, 1000);
}, 500);
}
},
'E[class=-45deg]': function(){
this.assertThrowsException(/Error/, function(){
select('#level1 *[class=-45deg]');
});
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level1 *[class=-45deg]');
}, 1000);
}, 500);
}
},
'E[class=8mm]': function(){
this.assertThrowsException(/Error/, function(){
select('#level1 *[class=8mm]');
});
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level1 *[class=8mm]');
}, 1000);
}, 500);
}
}
});
runner.addGroup("Structural pseudo-classes").addTests(null, {
"E:first-child": function(){
this.assertEqual(select('#level1>*:first-child')[0], getById('level2_1'));
this.assertEquivalent(select('#level1 *:first-child'), getById('level2_1', 'level3_1', 'level_only_child'));
this.assertEquivalent(select('#level1>div:first-child'), []);
this.assertEquivalent(select('#level1 span:first-child'), getById('level2_1', 'level3_1'));
this.assertEquivalent(select('#level1:first-child'), []);
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level1 *:first-child');
}, 1000);
}, 500);
}
},
"E:last-child": function(){
this.assertEqual(select('#level1>*:last-child')[0], getById('level2_3'));
this.assertEquivalent(select('#level1 *:last-child'), getById('level3_2', 'level_only_child', 'level2_3'));
this.assertEqual(select('#level1>div:last-child')[0], getById('level2_3'));
this.assertEqual(select('#level1 div:last-child')[0], getById('level2_3'));
this.assertEquivalent(select('#level1>span:last-child'), []);
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level1 *:last-child');
}, 1000);
}, 500);
}
},
"E:nth-child(n)": function(){
this.assertEqual(select('#p *:nth-child(3)')[0], getById('link_2'));
this.assertEqual(select('#p a:nth-child(3)')[0], getById('link_2'), 'nth-child');
this.assertEquivalent(select('#list > li:nth-child(n+2)'), getById('item_2', 'item_3'));
this.assertEquivalent(select('#list > li:nth-child(-n+2)'), getById('item_1', 'item_2'));
},
"E:nth-of-type(n)": function(){
this.assertEqual(select('#p a:nth-of-type(2)')[0], getById('link_2'), 'nth-of-type');
this.assertEqual(select('#p a:nth-of-type(1)')[0], getById('link_1'), 'nth-of-type');
},
"E:nth-last-of-type(n)": function(){
this.assertEqual(select('#p a:nth-last-of-type(1)')[0], getById('link_2'), 'nth-last-of-type');
},
"E:first-of-type": function(){
this.assertEqual(select('#p a:first-of-type')[0], getById('link_1'), 'first-of-type');
},
"E:last-of-type": function(){
this.assertEqual(select('#p a:last-of-type')[0], getById('link_2'), 'last-of-type');
},
"E:only-child": function(){
this.assertEqual(select('#level1 *:only-child')[0], getById('level_only_child'));
//Shouldn't return anything
this.assertEquivalent(select('#level1>*:only-child'), []);
this.assertEquivalent(select('#level1:only-child'), []);
this.assertEquivalent(select('#level2_2 :only-child:not(:last-child)'), []);
this.assertEquivalent(select('#level2_2 :only-child:not(:first-child)'), []);
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level1 *:only-child');
}, 1000);
}, 500);
}
},
"E:empty": function(){
getById('level3_1').children = [];
if(document.createEvent){
this.assertEquivalent(select('#level1 *:empty'), getById('level3_1', 'level3_2', 'level2_3'), '#level1 *:empty');
this.assertEquivalent(select('#level_only_child:empty'), [], 'newlines count as content!');
}else{
this.assertEqual(select('#level3_1:empty')[0], getById('level3_1'), 'IE forced empty content!');
//this.skip("IE forced empty content!");
}
//Shouldn't return anything
this.assertEquivalent(select('span:empty > *'), []);
}
});
runner.addTests(null, {
"E:not(s)": function(){
//Negation pseudo-class
this.assertEquivalent(select('a:not([href="#"])'), []);
this.assertEquivalent(select('div.brothers:not(.brothers)'), []);
this.assertEquivalent(select('a[class~=external]:not([href="#"])'), [], 'a[class~=external][href!="#"]');
this.assertEqual(select('#p a:not(:first-of-type)')[0], getById('link_2'), 'first-of-type');
this.assertEqual(select('#p a:not(:last-of-type)')[0], getById('link_1'), 'last-of-type');
this.assertEqual(select('#p a:not(:nth-of-type(1))')[0], getById('link_2'), 'nth-of-type');
this.assertEqual(select('#p a:not(:nth-last-of-type(1))')[0], getById('link_1'), 'nth-last-of-type');
this.assertEqual(select('#p a:not([rel~=nofollow])')[0], getById('link_2'), 'attribute 1');
this.assertEqual(select('#p a:not([rel^=external])')[0], getById('link_2'), 'attribute 2');
this.assertEqual(select('#p a:not([rel$=nofollow])')[0], getById('link_2'), 'attribute 3');
this.assertEqual(select('#p a:not([rel$="nofollow"]) > em')[0], getById('em'), 'attribute 4');
this.assertEqual(select('#list li:not(#item_1):not(#item_3)')[0], getById('item_2'), 'adjacent :not clauses');
this.assertEqual(select('#grandfather > div:not(#uncle) #son')[0], getById('son'));
this.assertEqual(select('#p a:not([rel$="nofollow"]) em')[0], getById('em'), 'attribute 4 + all descendants');
this.assertEqual(select('#p a:not([rel$="nofollow"])>em')[0], getById('em'), 'attribute 4 (without whitespace)');
}
});
runner.addGroup("UI element states pseudo-classes").addTests(null, {
"E:disabled": function(){
this.assertEqual(select('#troubleForm > p > *:disabled')[0], getById('disabled_text_field'));
},
"E:checked": function(){
this.assertEquivalent(select('#troubleForm *:checked'), getById('checked_box', 'checked_radio'));
}
});
runner.addGroup("Combinators").addTests(null, {
"E F": function(){
//Descendant
this.assertEquivalent(select('#fixtures a *'), getById('em2', 'em', 'span'));
this.assertEqual(select('div#fixtures p')[0], getById("p"));
},
"E + F": function(){
//Adjacent sibling
this.assertEqual(select('div.brothers + div.brothers')[0], getById("uncle"));
this.assertEqual(select('div.brothers + div')[0], getById('uncle'));
this.assertEqual(select('#level2_1+span')[0], getById('level2_2'));
this.assertEqual(select('#level2_1 + span')[0], getById('level2_2'));
this.assertEqual(select('#level2_1 + *')[0], getById('level2_2'));
this.assertEquivalent(select('#level2_2 + span'), []);
this.assertEqual(select('#level3_1 + span')[0], getById('level3_2'));
this.assertEqual(select('#level3_1 + *')[0], getById('level3_2'));
this.assertEquivalent(select('#level3_2 + *'), []);
this.assertEquivalent(select('#level3_1 + em'), []);
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level3_1 + span');
}, 1000);
}, 500);
}
},
"E > F": function(){
//Child
this.assertEquivalent(select('p.first > a'), getById('link_1', 'link_2'));
this.assertEquivalent(select('div#grandfather > div'), getById('father', 'uncle'));
this.assertEquivalent(select('#level1>span'), getById('level2_1', 'level2_2'));
this.assertEquivalent(select('#level1 > span'), getById('level2_1', 'level2_2'));
this.assertEquivalent(select('#level2_1 > *'), getById('level3_1', 'level3_2'));
this.assertEquivalent(select('div > #nonexistent'), []);
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level1 > span');
}, 1000);
}, 500);
}
},
"E ~ F": function(){
//General sibling
this.assertEqual(select('h1 ~ ul')[0], getById('list'));
this.assertEquivalent(select('#level2_2 ~ span'), []);
this.assertEquivalent(select('#level3_2 ~ *'), []);
this.assertEquivalent(select('#level3_1 ~ em'), []);
this.assertEquivalent(select('div ~ #level3_2'), []);
this.assertEquivalent(select('div ~ #level2_3'), []);
this.assertEqual(select('#level2_1 ~ span')[0], getById('level2_2'));
this.assertEquivalent(select('#level2_1 ~ *'), getById('level2_2', 'level2_3'));
this.assertEqual(select('#level3_1 ~ #level3_2')[0], getById('level3_2'));
this.assertEqual(select('span ~ #level3_2')[0], getById('level3_2'));
if(RUN_BENCHMARKS){
this.wait(function(){
this.benchmark(function(){
select('#level2_1 ~ span');
}, 1000);
}, 500);
}
}
});
runner.addTests(null, {
"NW.Dom.match": function(){
var element = getById('dupL1');
//Assertions
this.assert(match(element, 'span'));
this.assert(match(element, "span#dupL1"));
this.assert(match(element, "div > span"), "child combinator");
this.assert(match(element, "#dupContainer span"), "descendant combinator");
this.assert(match(element, "#dupL1"), "ID only");
this.assert(match(element, "span.span_foo"), "class name 1");
this.assert(match(element, "span.span_bar"), "class name 2");
this.assert(match(element, "span:first-child"), "first-child pseudoclass");
//Refutations
this.refute(match(element, "span.span_wtf"), "bogus class name");
this.refute(match(element, "#dupL2"), "different ID");
this.refute(match(element, "div"), "different tag name");
this.refute(match(element, "span span"), "different ancestry");
this.refute(match(element, "span > span"), "different parent");
this.refute(match(element, "span:nth-child(5)"), "different pseudoclass");
//Misc.
this.refute(match(getById('link_2'), 'a[rel^=external]'));
this.assert(match(getById('link_1'), 'a[rel^=external]'));
this.assert(match(getById('link_1'), 'a[rel^="external"]'));
this.assert(match(getById('link_1'), "a[rel^='external']"));
},
"Equivalent Selectors": function(){
this.assertEquivalent(select('div.brothers'), select('div[class~=brothers]'));
this.assertEquivalent(select('div.brothers'), select('div[class~=brothers].brothers'));
this.assertEquivalent(select('div:not(.brothers)'), select('div:not([class~=brothers])'));
this.assertEquivalent(select('li ~ li'), select('li:not(:first-child)'));
this.assertEquivalent(select('ul > li'), select('ul > li:nth-child(n)'));
this.assertEquivalent(select('ul > li:nth-child(even)'), select('ul > li:nth-child(2n)'));
this.assertEquivalent(select('ul > li:nth-child(odd)'), select('ul > li:nth-child(2n+1)'));
this.assertEquivalent(select('ul > li:first-child'), select('ul > li:nth-child(1)'));
this.assertEquivalent(select('ul > li:last-child'), select('ul > li:nth-last-child(1)'));
/* Opera 10 does not accept values > 128 as a parameter to :nth-child
See <http://operawiki.info/ArtificialLimits> */
this.assertEquivalent(select('ul > li:nth-child(n-128)'), select('ul > li'));
this.assertEquivalent(select('ul>li'), select('ul > li'));
this.assertEquivalent(select('#p a:not([rel$="nofollow"])>em'), select('#p a:not([rel$="nofollow"]) > em'));
},
"Multiple Selectors": function(){
//The next two assertions should return document-ordered lists of matching elements --Diego Perini
// this.assertEquivalent(select('#list, .first,*[xml:lang="es-us"] , #troubleForm'), getById('p', 'link_1', 'list', 'item_1', 'item_3', 'troubleForm'));
// this.assertEquivalent(select('#list, .first, *[xml:lang="es-us"], #troubleForm'), getById('p', 'link_1', 'list', 'item_1', 'item_3', 'troubleForm'));
this.assertEquivalent(select('form[title*="commas,"], input[value="#commaOne,#commaTwo"]'), getById('commaParent', 'commaChild'));
this.assertEquivalent(select('form[title*="commas,"], input[value="#commaOne,#commaTwo"]'), getById('commaParent', 'commaChild'));
}
});
}(runner));

92
node_modules/CSSselect/test/nwmatcher/test.html generated vendored Normal file
View File

@@ -0,0 +1,92 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>NWMatcher Tests</title>
<link rel="stylesheet" type="text/css" href="assets/style.css" media="screen" />
<script type="text/javascript" src="../../src/nwmatcher.js"></script>
<script type="text/javascript" src="scotch.js"></script>
<script type="text/javascript" src="test.js"></script>
</head>
<body>
<div id="container">
<div id="testlog" class="log"></div>
<!-- Test elements -->
<div id="fixtures" style="display: none;">
<h1 class="title">Some title <span>here</span></h1>
<p id="p" class="first summary">
<strong id="strong">This</strong> is a short blurb
<a id="link_1" class="first internal" rel="external nofollow" href="#">with a <em id="em2">link</em></a> or
<a id="link_2" class="internal highlight" href="#"><em id="em">two</em></a>.
Or <cite id="with_title" title="hello world!">a citation</cite>.
</p>
<ul id="list">
<li id="item_1" class="first"><a id="link_3" href="#" class="external"><span id="span">Another link</span></a></li>
<li id="item_2">Some text</li>
<li id="item_3" xml:lang="es-us" class="">Otra cosa</li>
</ul>
<!-- This form has a field with the name "id"; its "ID" property won't be "troubleForm" -->
<form id="troubleForm" action="">
<p>
<input type="hidden" name="id" id="hidden" />
<input type="text" name="disabled_text_field" id="disabled_text_field" disabled="disabled" />
<input type="text" name="enabled_text_field" id="enabled_text_field" />
<input type="checkbox" name="checkboxes" id="checked_box" checked="checked" value="Checked" />
<input type="checkbox" name="checkboxes" id="unchecked_box" value="Unchecked"/>
<input type="radio" name="radiobuttons" id="checked_radio" checked="checked" value="Checked" />
<input type="radio" name="radiobuttons" id="unchecked_radio" value="Unchecked" />
</p>
</form>
<form id="troubleForm2" action="">
<p>
<input type="checkbox" name="brackets[5][]" id="chk_1" checked="checked" value="1" />
<input type="checkbox" name="brackets[5][]" id="chk_2" value="2" />
</p>
</form>
<div id="level1">
<span id="level2_1">
<span id="level3_1"></span>
<!-- This comment should be ignored by the adjacent selector -->
<span id="level3_2"></span>
</span>
<span id="level2_2">
<em id="level_only_child">
</em>
</span>
<div id="level2_3"></div>
</div> <!-- #level1 -->
<div id="dupContainer">
<span id="dupL1" class="span_foo span_bar">
<span id="dupL2">
<span id="dupL3">
<span id="dupL4">
<span id="dupL5"></span>
</span>
</span>
</span>
</span>
</div> <!-- #dupContainer -->
<div id="grandfather"> grandfather
<div id="father" class="brothers men"> father
<div id="son"> son </div>
</div>
<div id="uncle" class="brothers men"> uncle </div>
</div>
<form id="commaParent" title="commas,are,good" action="">
<p>
<input type="hidden" id="commaChild" name="foo" value="#commaOne,#commaTwo" />
<input type="hidden" id="commaTwo" name="foo2" value="oops" />
</p>
</form>
<div id="counted_container"><div class="is_counted"></div></div>
</div>
</div>
</body>
</html>

132
node_modules/CSSselect/test/qwery/index.html generated vendored Normal file
View File

@@ -0,0 +1,132 @@
<!DOCTYPE HTML>
<html lang="en-us">
<head>
<meta http-equiv="Content-type" content="text/html; charset=utf-8">
<title>Qwery tests</title>
<style type="text/css">
#fixtures {
position: absolute;
top: -9999px;
}
</style>
<link rel="stylesheet" href="../node_modules/sink-test/src/sink.css" type="text/css">
<script src="../node_modules/sink-test/src/sink.js"></script>
<script src="../src/qwery.js"></script>
<script src="../pseudos/qwery-pseudos.js"></script>
<script type="text/javascript">
var Q = qwery
</script>
</head>
<body>
<h1>Qwery Tests</h1>
<div id="fixtures">
<ol id="list">
<li>hello</li>
<li>world</li>
<ol>
<li>world</li>
<li id="attr-child-boosh" attr="boosh">hello</li>
</ol>
<li>humans</li>
</ol>
<div id="spaced-tokens">
<p><em><a href="#"></a></em></p>
<p></p>
</div>
<div id="pseudos">
<div class="odd pseudos pseudo-1"></div>
<div class="even pseudos pseudo-2"></div>
<div class="odd"></div>
<div class="even"></div>
<a class="odd"></a>
<div class="even"></div>
<div class="odd"></div>
</div>
<div foo="bar"></div>
<div class="a"></div>
<div class="class-with-dashes"></div>
<div id="boosh">
<!-- comment -->
<!-- comment -->
<div class="a b">
<div class="d e" test="fg" id="booshTest"></div>
<!-- comment -->
<em nopass="copyrighters" rel="copyright booshrs" test="f g"></em>
<span class="h i a"></span>
</div>
<!-- comment -->
</div>
<div id="lonelyBoosh"></div>
<div id="attr-test1" -data-attr></div>
<div id="attr-test2" -data-attr></div>
<div id="attr-test3" class="found you" -data-attr title="whatup duders"></div>
<div id="attributes">
<div test="one" unique-test="baz" id="attr-test-1"></div>
<div test="two-foo" id="attr-test-2"></div>
<div test=" three " id="attr-test-3"></div>
<a href="#aname" id="attr-test-4">aname</a>
</div>
<div class="idless">
<div class="tokens" title="one" id="token-one"></div>
<div class="tokens" title="one two" id="token-two"></div>
<div class="tokens" title="one two three #%" id="token-three">
<a href="foo" id="token-four">
<div id="token-five"></div>
</a>
</div>
</div>
<div id="order-matters" class="order-matters">
<p class="order-matters"></p>
<a class="order-matters">
<em class="order-matters"></em><b class="order-matters"></b>
</a>
</div>
<div id="direct-descend" class="oogabooga">
<div></div>
<div class="direct-descend">
<span></span>
<div class="direct-descend">
<div class="lvl2" id="toodeep"><span></span></div>
</div>
<div class="direct-descend"><span></span></div>
<div class="lvl2" id="l2">
<span></span>
<div class="direct-descend"><span></span></div>
</div>
<div class="lvl2" id="l3"></div>
</div>
<div class="ignoreme"></div>
<div class="direct-descend">
<div class="direct-descend"></div>
<div class="lvl2" id="l4"></div>
</div>
<div></div>
</div>
<div id="sibling-selector"></div>
<div class="sibling-selector" id="sib1">
<div class="sibling-selector"></div>
<div class="sibling-selector"></div>
</div>
<div class="sibling-selector" id="sib2">
<div class="sibling-selector">
<div class="sibling-selector"></div>
</div>
</div>
<div class="parent">
<h1 class="sibling oldest"></h1>
<h2 class="sibling older"></h2>
<h3 class="sibling middle"></h3>
<h4 class="sibling younger"></h4>
<h5 class="sibling youngest"></h5>
</div>
<form>
<button></button>
<input type="text">
<input type="hidden">
</form>
</div>
<ol id="tests"></ol>
<iframe id="frame" style="width: 0; height: 0; margin-left: -1000px;"></iframe>
<script src="tests.js"></script>
</body>
</html>

549
node_modules/CSSselect/test/qwery/index.js generated vendored Normal file
View File

@@ -0,0 +1,549 @@
"use strict";
var expect = require("expect.js"),
DomUtils = require("htmlparser2").DomUtils,
helper = require("../tools/helper.js"),
path = require("path"),
document = helper.getDocument(path.join(__dirname, "index.html")),
CSSselect = helper.CSSselect;
var location = {hash: ""};
CSSselect.pseudos.target = function(elem){
return elem.attribs && elem.attribs.id === location.hash.substr(1);
};
//---
/*
The following is taken from https://github.com/ded/qwery/blob/master/tests/tests.js
*/
CSSselect.pseudos.humanoid = function(e) { return CSSselect.is(e, 'li:contains(human)') || CSSselect.is(e, 'ol:contains(human)'); };
var frag = helper.getDOM(
'<div class="d i v">' +
'<p id="oooo"><em></em><em id="emem"></em></p>' +
'</div>' +
'<p id="sep">' +
'<div class="a"><span></span></div>' +
'</p>'
);
var doc = helper.getDOM(
'<div id="hsoob">' +
'<div class="a b">' +
'<div class="d e sib" test="fg" id="booshTest"><p><span id="spanny"></span></p></div>' +
'<em nopass="copyrighters" rel="copyright booshrs" test="f g" class="sib"></em>' +
'<span class="h i a sib"></span>' +
'</div>' +
'<p class="odd"></p>' +
'</div>' +
'<div id="lonelyHsoob"></div>'
);
var el = DomUtils.getElementById('attr-child-boosh', document);
var pseudos = DomUtils.getElementById('pseudos', document).children.filter(DomUtils.isTag);
module.exports = {
'Contexts': {
'should be able to pass optional context': function () {
expect(CSSselect('.a', document)).to.have.length(3); //no context found 3 elements (.a)
expect(CSSselect('.a', CSSselect('#boosh', document))).to.have.length(2); //context found 2 elements (#boosh .a)
},
/*
'should be able to pass string as context': function() {
expect(CSSselect('.a', '#boosh')).to.have.length(2); //context found 2 elements(.a, #boosh)
expect(CSSselect('.a', '.a')).to.be.empty(); //context found 0 elements(.a, .a)
expect(CSSselect('.a', '.b')).to.have.length(1); //context found 1 elements(.a, .b)
expect(CSSselect('.a', '#boosh .b')).to.have.length(1); //context found 1 elements(.a, #boosh .b)
expect(CSSselect('.b', '#boosh .b')).to.be.empty(); //context found 0 elements(.b, #boosh .b)
},
*/
/*
'should be able to pass qwery result as context': function() {
expect(CSSselect('.a', CSSselect('#boosh', document))).to.have.length(2); //context found 2 elements(.a, #boosh)
expect(CSSselect('.a', CSSselect('.a', document))).to.be.empty(); //context found 0 elements(.a, .a)
expect(CSSselect('.a', CSSselect('.b', document))).to.have.length(1); //context found 1 elements(.a, .b)
expect(CSSselect('.a', CSSselect('#boosh .b', document))).to.have.length(1); //context found 1 elements(.a, #boosh .b)
expect(CSSselect('.b', CSSselect('#boosh .b', document))).to.be.empty(); //context found 0 elements(.b, #boosh .b)
},
*/
'should not return duplicates from combinators': function () {
expect(CSSselect('#boosh,#boosh', document)).to.have.length(1); //two booshes dont make a thing go right
expect(CSSselect('#boosh,.apples,#boosh', document)).to.have.length(1); //two booshes and an apple dont make a thing go right
},
'byId sub-queries within context': function() {
expect(CSSselect('#booshTest', CSSselect('#boosh', document))).to.have.length(1); //found "#id #id"
expect(CSSselect('.a.b #booshTest', CSSselect('#boosh', document))).to.have.length(1); //found ".class.class #id"
expect(CSSselect('.a>#booshTest', CSSselect('#boosh', document))).to.have.length(1); //found ".class>#id"
expect(CSSselect('>.a>#booshTest', CSSselect('#boosh', document))).to.have.length(1); //found ">.class>#id"
expect(CSSselect('#boosh', CSSselect('#booshTest', document)).length).to.not.be.ok(); //shouldn't find #boosh (ancestor) within #booshTest (descendent)
expect(CSSselect('#boosh', CSSselect('#lonelyBoosh', document)).length).to.not.be.ok(); //shouldn't find #boosh within #lonelyBoosh (unrelated)
}
},
'CSS 1': {
'get element by id': function () {
var result = CSSselect('#boosh', document);
expect(result[0]).to.be.ok(); //found element with id=boosh
expect(CSSselect('h1', document)[0]).to.be.ok(); //found 1 h1
},
'byId sub-queries': function() {
expect(CSSselect('#boosh #booshTest', document)).to.have.length(1); //found "#id #id"
expect(CSSselect('.a.b #booshTest', document)).to.have.length(1); //found ".class.class #id"
expect(CSSselect('#boosh>.a>#booshTest', document)).to.have.length(1); //found "#id>.class>#id"
expect(CSSselect('.a>#booshTest', document)).to.have.length(1); //found ".class>#id"
},
'get elements by class': function () {
expect(CSSselect('#boosh .a', document)).to.have.length(2); //found two elements
expect(CSSselect('#boosh div.a', document)[0]).to.be.ok(); //found one element
expect(CSSselect('#boosh div', document)).to.have.length(2); //found two {div} elements
expect(CSSselect('#boosh span', document)[0]).to.be.ok(); //found one {span} element
expect(CSSselect('#boosh div div', document)[0]).to.be.ok(); //found a single div
expect(CSSselect('a.odd', document)).to.have.length(1); //found single a
},
'combos': function () {
expect(CSSselect('#boosh div,#boosh span', document)).to.have.length(3); //found 2 divs and 1 span
},
'class with dashes': function() {
expect(CSSselect('.class-with-dashes', document)).to.have.length(1); //found something
},
'should ignore comment nodes': function() {
expect(CSSselect('#boosh *', document)).to.have.length(4); //found only 4 elements under #boosh
},
'deep messy relationships': function() {
// these are mostly characterised by a combination of tight relationships and loose relationships
// on the right side of the query it's easy to find matches but they tighten up quickly as you
// go to the left
// they are useful for making sure the dom crawler doesn't stop short or over-extend as it works
// up the tree the crawl needs to be comprehensive
expect(CSSselect('div#fixtures > div a', document)).to.have.length(5); //found four results for "div#fixtures > div a"
expect(CSSselect('.direct-descend > .direct-descend .lvl2', document)).to.have.length(1); //found one result for ".direct-descend > .direct-descend .lvl2"
expect(CSSselect('.direct-descend > .direct-descend div', document)).to.have.length(1); //found one result for ".direct-descend > .direct-descend div"
expect(CSSselect('.direct-descend > .direct-descend div', document)).to.have.length(1); //found one result for ".direct-descend > .direct-descend div"
expect(CSSselect('div#fixtures div ~ a div', document)).to.be.empty(); //found no results for odd query
expect(CSSselect('.direct-descend > .direct-descend > .direct-descend ~ .lvl2', document)).to.be.empty(); //found no results for another odd query
}
},
'CSS 2': {
'get elements by attribute': function () {
var wanted = CSSselect('#boosh div[test]', document)[0];
var expected = DomUtils.getElementById('booshTest', document);
expect(wanted).to.be(expected); //found attribute
expect(CSSselect('#boosh div[test=fg]', document)[0]).to.be(expected); //found attribute with value
expect(CSSselect('em[rel~="copyright"]', document)).to.have.length(1); //found em[rel~="copyright"]
expect(CSSselect('em[nopass~="copyright"]', document)).to.be.empty(); //found em[nopass~="copyright"]
},
'should not throw error by attribute selector': function () {
expect(CSSselect('[foo^="bar"]', document)).to.have.length(1); //found 1 element
},
'crazy town': function () {
var el = DomUtils.getElementById('attr-test3', document);
expect(CSSselect('div#attr-test3.found.you[title="whatup duders"]', document)[0]).to.be(el); //found the right element
}
},
'attribute selectors': {
/* CSS 2 SPEC */
'[attr]': function () {
var expected = DomUtils.getElementById('attr-test-1', document);
expect(CSSselect('#attributes div[unique-test]', document)[0]).to.be(expected); //found attribute with [attr]
},
'[attr=val]': function () {
var expected = DomUtils.getElementById('attr-test-2', document);
expect(CSSselect('#attributes div[test="two-foo"]', document)[0]).to.be(expected); //found attribute with =
expect(CSSselect("#attributes div[test='two-foo']", document)[0]).to.be(expected); //found attribute with =
expect(CSSselect('#attributes div[test=two-foo]', document)[0]).to.be(expected); //found attribute with =
},
'[attr~=val]': function () {
var expected = DomUtils.getElementById('attr-test-3', document);
expect(CSSselect('#attributes div[test~=three]', document)[0]).to.be(expected); //found attribute with ~=
},
'[attr|=val]': function () {
var expected = DomUtils.getElementById('attr-test-2', document);
expect(CSSselect('#attributes div[test|="two-foo"]', document)[0]).to.be(expected); //found attribute with |=
expect(CSSselect('#attributes div[test|=two]', document)[0]).to.be(expected); //found attribute with |=
},
'[href=#x] special case': function () {
var expected = DomUtils.getElementById('attr-test-4', document);
expect(CSSselect('#attributes a[href="#aname"]', document)[0]).to.be(expected); //found attribute with href=#x
},
/* CSS 3 SPEC */
'[attr^=val]': function () {
var expected = DomUtils.getElementById('attr-test-2', document);
expect(CSSselect('#attributes div[test^=two]', document)[0]).to.be(expected); //found attribute with ^=
},
'[attr$=val]': function () {
var expected = DomUtils.getElementById('attr-test-2', document);
expect(CSSselect('#attributes div[test$=foo]', document)[0]).to.be(expected); //found attribute with $=
},
'[attr*=val]': function () {
var expected = DomUtils.getElementById('attr-test-3', document);
expect(CSSselect('#attributes div[test*=hree]', document)[0]).to.be(expected); //found attribute with *=
},
'direct descendants': function () {
expect(CSSselect('#direct-descend > .direct-descend', document)).to.have.length(2); //found two direct descendents
expect(CSSselect('#direct-descend > .direct-descend > .lvl2', document)).to.have.length(3); //found three second-level direct descendents
},
'sibling elements': function () {
expect(CSSselect('#sibling-selector ~ .sibling-selector', document)).to.have.length(2); //found two siblings
expect(CSSselect('#sibling-selector ~ div.sibling-selector', document)).to.have.length(2); //found two siblings
expect(CSSselect('#sibling-selector + div.sibling-selector', document)).to.have.length(1); //found one sibling
expect(CSSselect('#sibling-selector + .sibling-selector', document)).to.have.length(1); //found one sibling
expect(CSSselect('.parent .oldest ~ .sibling', document)).to.have.length(4); //found four younger siblings
expect(CSSselect('.parent .middle ~ .sibling', document)).to.have.length(2); //found two younger siblings
expect(CSSselect('.parent .middle ~ h4', document)).to.have.length(1); //found next sibling by tag
expect(CSSselect('.parent .middle ~ h4.younger', document)).to.have.length(1); //found next sibling by tag and class
expect(CSSselect('.parent .middle ~ h3', document)).to.be.empty(); //an element can't be its own sibling
expect(CSSselect('.parent .middle ~ h2', document)).to.be.empty(); //didn't find an older sibling
expect(CSSselect('.parent .youngest ~ .sibling', document)).to.be.empty(); //found no younger siblings
expect(CSSselect('.parent .oldest + .sibling', document)).to.have.length(1); //found next sibling
expect(CSSselect('.parent .middle + .sibling', document)).to.have.length(1); //found next sibling
expect(CSSselect('.parent .middle + h4', document)).to.have.length(1); //found next sibling by tag
expect(CSSselect('.parent .middle + h3', document)).to.be.empty(); //an element can't be its own sibling
expect(CSSselect('.parent .middle + h2', document)).to.be.empty(); //didn't find an older sibling
expect(CSSselect('.parent .youngest + .sibling', document)).to.be.empty(); //found no younger siblings
}
},
/*
'Uniq': {
'duplicates arent found in arrays': function () {
expect(CSSselect.uniq(['a', 'b', 'c', 'd', 'e', 'a', 'b', 'c', 'd', 'e'])).to.have.length(5); //result should be a, b, c, d, e
expect(CSSselect.uniq(['a', 'b', 'c', 'c', 'c'])).to.have.length(3); //result should be a, b, c
}
},
*/
'element-context queries': {
/*
'relationship-first queries': function() {
expect(CSSselect('> .direct-descend', CSSselect('#direct-descend', document))).to.have.length(2); //found two direct descendents using > first
expect(CSSselect('~ .sibling-selector', CSSselect('#sibling-selector', document))).to.have.length(2); //found two siblings with ~ first
expect(CSSselect('+ .sibling-selector', CSSselect('#sibling-selector', document))).to.have.length(1); //found one sibling with + first
expect(CSSselect('> .tokens a', CSSselect('.idless', document)[0])).to.have.length(1); //found one sibling from a root with no id
},
*/
// should be able to query on an element that hasn't been inserted into the dom
'detached fragments': function() {
expect(CSSselect('.a span', frag)).to.have.length(1); //should find child elements of fragment
//expect(CSSselect('> div p em', frag)).to.have.length(2); //should find child elements of fragment, relationship first
},
'byId sub-queries within detached fragment': function () {
expect(CSSselect('#emem', frag)).to.have.length(1); //found "#id" in fragment
expect(CSSselect('.d.i #emem', frag)).to.have.length(1); //found ".class.class #id" in fragment
expect(CSSselect('.d #oooo #emem', frag)).to.have.length(1); //found ".class #id #id" in fragment
//expect(CSSselect('> div #oooo', frag)).to.have.length(1); //found "> .class #id" in fragment
expect(CSSselect('#oooo', CSSselect('#emem', frag)).length).to.not.be.ok(); //shouldn't find #oooo (ancestor) within #emem (descendent)
expect(CSSselect('#sep', CSSselect('#emem', frag)).length).to.not.be.ok(); //shouldn't find #sep within #emem (unrelated)
},
/*
'exclude self in match': function() {
expect(CSSselect('.order-matters', CSSselect('#order-matters', document))).to.have.length(4); //should not include self in element-context queries
},
*/
// because form's have .length
'forms can be used as contexts': function() {
expect(CSSselect('*', CSSselect('form', document)[0])).to.have.length(3); //found 3 elements under &lt;form&gt;
}
},
'tokenizer': {
'should not get weird tokens': function () {
expect(CSSselect('div .tokens[title="one"]', document)[0]).to.be(DomUtils.getElementById('token-one', document)); //found div .tokens[title="one"]
expect(CSSselect('div .tokens[title="one two"]', document)[0]).to.be(DomUtils.getElementById('token-two', document)); //found div .tokens[title="one two"]
expect(CSSselect('div .tokens[title="one two three #%"]', document)[0]).to.be(DomUtils.getElementById('token-three', document)); //found div .tokens[title="one two three #%"]
expect(CSSselect("div .tokens[title='one two three #%'] a", document)[0]).to.be(DomUtils.getElementById('token-four', document)); //found div .tokens[title=\'one two three #%\'] a
expect(CSSselect('div .tokens[title="one two three #%"] a[href$=foo] div', document)[0]).to.be(DomUtils.getElementById('token-five', document)); //found div .tokens[title="one two three #%"] a[href=foo] div
}
},
'interesting syntaxes': {
'should parse bad selectors': function () {
expect(CSSselect('#spaced-tokens p em a', document).length).to.be.ok(); //found element with funny tokens
}
},
'order matters': {
// <div id="order-matters">
// <p class="order-matters"></p>
// <a class="order-matters">
// <em class="order-matters"></em><b class="order-matters"></b>
// </a>
// </div>
'the order of elements return matters': function () {
function tag(el) {
return el.name.toLowerCase();
}
var els = CSSselect('#order-matters .order-matters', document);
expect(tag(els[0])).to.be('p'); //first element matched is a {p} tag
expect(tag(els[1])).to.be('a'); //first element matched is a {a} tag
expect(tag(els[2])).to.be('em'); //first element matched is a {em} tag
expect(tag(els[3])).to.be('b'); //first element matched is a {b} tag
}
},
'pseudo-selectors': {
':contains': function() {
expect(CSSselect('li:contains(humans)', document)).to.have.length(1); //found by "element:contains(text)"
expect(CSSselect(':contains(humans)', document)).to.have.length(5); //found by ":contains(text)", including all ancestors
// * is an important case, can cause weird errors
expect(CSSselect('*:contains(humans)', document)).to.have.length(5); //found by "*:contains(text)", including all ancestors
expect(CSSselect('ol:contains(humans)', document)).to.have.length(1); //found by "ancestor:contains(text)"
},
':not': function() {
expect(CSSselect('.odd:not(div)', document)).to.have.length(1); //found one .odd :not an &lt;a&gt;
},
':first-child': function () {
expect(CSSselect('#pseudos div:first-child', document)[0]).to.be(pseudos[0]); //found first child
expect(CSSselect('#pseudos div:first-child', document)).to.have.length(1); //found only 1
},
':last-child': function () {
var all = DomUtils.getElementsByTagName('div', pseudos);
expect(CSSselect('#pseudos div:last-child', document)[0]).to.be(all[all.length - 1]); //found last child
expect(CSSselect('#pseudos div:last-child', document)).to.have.length(1); //found only 1
},
'ol > li[attr="boosh"]:last-child': function () {
var expected = DomUtils.getElementById('attr-child-boosh', document);
expect(CSSselect('ol > li[attr="boosh"]:last-child', document)).to.have.length(1); //only 1 element found
expect(CSSselect('ol > li[attr="boosh"]:last-child', document)[0]).to.be(expected); //found correct element
},
':nth-child(odd|even|x)': function () {
var second = DomUtils.getElementsByTagName('div', pseudos)[1];
expect(CSSselect('#pseudos :nth-child(odd)', document)).to.have.length(4); //found 4 odd elements
expect(CSSselect('#pseudos div:nth-child(odd)', document)).to.have.length(3); //found 3 odd elements with div tag
expect(CSSselect('#pseudos div:nth-child(even)', document)).to.have.length(3); //found 3 even elements with div tag
expect(CSSselect('#pseudos div:nth-child(2)', document)[0]).to.be(second); //found 2nd nth-child of pseudos
},
':nth-child(expr)': function () {
var fifth = DomUtils.getElementsByTagName('a', pseudos)[0];
var sixth = DomUtils.getElementsByTagName('div', pseudos)[4];
expect(CSSselect('#pseudos :nth-child(3n+1)', document)).to.have.length(3); //found 3 elements
expect(CSSselect('#pseudos :nth-child(+3n-2)', document)).to.have.length(3); //found 3 elements'
expect(CSSselect('#pseudos :nth-child(-n+6)', document)).to.have.length(6); //found 6 elements
expect(CSSselect('#pseudos :nth-child(-n+5)', document)).to.have.length(5); //found 5 elements
expect(CSSselect('#pseudos :nth-child(3n+2)', document)[1]).to.be(fifth); //second :nth-child(3n+2) is the fifth child
expect(CSSselect('#pseudos :nth-child(3n)', document)[1]).to.be(sixth); //second :nth-child(3n) is the sixth child
},
':nth-last-child(odd|even|x)': function () {
var second = DomUtils.getElementsByTagName('div', pseudos)[1];
expect(CSSselect('#pseudos :nth-last-child(odd)', document)).to.have.length(4); //found 4 odd elements
expect(CSSselect('#pseudos div:nth-last-child(odd)', document)).to.have.length(3); //found 3 odd elements with div tag
expect(CSSselect('#pseudos div:nth-last-child(even)', document)).to.have.length(3); //found 3 even elements with div tag
expect(CSSselect('#pseudos div:nth-last-child(6)', document)[0]).to.be(second); //6th nth-last-child should be 2nd of 7 elements
},
':nth-last-child(expr)': function () {
var third = DomUtils.getElementsByTagName('div', pseudos)[2];
expect(CSSselect('#pseudos :nth-last-child(3n+1)', document)).to.have.length(3); //found 3 elements
expect(CSSselect('#pseudos :nth-last-child(3n-2)', document)).to.have.length(3); //found 3 elements
expect(CSSselect('#pseudos :nth-last-child(-n+6)', document)).to.have.length(6); //found 6 elements
expect(CSSselect('#pseudos :nth-last-child(-n+5)', document)).to.have.length(5); //found 5 elements
expect(CSSselect('#pseudos :nth-last-child(3n+2)', document)[0]).to.be(third); //first :nth-last-child(3n+2) is the third child
},
':nth-of-type(expr)': function () {
var a = DomUtils.getElementsByTagName('a', pseudos)[0];
expect(CSSselect('#pseudos div:nth-of-type(3n+1)', document)).to.have.length(2); //found 2 div elements
expect(CSSselect('#pseudos a:nth-of-type(3n+1)', document)).to.have.length(1); //found 1 a element
expect(CSSselect('#pseudos a:nth-of-type(3n+1)', document)[0]).to.be(a); //found the right a element
expect(CSSselect('#pseudos a:nth-of-type(3n)', document)).to.be.empty(); //no matches for every third a
expect(CSSselect('#pseudos a:nth-of-type(odd)', document)).to.have.length(1); //found the odd a
expect(CSSselect('#pseudos a:nth-of-type(1)', document)).to.have.length(1); //found the first a
},
':nth-last-of-type(expr)': function () {
var second = DomUtils.getElementsByTagName('div', pseudos)[1];
expect(CSSselect('#pseudos div:nth-last-of-type(3n+1)', document)).to.have.length(2); //found 2 div elements
expect(CSSselect('#pseudos a:nth-last-of-type(3n+1)', document)).to.have.length(1); //found 1 a element
expect(CSSselect('#pseudos div:nth-last-of-type(5)', document)[0]).to.be(second); //5th nth-last-of-type should be 2nd of 7 elements
},
':first-of-type': function () {
expect(CSSselect('#pseudos a:first-of-type', document)[0]).to.be(DomUtils.getElementsByTagName('a', pseudos)[0]); //found first a element
expect(CSSselect('#pseudos a:first-of-type', document)).to.have.length(1); //found only 1
},
':last-of-type': function () {
var all = DomUtils.getElementsByTagName('div', pseudos);
expect(CSSselect('#pseudos div:last-of-type', document)[0]).to.be(all[all.length - 1]); //found last div element
expect(CSSselect('#pseudos div:last-of-type', document)).to.have.length(1); //found only 1
},
':only-of-type': function () {
expect(CSSselect('#pseudos a:only-of-type', document)[0]).to.be(DomUtils.getElementsByTagName('a', pseudos)[0]); //found the only a element
expect(CSSselect('#pseudos a:first-of-type', document)).to.have.length(1); //found only 1
},
':target': function () {
location.hash = '';
expect(CSSselect('#pseudos:target', document)).to.be.empty(); //#pseudos is not the target
location.hash = '#pseudos';
expect(CSSselect('#pseudos:target', document)).to.have.length(1); //now #pseudos is the target
location.hash = '';
},
'custom pseudos': function() {
// :humanoid implemented just for testing purposes
expect(CSSselect(':humanoid', document)).to.have.length(2); //selected using custom pseudo
}
},
/*
'argument types': {
'should be able to pass in nodes as arguments': function () {
var el = DomUtils.getElementById('boosh', document);
expect(CSSselect(el)[0]).to.be(el); //CSSselect(el)[0] == el
expect(CSSselect(el, 'body')[0]).to.be(el); //CSSselect(el, 'body')[0] == el
expect(CSSselect(el, document)[0]).to.be(el); //CSSselect(el, document)[0] == el
expect(CSSselect(window)[0]).to.be(window); //CSSselect(window)[0] == window
expect(CSSselect(document)[0]).to.be(document); //CSSselect(document)[0] == document
},
'should be able to pass in an array of results as arguments': function () {
var el = DomUtils.getElementById('boosh', document);
var result = CSSselect([CSSselect('#boosh', document), CSSselect(document), CSSselect(window)]);
expect(result).to.have.length(3); //3 elements in the combined set
expect(result[0]).to.be(el); //result[0] == el
expect(result[1]).to.be(document); //result[0] == document
expect(result[2]).to.be(window); //result[0] == window
expect(CSSselect([CSSselect('#pseudos div.odd', document), CSSselect('#pseudos div.even', document)])).to.have.length(6); //found all the odd and even divs
}
},
*/
'is()': {
'simple selectors': function () {
expect(CSSselect.is(el, 'li')).to.be.ok(); //tag
expect(CSSselect.is(el, '*')).to.be.ok(); //wildcard
expect(CSSselect.is(el, '#attr-child-boosh')).to.be.ok(); //#id
expect(CSSselect.is(el, '[attr]')).to.be.ok(); //[attr]
expect(CSSselect.is(el, '[attr=boosh]')).to.be.ok(); //[attr=val]
expect(CSSselect.is(el, 'div')).to.not.be.ok(); //wrong tag
expect(CSSselect.is(el, '#foo')).to.not.be.ok(); //wrong #id
expect(CSSselect.is(el, '[foo]')).to.not.be.ok(); //wrong [attr]
expect(CSSselect.is(el, '[attr=foo]')).to.not.be.ok(); //wrong [attr=val]
},
'selector sequences': function () {
expect(CSSselect.is(el, 'li#attr-child-boosh[attr=boosh]')).to.be.ok(); //tag#id[attr=val]
expect(CSSselect.is(el, 'div#attr-child-boosh[attr=boosh]')).to.not.be.ok(); //wrong tag#id[attr=val]
},
'selector sequences combinators': function () {
expect(CSSselect.is(el, 'ol li')).to.be.ok(); //tag tag
expect(CSSselect.is(el, 'ol>li')).to.be.ok(); //tag>tag
expect(CSSselect.is(el, 'ol>li+li')).to.be.ok(); //tab>tag+tag
expect(CSSselect.is(el, 'ol#list li#attr-child-boosh[attr=boosh]')).to.be.ok(); //tag#id tag#id[attr=val]
expect(CSSselect.is(el, 'ol#list>li#attr-child-boosh[attr=boosh]')).to.not.be.ok(); //wrong tag#id>tag#id[attr=val]
expect(CSSselect.is(el, 'ol ol li#attr-child-boosh[attr=boosh]')).to.be.ok(); //tag tag tag#id[attr=val]
expect(CSSselect.is(CSSselect('#token-four', document)[0], 'div#fixtures>div a')).to.be.ok(); //tag#id>tag tag where ambiguous middle tag requires backtracking
},
'pseudos': function() {
//TODO: more tests!
expect(CSSselect.is(el, 'li:contains(hello)')).to.be.ok(); //matching :contains(text)
expect(CSSselect.is(el, 'li:contains(human)')).to.not.be.ok(); //non-matching :contains(text)
expect(CSSselect.is(CSSselect('#list>li', document)[2], ':humanoid')).to.be.ok(); //matching custom pseudo
expect(CSSselect.is(CSSselect('#list>li', document)[1], ':humanoid')).to.not.be.ok(); //non-matching custom pseudo
}/*,
'context': function () {
expect(CSSselect.is(el, 'li#attr-child-boosh[attr=boosh]', CSSselect('#list', document)[0])).to.be.ok(); //context
expect(CSSselect.is(el, 'ol#list li#attr-child-boosh[attr=boosh]', CSSselect('#boosh', document)[0])).to.not.be.ok(); //wrong context
}*/
},
'selecting elements in other documents': {
'get element by id': function () {
var result = CSSselect('#hsoob', doc);
expect(result[0]).to.be.ok(); //found element with id=hsoob
},
'get elements by class': function () {
expect(CSSselect('#hsoob .a', doc)).to.have.length(2); //found two elements
expect(CSSselect('#hsoob div.a', doc)[0]).to.be.ok(); //found one element
expect(CSSselect('#hsoob div', doc)).to.have.length(2); //found two {div} elements
expect(CSSselect('#hsoob span', doc)[0]).to.be.ok(); //found one {span} element
expect(CSSselect('#hsoob div div', doc)[0]).to.be.ok(); //found a single div
expect(CSSselect('p.odd', doc)).to.have.length(1); //found single br
},
'complex selectors': function () {
expect(CSSselect('.d ~ .sib', doc)).to.have.length(2); //found one ~ sibling
expect(CSSselect('.a .d + .sib', doc)).to.have.length(1); //found 2 + siblings
expect(CSSselect('#hsoob > div > .h', doc)).to.have.length(1); //found span using child selectors
expect(CSSselect('.a .d ~ .sib[test="f g"]', doc)).to.have.length(1); //found 1 ~ sibling with test attribute
},
'byId sub-queries': function () {
expect(CSSselect('#hsoob #spanny', doc)).to.have.length(1); //found "#id #id" in frame
expect(CSSselect('.a #spanny', doc)).to.have.length(1); //found ".class #id" in frame
expect(CSSselect('.a #booshTest #spanny', doc)).to.have.length(1); //found ".class #id #id" in frame
//expect(CSSselect('> #hsoob', doc)).to.have.length(1) //found "> #id" in frame
},
'byId sub-queries within sub-context': function () {
expect(CSSselect('#spanny', CSSselect('#hsoob', doc))).to.have.length(1); //found "#id -> #id" in frame
expect(CSSselect('.a #spanny', CSSselect('#hsoob', doc))).to.have.length(1); //found ".class #id" in frame
expect(CSSselect('.a #booshTest #spanny', CSSselect('#hsoob', doc))).to.have.length(1); //found ".class #id #id" in frame
expect(CSSselect('.a > #booshTest', CSSselect('#hsoob', doc))).to.have.length(1); //found "> .class #id" in frame
expect(CSSselect('#booshTest', CSSselect('#spanny', doc)).length).to.not.be.ok(); //shouldn't find #booshTest (ancestor) within #spanny (descendent)
expect(CSSselect('#booshTest', CSSselect('#lonelyHsoob', doc)).length).to.not.be.ok(); //shouldn't find #booshTest within #lonelyHsoob (unrelated)
}
}
};

1
node_modules/CSSselect/test/sizzle/data/fries.xml generated vendored Normal file
View File

@@ -0,0 +1 @@
<?xml version=1.0 encoding=UTF-8?> <soap:Envelope xmlns:soap=http://schemas.xmlsoap.org/soap/envelope/ xmlns:xsd=http://www.w3.org/2001/XMLSchema xmlns:xsi=http://www.w3.org/2001/XMLSchema-instance> <soap:Body> <jsconf xmlns=http://www.example.com/ns1> <response xmlns:ab=http://www.example.com/ns2> <meta> <component id=seite1 class=component> <properties xmlns:cd=http://www.example.com/ns3> <property name=prop1> <thing /> <value>1</value> </property> <property name=prop2> <thing att=something /> </property> <foo_bar>foo</foo_bar> </properties> </component> </meta> </response> </jsconf> </soap:Body> </soap:Envelope>

247
node_modules/CSSselect/test/sizzle/data/index.html generated vendored Normal file
View File

@@ -0,0 +1,247 @@
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en" dir="ltr" id="html">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Sizzle Test Suite</title>
<link rel="Stylesheet" media="screen" href="../bower_components/qunit/qunit/qunit.css" />
<script type="text/javascript" src="../bower_components/qunit/qunit/qunit.js"></script>
<script type="text/javascript" src="data/testinit.js"></script>
<script type="text/javascript" src="jquery.js"></script>
<script type="text/javascript" src="../dist/sizzle.js"></script>
<script type="text/javascript" src="unit/selector.js"></script>
<script type="text/javascript" src="unit/utilities.js"></script>
<script type="text/javascript" src="unit/extending.js"></script>
</head>
<body id="body">
<div id="qunit">
<h1 id="qunit-header">jQuery Test Suite</h1>
<h2 id="qunit-banner"></h2>
<div id="qunit-testrunner-toolbar"></div>
<h2 id="qunit-userAgent"></h2>
</div>
<!-- Test HTML -->
<dl id="dl" style="position:absolute;top:-32767px;left:-32767px;width:1px">
<div id="qunit-fixture">
<p id="firstp">See <a id="simon1" href="http://simon.incutio.com/archive/2003/03/25/#getElementsBySelector" rel="bookmark">this blog entry</a> for more information.</p>
<p id="ap">
Here are some [links] in a normal paragraph: <a id="google" href="http://www.google.com/" title="Google!">Google</a>,
<a id="groups" href="http://groups.google.com/" class="GROUPS">Google Groups (Link)</a>.
This link has <code id="code1"><a href="http://smin" id="anchor1">class="blog"</a></code>:
<a href="http://diveintomark.org/" class="blog" hreflang="en" id="mark">diveintomark</a>
</p>
<div id="foo">
<p id="sndp">Everything inside the red border is inside a div with <code>id="foo"</code>.</p>
<p lang="en" id="en">This is a normal link: <a id="yahoo" href="http://www.yahoo.com/" class="blogTest">Yahoo</a></p>
<p id="sap">This link has <code><a href="#2" id="anchor2">class="blog"</a></code>: <a href="http://simon.incutio.com/" class="blog link" id="simon">Simon Willison's Weblog</a></p>
</div>
<div id="nothiddendiv" style="height:1px;background:white;" class="nothiddendiv">
<div id="nothiddendivchild"></div>
</div>
<span id="name+value"></span>
<p id="first">Try them out:</p>
<ul id="firstUL"></ul>
<ol id="empty"><!-- comment --></ol>
<form id="form" action="formaction">
<label for="action" id="label-for">Action:</label>
<input type="text" name="action" value="Test" id="text1" maxlength="30"/>
<input type="text" name="text2" value="Test" id="text2" disabled="disabled"/>
<input type="radio" name="radio1" id="radio1" value="on"/>
<input type="radio" name="radio2" id="radio2" checked="checked"/>
<input type="checkbox" name="check" id="check1" checked="checked"/>
<input type="checkbox" id="check2" value="on"/>
<input type="hidden" name="hidden" id="hidden1"/>
<input type="text" style="display:none;" name="foo[bar]" id="hidden2"/>
<input type="text" id="name" name="name" value="name" />
<input type="search" id="search" name="search" value="search" />
<button id="button" name="button" type="button">Button</button>
<textarea id="area1" maxlength="30">foobar</textarea>
<select name="select1" id="select1">
<option id="option1a" class="emptyopt" value="">Nothing</option>
<option id="option1b" value="1">1</option>
<option id="option1c" value="2">2</option>
<option id="option1d" value="3">3</option>
</select>
<select name="select2" id="select2">
<option id="option2a" class="emptyopt" value="">Nothing</option>
<option id="option2b" value="1">1</option>
<option id="option2c" value="2">2</option>
<option id="option2d" selected="selected" value="3">3</option>
</select>
<select name="select3" id="select3" multiple="multiple">
<option id="option3a" class="emptyopt" value="">Nothing</option>
<option id="option3b" selected="selected" value="1">1</option>
<option id="option3c" selected="selected" value="2">2</option>
<option id="option3d" value="3">3</option>
<option id="option3e">no value</option>
</select>
<select name="select4" id="select4" multiple="multiple">
<optgroup disabled="disabled">
<option id="option4a" class="emptyopt" value="">Nothing</option>
<option id="option4b" disabled="disabled" selected="selected" value="1">1</option>
<option id="option4c" selected="selected" value="2">2</option>
</optgroup>
<option selected="selected" disabled="disabled" id="option4d" value="3">3</option>
<option id="option4e">no value</option>
</select>
<select name="select5" id="select5">
<option id="option5a" value="3">1</option>
<option id="option5b" value="2">2</option>
<option id="option5c" value="1">3</option>
</select>
<object id="object1" codebase="stupid">
<param name="p1" value="x1" />
<param name="p2" value="x2" />
</object>
<span id="台北Táiběi"></span>
<span id="台北" lang="中文"></span>
<span id="utf8class1" class="台北Táiběi 台北"></span>
<span id="utf8class2" class="台北"></span>
<span id="foo:bar" class="foo:bar"><span id="foo_descendent"></span></span>
<span id="test.foo[5]bar" class="test.foo[5]bar"></span>
<foo_bar id="foobar">test element</foo_bar>
</form>
<b id="floatTest">Float test.</b>
<iframe id="iframe" name="iframe"></iframe>
<form id="lengthtest">
<input type="text" id="length" name="test"/>
<input type="text" id="idTest" name="id"/>
</form>
<table id="table"></table>
<form id="name-tests">
<!-- Inputs with a grouped name attribute. -->
<input name="types[]" id="types_all" type="checkbox" value="all" />
<input name="types[]" id="types_anime" type="checkbox" value="anime" />
<input name="types[]" id="types_movie" type="checkbox" value="movie" />
</form>
<form id="testForm" action="#" method="get">
<textarea name="T3" rows="2" cols="15">?
Z</textarea>
<input type="hidden" name="H1" value="x" />
<input type="hidden" name="H2" />
<input name="PWD" type="password" value="" />
<input name="T1" type="text" />
<input name="T2" type="text" value="YES" readonly="readonly" />
<input type="checkbox" name="C1" value="1" />
<input type="checkbox" name="C2" />
<input type="radio" name="R1" value="1" />
<input type="radio" name="R1" value="2" />
<input type="text" name="My Name" value="me" />
<input type="reset" name="reset" value="NO" />
<select name="S1">
<option value="abc">ABC</option>
<option value="abc">ABC</option>
<option value="abc">ABC</option>
</select>
<select name="S2" multiple="multiple" size="3">
<option value="abc">ABC</option>
<option value="abc">ABC</option>
<option value="abc">ABC</option>
</select>
<select name="S3">
<option selected="selected">YES</option>
</select>
<select name="S4">
<option value="" selected="selected">NO</option>
</select>
<input type="submit" name="sub1" value="NO" />
<input type="submit" name="sub2" value="NO" />
<input type="image" name="sub3" value="NO" />
<button name="sub4" type="submit" value="NO">NO</button>
<input name="D1" type="text" value="NO" disabled="disabled" />
<input type="checkbox" checked="checked" disabled="disabled" name="D2" value="NO" />
<input type="radio" name="D3" value="NO" checked="checked" disabled="disabled" />
<select name="D4" disabled="disabled">
<option selected="selected" value="NO">NO</option>
</select>
<input id="list-test" type="text" />
<datalist id="datalist">
<option value="option"></option>
</datalist>
</form>
<div id="moretests">
<form>
<div id="checkedtest" style="display:none;">
<input type="radio" name="checkedtestradios" checked="checked"/>
<input type="radio" name="checkedtestradios" value="on"/>
<input type="checkbox" name="checkedtestcheckboxes" checked="checked"/>
<input type="checkbox" name="checkedtestcheckboxes" />
</div>
</form>
<div id="nonnodes"><span>hi</span> there <!-- mon ami --></div>
<div id="t2037">
<div><div class="hidden">hidden</div></div>
</div>
<div id="t6652">
<div></div>
</div>
<div id="t12087">
<input type="hidden" id="el12087" data-comma="0,1"/>
</div>
<div id="no-clone-exception"><object><embed></embed></object></div>
<div id="names-group">
<span id="name-is-example" name="example"></span>
<span id="name-is-div" name="div"></span>
</div>
<script id="script-no-src"></script>
<script id="script-src" src="http://src.test/path"></script>
<div id="id-name-tests">
<a id="tName1ID" name="tName1"><span></span></a>
<a id="tName2ID" name="tName2"><span></span></a>
<div id="tName1"><span id="tName1-span">C</span></div>
</div>
</div>
<div id="tabindex-tests">
<ol id="listWithTabIndex" tabindex="5">
<li id="foodWithNegativeTabIndex" tabindex="-1">Rice</li>
<li id="foodNoTabIndex">Beans</li>
<li>Blinis</li>
<li>Tofu</li>
</ol>
<div id="divWithNoTabIndex">I'm hungry. I should...</div>
<span>...</span><a href="#" id="linkWithNoTabIndex">Eat lots of food</a><span>...</span> |
<span>...</span><a href="#" id="linkWithTabIndex" tabindex="2">Eat a little food</a><span>...</span> |
<span>...</span><a href="#" id="linkWithNegativeTabIndex" tabindex="-1">Eat no food</a><span>...</span>
<span>...</span><a id="linkWithNoHrefWithNoTabIndex">Eat a burger</a><span>...</span>
<span>...</span><a id="linkWithNoHrefWithTabIndex" tabindex="1">Eat some funyuns</a><span>...</span>
<span>...</span><a id="linkWithNoHrefWithNegativeTabIndex" tabindex="-1">Eat some funyuns</a><span>...</span>
</div>
<div id="liveHandlerOrder">
<span id="liveSpan1"><a href="#" id="liveLink1"></a></span>
<span id="liveSpan2"><a href="#" id="liveLink2"></a></span>
</div>
<div id="siblingTest">
<em id="siblingfirst">1</em>
<em id="siblingnext">2</em>
<em id="siblingthird">
<em id="siblingchild">
<em id="siblinggrandchild">
<em id="siblinggreatgrandchild"></em>
</em>
</em>
</em>
<span id="siblingspan"></span>
</div>
</div>
</dl>
<br id="last"/>
</body>
</html>

87
node_modules/CSSselect/test/sizzle/data/testinit.js generated vendored Normal file
View File

@@ -0,0 +1,87 @@
var assert = require("assert"),
util = require("util"),
helper = require("../../tools/helper.js"),
CSSselect = helper.CSSselect,
path = require("path"),
docPath = path.join(__dirname, "index.html"),
document = null;
//in this module, the only use-case is to compare arrays of
function deepEqual(a, b, msg){
try {
assert.deepEqual(a, b, msg);
} catch(e) {
function getId(n){return n && n.attribs.id; }
e.actual = JSON.stringify(a.map(getId), 0, 2);
e.expected = JSON.stringify(b.map(getId), 0, 2);
throw e;
}
}
function loadDoc(){
return document = helper.getDocument(docPath);
}
module.exports = {
q: q,
t: t,
loadDoc: loadDoc,
createWithFriesXML: createWithFriesXML
};
/**
* Returns an array of elements with the given IDs
* @example q("main", "foo", "bar")
* @result [<div id="main">, <span id="foo">, <input id="bar">]
*/
function q() {
var r = [],
i = 0;
for ( ; i < arguments.length; i++ ) {
r.push( document.getElementById( arguments[i] ) );
}
return r;
}
/**
* Asserts that a select matches the given IDs
* @param {String} a - Assertion name
* @param {String} b - Sizzle selector
* @param {String} c - Array of ids to construct what is expected
* @example t("Check for something", "//[a]", ["foo", "baar"]);
* @result returns true if "//[a]" return two elements with the IDs 'foo' and 'baar'
*/
function t( a, b, c ) {
var f = CSSselect(b, document),
s = "",
i = 0;
for ( ; i < f.length; i++ ) {
s += ( s && "," ) + '"' + f[ i ].id + '"';
}
deepEqual(f, q.apply( q, c ), a + " (" + b + ")");
}
/**
* Add random number to url to stop caching
*
* @example url("data/test.html")
* @result "data/test.html?10538358428943"
*
* @example url("data/test.php?foo=bar")
* @result "data/test.php?foo=bar&10538358345554"
*/
function url( value ) {
return value + (/\?/.test(value) ? "&" : "?") + new Date().getTime() + "" + parseInt(Math.random()*100000);
}
var xmlDoc = helper.getDOMFromPath(path.join(__dirname, "fries.xml"), { xmlMode: true });
var filtered = xmlDoc.filter(function(t){return t.type === "tag"});
xmlDoc.lastChild = filtered[filtered.length - 1];
function createWithFriesXML() {
return xmlDoc;
}

1211
node_modules/CSSselect/test/sizzle/selector.js generated vendored Normal file

File diff suppressed because it is too large Load Diff

22
node_modules/CSSselect/test/test.js generated vendored Normal file
View File

@@ -0,0 +1,22 @@
describe("nwmatcher", function(){
require("./nwmatcher/");
});
describe("sizzle", function(){
describe("selector", function(){
require("./sizzle/selector");
});
});
describe("qwery", function(){
exportsRun(require("./qwery/"));
});
function exportsRun(mod){
Object.keys(mod).forEach(function(name){
if(typeof mod[name] === "object") describe(name, function(){
exportsRun(mod[name]);
});
else it(name, mod[name]);
});
}

10
node_modules/CSSselect/test/tools/bench.js generated vendored Normal file
View File

@@ -0,0 +1,10 @@
var ben = require("ben"),
testString = "doo, *#foo > elem.bar[class$=bAz i]:not([ id *= \"2\" ]):nth-child(2n)",
helper = require("./helper.js"),
CSSselect = helper.CSSselect,
compile = CSSselect.compile,
dom = helper.getDefaultDom();
//console.log("Parsing took:", ben(1e5, function(){compile(testString);}));
var compiled = compile(testString);
console.log("Executing took:", ben(1e6, function(){CSSselect(compiled, dom);})*1e3);

2034
node_modules/CSSselect/test/tools/docs/W3C_Selectors.html generated vendored Normal file

File diff suppressed because it is too large Load Diff

51
node_modules/CSSselect/test/tools/helper.js generated vendored Normal file
View File

@@ -0,0 +1,51 @@
var fs = require("fs"),
path = require("path"),
htmlparser2 = require("htmlparser2"),
DomUtils = htmlparser2.DomUtils,
CSSselect = require("../../");
function getDOMFromPath(path, options){
return htmlparser2.parseDOM(fs.readFileSync(path).toString(), options);
}
module.exports = {
CSSselect: CSSselect,
getFile: function(name, options){
return getDOMFromPath(path.join(__dirname, "docs", name), options);
},
getDOMFromPath: getDOMFromPath,
getDOM: htmlparser2.parseDOM,
getDefaultDom: function(){
return htmlparser2.parseDOM(
"<elem id=foo><elem class='bar baz'><tag class='boom'> This is some simple text </tag></elem></elem>"
);
},
getDocument: function(path){
var document = getDOMFromPath(path);
document.getElementsByTagName = function(name){
return DomUtils.getElementsByTagName("*", document);
};
document.getElementById = function(id){
return DomUtils.getElementById(id, document);
};
document.createTextNode = function(content){
return {
type: "text",
data: "content"
};
};
document.createElement = function(name){
return {
type: "tag",
name: name,
children: [],
attribs: {}
};
};
document.body = DomUtils.getElementsByTagName("body", document, true, 1)[0];
document.documentElement = document.filter(DomUtils.isTag)[0];
return document;
}
};

76
node_modules/CSSselect/test/tools/slickspeed.js generated vendored Normal file
View File

@@ -0,0 +1,76 @@
var helper = require("./helper.js"),
doc = helper.getFile("W3C_Selectors.html"),
CSSselect = helper.CSSselect,
soupselect = require("cheerio-soupselect"),
selectors = ["body", "div", "body div", "div p", "div > p", "div + p", "div ~ p", "div[class^=exa][class$=mple]", "div p a", "div, p, a", ".note", "div.example", "ul .tocline2", "div.example, div.note", "#title", "h1#title", "div #title", "ul.toc li.tocline2", "ul.toc > li.tocline2", "h1#title + div > p", "h1[id]:contains(Selectors)", "a[href][lang][class]", "div[class]", "div[class=example]", "div[class^=exa]", "div[class$=mple]", "div[class*=e]", "div[class|=dialog]", "div[class!=made_up]", "div[class~=example]"/*, "div:not(.example)", "p:contains(selectors)", "p:nth-child(even)", "p:nth-child(2n)", "p:nth-child(odd)", "p:nth-child(2n+1)", "p:nth-child(n)", "p:only-child", "p:last-child", "p:first-child"*/];
var engines = [function(a,b){return CSSselect(b,a);}, soupselect.select];
//returns true when an error occurs
function testResult(rule, index){
var results = engines
.map(function(func){ return func(doc, rule); });
//check if both had the same result
for(var i = 1; i < results.length; i++){
//TODO: might be hard to debug with more engines
if(results[i-1].length !== results[i].length){
//console.log(rule, results[i-1].length, results[i].length);
return true;
}
for(var j = 0; j < results[i].length; j++){
if(results[i-1][j] !== results[i][j]){
if(results[i-1].indexOf(results[i][j]) === -1){
return true;
}
}
}
//require("assert").deepEqual(results[i-1], results[i], rule + ": not the same elements");
}
return false;
}
selectors.filter(testResult).forEach(function(rule){ print(rule, "failed!\n"); });
process.exit(0); //don't run speed tests
print("-----\n\nChecking performance\n\n");
//test the speed
var ben = require("ben");
function testSpeed(rule){
print(rule, Array(28-rule.length).join(" "));
var results = engines
.map(function(func){ return function(){ return func(doc, rule); }});
//also add a precompiled CSSselect test
var compiled = CSSselect(rule);
results.unshift(function(){ return CSSselect.iterate(compiled, doc); });
results = results.map(ben);
var min = Math.min.apply(null, results);
var max = Math.max.apply(null, results);
results.forEach(function(result){
if(result === min) return print(" +", result, "+");
if(result === max) return print(" !", result, "!");
if(Math.abs(result-min) > Math.abs(result-max)){
return print(" =", result, "=");
}
print(" ~", result, "~");
});
print("\n");
}
print("RULE ", "CSSselect (pc)", "CSSselect", "soupselect\n");
selectors.forEach(testSpeed);
function print(){
process.stdout.write(Array.prototype.join.call(arguments, " "));
}