File: quickstart-create-model.xml

package info (click to toggle)
zendframework 1.12.9%2Bdfsg-2
  • links: PTS, VCS
  • area: main
  • in suites: jessie-kfreebsd
  • size: 133,584 kB
  • sloc: xml: 1,311,829; php: 570,173; sh: 170; makefile: 125; sql: 121
file content (753 lines) | stat: -rw-r--r-- 25,787 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
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
<?xml version="1.0" encoding="UTF-8"?>
<!-- EN-Revision: 24249 -->
<!-- Reviewed: no -->
<sect1 id="learning.quickstart.create-model">
    <title>Créer un modèle et une table en base de données</title>

    <para>
        Avant de démarrer, considérons ceci: où vont se trouver ces classes et comment les retrouver?
        Le projet par défaut que nous avons conçu instancie un autoloader. Nous pouvons lui attacher
        d'autres autoloaders pour qu'il puisse trouver des classes différentes. Typiquement nous
        voulons que nos classes MVC soient groupées sous une même arborescence -- dans ce cas,
        <filename>application/</filename> -- et nous utiliserons un préfixe commun.
    </para>

    <para>
        <classname>Zend_Controller_Front</classname> a une notion de "modules", qui sont des
        mini-applications individuelles. Les modules reflètent la structure de répertoires que la
        commande <command>zf</command> crée sous <filename>application/</filename>, et toutes les
        classes à l'intérieur sont supposées commencer par un préfixe étant le nom du module.
        <filename>application/</filename> est lui-même un module -- le module "default" ou
        "application". Ainsi, nous allons vouloir configurer un autoload pour les ressources sous
        ce dossier.
    </para>

    <para>
        <classname>Zend_Application_Module_Autoloader</classname> propose la fonctionnalité nécessaire
        à la correspondance entre les ressources d'un module et ses dossiers, il propose pour cela
        un mécanisme de nommage standard. Une instance de la classe est créee par défaut pendant
        l'initialisation de l'objet de bootstrap et utilisera le préfixe de module "Application".
        De ce fait, nos classes de modèles, formulaires, et tables commenceront toutes par le préfixe
        de classe "Application_".
    </para>

   <para>
        Maintenant voyons de quoi est fait un livre d'or. Typiquement il existe simplement une liste
        d'entrées avec un <emphasis>commentaire</emphasis>, <emphasis>timestamp</emphasis>, et souvent
        une <emphasis>adresse email</emphasis>. En supposant que nous stockons cela dans une base de
        données, nous aurons aussi besoin d'un <emphasis>identifiant unique</emphasis> pour chaque
        entrée. Nous voudrons aussi sauvegarder une entrée, récupérer une entrée individuelle ou encore
        récupérer toutes les entrées. De ce fait, l'<acronym>API</acronym> du modèle d'un simple livre
        d'or ressemblerait à ceci:
    </para>

    <programlisting language="php"><![CDATA[
// application/models/Guestbook.php

class Application_Model_Guestbook
{
    protected $_comment;
    protected $_created;
    protected $_email;
    protected $_id;

    public function __set($name, $value);
    public function __get($name);

    public function setComment($text);
    public function getComment();

    public function setEmail($email);
    public function getEmail();

    public function setCreated($ts);
    public function getCreated();

    public function setId($id);
    public function getId();
}

class Application_Model_GuestbookMapper
{
    public function save(Application_Model_Guestbook $guestbook);
    public function find($id);
    public function fetchAll();
}
]]></programlisting>

    <para>
        <methodname>__get()</methodname> et <methodname>__set()</methodname> nous simpliferons l'accès
        aux attributs et proxieront vers les autres getters et setters. Ils nous permettront de même
        de nous assurer que seuls les attributs que nous avons définis seront accessibles dans l'objet.
    </para>

    <para>
        <methodname>find()</methodname> et <methodname>fetchAll()</methodname> permettent de récupérer
        une seule entrée ou toutes les entrées alors que <methodname>save()</methodname> offrira la
        possibilité de stocker une entrée dans le support de stockage.
    </para>

    <para>
        Maintenant à partir de là, nous pouvons commecer à penser en terme de base de données.
    </para>

    <para>
        Nous devons d'abord intialiser une ressource <classname>Db</classname>. Comme pour les
        ressources <classname>Layout</classname> et <classname>View</classname>, nous pouvons utiliser
        de la configuration pour <classname>Db</classname>. Cela est possible au moyen de la commande
        <command>zf configure db-adapter</command>:
    </para>

    <programlisting language="shell"><![CDATA[
% zf configure db-adapter \
> 'adapter=PDO_SQLITE&dbname=APPLICATION_PATH "/../data/db/guestbook.db"' \
> production
A db configuration for the production has been written to the application config file.

% zf configure db-adapter \
> 'adapter=PDO_SQLITE&dbname=APPLICATION_PATH "/../data/db/guestbook-testing.db"' \
> testing
A db configuration for the production has been written to the application config file.

% zf configure db-adapter \
> 'adapter=PDO_SQLITE&dbname=APPLICATION_PATH "/../data/db/guestbook-dev.db"' \
> development
A db configuration for the production has been written to the application config file.
]]></programlisting>

    <para>
        Editez maintenant le fichier <filename>application/configs/application.ini</filename>, vous
        verrez que les lignes suivantes ont été ajoutées dans les sections appropriées:
    </para>

    <programlisting language="ini"><![CDATA[
; application/configs/application.ini

[production]
; ...
resources.db.adapter = "PDO_SQLITE"
resources.db.params.dbname = APPLICATION_PATH "/../data/db/guestbook.db"

[testing : production]
; ...
resources.db.adapter = "PDO_SQLITE"
resources.db.params.dbname = APPLICATION_PATH "/../data/db/guestbook-testing.db"

[development : production]
; ...
resources.db.adapter = "PDO_SQLITE"
resources.db.params.dbname = APPLICATION_PATH "/../data/db/guestbook-dev.db"
]]></programlisting>

    <para>
        Votre fichier de configuration final devrait ressembler à ceci:
    </para>

    <programlisting language="ini"><![CDATA[
; application/configs/application.ini

[production]
phpSettings.display_startup_errors = 0
phpSettings.display_errors = 0
bootstrap.path = APPLICATION_PATH "/Bootstrap.php"
bootstrap.class = "Bootstrap"
appnamespace = "Application"
resources.frontController.controllerDirectory = APPLICATION_PATH "/controllers"
resources.frontController.params.displayExceptions = 0
resources.layout.layoutPath = APPLICATION_PATH "/layouts/scripts"
resources.view[] =
resources.db.adapter = "PDO_SQLITE"
resources.db.params.dbname = APPLICATION_PATH "/../data/db/guestbook.db"

[staging : production]

[testing : production]
phpSettings.display_startup_errors = 1
phpSettings.display_errors = 1
resources.db.adapter = "PDO_SQLITE"
resources.db.params.dbname = APPLICATION_PATH "/../data/db/guestbook-testing.db"

[development : production]
phpSettings.display_startup_errors = 1
phpSettings.display_errors = 1
resources.db.adapter = "PDO_SQLITE"
resources.db.params.dbname = APPLICATION_PATH "/../data/db/guestbook-dev.db"
]]></programlisting>

    <para>
        Notez que la/les base(s) de données seront stockées sous <filename>data/db/</filename>. Créez ces dossiers
        et affectez leur les bons droits. Sur les systèmes Unix utilisez:
    </para>

    <programlisting language="shell"><![CDATA[
% mkdir -p data/db; chmod -R a+rwX data
]]></programlisting>

    <para>
        Sur Windows, vous devrez créer le dossier avec l'explorateur et lui donner les bonnes permissions pour que
        tout le monde puisse y écrire.
    </para>

    <para>
        Dès lors, nous possédons une connexion à une base de données, dans notre cas il s'agit de Sqlite et la base
        est placée sous le dossier <filename>application/data/</filename>. Créons maintenant une table pour
        stocker nos entrées de livre d'or.
    </para>

    <programlisting language="sql"><![CDATA[
-- scripts/schema.sqlite.sql
--
-- You will need load your database schema with this SQL.

CREATE TABLE guestbook (
    id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
    email VARCHAR(32) NOT NULL DEFAULT 'noemail@test.com',
    comment TEXT NULL,
    created DATETIME NOT NULL
);

CREATE INDEX "id" ON "guestbook" ("id");
]]></programlisting>

    <para>
        Puis pour ne pas travailler dans le vide, créons quelques enregistrements de départ.
    </para>

    <programlisting language="sql"><![CDATA[
-- scripts/data.sqlite.sql
--
-- You can begin populating the database with the following SQL statements.

INSERT INTO guestbook (email, comment, created) VALUES
    ('ralph.schindler@zend.com',
    'Hello! Hope you enjoy this sample zf application!',
    DATETIME('NOW'));
INSERT INTO guestbook (email, comment, created) VALUES
    ('foo@bar.com',
    'Baz baz baz, baz baz Baz baz baz - baz baz baz.',
    DATETIME('NOW'));
]]></programlisting>

    <para>
        Maintenant que nous avons la définition de la base de données ainsi que des données, créons un
        script qui pourra être lancé pour entièrement initialiser la base de données de manière
        autonomme. Bien sûr cela ne sera pas nécessaire en production. Créez le script
        <filename>scripts/load.sqlite.php</filename> avec le contenu suivant:
    </para>

    <programlisting language="php"><![CDATA[
// scripts/load.sqlite.php

/**
 * Script pour créer et charger la base
 */

// Initialise le chemin vers l'application et l'autoload
defined('APPLICATION_PATH')
    || define('APPLICATION_PATH', realpath(dirname(__FILE__) . '/../application'));
set_include_path(implode(PATH_SEPARATOR, array(
    APPLICATION_PATH . '/../library',
    get_include_path(),
)));
require_once 'Zend/Loader/Autoloader.php';
Zend_Loader_Autoloader::getInstance();

// Definit des options CLI
$getopt = new Zend_Console_Getopt(array(
    'withdata|w' => 'Load database with sample data',
    'env|e-s'    => 'Application environment for which to create database (defaults to development)',
    'help|h'     => 'Help -- usage message',
));
try {
    $getopt->parse();
} catch (Zend_Console_Getopt_Exception $e) {
    // Mauvaises options passées: afficher l'aide
    echo $e->getUsageMessage();
    return false;
}

// Si l'aid eest demandée, l'afficher
if ($getopt->getOption('h')) {
    echo $getopt->getUsageMessage();
    return true;
}

// Initialise des valeurs selon la présence ou absence d'options CLI
$withData = $getopt->getOption('w');
$env      = $getopt->getOption('e');
defined('APPLICATION_ENV')
    || define('APPLICATION_ENV', (null === $env) ? 'development' : $env);

// Initialise Zend_Application
$application = new Zend_Application(
    APPLICATION_ENV,
    APPLICATION_PATH . '/configs/application.ini'
);

// Initialise et récupère la ressoucre DB
$bootstrap = $application->getBootstrap();
$bootstrap->bootstrap('db');
$dbAdapter = $bootstrap->getResource('db');

// Informons l'utilisateur de ce qui se passe (nous créons une base de données
// ici)
if ('testing' != APPLICATION_ENV) {
    echo 'Writing Database Guestbook in (control-c to cancel): ' . PHP_EOL;
    for ($x = 5; $x > 0; $x--) {
        echo $x . "\r"; sleep(1);
    }
}

// Vérifions si un fichier pour la base existe déja
$options = $bootstrap->getOption('resources');
$dbFile  = $options['db']['params']['dbname'];
if (file_exists($dbFile)) {
    unlink($dbFile);
}

// Chargement du fichier de la base de données.
try {
    $schemaSql = file_get_contents(dirname(__FILE__) . '/schema.sqlite.sql');
    // utilise la connexion directement pour charger le sql
    $dbAdapter->getConnection()->exec($schemaSql);
    chmod($dbFile, 0666);

    if ('testing' != APPLICATION_ENV) {
        echo PHP_EOL;
        echo 'Database Created';
        echo PHP_EOL;
    }

    if ($withData) {
        $dataSql = file_get_contents(dirname(__FILE__) . '/data.sqlite.sql');
        // utilise la connexion directement pour charger le sql
        $dbAdapter->getConnection()->exec($dataSql);
        if ('testing' != APPLICATION_ENV) {
            echo 'Data Loaded.';
            echo PHP_EOL;
        }
    }

} catch (Exception $e) {
    echo 'AN ERROR HAS OCCURED:' . PHP_EOL;
    echo $e->getMessage() . PHP_EOL;
    return false;
}

// Ce script sera lancé depuis la ligne de commandes
return true;
]]></programlisting>

    <para>
        Exécutons ce script. Depuis un terminal ou un invite DOS, effectuez:
    </para>

    <programlisting language="shell"><![CDATA[
% php scripts/load.sqlite.php --withdata
]]></programlisting>

    <para>
        Vous devriez voir ceci:
    </para>

    <programlisting language="text"><![CDATA[
path/to/ZendFrameworkQuickstart/scripts$ php load.sqlite.php --withdata
Writing Database Guestbook in (control-c to cancel):
1
Database Created
Data Loaded.
]]></programlisting>

    <para>
        Nous avons maintenant une base de données et une table pour notre application de livre d'or.
        Les prochaines étapes seront de créer le code applicatif. Ceci incluera une source de données
        (dans notre cas nous utiliserons <classname>Zend_Db_Table</classname>), un datamapper pour
        connecter cette source à notre modèle et enfin un contrôleur pour intéragir avec le modèle
        et afficher du contenu divers.
    </para>

    <para>
        Nous allons utiliser un <ulink url="http://martinfowler.com/eaaCatalog/tableDataGateway.html">Table
        Data Gateway</ulink> pour se connecter à notre source de données; <classname>Zend_Db_Table</classname>
        propose cette fonctionnalité. Créons les classes basées sur <classname>Zend_Db_Table</classname>.
        Comme nous avons opéré pour les layouts ou la base, nous pouvons utiliser la commande
        <command>zf</command> pour nous aider, avec la commande complète
        <command>create db-table</command>. Celle-ci prend deux arguments au minimum, le nom de la classe à
        créer et la table qui y fera référence.
    </para>

    <programlisting language="shell"><![CDATA[
% zf create db-table Guestbook guestbook
Creating a DbTable at application/models/DbTable/Guestbook.php
Updating project profile 'zfproject.xml'
]]></programlisting>

    <para>
        En regardant l'orborescence du projet, un nouveau dossier
        <filename>application/models/DbTable/</filename> a été crée contenant le fichier
        <filename>Guestbook.php</filename>. Si vous ouvrez ce fichier, vous y verrez le contenu suivant:
    </para>

    <programlisting language="php"><![CDATA[
// application/models/DbTable/Guestbook.php

/**
 * This is the DbTable class for the guestbook table.
 */
class Application_Model_DbTable_Guestbook extends Zend_Db_Table_Abstract
{
    /** Table name */
    protected $_name    = 'guestbook';
}
]]></programlisting>

    <para>
        Notez le préfixe de classe: <classname>Application_Model_DbTable</classname>. Le premier segment
        est "Application", le nom du module, puis vient le nom du composant "Model_DbTable" qui est lié
        au dossier <filename>models/DbTable/</filename> du module.
    </para>

    <para>
        Pour étendre <classname>Zend_Db_Table</classname>, seuls un nom de table et éventuellement un
        nom de clé primaire (si ce n'est pas "id") sont nécessaires.
    </para>

    <para>
        Créons maintenant un <ulink url="http://martinfowler.com/eaaCatalog/dataMapper.html">Data
            Mapper</ulink>. Un <emphasis>Data Mapper</emphasis> fait correspondre un objet métier à la
        base de données. Dans notre cas <classname>Application_Model_Guestbook</classname> vers la
        source de données <classname>Application_Model_DbTable_Guestbook</classname>. Une
        <acronym>API</acronym> typique pour un data mapper est:
    </para>

    <programlisting language="php"><![CDATA[
// application/models/GuestbookMapper.php

class Application_Model_GuestbookMapper
{
    public function save($model);
    public function find($id, $model);
    public function fetchAll();
}
]]></programlisting>

    <para>
        En plus de ces méthodes nous allons ajouter des méthodes pour affecter/récupérer l'objet
        Table Data Gateway. Pour créer la classe initiale, utilsez l'outil CLI
        <command>zf</command>:
    </para>

    <programlisting language="shell"><![CDATA[
% zf create model GuestbookMapper
Creating a model at application/models/GuestbookMapper.php
Updating project profile '.zfproject.xml'
]]></programlisting>

    <para>
        Maintenant, éditez la classe <classname>Application_Model_GuestbookMapper</classname> dans
        <filename>application/models/GuestbookMapper.php</filename> pour y voir ceci:
    </para>

    <programlisting language="php"><![CDATA[
// application/models/GuestbookMapper.php

class Application_Model_GuestbookMapper
{
    protected $_dbTable;

    public function setDbTable($dbTable)
    {
        if (is_string($dbTable)) {
            $dbTable = new $dbTable();
        }
        if (!$dbTable instanceof Zend_Db_Table_Abstract) {
            throw new Exception('Invalid table data gateway provided');
        }
        $this->_dbTable = $dbTable;
        return $this;
    }

    public function getDbTable()
    {
        if (null === $this->_dbTable) {
            $this->setDbTable('Application_Model_DbTable_Guestbook');
        }
        return $this->_dbTable;
    }

    public function save(Application_Model_Guestbook $guestbook)
    {
        $data = array(
            'email'   => $guestbook->getEmail(),
            'comment' => $guestbook->getComment(),
            'created' => date('Y-m-d H:i:s'),
        );

        if (null === ($id = $guestbook->getId())) {
            unset($data['id']);
            $this->getDbTable()->insert($data);
        } else {
            $this->getDbTable()->update($data, array('id = ?' => $id));
        }
    }

    public function find($id, Application_Model_Guestbook $guestbook)
    {
        $result = $this->getDbTable()->find($id);
        if (0 == count($result)) {
            return;
        }
        $row = $result->current();
        $guestbook->setId($row->id)
                  ->setEmail($row->email)
                  ->setComment($row->comment)
                  ->setCreated($row->created);
    }

    public function fetchAll()
    {
        $resultSet = $this->getDbTable()->fetchAll();
        $entries   = array();
        foreach ($resultSet as $row) {
            $entry = new Application_Model_Guestbook();
            $entry->setId($row->id)
                  ->setEmail($row->email)
                  ->setComment($row->comment)
                  ->setCreated($row->created);
            $entries[] = $entry;
        }
        return $entries;
    }
}
]]></programlisting>

    <para>
        Maintenant il faut créer la classe de modèle. Une fois de plus, nous utiliserons la commande
        <command>zf create model</command>:
    </para>

    <programlisting language="shell"><![CDATA[
% zf create model Guestbook
Creating a model at application/models/Guestbook.php
Updating project profile '.zfproject.xml'
]]></programlisting>

    <para>
        Nous allons modifier cette classe <acronym>PHP</acronym> vide pour simplifier le remplissage
        du modèle via un tableau dans le constructeur ou une méthode
        <methodname>setOptions()</methodname>. Le code final de la classe de modèle stockée dans
        <filename>application/models/Guestbook.php</filename> devrait ressembler à ceci:
    </para>

    <programlisting language="php"><![CDATA[
// application/models/Guestbook.php

class Application_Model_Guestbook
{
    protected $_comment;
    protected $_created;
    protected $_email;
    protected $_id;

    public function __construct(array $options = null)
    {
        if (is_array($options)) {
            $this->setOptions($options);
        }
    }

    public function __set($name, $value)
    {
        $method = 'set' . $name;
        if (('mapper' == $name) || !method_exists($this, $method)) {
            throw new Exception('Invalid guestbook property');
        }
        $this->$method($value);
    }

    public function __get($name)
    {
        $method = 'get' . $name;
        if (('mapper' == $name) || !method_exists($this, $method)) {
            throw new Exception('Invalid guestbook property');
        }
        return $this->$method();
    }

    public function setOptions(array $options)
    {
        $methods = get_class_methods($this);
        foreach ($options as $key => $value) {
            $method = 'set' . ucfirst($key);
            if (in_array($method, $methods)) {
                $this->$method($value);
            }
        }
        return $this;
    }

    public function setComment($text)
    {
        $this->_comment = (string) $text;
        return $this;
    }

    public function getComment()
    {
        return $this->_comment;
    }

    public function setEmail($email)
    {
        $this->_email = (string) $email;
        return $this;
    }

    public function getEmail()
    {
        return $this->_email;
    }

    public function setCreated($ts)
    {
        $this->_created = $ts;
        return $this;
    }

    public function getCreated()
    {
        return $this->_created;
    }

    public function setId($id)
    {
        $this->_id = (int) $id;
        return $this;
    }

    public function getId()
    {
        return $this->_id;
    }
}
]]></programlisting>

    <para>
        Enfin, pour connecter tous ces éléments ensemble, créons un contrôleur qui listera les entrées
        de la base de données.
    </para>

    <para>
        Pour créer le nouveau contrôleur, utilisez la commande <command>zf create controller</command>:
    </para>

    <programlisting language="shell"><![CDATA[
% zf create controller Guestbook
Creating a controller at
    application/controllers/GuestbookController.php
Creating an index action method in controller Guestbook
Creating a view script for the index action method at
    application/views/scripts/guestbook/index.phtml
Creating a controller test file at
    tests/application/controllers/GuestbookControllerTest.php
Updating project profile '.zfproject.xml'
]]></programlisting>

    <para>
        Ceci va créer <classname>GuestbookController</classname> dans
        <filename>application/controllers/GuestbookController.php</filename>, avec une seule action
        <methodname>indexAction()</methodname>. Un script de vue sera aussi crée pour ce contrôleur,
        il sera logé dans <filename>application/views/scripts/guestbook/</filename>, avec une vue
        pour l'action index.
    </para>

    <para>
        Nous allons utiliser l'action "index" pour lister toutes les entrées du livre d'or.
    </para>

    <para>
        Un aterrissage sur <methodname>indexAction()</methodname> devra lister toutes les
        entrées du livre d'or. Ceci ressemblera à ce qui suit:
    </para>

    <programlisting language="php"><![CDATA[
// application/controllers/GuestbookController.php

class GuestbookController extends Zend_Controller_Action
{
    public function indexAction()
    {
        $guestbook = new Application_Model_GuestbookMapper();
        $this->view->entries = $guestbook->fetchAll();
    }
}
]]></programlisting>

    <para>
        Et bien sûr un script de vue sera nécessaire. Editez
        <filename>application/views/scripts/guestbook/index.phtml</filename> pour y
        inclure ceci:
    </para>

    <programlisting language="php"><![CDATA[
<!-- application/views/scripts/guestbook/index.phtml -->

<p><a href="<?php echo $this->url(
    array(
        'controller' => 'guestbook',
        'action'     => 'sign'
    ),
    'default',
    true) ?>">Sign Our Guestbook</a></p>

Guestbook Entries: <br />
<dl>
    <?php foreach ($this->entries as $entry): ?>
    <dt><?php echo $this->escape($entry->email) ?></dt>
    <dd><?php echo $this->escape($entry->comment) ?></dd>
    <?php endforeach ?>
</dl>
]]></programlisting>

    <note>
        <title>Checkpoint</title>

        <para>
            Naviguez maintenant vers "http://localhost/guestbook". Vous devriez voir ceci
            apparaitre dans votre navigateur:
        </para>

        <para>
            <inlinegraphic width="525" scale="100" align="center" valign="middle"
                fileref="figures/learning.quickstart.create-model.png" format="PNG" />
        </para>
    </note>

    <note>
        <title>Utiliser le script de chargement des données</title>

        <para>
            Le script de chargement des données montré dans la section en question
            (<filename>scripts/load.sqlite.php</filename>) peut être utilisé pour créer une base
            de données pour chaque environnement défini et la remplir de données d'exemple. En
            interne, il utilise <classname>Zend_Console_Getopt</classname>, qui permet de préciser
            des options à la commande. Si vous passez "-h" ou "--help", toutes les options
            disponibles seront affichées:
        </para>

        <programlisting language="php"><![CDATA[
Usage: load.sqlite.php [ options ]
--withdata|-w         Load database with sample data
--env|-e [  ]         Application environment for which to create database
                      (defaults to development)
--help|-h             Help -- usage message)]]
]]></programlisting>

        <para>
            L'option "-e" permet de préciser la valeur de la constante
            <constant>APPLICATION_ENV</constant> -- ce qui en effet permet de créer une base de
            données SQLite pour chaque environnement défini. N'oubliez pas l'envrionnement
            lorsque vous utilisez ce script.
        </para>
    </note>
</sect1>