1 Layout Engine Visual Tests (reftest)
2 L. David Baron <dbaron@dbaron.org>, Mozilla Corporation
5 This code is designed to run tests of Mozilla's layout engine. These
6 tests consist of an HTML (or other format) file along with a reference
7 in the same format. The tests are run based on a manifest file, and for
8 each test, PASS or FAIL is reported, and UNEXPECTED is reported if the
9 result (PASS or FAIL) was not the expected result noted in the manifest.
14 Writing HTML tests where the reference rendering is also in HTML is
15 harder than simply writing bits of HTML that can be regression-tested by
16 comparing the rendering of an older build to that of a newer build
17 (perhaps using stored reference images from the older build). However,
18 comparing across time has major disadvantages:
20 * Comparisons across time either require two runs for every test, or
21 they require stored reference images appropriate for the platform and
22 configuration (often limiting testing to a very specific
25 * Comparisons across time may fail due to expected changes, for
26 example, changes in the default style sheet for HTML, changes in the
27 appearance of form controls, or changes in default preferences like
28 default font size or default colors.
30 Using tests for which the pass criteria were explicitly chosen allows
31 running tests at any time to see whether they still pass.
36 The test manifest format is a plain text file. The "#" makes the
37 remainder of a line a comment. Each non-blank line (after removal of
38 comments) must be one of the following:
40 1. Inclusion of another manifest
42 include <relative_path>
46 <failure-type>* <type> <url> <url_ref>
50 a. <failure-type> (optional) is one of the following:
52 fails The test passes if the images of the two renderings DO NOT
53 meet the conditions specified in the <type>.
55 fails-if(condition) If the condition is met, the test passes if the
56 images of the two renderings DO NOT meet the
57 conditions of <type>. If the condition is not met,
58 the test passes if the conditions of <type> are met.
60 random The results of the test are random and therefore not to be
61 considered in the output.
63 random-if(condition) The results of the test are random if a given
66 skip This test should not be run. This is useful when a test fails in a
67 catastrophic way, such as crashing or hanging the browser. Using
68 'skip' is prefered to simply commenting out the test because we
69 want to report the test failure at the end of the test run.
71 skip-if(condition) If the condition is met, the test is not run. This is
72 useful if, for example, the test crashes only on a
73 particular platform (i.e. it allows us to get test
74 coverage on the other platforms).
76 Examples of using conditions:
77 fails-if(MOZ_WIDGET_TOOLKIT=="windows") ...
78 fails-if(MOZ_WIDGET_TOOLKIT=="cocoa") ...
79 fails-if(MOZ_WIDGET_TOOLKIT=="gtk2") ...
81 b. <type> is one of the following:
83 == The test passes if the images of the two renderings are the
85 != The test passes if the images of the two renderings are
88 c. <url> is either a relative file path or an absolute URL for the
91 d. <url_ref> is either a relative file path or an absolute URL for
94 The only difference between <url> and <url_ref> is that results of
95 the test are reported using <url> only.
97 This test manifest format could be used by other harnesses, such as ones
98 that do not depend on XUL, or even ones testing other layout engines.
103 At some point in the future there will hopefully be a cleaner way to do
104 this. For now, go to your object directory, and run (perhaps using
105 MOZ_NO_REMOTE=1 or the -profile <directory> option)
107 ./firefox -reftest /path/to/srcdir/mozilla/layout/reftests/reftest.list > reftest.out
109 and then search/grep reftest.out for "UNEXPECTED".
111 There are two scripts provided to convert the reftest.out to HTML.
112 clean-reftest-output.pl converts reftest.out into simple HTML, stripping
113 lines from the log that aren't relevant. reftest-to-html.pl converts
114 the output into html that makes it easier to visually check for
120 This framework is capable of testing many areas of the layout engine.
121 It is particularly well-suited to testing dynamic change handling (by
122 comparison to the static end-result as a reference) and incremental
123 layout (comparison of a script-interrupted layout to one that was not).
124 However, it is also possible to write tests for many other things that
125 can be described in terms of equivalence, for example:
127 * CSS cascading could be tested by comparing the result of a
128 complicated set of style rules that makes a word green to <span
129 style="color:green">word</span>.
131 * <canvas> compositing operators could be tested by comparing the
132 result of drawing using canvas to a block-level element with the
133 desired color as a CSS background-color.
135 * CSS counters could be tested by comparing the text output by counters
136 with a page containing the text written out
138 * complex margin collapsing could be tested by comparing the complex
139 case to a case where the margin is written out, or where the margin
140 space is created by an element with 'height' and transparent
143 When it is not possible to test by equivalence, it may be possible to
144 test by non-equivalence. For example, testing justification in cases
145 with more than two words, or more than three different words, is
146 difficult. However, it is simple to test that justified text is at
147 least displayed differently from left-, center-, or right-aligned text.
152 When writing tests for this framework, it is important for the test to
153 depend only on behaviors that are known to be correct and permanent.
154 For example, tests should not depend on default font sizes, default
155 margins of the body element, the default style sheet used for HTML, the
156 default appearance of form controls, or anything else that can be
159 In general, the best way to achieve this is to make the test and the
160 reference identical in as many aspects as possible. For example:
163 <div style="color:green"><table><tr><td><span>green
164 </span></td></tr></table></div>
166 Good reference markup:
167 <div><table><tr><td><span style="color:green">green
168 </span></td></tr></table></div>
170 BAD reference markup:
171 <!-- 3px matches the default cellspacing and cellpadding -->
172 <div style="color:green; padding: 3px">green
176 <!-- span doesn't change the positioning, so skip it -->
177 <div style="color:green"><table><tr><td>green
178 </td></tr></table></div>
183 Normally reftest takes a snapshot of the given markup's rendering right
184 after the load event fires for content. If your test needs to postpone
185 the moment the snapshot is taken, it should make sure a class
186 'reftest-wait' is on the root element by the moment the load event
187 fires. The easiest way to do this is to put it in the markup, e.g.:
188 <html class="reftest-wait">
190 When your test is ready, you should remove this class from the root
191 element, for example using this code:
192 document.documentElement.className = "";
195 Note that in layout tests it is often enough to trigger layout using
196 document.body.offsetWidth // HTML example
198 When possible, you should use this technique instead of making your
203 Now that the patch for bug 374050 has landed
204 (https://bugzilla.mozilla.org/show_bug.cgi?id=374050), it is possible to
205 create reftests that run in a paginated context.
207 The page size used is 5in wide and 3in tall (with the default half-inch
208 margins). This is to allow tests to have less text and to make the
209 entire test fit on the screen.
211 There is a layout/reftests/printing directory for printing reftests; however,
212 there is nothing special about this directory. You can put printing reftests
213 anywhere that is appropriate.
215 The suggested first lines for any printing test is
216 <!DOCTYPE html><html class="reftest-print">
217 <style>html{font-size:12pt}</style>
219 The reftest-print class on the root element triggers the reftest to
220 switch into page mode on load. Fixing the font size is suggested,
221 although not required, because the pages are a fixed size in inches.
223 The underlying layout support for this mode isn't really complete; it
224 doesn't use exactly the same codepath as real print preview/print. In
225 particular, scripting and frames are likely to cause problems; it is untested,
226 theough. That said, it should be sufficient for testing layout issues related