mozilla

Compare Revisions

Writing xpcshell-based unit tests

Change Revisions

Revision 472935:

Revision 472935 by gps on

Revision 481773:

Revision 481773 by Ms2ger on

Title:
Writing xpcshell-based unit tests
Writing xpcshell-based unit tests
Slug:
Writing_xpcshell-based_unit_tests
Writing_xpcshell-based_unit_tests
Tags:
"Developing Mozilla", "Automated testing"
"Developing Mozilla", "Automated testing"
Content:

Revision 472935
Revision 481773
n27      This doesn't really test anything, but it gives you an idean27      This doesn't really test anything, but it gives you an idea
> how you'd actually write a test. If you want to execute the test> how you'd actually write a test. If you want to execute the test
>, you must first add it to the <a href="/en/Writing_xpcshell-base>, you must first add it to the <a href="/en/Writing_xpcshell-base
>d_unit_tests#Adding_your_tests_to_the_xpcshell_manifest" title="e>d_unit_tests#Adding_your_tests_to_the_xpcshell_manifest" title="e
>n/Writing_xpcshell-based_unit_tests#Adding_your_tests_to_the_xpcs>n/Writing_xpcshell-based_unit_tests#Adding_your_tests_to_the_xpcs
>hell_manifest">xpcshell.ini manifest</a>.&nbsp; Add the test file>hell_manifest">xpcshell.ini manifest</a>. Add the test file to an
> to an existing set of tests (say, for example, {{ Source("netwer> existing set of tests (say, for example, {{ Source("netwerk/test
>k/test/unit/") }}, but you should put it near the code it tests).>/unit/") }}, but you should put it near the code it tests). You t
> You then execute your test using make xpcshell-tests:>hen execute your test using <a href="/en-US/docs/Developer_Guide/
 >mach" title="/en-US/docs/Developer_Guide/mach">mach</a>:
28    </p>
29    <pre>28    </p>
30$ cd objdir29    <pre>
31$ make -C netwerk/test/ xpcshell-tests30$ ./mach xpcshell-test netwerk/test/
n33</pre>n
34    <p>
35      or using <a href="/en-US/docs/Developer_Guide/mach" title="
>/en-US/docs/Developer_Guide/mach">mach</a>: 
36    </p>
37    <pre>
38$ cd objdir
39$ ./mach xpcshell-test &lt;path_to_directory&gt;
n73      xpcshell tests have access to the following utility function65      xpcshell tests have access to the following utility functio
>ns.&nbsp; All of them are defined in <a class="external" href="ht>ns. All of them are defined in <a class="external" href="http://m
>tp://mxr.mozilla.org/mozilla-central/source/testing/xpcshell/head>xr.mozilla.org/mozilla-central/source/testing/xpcshell/head.js" t
>.js" title="http://mxr.mozilla.org/mozilla-central/source/testing>itle="http://mxr.mozilla.org/mozilla-central/source/testing/xpcsh
>/xpcshell/head.js">testing/xpcshell/head.js</a> if you want to se>ell/head.js">testing/xpcshell/head.js</a> if you want to see how 
>e how they work.>they work.
n77        <code>add_test(<em>testFunction</em>)</code>n69        <code>add_test(<var>testFunction</var>)</code>
n82    </dl>n
83    <dl>74      <dt>
84      <dt>
85        <code>do_throw(<em>messageText</em>)</code>75        <code>do_throw(<var>messageText</var>)</code>
n93    </dl>n
94    <dl>83      <dt>
95      <dt>
96        <code>do_check_eq(<em>a</em>, <em>b</em>)</code>84        <code>do_check_eq(<var>a</var>, <var>b</var>)</code>
n101    </dl>n
102    <dl>89      <dt>
103      <dt>
104        <code>do_check_neq(<em>a</em>, <em>b</em>)</code>90        <code>do_check_neq(<var>a</var>, <var>b</var>)</code>
n109    </dl>n
110    <dl>95      <dt>
111      <dt>
112        <code>do_check_true(<em>expr</em>)</code>96        <code>do_check_true(<var>expr</var>)</code>
n117    </dl>n
118    <dl>101      <dt>
119      <dt>
120        <code>do_check_false(<em>expr</em>)</code>102        <code>do_check_false(<var>expr</var>)</code>
n125    </dl>n
126    <dl>107      <dt>
127      <dt>
128        <code>do_check_null(<em>expr</em>)</code>108        <code>do_check_null(<var>expr</var>)</code>
n134        <code>do_print(<em>messageText</em>)</code>n114        <code>do_print(<var>messageText</var>)</code>
n139    </dl>n
140    <dl>119      <dt>
141      <dt>
142        <code>do_execute_soon(<em>callback</em>)</code>120        <code>do_execute_soon(<var>callback</var>)</code>
n147    </dl>n
148    <p>
149      &nbsp;
150    </p>
151    <dl>125      <dt>
152      <dt>
153        <code>do_get_file(<em>testdirRelativePath, allowNonexiste126        <code>do_get_file(<var>testdirRelativePath</var><var>al
>nt</em>)</code>>lowNonexistent</var>)</code>
n161    </dl>n
162    <dl>
n169    </dl>n
170    <dl>
n177    </dl>n
178    <dl>
179      <dt>
180        <code>load(<em><span style="font-style: italic;">test</sp
>an>dirRelativePath</em>)</code> 
181      </dt>146      <dt>
182      <dd>147        <code>load(<var>testdirRelativePath</var>)</code>
183        Imports the JavaScript file referenced by <code><em>testd
>irRelativePath</em></code> into the global script context, execut 
>ing the code inside it. The file specified is a file within the t 
>est directory. For example, if your test is unit/test_something.j 
>s and you have another file unit/extra_helpers.js, you can load t 
>he second file from the first simply by calling <code>load('extra 
>_helper.js')</code>. 
184      </dd>
185    </dl>
186    <dl>
187      <dt>148      </dt>
188        <code>do_load_module(</code><code><em>testdirRelativePath
></em></code><code>)</code> 
189      </dt>
190      <dd>
191        Calls do_get_file(<code><em>testdirRelativePath</em></cod
>e>), then registers the returned file. 
192      </dd>149      <dd>
193    </dl>150        Imports the JavaScript file referenced by <code><var>test
 >dirRelativePath</var></code> into the global script context, exec
 >uting the code inside it. The file specified is a file within the
 > test directory. For example, if your test is unit/test_something
 >.js and you have another file unit/extra_helpers.js, you can load
 > the second file from the first simply by calling <code>load('ext
 >ra_helper.js')</code>.
194    <dl>
195      <dt>
196        <code>do_parse_document(<em><span style="font-style: ital
>ic;">p</span></em></code><code><em><em>ath</em>, type</em></code> 
><code>)</code> 
197      </dt>
198      <dd>151      </dd>
152      <dt>
153        <code>do_load_module(<var>testdirRelativePath</var>)</cod
 >e>
154      </dt>
155      <dd>
156        Calls do_get_file(<code><var>testdirRelativePath</var></c
 >ode>), then registers the returned file.
157      </dd>
158      <dt>
159        <code>do_parse_document(<var>path</var>, <var>type</var>)
 ></code>
160      </dt>
161      <dd>
199        Parses and returns a DOM&nbsp;document.162        Parses and returns a DOM document.
n205        By default XPCShell tests will disable the idle service, n168        By default XPCShell tests will disable the idle service, 
>so that idle time will always be reported as 0.&nbsp; Calling thi>so that idle time will always be reported as 0. Calling this func
>s function will re-enable the service and return a handle to it, >tion will re-enable the service and return a handle to it, the id
>the idle time will be then correctly requested to the underlying >le time will be then correctly requested to the underlying OS. Th
>OS.&nbsp; The idle-daily notification could be fired when request>e idle-daily notification could be fired when requesting idle ser
>ing idle service. It is suggested to always get the service throu>vice. It is suggested to always get the service through this meth
>gh this method if the test has to use idle.>od if the test has to use idle.
206      </dd>
207    </dl>
208    <dl>
209      <dt>169      </dd>
210        &nbsp;
211      </dt>170      <dt>
212      <dt>
213        <code>do_register_cleanup(<em>callback</em>)</code>171        <code>do_register_cleanup(<var>callback</var>)</code>
n218    </dl>n
219    <p>
220      &nbsp;
221    </p>
222    <dl>
223      <dt>
224        <code>do_timeout(<em>delay</em>, <em>fun</em>)</code>
225      </dt>176      <dt>
177        <code>do_timeout(<var>delay</var>, <var>fun</var>)</code>
226      <dd>178      </dt>
179      <dd>
227        Call this function to schedule a timeout. The given funct180        Call this function to schedule a timeout. The given funct
>ion will be called with no arguments provided after the specified>ion will be called with no arguments provided after the specified
> delay (in milliseconds). Note that you must call do_test_pending> delay (in milliseconds). Note that you must call do_test_pending
> so that the test isn't completed before your timer fires, and yo> so that the test isn't completed before your timer fires, and yo
>u must call do_test_finished when the actions you perform in the >u must call do_test_finished when the actions you perform in the 
>timeout complete, if you have no other functionality to test.&nbs>timeout complete, if you have no other functionality to test. (No
>p; (Note: the function argument used to be a string argument to b>te: the function argument used to be a string argument to be pass
>e passed to eval, and some older branches support only a string a>ed to eval, and some older branches support only a string argumen
>rgument or support both string and function.)>t or support both string and function.)
228      </dd>
229    </dl>181      </dd>
230    <dl>
n237    </dl>n
238    <dl>
n298      Since not all platforms support multi-process (electrolysisn247      Since not all platforms support multi-process (electrolysis
>, aka "e10s"), you need to put any e10s-specific tests in a separ>, aka "e10s"), you need to put any e10s-specific tests in a separ
>ate directory, and only run them if MOZ_IPC is defined.&nbsp; See>ate directory, and only run them if MOZ_IPC is defined. See /netw
> /netwerk/test/Makefile.in for an example.&nbsp;&nbsp; Note that >erk/test/Makefile.in for an example. Note that any "head_" or "ta
>any "head_" or "tail_" scripts you have in your usual tests direc>il_" scripts you have in your usual tests directory will not be r
>tory will not be run automatically in the new directory (but you >un automatically in the new directory (but you can write a simple
>can write a simple wrapper to load them: see "head_channels_clone> wrapper to load them: see "head_channels_clone.js" in netwerk/te
>.js" in netwerk/test/unit_ipc).>st/unit_ipc).
299    </p>
300    <p>248    </p>
249    <p>
301      By default xpcshell tests run in the parent process.&nbsp; 250      By default xpcshell tests run in the parent process. If you
>If you wish to run test logic in the child, you have several ways> wish to run test logic in the child, you have several ways to do
> to do it:> it:
n304      <li>Create a regular test_foo.js test, and then write a wran253      <li>Create a regular test_foo.js test, and then write a wra
>pper test_foo_wrap.js file that uses the run_test_in_child() func>pper test_foo_wrap.js file that uses the run_test_in_child() func
>tion to run an entire script file in the child.&nbsp;&nbsp; This >tion to run an entire script file in the child. This is an easy w
>is an easy way to arrange for a test to be run twice, once in chr>ay to arrange for a test to be run twice, once in chrome and then
>ome and then later (via the _wrap.js file) in content.&nbsp; See > later (via the _wrap.js file) in content. See /network/test/unit
>/network/test/unit_ipc for examples.&nbsp; The run_test_in_child(>_ipc for examples. The run_test_in_child() function takes a callb
>) function takes a callback, so you should be able to call it mul>ack, so you should be able to call it multiple times with differe
>tiple times with different files, if that's useful.>nt files, if that's useful.
n306      <li>For tests that need to run logic in both the parent + cn255      <li>For tests that need to run logic in both the parent + c
>hild processes during a single test run, you may use the poorly d>hild processes during a single test run, you may use the poorly d
>ocumented SendCommand() function, which takes a code string to be>ocumented SendCommand() function, which takes a code string to be
> executed on the child, and a callback function to be run on the > executed on the child, and a callback function to be run on the 
>parent when it has completed.&nbsp; You will want to first call d>parent when it has completed. You will want to first call do_load
>o_load_child_test_harness() to set up a reasonable test environme>_child_test_harness() to set up a reasonable test environment on 
>nt on the child.&nbsp; SendCommand returns immediately, so you wi>the child. SendCommand returns immediately, so you will generally
>ll generally want to use do_test_pending/do_test_finished with it> want to use do_test_pending/do_test_finished with it. NOTE: this
>.&nbsp;&nbsp;&nbsp; NOTE:&nbsp; this method of test has not been > method of test has not been used much, and your level of pain ma
>used much, and your level of pain may be significant.&nbsp; Consi>y be significant. Consider option #1 if possible.
>der option #1 if possible. 
n310      See the documentation for&nbsp; run_test_in_child() and do_n259      See the documentation for run_test_in_child() and do_load_c
>load_child_test_harness() in testing/xpcshell/head.js for more in>hild_test_harness() in testing/xpcshell/head.js for more informat
>formation.>ion.
n441      Tests should be run using <code>make -C <em>OBJDIR/path_to_n390      Tests should be run using <code>./mach xpcshell-test <var>p
>tests/</em></code> (to copy tests) and then <code>make -C <em>OBJ>ath/to/tests/</var></code>. To run a single test, use <code>./mac
>DIR/path_to_tests/</em></code> <em><code>xpcshell-tests</code></e>h xpcshell-test <var>path/to/test.js</var></code>.
>m> (to run tests). Just <code>cd</code> to an appropriate directo 
>ry (e.g. to run tests for a single module, go to <code><a href="/ 
>en/MOZ_OBJDIR" title="en/MOZ_OBJDIR">MOZ_OBJDIR</a>/<em>path_to_t 
>ests</em>/test/</code>) and run <code>make</code> <em><code>xpcsh 
>ell-tests</code></em>. 
442    </p>
443    <p>391    </p>
444      To run a single test, use the <code>check-one</code> target
>, as described above. 
445    </p>
446    <div class="note">
447      <strong>Note:</strong> You must run <code>make -C <em>OBJDI
>R/path_to_tests/</em></code> before trying to run tests; the test 
>s are copied to a central location to be executed, and this copyi 
>ng occurs in the <code>libs</code> target of the build, which <co 
>de>make <em><span style="font-family: Verdana,Tahoma,sans-serif;" 
>>xpcshell-tests</span></em></code> does not invoke. On platforms  
>with symlinks, you can edit and re-run the test without re-making 
> the libs target, since the symlink will point to the file in you 
>r source directory. 
448    </div>
n471      Under e10s you have two processes.&nbsp; You can debug the n414      Under e10s you have two processes. You can debug the chrome
>chrome process, the child process, or both at the same time.&nbsp> process, the child process, or both at the same time.
>; 
n477      simply use "make check-interactive" as described above.&nbsn420      simply use "make check-interactive" as described above.
>p;&nbsp; 
t483      The child process is where your xpcshell test's JS code is t426      The child process is where your xpcshell test's JS code is 
>being run, so it is often--but not always--the process you're int>being run, so it is often--but not always--the process you're int
>erested in.&nbsp; To debug the child, set MOZ_DEBUG_CHILD_PROCESS>erested in. To debug the child, set MOZ_DEBUG_CHILD_PROCESS=1 in 
>=1 in your environment (or on the command line) and run "make che>your environment (or on the command line) and run "make check-one
>ck-one", and you will see the child process emit a printf with it>", and you will see the child process emit a printf with its proc
>s process ID, then sleep.&nbsp; Attach a debugger to the child's >ess ID, then sleep. Attach a debugger to the child's pid, and whe
>pid, and when it wakes up you can debug it: &nbsp;>n it wakes up you can debug it:

Back to History