File: gain_control_tutorial.xml

package info (click to toggle)
postfixadmin 2.3.5-2%2Bdeb7u1
  • links: PTS, VCS
  • area: main
  • in suites: wheezy
  • size: 6,200 kB
  • sloc: php: 25,767; xml: 14,485; perl: 964; sh: 664; python: 169; makefile: 84
file content (215 lines) | stat: -rw-r--r-- 11,794 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
<?xml version="1.0" encoding="ISO-8859-1" ?>
<page title="Prendre le contrle des tests" here="Prendre le contrle des tests">
    <long_title>Tutorial de test unitaire en PHP  - Isoler les variables pendant le test</long_title>
    <content>
        <p>
            Pour tester un module de code vous avez besoin d'avoir un contrle trs prcis sur son environnement. Si quelque chose change dans les coulisses, par exemple dans un fichier de configuration, alors les tests peuvent chouer de faon inattendue. Il ne s'agirait plus d'un test de code sans quivoque et pourrait vous faire perdre des heures prcieuses  la recherche d'erreurs dans un code qui fonctionne. Alors qu'il s'agit d'un problme de configuration qui plante le test en question. Au mieux vos scnarios de test deviennent de plus en plus compliqus afin de prendre en compte toutes les variations possibles.
        </p>
        <p>
            <a class="target" name="temps"><h2>Contrler le temps</h2></a>
        <p>
        </p>
            Il y a souvent beaucoup de variables videntes qui peuvent affecter un scnario de test unitaire, d'autant plus dans un environnement de dveloppement web dans lequel PHP a ses aises. Parmi celles-ci, on trouve les paramtres de connexion  la base de donnes et ceux de configuration, les droits de fichier et les ressources rseau, etc. L'chec ou la mauvaise installation de l'un ou l'autre de ces composants cassera la suite de test. Est-ce que nous devons ajouter des tests pour valider l'installation de ces composants ? C'est une bonne ide mais si vous les placez dans les tests du module de code vous aller commencer  encombrer votre code de test avec des dtails hors de propos avec la tche en cours. Ils doivent tre placs dans leur propre groupe de tests.
        </p>
        <p>
            Par contre un autre problme reste : nos machines de dveloppement doivent aussi avoir tous les composants systme d'installs avant l'excution de la suite de test. Et vos tests s'excuteront plus lentement.
        </p>
        <p>
            Devant un tel dilemme, nous crerons souvent des versions enveloppantes des classes qui grent ces ressources. Les vilains dtails de ces ressources sont ensuite cods une seule fois. J'aime bien appeler ces classes des &quot;classes frontire&quot; tant donn qu'elles existent en bordure de l'application, l'interface entre votre application et le reste du systme. Ces classes frontire sont - dans le meilleur des cas - simules pendant les tests par des versions de simulacre. Elles s'excutent plus rapidement et sont souvent appeles &quot;bouchon serveur [Ndt : Server Stubs]&quot; ou dans leur forme plus gnrique &quot;objet fantaisie [Ndt : Mock Objects]&quot;. Envelopper et bouchonner chacune de ces ressources permet d'conomiser pas mal de temps.
        </p>
        <p>
            Un des facteurs souvent ngligs reste le temps. Par exemple, pour tester l'expiration d'une session des codeurs vont souvent temporairement en caler la dure  une valeur trs courte, disons 2 secondes, et ensuite effectuer un <code>sleep(3)</code> : ils estiment alors que la session a expire. Sauf que cette opration ajoute 3 secondes  la suite de test : il s'agit souvent de beaucoup de code en plus pour rendre la classe de session aussi mallable. Plus simple serait d'avoir un moyen d'avancer l'horloge arbitrairement. De contrler le temps.
        </p>
        <p>
            <a class="target" name="horloge"><h2>Une classe horloge</h2></a>
            Une nouvelle fois, nous allons effectuer notre conception d'une enveloppe d'horloge via l'criture de tests. Premirement nous ajoutons un scnario de test d'horloge dans notre suite de test <em>tests/all_tests.php</em>...
<php><![CDATA[
<?php
    if (! defined('SIMPLE_TEST')) {
        define('SIMPLE_TEST', 'simpletest/');
    }
    require_once(SIMPLE_TEST . 'unit_tester.php');
    require_once(SIMPLE_TEST . 'reporter.php');
    require_once('log_test.php');<strong>
    require_once('clock_test.php');</strong>

    $test = &new GroupTest('All tests');
    $test->addTestCase(new TestOfLogging());<strong>
    $test->addTestCase(new TestOfClock());</strong>
    $test->run(new HtmlReporter());
?>
]]></php>
            Ensuite nous crons le scnario de test dans un nouveau fichier <em>tests/clock_test.php</em>...
<php><![CDATA[
<strong><?php
    require_once('../classes/clock.php');

    class TestOfClock extends UnitTestCase {
        function TestOfClock() {
            $this->UnitTestCase('Clock class test');
        }
        function testClockTellsTime() {
            $clock = new Clock();
            $this->assertEqual($clock->now(), time(), 'Now is the right time');
        }
        function testClockAdvance() {
        }
    }
?></strong>
]]></php>
            Notre unique test pour le moment, c'est que notre nouvelle class <code>Clock</code> se comporte comme un simple substitut de la fonction <code>time()</code> en PHP. L'autre mthode tient lieu d'emploi. C'est notre <em>chose  faire</em> en quelque sorte. Nous ne lui avons pas donne de test parce que a casserait notre rythme. Nous crirons cette fonctionnalit de dcalage dans le temps une fois que nous serons au vert. Pour le moment nous ne sommes videmment pas dans le vert...
            <div class="demo">
                <br />
                <b>Fatal error</b>:  Failed opening required '../classes/clock.php' (include_path='') in
                <b>/home/marcus/projects/lastcraft/tutorial_tests/tests/clock_test.php</b> on line <b>2</b>
                <br />
            </div>
            Nous crons un fichier <em>classes/clock.php</em> comme ceci...
<php><![CDATA[
<strong><?php
    class Clock {
        
        function Clock() {
        }
        
        function now() {
        }
    }
?></strong>
]]></php>
            De la sorte nous reprenons le cours du code.
            <div class="demo">
                <h1>All tests</h1>
                <span class="fail">Fail</span>: Clock class test-&gt;testclocktellstime-&gt;[NULL: ] should be equal to [integer: 1050257362]<br />
                <div style="padding: 8px; margin-top: 1em; background-color: red; color: white;">3/3 test cases complete.
                <strong>4</strong> passes and <strong>1</strong> fails.</div>
            </div>
            Facile  corriger...
<php><![CDATA[
class Clock {
    
    function Clock() {
    }
    
    function now() {<strong>
        return time();</strong>
    }
}
]]></php>
            Et nous revoici dans le vert...
            <div class="demo">
                <h1>All tests</h1>
                <div style="padding: 8px; margin-top: 1em; background-color: green; color: white;">3/3 test cases complete.
                <strong>5</strong> passes and <strong>0</strong> fails.</div>
            </div>
            Il y a juste un petit problme. L'horloge pourrait basculer pendant l'assertion et crer un cart d'une seconde. Les probabilits sont assez faibles mais s'il devait y avoir beaucoup de tests de chronomtrage nous finirions avec une suite de test qui serait erratique et forcment presque inutile. Nous nous <a href="subclass_tutorial.php">y attaquerons bientt</a> et pour l'instant nous l'ajoutons dans la liste des &quot;choses  faire&quot;.
        </p>
        <p>
            Le test d'avancement ressemble ...
<php><![CDATA[
class TestOfClock extends UnitTestCase {
    function TestOfClock() {
        $this->UnitTestCase('Clock class test');
    }
    function testClockTellsTime() {
        $clock = new Clock();
        $this->assertEqual($clock->now(), time(), 'Now is the right time');
    }<strong>
    function testClockAdvance() {
        $clock = new Clock();
        $clock->advance(10);
        $this->assertEqual($clock->now(), time() + 10, 'Advancement');
    }</strong>
}
]]></php>
            Le code pour arriver au vert est direct : il suffit d'ajouter un dcalage de temps.
<php><![CDATA[
class Clock {<strong>
    var $_offset;</strong>
    
    function Clock() {<strong>
        $this->_offset = 0;</strong>
    }
    
    function now() {
        return time()<strong> + $this->_offset</strong>;
    }
    <strong>
    function advance($offset) {
        $this->_offset += $offset;
    }</strong>
}
]]></php>
        </p>
        <p>
            <a class="target" name="nettoyer"><h2>Nettoyer le test de groupe</h2></a>
            Notre fichier <em>all_tests.php</em> contient des rptitions dont nous pourrions nous dbarrasser. Nous devons ajouter manuellement tous nos scnarios de test depuis chaque fichier inclus. C'est possible de les enlever mais avec les prcautions suivantes. La classe <code>GroupTest</code> inclue une mthode bien pratique appele <code>addTestFile()</code> qui prend un fichier PHP comme paramtre. Ce mcanisme prend note de toutes les classes : elle inclut le fichier et ensuite regarde toutes les classes nouvellement cres. S'il y a des filles de <code>TestCase</code> elles sont ajoutes au nouveau test de groupe.
        </p>
        <p>
            Voici notre suite de test remanie en appliquant cette mthode...
<php><![CDATA[
<?php
    if (! defined('SIMPLE_TEST')) {
        define('SIMPLE_TEST', 'simpletest/');
    }<strong>
    require_once(SIMPLE_TEST . 'unit_tester.php');
    require_once(SIMPLE_TEST . 'reporter.php');</strong>

    $test = &new GroupTest('All tests');<strong>
    $test->addTestFile('log_test.php');
    $test->addTestFile('clock_test.php');</strong>
    $test->run(new HtmlReporter());
?>
]]></php>
            Les inconvniants sont les suivants...
            <ol>
                <li>
                    Si le fichier de test a dj t inclus, aucune nouvelle classe ne sera ajoute au groupe.
                </li>
                <li>
                    Si le fichier de test contient d'autres classes relies  <code>TestCase</code> alors celles-ci aussi seront ajout au test de groupe.
                </li>
            </ol>
            Dans nos test nous n'avons que des scnarios dans les fichiers de test et en plus nous avons supprim leur inclusion du script <em>all_tests.php</em> : nous sommes donc en rgle. C'est la situation la plus commune.
        </p>
        <p>
            Nous devrions corriger au plus vite le petit problme de dcalage possible sur l'horloge : c'est ce que nous <a href="subclass_tutorial.php">faisons ensuite</a>.
        </p>
    </content>
    <internal>
        <link>Le <a href="#temps">temps</a> est souvent une variable nglige dans les tests.</link>
        <link>Une <a href="#horloge">classe horloge</a> nous permet de modifier le temps.</link>
        <link><a href="#nettoyer">Nettoyer le test de groupe</a>.</link>
    </internal>
    <external>
        <link>
            La section prcdente : <a href="group_test_tutorial.php">grouper des tests unitaires</a>.
        </link>
        <link>
            La section suivante : <a href="subclass_tutorial.php">sous classer les scnarios de test</a>.
        </link>
        <link>
            Vous aurez besoin du <a href="simple_test.php">testeur unitaire SimpleTest</a> pour les exemples.
        </link>
    </external>
    <meta>
        <keywords>
            dveloppement logiciel,
            programmation php,
            outils de dveloppement logiciel,
            tutorial php,
            scripts php gratuits,
            organisation de tests unitaires,
            conseil de test,
            astuce de dveloppement,
            architecture logicielle pour des tests,
            exemple de code php,
            objets fantaisie,
            junit,
            test php,
            outil de test unitaire,
            suite de test php
        </keywords>
    </meta>
</page>