envjs 0.1.7 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (187) hide show
  1. data/.jslintrbrc +29 -0
  2. data/.project +17 -0
  3. data/CHANGELOG.rdoc +3 -0
  4. data/DTD/xhtml-lat1.ent +196 -0
  5. data/DTD/xhtml-special.ent +80 -0
  6. data/DTD/xhtml-symbol.ent +237 -0
  7. data/DTD/xhtml.soc +14 -0
  8. data/DTD/xhtml1-frameset.dtd +1235 -0
  9. data/DTD/xhtml1-strict.dtd +978 -0
  10. data/DTD/xhtml1-transitional.dtd +1201 -0
  11. data/DTD/xhtml1.dcl +192 -0
  12. data/Makefile +7 -0
  13. data/Manifest.txt +287 -0
  14. data/{README → README.rdoc} +24 -3
  15. data/Rakefile +196 -0
  16. data/Wakefile +24 -0
  17. data/build.properties +9 -0
  18. data/build.xml +247 -0
  19. data/gm/jquery.js +6002 -0
  20. data/gm/mainx.js +2648 -0
  21. data/gm/sensx.js +135 -0
  22. data/gm/t.js +6 -0
  23. data/gm/x.html +76 -0
  24. data/htmlparser/BrowserTreeBuilder.java +456 -0
  25. data/htmlparser/README +34 -0
  26. data/htmlparser/build.sh +38 -0
  27. data/jsl/jsl +0 -0
  28. data/jsl/jsl.default.conf +129 -0
  29. data/jsl/jsl.exe +0 -0
  30. data/lib/envjs.rb +2 -0
  31. data/lib/envjs/env.js +22 -3
  32. data/lib/envjs/event_loop.js +2 -0
  33. data/lib/envjs/static.js +155 -21
  34. data/licenses/GPL-LICENSE.txt +278 -0
  35. data/licenses/MIT-LICENSE.txt +20 -0
  36. data/src/base64.js +80 -0
  37. data/src/build.js +6 -0
  38. data/src/cruft/bad.html +24 -0
  39. data/src/cruft/dom.js +606 -0
  40. data/src/cruft/element.js +297 -0
  41. data/src/cruft/good.html +30 -0
  42. data/src/cruft/good.js +32 -0
  43. data/src/cruft/internal.js +81 -0
  44. data/src/cruft/parser.js +458 -0
  45. data/src/css/properties.js +293 -0
  46. data/src/css/rule.js +22 -0
  47. data/src/css/sizzle.js +717 -0
  48. data/src/css/stylesheet.js +52 -0
  49. data/src/dom/attr.js +55 -0
  50. data/src/dom/cdatasection.js +31 -0
  51. data/src/dom/characterdata.js +119 -0
  52. data/src/dom/comment.js +30 -0
  53. data/src/dom/doctype.js +9 -0
  54. data/src/dom/document.js +553 -0
  55. data/src/dom/dom.js +134 -0
  56. data/src/dom/element.js +217 -0
  57. data/src/dom/entities.js +273 -0
  58. data/src/dom/exception.js +28 -0
  59. data/src/dom/fragment.js +37 -0
  60. data/src/dom/implementation.js +602 -0
  61. data/src/dom/instruction.js +51 -0
  62. data/src/dom/namednodemap.js +374 -0
  63. data/src/dom/namespace.js +50 -0
  64. data/src/dom/node.js +618 -0
  65. data/src/dom/nodelist.js +195 -0
  66. data/src/dom/parser.js +1207 -0
  67. data/src/dom/text.js +73 -0
  68. data/src/event/event.js +39 -0
  69. data/src/event/mouseevent.js +4 -0
  70. data/src/event/uievent.js +8 -0
  71. data/src/html/a.js +110 -0
  72. data/src/html/anchor.js +80 -0
  73. data/src/html/area.js +57 -0
  74. data/src/html/base.js +26 -0
  75. data/src/html/blockquote-q.js +19 -0
  76. data/src/html/body.js +19 -0
  77. data/src/html/button.js +21 -0
  78. data/src/html/canvas.js +14 -0
  79. data/src/html/col-colgroup.js +49 -0
  80. data/src/html/collection.js +72 -0
  81. data/src/html/cookie.js +151 -0
  82. data/src/html/del-ins.js +25 -0
  83. data/src/html/div.js +28 -0
  84. data/src/html/document.js +359 -0
  85. data/src/html/element.js +380 -0
  86. data/src/html/fieldset.js +19 -0
  87. data/src/html/form.js +484 -0
  88. data/src/html/frame.js +89 -0
  89. data/src/html/frameset.js +25 -0
  90. data/src/html/head.js +44 -0
  91. data/src/html/html.js +0 -0
  92. data/src/html/htmlparser.js +340 -0
  93. data/src/html/iframe.js +26 -0
  94. data/src/html/image.js +0 -0
  95. data/src/html/img.js +62 -0
  96. data/src/html/input-elements.js +307 -0
  97. data/src/html/input.js +65 -0
  98. data/src/html/label.js +26 -0
  99. data/src/html/legend.js +19 -0
  100. data/src/html/link.js +82 -0
  101. data/src/html/map.js +22 -0
  102. data/src/html/meta.js +37 -0
  103. data/src/html/object.js +89 -0
  104. data/src/html/optgroup.js +25 -0
  105. data/src/html/option.js +97 -0
  106. data/src/html/param.js +38 -0
  107. data/src/html/script.js +122 -0
  108. data/src/html/select.js +129 -0
  109. data/src/html/style.js +31 -0
  110. data/src/html/table.js +199 -0
  111. data/src/html/tbody-thead-tfoot.js +91 -0
  112. data/src/html/td-th.js +18 -0
  113. data/src/html/textarea.js +25 -0
  114. data/src/html/title.js +20 -0
  115. data/src/html/tr.js +114 -0
  116. data/src/intro.js +141 -0
  117. data/src/outro.js +70 -0
  118. data/src/parser/html5.detailed.js +10762 -0
  119. data/src/parser/html5.min.js +503 -0
  120. data/src/parser/html5.pretty.js +10815 -0
  121. data/src/parser/intro.js +42 -0
  122. data/src/parser/outro.js +9 -0
  123. data/src/platform/core.js +323 -0
  124. data/src/platform/johnson.js +479 -0
  125. data/src/platform/rhino.js +327 -0
  126. data/src/platform/static/intro.js +41 -0
  127. data/src/platform/static/outro.js +30 -0
  128. data/src/profile/aop.js +238 -0
  129. data/src/profile/profile.js +402 -0
  130. data/src/serializer/xml.js +21 -0
  131. data/src/svg/animatedstring.js +25 -0
  132. data/src/svg/document.js +25 -0
  133. data/src/svg/element.js +22 -0
  134. data/src/svg/locatable.js +17 -0
  135. data/src/svg/rect.js +18 -0
  136. data/src/svg/rectelement.js +24 -0
  137. data/src/svg/stylable.js +49 -0
  138. data/src/svg/svgelement.js +22 -0
  139. data/src/svg/transformable.js +15 -0
  140. data/src/window/css.js +15 -0
  141. data/src/window/dialog.js +16 -0
  142. data/src/window/document.js +28 -0
  143. data/src/window/event.js +262 -0
  144. data/src/window/history.js +62 -0
  145. data/src/window/location.js +138 -0
  146. data/src/window/navigator.js +48 -0
  147. data/src/window/screen.js +53 -0
  148. data/src/window/timer.js +21 -0
  149. data/src/window/window.js +284 -0
  150. data/src/window/xhr.js +127 -0
  151. data/src/xpath/expression.js +49 -0
  152. data/src/xpath/implementation.js +2482 -0
  153. data/src/xpath/result.js +67 -0
  154. data/src/xpath/util.js +551 -0
  155. data/src/xpath/xmltoken.js +149 -0
  156. data/src/xslt/COPYING +34 -0
  157. data/src/xslt/ajaxslt-0.8.1/AUTHORS +1 -0
  158. data/src/xslt/ajaxslt-0.8.1/ChangeLog +136 -0
  159. data/src/xslt/ajaxslt-0.8.1/Makefile +49 -0
  160. data/src/xslt/ajaxslt-0.8.1/README +102 -0
  161. data/src/xslt/ajaxslt-0.8.1/TODO +15 -0
  162. data/src/xslt/ajaxslt-0.8.1/dom.js +566 -0
  163. data/src/xslt/ajaxslt-0.8.1/dom_unittest.html +24 -0
  164. data/src/xslt/ajaxslt-0.8.1/dom_unittest.js +131 -0
  165. data/src/xslt/ajaxslt-0.8.1/simplelog.js +79 -0
  166. data/src/xslt/ajaxslt-0.8.1/test/xpath.html +18 -0
  167. data/src/xslt/ajaxslt-0.8.1/test/xpath_script.js +45 -0
  168. data/src/xslt/ajaxslt-0.8.1/test/xslt.html +58 -0
  169. data/src/xslt/ajaxslt-0.8.1/test/xslt_script.js +33 -0
  170. data/src/xslt/ajaxslt-0.8.1/unittestsuite.html +26 -0
  171. data/src/xslt/ajaxslt-0.8.1/xmltoken.js +149 -0
  172. data/src/xslt/ajaxslt-0.8.1/xmltoken_unittest.html +18 -0
  173. data/src/xslt/ajaxslt-0.8.1/xmltoken_unittest.js +811 -0
  174. data/src/xslt/ajaxslt-0.8.1/xpath_unittest.html +39 -0
  175. data/src/xslt/ajaxslt-0.8.1/xpath_unittest.js +557 -0
  176. data/src/xslt/ajaxslt-0.8.1/xpathdebug.js +234 -0
  177. data/src/xslt/ajaxslt-0.8.1/xslt_unittest.html +138 -0
  178. data/src/xslt/ajaxslt-0.8.1/xslt_unittest.js +68 -0
  179. data/src/xslt/implementation.js +625 -0
  180. data/src/xslt/processor.js +37 -0
  181. data/src/xslt/util.js +449 -0
  182. data/test/foo.html +8 -0
  183. data/test/foo.js +40 -0
  184. data/test/jquery.js +6002 -0
  185. data/test/x.js +1 -0
  186. data/test/y.js +1 -0
  187. metadata +245 -14
@@ -0,0 +1,39 @@
1
+ <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
2
+ "http://www.w3.org/TR/html4/loose.dtd">
3
+
4
+ <html>
5
+ <head>
6
+ <title>JsUnit test page for file xpath.js of goog-ajaxslt</title>
7
+ <script language="JavaScript" type="text/javascript"
8
+ src="jsunit/app/jsUnitCore.js"></script>
9
+ <script language="JavaScript" type="text/javascript"
10
+ src="xmltoken.js"></script>
11
+ <script language="JavaScript" type="text/javascript"
12
+ src="util.js"></script>
13
+ <script language="JavaScript" type="text/javascript"
14
+ src="dom.js"></script>
15
+ <script language="JavaScript" type="text/javascript"
16
+ src="xpath.js"></script>
17
+ <script language="JavaScript" type="text/javascript"
18
+ src="xpathdebug.js"></script>
19
+ <script language="JavaScript" type="text/javascript"
20
+ src="xpath_unittest.js"></script>
21
+ </head>
22
+
23
+ <body>
24
+ This is a <a href="http://www.jsunit.net/">jsUnit</a> test
25
+ page. Run it using the <a
26
+ href="jsunit/testRunner.html">jsUnit runner</a>.
27
+
28
+ <!-- used in the test cases -->
29
+
30
+ <div id="test1"></div>
31
+ <div id="testid">test1</div>
32
+ <a id="jshref" href="javascript:doFoo('a', 'b')">javascript href with spaces</a>
33
+
34
+ <!-- for union expression -->
35
+ <span id="u1" class="u"></span>
36
+ <span id="u2" class="u"></span>
37
+ <span id="u3" class="u"></span>
38
+ </body>
39
+ </html>
@@ -0,0 +1,557 @@
1
+ // Copyright 2005, Google Inc.
2
+ // All Rights Reserved.
3
+ //
4
+ // Unit test for the XPath parser and engine.
5
+ //
6
+ // Author: Steffen Meschkat <mesch@google.com>
7
+ // Junji Takagi <jtakagi@google.com>
8
+
9
+ //********************************************
10
+ // DGF BEWARE! You MUST update this function if you add tests!
11
+ //********************************************
12
+ function exposeTestFunctionNames() {
13
+ return ['testParse', 'testEval', 'testAxes', 'testAttributeAsterisk', 'testEvalDom', 'testEvalDomJapanese'];
14
+ }
15
+
16
+ var expr = [
17
+ "@*",
18
+ "@*|node()",
19
+ "/descendant-or-self::div",
20
+ "/div",
21
+ "//div",
22
+ "/descendant-or-self::node()/child::para",
23
+ "substring('12345', 0, 3)",
24
+ "//title | //link",
25
+ "$x//title",
26
+ // "$x/title", // TODO(mesch): parsing of this expression is broken
27
+ "id('a')//title",
28
+ "//*[@about]",
29
+ "count(descendant::*)",
30
+ "count(descendant::*) + count(ancestor::*)",
31
+ "concat(substring-before(@image,'marker'),'icon',substring-after(@image,'marker'))",
32
+ "@*|text()",
33
+ "*|/",
34
+ "source|destination",
35
+ "$page != 'to' and $page != 'from'",
36
+ "substring-after(icon/@image, '/mapfiles/marker')",
37
+ "substring-before($str, $c)",
38
+ "$page = 'from'",
39
+ "segments/@time",
40
+ "child::para",
41
+ "child::*",
42
+ "child::text()",
43
+ "child::node()",
44
+ "attribute::name",
45
+ "attribute::*",
46
+ "descendant::para",
47
+ "ancestor::div",
48
+ "ancestor-or-self::div",
49
+ "descendant-or-self::para",
50
+ "self::para",
51
+ "child::chapter/descendant::para",
52
+ "child::*/child::para",
53
+ "/",
54
+ "/descendant::para",
55
+ "/descendant::olist/child::item",
56
+ "child::para[position()=1]",
57
+ "child::para[position()=last()]",
58
+ "child::para[position()=last()-1]",
59
+ "child::para[position()>1]",
60
+ "following-sibling::chapter[position()=1]",
61
+ "preceding-sibling::chapter[position()=1]",
62
+ "/descendant::figure[position()=42]",
63
+ "/child::doc/child::chapter[position()=5]/child::section[position()=2]",
64
+ "child::para[attribute::type='warning']",
65
+ "child::para[attribute::type='warning'][position()=5]",
66
+ "child::para[position()=5][attribute::type='warning']",
67
+ "child::chapter[child::title='Introduction']",
68
+ "child::chapter[child::title]",
69
+ "child::*[self::chapter or self::appendix]",
70
+ "child::*[self::chapter or self::appendix][position()=last()]",
71
+ "count(//*[id='u1']|//*[id='u2'])",
72
+ "count(//*[id='u1']|//*[class='u'])",
73
+ "count(//*[class='u']|//*[class='u'])",
74
+ "count(//*[class='u']|//*[id='u1'])",
75
+
76
+ // Axis expressions
77
+ "count(//*[@id='self']/ancestor-or-self::*)",
78
+ "count(//*[@id='self']/ancestor::*)",
79
+ "count(//*[@id='self']/attribute::*)",
80
+ "count(//*[@id='self']/child::*)",
81
+ "count(//*[@id='self']/descendant-or-self::*)",
82
+ "count(//*[@id='self']/descendant::*)",
83
+ "count(//*[@id='self']/following-sibling::*)",
84
+ "count(//*[@id='self']/following::*)",
85
+ "//*[@id='self']/parent::*/@id",
86
+ "count(//*[@id='self']/preceding-sibling::*)",
87
+ "count(//*[@id='self']/preceding::*)",
88
+ "//*[@id='self']/self::*/@id",
89
+
90
+ // (Japanese)
91
+ "/descendant-or-self::\u90e8\u5206",
92
+ "//\u90e8\u5206",
93
+ "substring('\uff11\uff12\uff13\uff14\uff15', 0, 3)",
94
+ "//\u30bf\u30a4\u30c8\u30eb | //\u30ea\u30f3\u30af",
95
+ "$\u8b0e//\u30bf\u30a4\u30c8\u30eb",
96
+ "//*[@\u30c7\u30b9\u30c6\u30a3\u30cd\u30a4\u30b7\u30e7\u30f3]",
97
+ "concat(substring-before(@\u30a4\u30e1\u30fc\u30b8,'\u76ee\u5370'),'\u30a2\u30a4\u30b3\u30f3',substring-after(@\u30a4\u30e1\u30fc\u30b8,'\u76ee\u5370'))",
98
+ "\u30bd\u30fc\u30b9|\u30c7\u30b9\u30c6\u30a3\u30cd\u30a4\u30b7\u30e7\u30f3",
99
+ "$\u30da\u30fc\u30b8 != '\u307e\u3067' and $\u30da\u30fc\u30b8 != '\u304b\u3089'",
100
+ "substring-after(\u30a2\u30a4\u30b3\u30f3/@\u30a4\u30e1\u30fc\u30b8, '/\u5730\u56f3\u30d5\u30a1\u30a4\u30eb/\u76ee\u5370')",
101
+ "substring-before($\u6587\u5b57\u5217, $\u6587\u5b57)",
102
+ "$\u30da\u30fc\u30b8 = '\u304b\u3089'",
103
+ "\u30bb\u30b0\u30e1\u30f3\u30c8/@\u6642\u523b",
104
+ "child::\u6bb5\u843d",
105
+ "attribute::\u540d\u524d",
106
+ "descendant::\u6bb5\u843d",
107
+ "ancestor::\u90e8\u5206",
108
+ "ancestor-or-self::\u90e8\u5206",
109
+ "descendant-or-self::\u6bb5\u843d",
110
+ "self::\u6bb5\u843d",
111
+ "child::\u7ae0/descendant::\u6bb5\u843d",
112
+ "child::*/child::\u6bb5\u843d",
113
+ "/descendant::\u6bb5\u843d",
114
+ "/descendant::\u9806\u5e8f\u30ea\u30b9\u30c8/child::\u9805\u76ee",
115
+ "child::\u6bb5\u843d[position()=1]",
116
+ "child::\u6bb5\u843d[position()=last()]",
117
+ "child::\u6bb5\u843d[position()=last()-1]",
118
+ "child::\u6bb5\u843d[position()>1]",
119
+ "following-sibling::\u7ae0[position()=1]",
120
+ "preceding-sibling::\u7ae0[position()=1]",
121
+ "/descendant::\u56f3\u8868[position()=42]",
122
+ "/child::\u6587\u66f8/child::\u7ae0[position()=5]/child::\u7bc0[position()=2]",
123
+ "child::\u6bb5\u843d[attribute::\u30bf\u30a4\u30d7='\u8b66\u544a']",
124
+ "child::\u6bb5\u843d[attribute::\u30bf\u30a4\u30d7='\u8b66\u544a'][position()=5]",
125
+ "child::\u6bb5\u843d[position()=5][attribute::\u30bf\u30a4\u30d7='\u8b66\u544a']",
126
+ "child::\u7ae0[child::\u30bf\u30a4\u30c8\u30eb='\u306f\u3058\u3081\u306b']",
127
+ "child::\u7ae0[child::\u30bf\u30a4\u30c8\u30eb]",
128
+ "child::*[self::\u7ae0 or self::\u4ed8\u9332]",
129
+ "child::*[self::\u7ae0 or self::\u4ed8\u9332][position()=last()]",
130
+
131
+ //Selenium bugs
132
+ "id('nested1')/div[1]//input[2]",
133
+ "id('foo')//div[contains(@id, 'useful')]//input",
134
+ "(//table[@class='stylee'])//th[text()='theHeaderText']/../td",
135
+
136
+ // The following are all expressions that used to occur in google
137
+ // maps XSLT templates.
138
+ "$address",
139
+ "$address=string(/page/user/defaultlocation)",
140
+ "$count-of-snippet-of-url = 0",
141
+ "$daddr",
142
+ "$form",
143
+ "$form = 'from'",
144
+ "$form = 'to'",
145
+ "$form='near'",
146
+ "$home",
147
+ "$i",
148
+ "$i > $page and $i < $page + $range",
149
+ "$i < $page and $i >= $page - $range",
150
+ "$i < @max",
151
+ "$i <= $page",
152
+ "$i + 1",
153
+ "$i = $page",
154
+ "$i = 1",
155
+ "$info = position() or (not($info) and position() = 1)",
156
+ "$is-first-order",
157
+ "$is-first-order and $snippets-exist",
158
+ "$more",
159
+ "$more > 0",
160
+ "$near-point",
161
+ "$page",
162
+ "$page != 'from'",
163
+ "$page != 'to'",
164
+ "$page != 'to' and $page != 'from'",
165
+ "$page > 1",
166
+ "$page = 'basics'",
167
+ "$page = 'details'",
168
+ "$page = 'from'",
169
+ "$page = 'to'",
170
+ "$page='from'",
171
+ "$page='to'",
172
+ "$r >= 0.5",
173
+ "$r >= 1",
174
+ "$r - 0",
175
+ "$r - 1",
176
+ "$r - 2",
177
+ "$r - 3",
178
+ "$r - 4",
179
+ "$saddr",
180
+ "$sources",
181
+ "$sources[position() < $details]",
182
+ "$src",
183
+ "$str",
184
+ "\"'\"",
185
+ "(//location[string(info/references/reference[1]/url)=string($current-url)]/info/references/reference[1])[1]",
186
+ "(not($count-of-snippet-of-url = 0) and (position() = 1) or not($current-url = //locations/location[position() = $last-pos]//reference[1]/url))",
187
+ "(not($info) and position() = 1) or $info = position()",
188
+ ".",
189
+ "../@arg0",
190
+ "../@filterpng",
191
+ "/page/@filterpng",
192
+ "4",
193
+ "@attribution",
194
+ "@id",
195
+ "@max > @num",
196
+ "@meters > 16093",
197
+ "@name",
198
+ "@start div @num + 1",
199
+ "@url",
200
+ "ad",
201
+ "address/line",
202
+ "adsmessage",
203
+ "attr",
204
+ "boolean(location[@id='near'][icon/@image])",
205
+ "bubble/node()",
206
+ "calltoaction/node()",
207
+ "category",
208
+ "contains($str, $c)",
209
+ "count(//location[string(info/references/reference[1]/url)=string($current-url)]//snippet)",
210
+ "count(//snippet)",
211
+ "count(attr)",
212
+ "count(location)",
213
+ "count(structured/source) > 1",
214
+ "description/node()",
215
+ "destination",
216
+ "destinationAddress",
217
+ "domain",
218
+ "false()",
219
+ "icon/@class != 'noicon'",
220
+ "icon/@image",
221
+ "info",
222
+ "info/address/line",
223
+ "info/distance",
224
+ "info/distance and $near-point",
225
+ "info/distance and info/phone and $near-point",
226
+ "info/distance or info/phone",
227
+ "info/panel/node()",
228
+ "info/phone",
229
+ "info/references/reference[1]",
230
+ "info/references/reference[1]/snippet",
231
+ "info/references/reference[1]/url",
232
+ "info/title",
233
+ "info/title/node()",
234
+ "line",
235
+ "location",
236
+ "location[@id!='near']",
237
+ "location[@id='near'][icon/@image]",
238
+ "location[position() > $numlocations div 2]",
239
+ "location[position() <= $numlocations div 2]",
240
+ "locations",
241
+ "locations/location",
242
+ "near",
243
+ "node()",
244
+ "not($count-of-snippets = 0)",
245
+ "not($form = 'from')",
246
+ "not($form = 'near')",
247
+ "not($form = 'to')",
248
+ "not(../@page)",
249
+ "not(structured/source)",
250
+ "notice",
251
+ "number(../@info)",
252
+ "number(../@items)",
253
+ "number(/page/@linewidth)",
254
+ "page/ads",
255
+ "page/directions",
256
+ "page/error",
257
+ "page/overlay",
258
+ "page/overlay/locations/location",
259
+ "page/refinements",
260
+ "page/request/canonicalnear",
261
+ "page/request/near",
262
+ "page/request/query",
263
+ "page/spelling/suggestion",
264
+ "page/user/defaultlocation",
265
+ "phone",
266
+ "position()",
267
+ "position() != 1",
268
+ "position() != last()",
269
+ "position() > 1",
270
+ "position() < $details",
271
+ "position()-1",
272
+ "query",
273
+ "references/@total",
274
+ "references/reference",
275
+ "references/reference/domain",
276
+ "references/reference/url",
277
+ "reviews/@positive div (reviews/@positive + reviews/@negative) * 5",
278
+ "reviews/@positive div (reviews/@positive + reviews/@negative) * (5)",
279
+ "reviews/@total",
280
+ "reviews/@total > 1",
281
+ "reviews/@total > 5",
282
+ "reviews/@total = 1",
283
+ "segments/@distance",
284
+ "segments/@time",
285
+ "segments/segment",
286
+ "shorttitle/node()",
287
+ "snippet",
288
+ "snippet/node()",
289
+ "source",
290
+ "sourceAddress",
291
+ "sourceAddress and destinationAddress",
292
+ "string(../@daddr)",
293
+ "string(../@form)",
294
+ "string(../@page)",
295
+ "string(../@saddr)",
296
+ "string(info/title)",
297
+ "string(page/request/canonicalnear) != ''",
298
+ "string(page/request/near) != ''",
299
+ "string-length($address) > $linewidth",
300
+ "structured/@total - $details",
301
+ "structured/source",
302
+ "structured/source[@name]",
303
+ "substring($address, 1, $linewidth - 3)",
304
+ "substring-after($str, $c)",
305
+ "substring-after(icon/@image, '/mapfiles/marker')",
306
+ "substring-before($str, $c)",
307
+ "tagline/node()",
308
+ "targetedlocation",
309
+ "title",
310
+ "title/node()",
311
+ "true()",
312
+ "url",
313
+ "visibleurl"
314
+ ];
315
+
316
+ function testParse() {
317
+ for (var i = 0; i < expr.length; ++i) {
318
+ assert(expr[i], xpathParse(expr[i]));
319
+ }
320
+ }
321
+
322
+ var numExpr = [
323
+ /* number expressions */
324
+ [ "1+1", 2 ],
325
+ [ "floor( -3.1415 )", -4 ],
326
+ [ "-5 mod -2", -1 ],
327
+ [ "-5 mod 2", -1 ],
328
+ [ "5 mod -2", 1 ],
329
+ [ "5 mod 2", 1 ],
330
+ [ "ceiling( 3.1415 )", 4.0 ],
331
+ [ "floor( 3.1415 )", 3.0 ],
332
+ [ "ceiling( -3.1415 )", -3.0 ],
333
+ /* string expressions */
334
+ [ "substring('12345', -42, 1 div 0)", "12345" ],
335
+ [ "normalize-space( ' qwerty ' )", "qwerty" ],
336
+ [ "contains('1234567890','9')", true ],
337
+ [ "contains('1234567890','1')", true ],
338
+ [ "'Hello World!'", 'Hello World!' ],
339
+ [ "substring('12345', 1.5, 2.6)", "234" ],
340
+ [ "substring('12345', 0, 3)", "12" ],
341
+ /* string expressions (Japanese) */
342
+ [ "substring('\u3042\u3044\u3046\u3048\u304a', -42, 1 div 0)",
343
+ "\u3042\u3044\u3046\u3048\u304a" ],
344
+ [ "normalize-space( ' \u3044\u308d\u306f\u306b\u307b\u3078\u3068 ' )",
345
+ "\u3044\u308d\u306f\u306b\u307b\u3078\u3068" ],
346
+ [ "contains('\u5357\u7121\u5999\u6cd5\u9023\u83ef\u7d4c','\u7d4c')",
347
+ true ],
348
+ [ "contains('\u5357\u7121\u5999\u6cd5\u9023\u83ef\u7d4c','\u5357')",
349
+ true ],
350
+ [ "'\u3053\u3093\u306b\u3061\u306f\u3001\u4e16\u754c\uff01'",
351
+ '\u3053\u3093\u306b\u3061\u306f\u3001\u4e16\u754c\uff01' ],
352
+ [ "substring('\uff11\uff12\uff13\uff14\uff15', 1.5, 2.6)",
353
+ "\uff12\uff13\uff14" ],
354
+ [ "substring('\uff11\uff12\uff13\uff14\uff15', 0, 3)",
355
+ "\uff11\uff12" ],
356
+ /* selenium bug SEL-347, AJAXSLT issue 19 */
357
+ [ "count(//a[@href=\"javascript:doFoo('a', 'b')\"])", 1 ],
358
+ /* variables */
359
+ [ "$foo", 'bar', { foo: 'bar' } ],
360
+ [ "$foo", 100, { foo: 100 } ],
361
+ [ "$foo", true, { foo: true } ],
362
+ [ "$foo + 1", 101, { foo: 100 } ],
363
+ /* variables (Japanese) */
364
+ [ "$\u307b\u3052", '\u307b\u3048', { \u307b\u3052: '\u307b\u3048' } ],
365
+ [ "$\u307b\u3052", 100, { \u307b\u3052: 100 } ],
366
+ [ "$\u307b\u3052", true, { \u307b\u3052: true } ],
367
+ [ "$\u307b\u3052 + 1", 101, { \u307b\u3052: 100 } ],
368
+ /* functions */
369
+ // function id() with string argument
370
+ [ "count(id('test1'))", 1 ],
371
+ // function id() with node-set argument
372
+ [ "count(id(//*[@id='testid']))", 1 ],
373
+ /* union expressions */
374
+ [ "count(//*[@id='u1'])", 1 ],
375
+ [ "count(//*[@class='u'])", 3 ],
376
+ [ "count(//*[@id='u1']|//*[@id='u2'])", 2 ],
377
+ [ "count(//*[@id='u1']|//*[@class='u'])", 3 ],
378
+ [ "count(//*[@class='u']|//*[@class='u'])", 3 ],
379
+ [ "count(//*[@class='u']|//*[@id='u1'])", 3 ]
380
+ ];
381
+
382
+ function testEval() {
383
+ for (var i = 0; i < numExpr.length; ++i) {
384
+ var ctx = new ExprContext(document.body);
385
+ var e = numExpr[i];
386
+ if (e[2]) {
387
+ for (var k in e[2]) {
388
+ var v = e[2][k];
389
+ if (typeof v == 'number') {
390
+ ctx.setVariable(k, new NumberValue(v));
391
+ } else if (typeof v == 'string') {
392
+ ctx.setVariable(k, new StringValue(v));
393
+ } else if (typeof v == 'boolean') {
394
+ ctx.setVariable(k, new BooleanValue(v));
395
+ }
396
+ }
397
+ }
398
+ var result = xpathParse(e[0]).evaluate(ctx);
399
+ if (typeof e[1] == 'number') {
400
+ assertEquals(e[0], e[1], result.numberValue());
401
+ } else if (typeof e[1] == 'string') {
402
+ assertEquals(e[0], e[1], result.stringValue());
403
+ } else if (typeof e[1] == 'boolean') {
404
+ assertEquals(e[0], e[1], result.booleanValue());
405
+ }
406
+ }
407
+ }
408
+
409
+ // For the following axis expressions, we need full control over the
410
+ // entire document, so we cannot evaluate them against document.body,
411
+ // but use our own XML document here. We verify that they give the
412
+ // right results by counting the nodes in their result node sets. For
413
+ // the axes that contain only one node, we check that we found the
414
+ // right node using the id. For axes that contain elements, we only
415
+ // count the elements, so we don't have to worry about whitespace
416
+ // normalization for the text nodes.
417
+ var axisTests = [
418
+ [ "count(//*[@id='self']/ancestor-or-self::*)", 3 ],
419
+ [ "count(//*[@id='self']/ancestor::*)", 2 ],
420
+ [ "count(//*[@id='self']/attribute::node())", 1 ],
421
+ [ "count(//*[@id='self']/child::*)", 1 ],
422
+ [ "count(//*[@id='self']/descendant-or-self::*)", 3 ],
423
+ [ "count(//*[@id='self']/descendant::*)", 2 ],
424
+ [ "count(//*[@id='self']/following-sibling::*)", 3 ],
425
+ [ "count(//*[@id='self']/@*/following-sibling::*)", 0 ],
426
+ [ "count(//*[@id='self']/following::*)", 4 ],
427
+ [ "//*[@id='self']/parent::*/@id", "parent" ],
428
+ [ "count(/parent::*)", 0 ],
429
+ [ "count(//*[@id='self']/preceding-sibling::*)", 1 ],
430
+ [ "count(//*[@id='self']/@*/preceding-sibling::*)", 0 ],
431
+ [ "count(//*[@id='self']/preceding::*)", 2 ],
432
+ [ "//*[@id='self']/self::*/@id", "self" ]
433
+ ];
434
+
435
+ function testAxes() {
436
+ var xml = [
437
+ '<page>',
438
+ ' <p></p>',
439
+ ' <list id="parent">',
440
+ ' <item></item>',
441
+ ' <item id="self"><d><d></d></d></item>',
442
+ ' <item></item>',
443
+ ' <item></item>',
444
+ ' <item></item>',
445
+ ' </list>',
446
+ ' <f></f>',
447
+ '</page>'
448
+ ].join("");
449
+ var ctx = new ExprContext(xmlParse(xml));
450
+ for (var i = 0; i < axisTests.length; ++i) {
451
+ var e = axisTests[i];
452
+ var result = xpathParse(e[0]).evaluate(ctx);
453
+ if (typeof e[1] == 'number') {
454
+ assertEquals(e[0], e[1], result.numberValue());
455
+ } else if (typeof e[1] == 'string') {
456
+ assertEquals(e[0], e[1], result.stringValue());
457
+ } else if (typeof e[1] == 'boolean') {
458
+ assertEquals(e[0], e[1], result.booleanValue());
459
+ }
460
+ }
461
+ }
462
+
463
+
464
+ function testAttributeAsterisk() {
465
+ var ctx = new ExprContext(xmlParse('<x a="1" b="1"><y><z></z></y></x>'));
466
+ var expr = xpathParse("count(/x/@*)");
467
+ assertEquals(2, expr.evaluate(ctx).numberValue());
468
+ }
469
+
470
+
471
+ // eval an xpath expression to a single node
472
+ function evalNodeSet(expr, ctx) {
473
+ var expr1 = xpathParse(expr);
474
+ var e = expr1.evaluate(ctx);
475
+ return e.nodeSetValue();
476
+ }
477
+
478
+ function testEvalDom() {
479
+ var xml = [
480
+ '<page>',
481
+ '<request>',
482
+ '<q>new york</q>',
483
+ '</request>',
484
+ '<location lat="100" lon="200"/>',
485
+ '</page>'
486
+ ].join('');
487
+
488
+ doTestEvalDom(xml, 'page', 'location', 'lat', '100', 'lon', '200');
489
+ }
490
+
491
+ function testEvalDomJapanese() {
492
+ var xml = [
493
+ '<\u30da\u30fc\u30b8>',
494
+ '<\u30ea\u30af\u30a8\u30b9\u30c8>',
495
+ '<\u30af\u30a8\u30ea>\u6771\u4eac</\u30af\u30a8\u30ea>',
496
+ '</\u30ea\u30af\u30a8\u30b9\u30c8>',
497
+ '<\u4f4d\u7f6e \u7def\u5ea6="\u4e09\u5341\u4e94" ',
498
+ "\u7d4c\u5ea6='\u767e\u56db\u5341'/>",
499
+ '</\u30da\u30fc\u30b8>'
500
+ ].join('');
501
+
502
+ doTestEvalDom(xml, '\u30da\u30fc\u30b8', '\u4f4d\u7f6e',
503
+ '\u7def\u5ea6', '\u4e09\u5341\u4e94',
504
+ '\u7d4c\u5ea6', '\u767e\u56db\u5341');
505
+ }
506
+
507
+ function doTestEvalDom(xml, page, location, lat, latValue, lon, lonValue) {
508
+ var slashPage = '/' + page;
509
+ var slashPageLocationAtLat = '/' + page + '/' + location + '/@' + lat;
510
+ var slashPageLocationAtLon = '/' + page + '/' + location + '/@' + lon;
511
+
512
+ var ctx = new ExprContext(xmlParse(xml));
513
+ // DGF if we have access to an official DOMParser, compare output with that also
514
+ var ctx1;
515
+ if (typeof(DOMParser) != 'undefined') {
516
+ ctx1 = new ExprContext((new DOMParser).parseFromString(xml, 'text/xml'));
517
+ } else {
518
+ ctx1 = ctx;
519
+ }
520
+
521
+ var ns = evalNodeSet(page, ctx);
522
+ assertEquals(page, ns.length, 1);
523
+
524
+ ns = evalNodeSet(page, ctx1);
525
+ assertEquals(page, ns.length, 1);
526
+
527
+ ns = evalNodeSet(slashPage, ctx);
528
+ assertEquals(slashPage, ns.length, 1);
529
+
530
+ ns = evalNodeSet(slashPage, ctx1);
531
+ assertEquals(slashPage, ns.length, 1);
532
+
533
+ assertEquals('/', evalNodeSet('/', ctx).length, 1);
534
+ assertEquals('/', evalNodeSet('/', ctx1).length, 1);
535
+
536
+ assertEquals('/', evalNodeSet('/', ctx)[0].nodeName, '#document');
537
+ assertEquals('/', evalNodeSet('/', ctx1)[0].nodeName, '#document');
538
+
539
+ assertEquals(slashPage, evalNodeSet(slashPage, ctx)[0].nodeName, page);
540
+ assertEquals(slashPage, evalNodeSet(slashPage, ctx1)[0].nodeName, page);
541
+
542
+ var n = evalNodeSet(slashPageLocationAtLat, ctx)[0];
543
+ assertEquals(slashPageLocationAtLat, n.nodeName, lat);
544
+ assertEquals(slashPageLocationAtLat, n.nodeValue, latValue);
545
+
546
+ n = evalNodeSet(slashPageLocationAtLat, ctx1)[0];
547
+ assertEquals(slashPageLocationAtLat, n.nodeName, lat);
548
+ assertEquals(slashPageLocationAtLat, n.nodeValue, latValue);
549
+
550
+ var n = evalNodeSet(slashPageLocationAtLon, ctx)[0];
551
+ assertEquals(slashPageLocationAtLon, n.nodeName, lon);
552
+ assertEquals(slashPageLocationAtLon, n.nodeValue, lonValue);
553
+
554
+ n = evalNodeSet(slashPageLocationAtLon, ctx1)[0];
555
+ assertEquals(slashPageLocationAtLon, n.nodeName, lon);
556
+ assertEquals(slashPageLocationAtLon, n.nodeValue, lonValue);
557
+ }