58 lines
18 KiB
HTML
58 lines
18 KiB
HTML
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
|
|
<html><head><meta http-equiv="content-type" content="text-html; charset=utf-8" /><title>2 The Philosophy of SchemeUnit</title><link rel="stylesheet" type="text/css" href="scribble.css" title="default" /><script type="text/javascript" src="scribble-common.js"></script></head><body id="scribble-plt-scheme-org"><div class="tocset"><div class="tocview"><div class="tocviewlist" style="margin-bottom: 1em;"><div class="tocviewtitle"><table cellspacing="0" cellpadding="0"><tr><td style="width: 1em;"><a href="javascript:void(0);" title="Expand/Collapse" class="tocviewtoggle" onclick="TocviewToggle(this,"tocview_0");">▼</a></td><td></td><td><a href="index.html" class="tocviewlink"><b>Scheme<span class="mywbr"> </span>Unit</b>:<span class="mywbr"> </span> Unit Testing for Scheme</a></td></tr></table></div><div class="tocviewsublisttop" style="display: block;" id="tocview_0"><table cellspacing="0" cellpadding="0"><tr><td align="right">1 </td><td><a href="quick-start.html" class="tocviewlink">Quick Start Guide for Scheme<span class="mywbr"> </span>Unit</a></td></tr><tr><td align="right">2 </td><td><a href="philosophy.html" class="tocviewselflink">The Philosophy of Scheme<span class="mywbr"> </span>Unit</a></td></tr><tr><td align="right">3 </td><td><a href="api.html" class="tocviewlink">Scheme<span class="mywbr"> </span>Unit API</a></td></tr><tr><td align="right">4 </td><td><a href="Release_Notes.html" class="tocviewlink">Release Notes</a></td></tr><tr><td align="right">5 </td><td><a href="Acknowlegements.html" class="tocviewlink">Acknowlegements</a></td></tr><tr><td align="right"></td><td><a href="doc-index.html" class="tocviewlink">Index</a></td></tr></table></div></div><div class="tocviewlist"><table cellspacing="0" cellpadding="0"><tr><td style="width: 1em;"><a href="javascript:void(0);" title="Expand/Collapse" class="tocviewtoggle" onclick="TocviewToggle(this,"tocview_1");">►</a></td><td>2 </td><td><a href="philosophy.html" class="tocviewselflink">The Philosophy of Scheme<span class="mywbr"> </span>Unit</a></td></tr></table><div class="tocviewsublistbottom" style="display: none;" id="tocview_1"><table cellspacing="0" cellpadding="0"><tr><td align="right">2.1 </td><td><a href="philosophy.html#(part._.Historical_.Context)" class="tocviewlink">Historical Context</a></td></tr></table></div></div></div><div class="tocsub"><div class="tocsubtitle">On this page:</div><table class="tocsublist" cellspacing="0"><tr><td><span class="tocsublinknumber">2.1<tt> </tt></span><a href="#(part._.Historical_.Context)" class="tocsubseclink">Historical Context</a></td></tr></table></div></div><div class="maincolumn"><div class="main"><div class="versionbox"><span class="version">Version: 4.1.5.3</span></div><div class="navsettop"><span class="navleft"> </span><span class="navright"><a href="quick-start.html" title="backward to "1 Quick Start Guide for SchemeUnit"">← prev</a> <a href="index.html" title="up to "SchemeUnit: Unit Testing for Scheme"">up</a> <a href="api.html" title="forward to "3 SchemeUnit API"">next →</a></span> </div><h3>2<tt> </tt><a name="(part._philosophy)"></a>The Philosophy of SchemeUnit</h3><p>SchemeUnit is designed to allow tests to evolve in step with
|
|
the evolution of the program under testing. SchemeUnit
|
|
scales from the unstructed checks suitable for simple
|
|
programs to the complex structure necessary for large
|
|
projects.</p><p>Simple programs, such as those in How to Design Programs,
|
|
are generally purely functional with no setup required to
|
|
obtain a context in which the function may operate.
|
|
Therefore the tests for these programs are extremely simple:
|
|
the test expressions are single checks, usually for
|
|
equality, and there are no dependencies between expressions.
|
|
For example, a HtDP student may be writing simple list
|
|
functions such as length, and the properties they are
|
|
checking are of the form:</p><p><table cellspacing="0" class="schemeblock"><tr><td><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZGVmIGMgKGMgKGMgcXVvdGUgYyAjJWtlcm5lbCkgYyBl%0D%0AcXVhbD8pKSk%3D%0D%0A" class="schemevaluelink">equal?</a></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZGVmIGMgKGMgKGMgcXVvdGUgYyAjJWtlcm5lbCkgYyBs%0D%0AZW5ndGgpKSk%3D%0D%0A" class="schemevaluelink">length</a></span><span class="hspace"> </span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZGVmIGMgKGMgKGMgcXVvdGUgYyAjJWtlcm5lbCkgYyBu%0D%0AdWxsKSkp%0D%0A" class="schemevaluelink">null</a></span><span class="schemeparen">)</span><span class="hspace"> </span><span class="schemevalue">0</span><span class="schemeparen">)</span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="schemeparen">(</span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZGVmIGMgKGMgKGMgcXVvdGUgYyAjJWtlcm5lbCkgYyBl%0D%0AcXVhbD8pKSk%3D%0D%0A" class="schemevaluelink">equal?</a></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZGVmIGMgKGMgKGMgcXVvdGUgYyAjJWtlcm5lbCkgYyBs%0D%0AZW5ndGgpKSk%3D%0D%0A" class="schemevaluelink">length</a></span><span class="hspace"> </span><span class="schemevalue">'</span><span class="schemevalue">(</span><span class="schemevalue">a</span><span class="schemevalue">)</span><span class="schemeparen">)</span><span class="hspace"> </span><span class="schemevalue">1</span><span class="schemeparen">)</span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="schemeparen">(</span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZGVmIGMgKGMgKGMgcXVvdGUgYyAjJWtlcm5lbCkgYyBl%0D%0AcXVhbD8pKSk%3D%0D%0A" class="schemevaluelink">equal?</a></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZGVmIGMgKGMgKGMgcXVvdGUgYyAjJWtlcm5lbCkgYyBs%0D%0AZW5ndGgpKSk%3D%0D%0A" class="schemevaluelink">length</a></span><span class="hspace"> </span><span class="schemevalue">'</span><span class="schemevalue">(</span><span class="schemevalue">a</span><span class="hspace"> </span><span class="schemevalue">b</span><span class="schemevalue">)</span><span class="schemeparen">)</span><span class="hspace"> </span><span class="schemevalue">2</span><span class="schemeparen">)</span></td></tr></table></p><p>SchemeUnit directly supports this style of testing. A check
|
|
on its own is a valid test. So the above examples may be
|
|
written in SchemeUnit as:</p><p><table cellspacing="0" class="schemeblock"><tr><td><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">check-equal?</span></span></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZGVmIGMgKGMgKGMgcXVvdGUgYyAjJWtlcm5lbCkgYyBs%0D%0AZW5ndGgpKSk%3D%0D%0A" class="schemevaluelink">length</a></span><span class="hspace"> </span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZGVmIGMgKGMgKGMgcXVvdGUgYyAjJWtlcm5lbCkgYyBu%0D%0AdWxsKSkp%0D%0A" class="schemevaluelink">null</a></span><span class="schemeparen">)</span><span class="hspace"> </span><span class="schemevalue">0</span><span class="schemeparen">)</span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="schemeparen">(</span><span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">check-equal?</span></span></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZGVmIGMgKGMgKGMgcXVvdGUgYyAjJWtlcm5lbCkgYyBs%0D%0AZW5ndGgpKSk%3D%0D%0A" class="schemevaluelink">length</a></span><span class="hspace"> </span><span class="schemevalue">'</span><span class="schemevalue">(</span><span class="schemevalue">a</span><span class="schemevalue">)</span><span class="schemeparen">)</span><span class="hspace"> </span><span class="schemevalue">1</span><span class="schemeparen">)</span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="schemeparen">(</span><span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">check-equal?</span></span></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZGVmIGMgKGMgKGMgcXVvdGUgYyAjJWtlcm5lbCkgYyBs%0D%0AZW5ndGgpKSk%3D%0D%0A" class="schemevaluelink">length</a></span><span class="hspace"> </span><span class="schemevalue">'</span><span class="schemevalue">(</span><span class="schemevalue">a</span><span class="hspace"> </span><span class="schemevalue">b</span><span class="schemevalue">)</span><span class="schemeparen">)</span><span class="hspace"> </span><span class="schemevalue">2</span><span class="schemeparen">)</span></td></tr></table></p><p>Simple programs now get all the benefits of SchemeUnit with
|
|
very little overhead.</p><p>There are limitations to this style of testing that more
|
|
complex programs will expose. For example, there might be
|
|
dependencies between expressions, caused by state, so that
|
|
it does not make sense to evaluate some expressions if
|
|
earlier ones have failed. This type of program needs a way
|
|
to group expressions so that a failure in one group causes
|
|
evaluation of that group to stop and immediately proceed to
|
|
the next group. In SchemeUnit all that is required is to
|
|
wrap a <span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">test-begin</span></span></span> expression around a group of
|
|
expressions:</p><p><table cellspacing="0" class="schemeblock"><tr><td><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">test-begin</span></span></span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol">setup-some-state!</span><span class="schemeparen">)</span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">check-equal?</span></span></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol">foo!</span><span class="hspace"> </span><span class="schemevalue">1</span><span class="schemeparen">)</span><span class="hspace"> </span><span class="schemevalue">'</span><span class="schemevalue">expected-value-1</span><span class="schemeparen">)</span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">check-equal?</span></span></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol">foo!</span><span class="hspace"> </span><span class="schemevalue">2</span><span class="schemeparen">)</span><span class="hspace"> </span><span class="schemevalue">'</span><span class="schemevalue">expected-value-2</span><span class="schemeparen">)</span><span class="schemeparen">)</span></td></tr></table></p><p>Now if any expression within the <span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">test-begin</span></span></span>
|
|
expression fails no further expressions in that group will
|
|
be evaluated.</p><p>Notice that all the previous tests written in the simple
|
|
style are still valid. Introducing grouping is a local
|
|
change only. This is a key feature of SchemeUnit’s support
|
|
for the evolution of the program.</p><p>The programmer may wish to name a group of tests. This is
|
|
done using the <span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">test-case</span></span></span> expression, a simple
|
|
variant on test-begin:</p><p><table cellspacing="0" class="schemeblock"><tr><td><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">test-case</span></span></span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="hspace"> </span><span class="schemevalue">"The name"</span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="hspace"> </span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZm9ybSBjIChjIChjIGxpYiBjICh1IC4gc2NoZW1lL3By%0D%0AaXZhdGUvc3R4Y2FzZS1zY2hlbWUuc3MpKSBjIC4uLikpKQ%3D%3D%0D%0A" class="schemesyntaxlink">...</a></span><span class="hspace"> </span><span class="schemesymbol">test</span><span class="hspace"> </span><span class="schemesymbol">expressions</span><span class="hspace"> </span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZm9ybSBjIChjIChjIGxpYiBjICh1IC4gc2NoZW1lL3By%0D%0AaXZhdGUvc3R4Y2FzZS1zY2hlbWUuc3MpKSBjIC4uLikpKQ%3D%3D%0D%0A" class="schemesyntaxlink">...</a></span><span class="schemeparen">)</span></td></tr></table></p><p>Most programs will stick with this style. However,
|
|
programmers writing very complex programs may wish to
|
|
maintain separate groups of tests for different parts of the
|
|
program, or run their tests in different ways to the normal
|
|
SchemeUnit manner (for example, test results may be logged
|
|
for the purpose of improving software quality, or they may
|
|
be displayed on a website to indicate service quality). For
|
|
these programmers it is necessary to delay the execution of
|
|
tests so they can processed in the programmer’s chosen
|
|
manner. To do this, the programmer simply wraps a test-suite
|
|
around their tests:</p><p><table cellspacing="0" class="schemeblock"><tr><td><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">test-suite</span></span></span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="hspace"> </span><span class="schemevalue">"Suite name"</span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">check</span></span></span><span class="hspace"> </span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZm9ybSBjIChjIChjIGxpYiBjICh1IC4gc2NoZW1lL3By%0D%0AaXZhdGUvc3R4Y2FzZS1zY2hlbWUuc3MpKSBjIC4uLikpKQ%3D%3D%0D%0A" class="schemesyntaxlink">...</a></span><span class="schemeparen">)</span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">test-begin</span></span></span><span class="hspace"> </span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZm9ybSBjIChjIChjIGxpYiBjICh1IC4gc2NoZW1lL3By%0D%0AaXZhdGUvc3R4Y2FzZS1zY2hlbWUuc3MpKSBjIC4uLikpKQ%3D%3D%0D%0A" class="schemesyntaxlink">...</a></span><span class="schemeparen">)</span></td></tr><tr><td><span class="schemeplain"><span class="hspace"> </span></span><span class="hspace"> </span><span class="schemeparen">(</span><span class="schemesymbol"><span class="badlink"><span class="schemevaluelink">test-case</span></span></span><span class="hspace"> </span><span class="schemesymbol"><a href="/servlets/doc-search.ss?tag=KCgxKSAwICgpIDAgKCkgKCkgKGMgZm9ybSBjIChjIChjIGxpYiBjICh1IC4gc2NoZW1lL3By%0D%0AaXZhdGUvc3R4Y2FzZS1zY2hlbWUuc3MpKSBjIC4uLikpKQ%3D%3D%0D%0A" class="schemesyntaxlink">...</a></span><span class="schemeparen">)</span><span class="schemeparen">)</span></td></tr></table></p><p>The tests now change from expressions that are immediately
|
|
evaluated to objects that may be programmatically
|
|
manipulated. Note again this is a local change. Tests
|
|
outside the suite continue to evaluate as before.</p><h4>2.1<tt> </tt><a name="(part._.Historical_.Context)"></a>Historical Context</h4><p>Most testing frameworks, including earlier versions of
|
|
SchemeUnit, support only the final form of testing. This is
|
|
likely due to the influence of the SUnit testing framework,
|
|
which is the ancestor of SchemeUnit and the most widely used
|
|
frameworks in Java, .Net, Python, and Ruby, and many other
|
|
languages. That this is insufficient for all users is
|
|
apparent if one considers the proliferation of "simpler"
|
|
testing frameworks in Scheme such as SRFI-78, or the the
|
|
practice of beginner programmers. Unfortunately these
|
|
simpler methods are inadequate for testing larger
|
|
systems. To the best of my knowledge SchemeUnit is the only
|
|
testing framework that makes a conscious effort to support
|
|
the testing style of all levels of programmer.</p><div class="navsetbottom"><span class="navleft"> </span><span class="navright"><a href="quick-start.html" title="backward to "1 Quick Start Guide for SchemeUnit"">← prev</a> <a href="index.html" title="up to "SchemeUnit: Unit Testing for Scheme"">up</a> <a href="api.html" title="forward to "3 SchemeUnit API"">next →</a></span> </div></div></div></body></html> |