2 <meta http-equiv=
"Pragma" content=
"no-cache" />
3 <meta http-equiv=
"Expires" content=
"-1" />
4 <link rel=
"stylesheet" href=
"test_page.css">
6 function AdjustHeight(frameWin
) {
7 var div
= frameWin
.document
.getElementsByTagName("div")[0];
8 var height
= frameWin
.getComputedStyle(div
).height
;
9 frameWin
.frameElement
.style
.height
= height
;
12 function DidExecuteTests() {
13 var plugin
= document
.getElementById("plugin");
14 plugin
.parentNode
.removeChild(plugin
);
16 CheckPostConditions();
21 // Otherwise, we are in a subframe, so we can use this opportunity to resize
26 function AppendFrame(testcase
, i
) {
27 var p
= document
.createElement("P");
28 p
.setAttribute("class", "frame-container");
30 var title
= document
.createElement("H2");
31 title
.appendChild(document
.createTextNode(testcase
));
34 var frame
= document
.createElement("IFRAME");
35 var mode
= ExtractSearchParameter("mode");
36 var websocket_host
= ExtractSearchParameter("websocket_host");
37 var websocket_port
= ExtractSearchParameter("websocket_port");
38 var ssl_server_port
= ExtractSearchParameter("ssl_server_port");
39 var src
= "?testcase=" + testcase
;
42 if (websocket_host
!= "")
43 src
+= "&websocket_host=" + websocket_host
;
44 if (websocket_port
!= "")
45 src
+= "&websocket_port=" + websocket_port
;
46 if (ssl_server_port
!= "")
47 src
+= "&ssl_server_port=" + ssl_server_port
;
48 frame
.setAttribute("src", src
);
50 frame
.setAttribute("onload", "LoadNext(" + (i
+ 1) + ")");
53 document
.body
.appendChild(p
);
56 function LoadNext(i
) {
57 var links
= document
.links
;
59 AppendFrame(links
[i
].firstChild
.nodeValue
, i
);
63 // Remove any existing frames.
64 var existing
= document
.getElementsByClassName("frame-container");
65 while (existing
.length
)
66 existing
[0].parentNode
.removeChild(existing
[0]);
68 // Add new frames for each test, but do so one frame at a time.
72 function ExtractSearchParameter(name
) {
73 var nameIndex
= location
.search
.indexOf(name
+ "=");
74 if (nameIndex
!= -1) {
75 var value
= location
.search
.substring(nameIndex
+ name
.length
+ 1);
76 var endIndex
= value
.indexOf("&");
78 value
= value
.substring(0, endIndex
);
84 // Parses the message, looking for strings of the form:
85 // TESTING_MESSAGE:<message_type>:<message_contents>
87 // If the message_data is not a string or does not match the above format, then
88 // undefined is returned.
90 // Otherwise, returns an array containing 2 items. The 0th element is the
91 // message_type, one of:
98 // The second item is the verbatim message_contents.
99 function ParseTestingMessage(message_data
) {
100 if (typeof(message_data
) != "string")
102 var testing_message_prefix
= "TESTING_MESSAGE";
104 var delim1
= message_data
.indexOf(delim_str
);
105 if (message_data
.substring(0, delim1
) !== testing_message_prefix
)
107 var delim2
= message_data
.indexOf(delim_str
, delim1
+ 1);
109 delim2
= message_data
.length
;
110 var message_type
= message_data
.substring(delim1
+ 1, delim2
);
111 var message_contents
= message_data
.substring(delim2
+ 1);
112 return [message_type
, message_contents
];
115 function ClearConsole() {
116 window
.document
.getElementById("console").innerHTML
= "";
119 function LogHTML(html
) {
120 window
.document
.getElementById("console").innerHTML
+= html
;
123 function sendAutomationMessage(msg
) {
124 if (window
.domAutomationController
) {
125 window
.domAutomationController
.setAutomationId(0);
126 window
.domAutomationController
.send(msg
);
130 // If something goes really wrong, the test running inside the plugin may not
131 // terminate. For example, if the plugin does not load, the test will never
132 // send "PASS" to the browser. In this case we should explicitly use the
133 // automation controller to terminate the test.
134 function InternalError(msg
) {
135 LogHTML("<p>" + msg
);
136 sendAutomationMessage(msg
);
139 function SetCookie(key_value_string
) {
140 window
.document
.cookie
= key_value_string
+ "; path=/";
143 function EvalScript(script
) {
151 // Add a "PostCondition". These are bits of script that are run after the plugin
152 // is destroyed. If they evaluate to false or throw an exception, it's
153 // considered a failure.
154 function AddPostCondition(script
) {
155 conditions
.push(script
);
157 // Update the HTML to show the failure and update cookies so that ui_tests
158 // doesn't count this as a pass.
159 function ConditionFailed(error
) {
160 error_string
= "Post condition check failed: " + error
;
162 // If the plugin thinks the test passed but a post-condition failed, we want
163 // to clear the PASS cookie so that ui_tests doesn't count it is a passed
165 if (window
.document
.cookie
.indexOf("PASS") != -1) {
166 while (window
.document
.cookie
.indexOf("PPAPI_PROGRESS_" + i
) != -1) {
167 window
.document
.cookie
= "PPAPI_PROGRESS_" + i
+ "=; max-age=0";
170 window
.document
.cookie
= "PPAPI_PROGRESS_0=" + error_string
172 LogHTML("<p>" + error_string
);
174 // Iterate through the post conditions defined in |conditions| and check that
176 function CheckPostConditions() {
177 for (var i
= 0; i
< conditions
.length
; ++i
) {
178 var script
= conditions
[i
];
181 ConditionFailed("\"" + script
+ "\"");
184 ConditionFailed("\"" + script
+ "\"" + " failed with exception: " +
185 "\"" + ex
.toString() + "\"");
190 function IsTestingMessage(message_data
) {
191 return (ParseTestingMessage(message_data
) != undefined);
194 function handleTestingMessage(message_event
) {
195 var type_contents_tuple
= ParseTestingMessage(message_event
.data
);
196 if (type_contents_tuple
) {
197 var type
= type_contents_tuple
[0];
198 var contents
= type_contents_tuple
[1];
199 if (type
=== "ClearConsole")
201 else if (type
=== "DidExecuteTests")
203 else if (type
=== "LogHTML")
205 else if (type
=== "SetCookie")
207 else if (type
=== "EvalScript")
208 EvalScript(contents
);
209 else if (type
== "AddPostCondition")
210 AddPostCondition(contents
);
214 function sendProgress() {
215 // We send "..." to signal that we're still working. See
216 // ppapi/tests/testing_instance.h for how this works.
217 sendAutomationMessage("...");
220 onload = function() {
221 var testcase
= ExtractSearchParameter("testcase");
222 var mode
= ExtractSearchParameter("mode");
223 document
.title
= 'Test ' + testcase
;
225 if (mode
== "nacl_newlib") {
226 obj
= document
.createElement("EMBED");
227 obj
.setAttribute("src", "ppapi_nacl_tests_newlib.nmf");
228 obj
.setAttribute("type", "application/x-nacl");
229 obj
.setAttribute("mode", mode
);
230 } else if (mode
== "nacl_glibc") {
231 obj
= document
.createElement("EMBED");
232 obj
.setAttribute("src", "ppapi_nacl_tests_glibc.nmf");
233 obj
.setAttribute("type", "application/x-nacl");
234 obj
.setAttribute("mode", mode
);
235 } else if (mode
== "nacl_pnacl") {
236 obj
= document
.createElement("EMBED");
237 obj
.setAttribute("src", "ppapi_nacl_tests_pnacl.nmf");
238 obj
.setAttribute("type", "application/x-nacl");
239 obj
.setAttribute("mode", mode
);
241 var mimeType
= "application/x-ppapi-tests";
242 if (mimeType
in navigator
.mimeTypes
) {
243 obj
= document
.createElement("EMBED");
244 obj
.setAttribute("src", "http://a.b.c/test");
245 obj
.setAttribute("type", mimeType
);
247 document
.getElementById("console").innerHTML
=
248 '<span class="fail">FAIL</span>: ' +
249 '<span class="err_msg">Test plug-in is not registered.</span>';
253 obj
.setAttribute("width", 80);
254 obj
.setAttribute("height", 80);
255 obj
.setAttribute("style",
256 "background-color:#AAAAAA;border:1px solid black;");
257 obj
.setAttribute("id", "plugin");
258 obj
.setAttribute("testcase", testcase
);
259 obj
.setAttribute("protocol", window
.location
.protocol
);
260 var websocket_host
= ExtractSearchParameter("websocket_host");
261 if (websocket_host
!= "")
262 obj
.setAttribute("websocket_host", websocket_host
);
263 var websocket_port
= ExtractSearchParameter("websocket_port");
264 if (websocket_port
!= "")
265 obj
.setAttribute("websocket_port", websocket_port
);
266 var ssl_server_port
= ExtractSearchParameter("ssl_server_port");
267 if (ssl_server_port
!= "")
268 obj
.setAttribute("ssl_server_port", ssl_server_port
);
270 var container
= document
.getElementById("container");
271 container
.addEventListener("message", handleTestingMessage
, true);
273 // "error" and "crash" events will only fire for NaCl, but adding these
274 // listeners doesn't hurt in the non-NaCl cases.
275 obj
.addEventListener("error", function() {
276 InternalError("Plugin did not load. '" + obj
.lastError
+ "'");
278 obj
.addEventListener("crash", function() {
279 InternalError("Plugin crashed. '" + obj
.lastError
+ "'");
282 // NaCl sends progress events while loading. When we get one, notify the
283 // domAutomationController so that it knows we're still working.
284 obj
.addEventListener("loadstart", sendProgress
, true);
285 obj
.addEventListener("progress", sendProgress
, true);
286 obj
.addEventListener("load", sendProgress
, true);
287 obj
.addEventListener("loadend", sendProgress
, true);
289 // Register a bad dispatchEvent to make sure it isn't used. See 'EVIL' note
291 var original
= obj
.dispatchEvent
;
292 obj
.dispatchEvent = function() {
293 // TODO(dmichael): NaCl triggers this; take out the special case for NaCl
294 // when crbug.com/109775 is fixed.
295 if (mode
.indexOf("nacl") !== 0)
296 InternalError("Bad dispatchEvent called!");
298 // Pass it on anyways, we need the event to detect load progress and
300 return original
.apply(obj
, arguments
);
302 container
.appendChild(obj
);
307 // This part of the script does some nefarious things to make sure that it
308 // doesn't affect the behavior of PostMessage (on which all the tests rely). In
309 // particular, we replace document.createEvent, MessageEvent.initMessageEvent,
310 // and the MessageEvent constructor. Previous versions of the PostMessage
311 // implementation made use of these and would fail (http://crbug.com/82604).
312 // The NaCl plugin uses dispatchEvent for progress events, hence we are careful
313 // to make that still pass for NaCl (see above, and see crbug.com/109775).
314 document
.createEvent = function() {
315 InternalError("Bad document.createEvent called!");
317 function MessageEvent() {
318 InternalError("Bad MessageEvent constructor called!");
320 MessageEvent
.prototype.initMessageEvent = function() {
321 InternalError("Bad MessageEvent.initMessageEvent called!");
327 <div id=
"container"></div>
328 <div id=
"console"><span class=
"load_msg">loading...
</span></div>