diff options
Diffstat (limited to 'demos/blog-tutorial')
-rwxr-xr-x | demos/blog-tutorial/protected/pages/Day1/CreateContact.page | 31 | ||||
-rwxr-xr-x | demos/blog-tutorial/protected/pages/Day1/Setup.page | 5 | ||||
-rwxr-xr-x | demos/blog-tutorial/protected/pages/Day1/ShareLayout.page | 2 | ||||
-rwxr-xr-x | demos/blog-tutorial/protected/pages/Day1/fr/CreateContact.page | 33 | ||||
-rwxr-xr-x | demos/blog-tutorial/protected/pages/Day1/fr/Setup.page | 7 | ||||
-rwxr-xr-x | demos/blog-tutorial/protected/pages/Day1/fr/ShareLayout.page | 4 | ||||
-rwxr-xr-x | demos/blog-tutorial/protected/pages/Day1/id/CreateContact.page | 31 | ||||
-rwxr-xr-x | demos/blog-tutorial/protected/pages/Day1/id/Setup.page | 5 | ||||
-rwxr-xr-x | demos/blog-tutorial/protected/pages/Day1/id/ShareLayout.page | 2 | ||||
-rw-r--r--[-rwxr-xr-x] | demos/blog-tutorial/protected/pages/Day2/CreateAR.page | 303 | ||||
-rw-r--r-- | demos/blog-tutorial/protected/pages/Day2/blog_wsat_generate_ar.png | bin | 0 -> 69184 bytes | |||
-rw-r--r-- | demos/blog-tutorial/protected/pages/Day2/wsat_login.png | bin | 0 -> 47951 bytes |
12 files changed, 180 insertions, 243 deletions
diff --git a/demos/blog-tutorial/protected/pages/Day1/CreateContact.page b/demos/blog-tutorial/protected/pages/Day1/CreateContact.page index 28ad4b21..0d9fc026 100755 --- a/demos/blog-tutorial/protected/pages/Day1/CreateContact.page +++ b/demos/blog-tutorial/protected/pages/Day1/CreateContact.page @@ -45,11 +45,11 @@ We use template to organize the presentational layout of the feedback form. In t <h1>Contact</h1>
<p>Please fill out the following form to let me know your feedback on my blog. Thanks!</p>
-<com:TForm>
+<com:TForm>
<span>Your Name:</span>
<com:TRequiredFieldValidator ControlToValidate="Name"
- ErrorMessage="Please provide your name."
+ ErrorMessage="Please provide your name."
Display="Dynamic" />
<br/>
<com:TTextBox ID="Name" />
@@ -57,10 +57,10 @@ We use template to organize the presentational layout of the feedback form. In t <br/>
<span>Your Email:</span>
<com:TRequiredFieldValidator ControlToValidate="Email"
- ErrorMessage="Please provide your email address."
+ ErrorMessage="Please provide your email address."
Display="Dynamic" />
<com:TEmailAddressValidator ControlToValidate="Email"
- ErrorMessage="You entered an invalid email address."
+ ErrorMessage="You entered an invalid email address."
Display="Dynamic" />
<br/>
<com:TTextBox ID="Email" />
@@ -68,11 +68,11 @@ We use template to organize the presentational layout of the feedback form. In t <br/>
<span>Feedback:</span>
<com:TRequiredFieldValidator ControlToValidate="Feedback"
- ErrorMessage="Please provide your feedback."
+ ErrorMessage="Please provide your feedback."
Display="Dynamic" />
<br/>
-<com:TTextBox ID="Feedback"
- TextMode="MultiLine"
+<com:TTextBox ID="Feedback"
+ TextMode="MultiLine"
Rows="10"
Columns="40" />
@@ -99,13 +99,13 @@ Besides <tt>TTextBox</tt> controls, the template also uses many validator contro <com:TTextHighlighter CssClass="source" Language="prado">
<span>Your Email:</span>
-<com:TRequiredFieldValidator
+<com:TRequiredFieldValidator
ControlToValidate="Email"
- ErrorMessage="Please provide your email address."
+ ErrorMessage="Please provide your email address."
Display="Dynamic" />
-<com:TEmailAddressValidator
+<com:TEmailAddressValidator
ControlToValidate="Email"
- ErrorMessage="You entered an invalid email address."
+ ErrorMessage="You entered an invalid email address."
Display="Dynamic" />
<br/>
<com:TTextBox ID="Email" />
@@ -152,28 +152,27 @@ class Contact extends TPage /**
* Event handler for the OnClick event of the submit button.
* @param TButton the button triggering the event
- * @param TEventParameter event parameter (null here)
+ * @param TEventParameter event parameter (null here)
*/
public function submitButtonClicked($sender, $param)
{
if ($this->IsValid) // check if input validation is successful
{
// obtain the user name, email, feedback from the textboxes
- $name = $this->Name->Text;
+ $name = $this->Name->Text;
$email = $this->Email->Text;
$feedback = $this->Feedback->Text;
-
+
// send an email to administrator with the above information
$this->mailFeedback($name, $email, $feedback);
}
}
-
+
protected function mailFeedback($name, $email, $feedback)
{
// implementation of sending the feedback email
}
}
-?>
</com:TTextHighlighter>
<p>
diff --git a/demos/blog-tutorial/protected/pages/Day1/Setup.page b/demos/blog-tutorial/protected/pages/Day1/Setup.page index e8316253..582d0399 100755 --- a/demos/blog-tutorial/protected/pages/Day1/Setup.page +++ b/demos/blog-tutorial/protected/pages/Day1/Setup.page @@ -52,7 +52,6 @@ require_once('path/to/prado.php'); $application = new TApplication;
// run the application and handle user requests
$application->run();
-?>
</com:TTextHighlighter>
<com:InfoBox>
@@ -148,8 +147,8 @@ To change the location of the root page directory and change the name of homepag <?xml version="1.0" encoding="utf-8"?>
<application id="blog" mode="Debug">
<services>
- <service id="page"
- class="TPageService"
+ <service id="page"
+ class="TPageService"
BasePath="path.to.pages"
DefaultPage="NewHome"
/>
diff --git a/demos/blog-tutorial/protected/pages/Day1/ShareLayout.page b/demos/blog-tutorial/protected/pages/Day1/ShareLayout.page index 9cd0410b..6115ef22 100755 --- a/demos/blog-tutorial/protected/pages/Day1/ShareLayout.page +++ b/demos/blog-tutorial/protected/pages/Day1/ShareLayout.page @@ -66,7 +66,6 @@ The class file <tt>MainLayout.php</tt> is very simple: class MainLayout extends TTemplateControl
{
}
-?>
</com:TTextHighlighter>
<com:InfoBox>
@@ -145,7 +144,6 @@ class Contact extends TPage // ...
}
-?>
</com:TTextHighlighter>
<p>
diff --git a/demos/blog-tutorial/protected/pages/Day1/fr/CreateContact.page b/demos/blog-tutorial/protected/pages/Day1/fr/CreateContact.page index e85d8bfe..0105f656 100755 --- a/demos/blog-tutorial/protected/pages/Day1/fr/CreateContact.page +++ b/demos/blog-tutorial/protected/pages/Day1/fr/CreateContact.page @@ -45,11 +45,11 @@ Nous utilisons un fichier gabarit pour organiser la présentation de notre formu <h1>Contact</h1>
<p>Veuillez remplir le formulaire suivant pour me laisser vos impressions au sujet de mon blog. Merci !</p>
-<com:TForm>
+<com:TForm>
<span>Votre nom:</span>
<com:TRequiredFieldValidator ControlToValidate="Name"
- ErrorMessage="Veuillez indiquer votre nom."
+ ErrorMessage="Veuillez indiquer votre nom."
Display="Dynamic" />
<br/>
<com:TTextBox ID="Name" />
@@ -57,10 +57,10 @@ Nous utilisons un fichier gabarit pour organiser la présentation de notre formu <br/>
<span>Votre email:</span>
<com:TRequiredFieldValidator ControlToValidate="Email"
- ErrorMessage="Veuillez indiquer votre email."
+ ErrorMessage="Veuillez indiquer votre email."
Display="Dynamic" />
<com:TEmailAddressValidator ControlToValidate="Email"
- ErrorMessage="Vous avez saisi un email invalide."
+ ErrorMessage="Vous avez saisi un email invalide."
Display="Dynamic" />
<br/>
<com:TTextBox ID="Email" />
@@ -68,11 +68,11 @@ Nous utilisons un fichier gabarit pour organiser la présentation de notre formu <br/>
<span>Commentaires:</span>
<com:TRequiredFieldValidator ControlToValidate="Feedback"
- ErrorMessage="Veuillez saisir un commentaire."
+ ErrorMessage="Veuillez saisir un commentaire."
Display="Dynamic" />
<br/>
-<com:TTextBox ID="Feedback"
- TextMode="MultiLine"
+<com:TTextBox ID="Feedback"
+ TextMode="MultiLine"
Rows="10"
Columns="40" />
@@ -99,13 +99,13 @@ Avant le contrôle <tt>TTextBox</tt>, le gabarit utilise aussi plusieurs validat <com:TTextHighlighter CssClass="source" Language="prado">
<span>Your Email:</span>
-<com:TRequiredFieldValidator
+<com:TRequiredFieldValidator
ControlToValidate="Email"
- ErrorMessage="Veuillez indiquer votre email."
+ ErrorMessage="Veuillez indiquer votre email."
Display="Dynamic" />
-<com:TEmailAddressValidator
+<com:TEmailAddressValidator
ControlToValidate="Email"
- ErrorMessage="Vous avez saisi un email invalide."
+ ErrorMessage="Vous avez saisi un email invalide."
Display="Dynamic" />
<br/>
<com:TTextBox ID="Email" />
@@ -152,28 +152,27 @@ class Contact extends TPage /**
* Gestionnaire d'évènement pour OnClick (bouton submit).
* @param TButton le bouton qui a générer l'évènement
- * @param TEventParameter les paramètres de l'évènement (null dans ce cas)
+ * @param TEventParameter les paramètres de l'évènement (null dans ce cas)
*/
public function submitButtonClicked($sender, $param)
{
if ($this->IsValid) // vérifie que les validations sont Ok
{
// récupère le nom de l'utilisateur, son email et son commentaire
- $name = $this->Name->Text;
+ $name = $this->Name->Text;
$email = $this->Email->Text;
$feedback = $this->Feedback->Text;
-
- // envoie un email à l'administrateur avec les informations
+
+ // envoie un email à l'administrateur avec les informations
$this->mailFeedback($name, $email, $feedback);
}
}
-
+
protected function mailFeedback($name, $email, $feedback)
{
// implémentation de l'envoi de l'email
}
}
-?>
</com:TTextHighlighter>
<p>
diff --git a/demos/blog-tutorial/protected/pages/Day1/fr/Setup.page b/demos/blog-tutorial/protected/pages/Day1/fr/Setup.page index 22a7891c..0be1c1f0 100755 --- a/demos/blog-tutorial/protected/pages/Day1/fr/Setup.page +++ b/demos/blog-tutorial/protected/pages/Day1/fr/Setup.page @@ -49,11 +49,10 @@ require_once('path/to/prado.php'); $application = new TApplication;
// run the application and handle user requests
$application->run();
-?>
</com:TTextHighlighter>
<com:InfoBox>
-Le nom du script ne doit pas être obligatoirement <tt>index.php</tt>. Il peut porter n'importe quel nom à partir du moment ou le serveur peut l'interpréter comme étant un script PHP5. Par exemple, sur certains hébergements mutualisés, le script devra porter le nom <tt>index.php5</tt>, ce qui permettra au serveur Web de le traiter correctement.
+Le nom du script ne doit pas être obligatoirement <tt>index.php</tt>. Il peut porter n'importe quel nom à partir du moment ou le serveur peut l'interpréter comme étant un script PHP5. Par exemple, sur certains hébergements mutualisés, le script devra porter le nom <tt>index.php5</tt>, ce qui permettra au serveur Web de le traiter correctement.
</com:InfoBox>
<h3>Le fichier de configuration de l'application</h3>
@@ -145,8 +144,8 @@ Pour changer l'emplacement du dossier racine des pages et le nom de la page d'ac <?xml version="1.0" encoding="utf-8"?>
<application id="blog" mode="Debug">
<services>
- <service id="page"
- class="TPageService"
+ <service id="page"
+ class="TPageService"
BasePath="path.to.pages"
DefaultPage="NewHome"
/>
diff --git a/demos/blog-tutorial/protected/pages/Day1/fr/ShareLayout.page b/demos/blog-tutorial/protected/pages/Day1/fr/ShareLayout.page index cefff770..539b8376 100755 --- a/demos/blog-tutorial/protected/pages/Day1/fr/ShareLayout.page +++ b/demos/blog-tutorial/protected/pages/Day1/fr/ShareLayout.page @@ -68,7 +68,6 @@ Le fichier de classe <tt>MainLayout.php</tt> est très simple : class MainLayout extends TTemplateControl
{
}
-?>
</com:TTextHighlighter>
<com:InfoBox>
@@ -147,13 +146,12 @@ class Contact extends TPage // ...
}
-?>
</com:TTextHighlighter>
<p>
Ci-dessus, nous indiquons d'utiliser le gabarit principal <tt>MasterClass</tt> dans la méthode <tt>onPreInit()</tt> qui est héritée de <tt>TPage</tt>. Cette méthode est appelé par PRADO juste après que l'instance de la page soit créée. Nous pouvons ainsi déclarer au moment où la page est requise quel gabarit principal utiliser. Par exemple, quand la page est requise par un utilisateur enregistré, nous pouvons utiliser le gabarit A, et le gabarit B si l'utilisateur qui demande la page est un invité.
</p>
- +
<p>
Nous pouvons aussi spécifier quel gabarit principal utiliser dans le fichier de <a href="http://www.pradosoft.com/demos/quickstart/?page=Configurations.AppConfig">configuration de l'application</a> ou encore dans le fichier de <a href="http://www.pradosoft.com/demos/quickstart/?page=Configurations.PageConfig">configuration de la page</a>. Ci-dessous, le fichier de configuration de l'application modifié pour notre blog.
</p>
diff --git a/demos/blog-tutorial/protected/pages/Day1/id/CreateContact.page b/demos/blog-tutorial/protected/pages/Day1/id/CreateContact.page index 65be6417..caee30d0 100755 --- a/demos/blog-tutorial/protected/pages/Day1/id/CreateContact.page +++ b/demos/blog-tutorial/protected/pages/Day1/id/CreateContact.page @@ -45,11 +45,11 @@ Kita menggunakan template untuk menghatur tata letak penyajian terhadap formulir <h1>Contact</h1>
<p>Please fill out the following form to let me know your feedback on my blog. Thanks!</p>
-<com:TForm>
+<com:TForm>
<span>Your Name:</span>
<com:TRequiredFieldValidator ControlToValidate="Name"
- ErrorMessage="Please provide your name."
+ ErrorMessage="Please provide your name."
Display="Dynamic" />
<br/>
<com:TTextBox ID="Name" />
@@ -57,10 +57,10 @@ Kita menggunakan template untuk menghatur tata letak penyajian terhadap formulir <br/>
<span>Your Email:</span>
<com:TRequiredFieldValidator ControlToValidate="Email"
- ErrorMessage="Please provide your email address."
+ ErrorMessage="Please provide your email address."
Display="Dynamic" />
<com:TEmailAddressValidator ControlToValidate="Email"
- ErrorMessage="You entered an invalid email address."
+ ErrorMessage="You entered an invalid email address."
Display="Dynamic" />
<br/>
<com:TTextBox ID="Email" />
@@ -68,11 +68,11 @@ Kita menggunakan template untuk menghatur tata letak penyajian terhadap formulir <br/>
<span>Feedback:</span>
<com:TRequiredFieldValidator ControlToValidate="Feedback"
- ErrorMessage="Please provide your feedback."
+ ErrorMessage="Please provide your feedback."
Display="Dynamic" />
<br/>
-<com:TTextBox ID="Feedback"
- TextMode="MultiLine"
+<com:TTextBox ID="Feedback"
+ TextMode="MultiLine"
Rows="10"
Columns="40" />
@@ -99,13 +99,13 @@ Selain kontrol <tt>TTextBox</tt>, template juga menggunakan banyak kontrol valid <com:TTextHighlighter CssClass="source" Language="prado">
<span>Your Email:</span>
-<com:TRequiredFieldValidator
+<com:TRequiredFieldValidator
ControlToValidate="Email"
- ErrorMessage="Please provide your email address."
+ ErrorMessage="Please provide your email address."
Display="Dynamic" />
-<com:TEmailAddressValidator
+<com:TEmailAddressValidator
ControlToValidate="Email"
- ErrorMessage="You entered an invalid email address."
+ ErrorMessage="You entered an invalid email address."
Display="Dynamic" />
<br/>
<com:TTextBox ID="Email" />
@@ -152,28 +152,27 @@ class Contact extends TPage /**
* Pengendali event untuk event OnClick pada tombol submit.
* @param TButton tombol yang memicu event
- * @param TEventParameter parameter event (null di sini)
+ * @param TEventParameter parameter event (null di sini)
*/
public function submitButtonClicked($sender, $param)
{
if ($this->IsValid) // memeriksa apakan validasi input berhasil
{
// mendapatkan nama pengguna, email, umpan balik dari kotak teks
- $name = $this->Name->Text;
+ $name = $this->Name->Text;
$email = $this->Email->Text;
$feedback = $this->Feedback->Text;
-
+
// mengirimkan email ke administrator dengan informasi di atas
$this->mailFeedback($name, $email, $feedback);
}
}
-
+
protected function mailFeedback($name, $email, $feedback)
{
// implementasi pengiriman email umpan balik
}
}
-?>
</com:TTextHighlighter>
<p>
diff --git a/demos/blog-tutorial/protected/pages/Day1/id/Setup.page b/demos/blog-tutorial/protected/pages/Day1/id/Setup.page index edc469d5..45ae8cf5 100755 --- a/demos/blog-tutorial/protected/pages/Day1/id/Setup.page +++ b/demos/blog-tutorial/protected/pages/Day1/id/Setup.page @@ -52,7 +52,6 @@ require_once('path/to/prado.php'); $application = new TApplication;
// jalankan aplikasi dan tangani permintaan pengguna
$application->run();
-?>
</com:TTextHighlighter>
<com:InfoBox>
@@ -148,8 +147,8 @@ Untuk membuat lokasi akar direktori halaman dan mengubah nama homepage, seseoran <?xml version="1.0" encoding="utf-8"?>
<application id="blog" mode="Debug">
<services>
- <service id="page"
- class="TPageService"
+ <service id="page"
+ class="TPageService"
BasePath="path.to.pages"
DefaultPage="NewHome"
/>
diff --git a/demos/blog-tutorial/protected/pages/Day1/id/ShareLayout.page b/demos/blog-tutorial/protected/pages/Day1/id/ShareLayout.page index d505beed..0c40181b 100755 --- a/demos/blog-tutorial/protected/pages/Day1/id/ShareLayout.page +++ b/demos/blog-tutorial/protected/pages/Day1/id/ShareLayout.page @@ -66,7 +66,6 @@ File kelas <tt>MainLayout.php</tt> sangat sederhana: class MainLayout extends TTemplateControl
{
}
-?>
</com:TTextHighlighter>
<com:InfoBox>
@@ -145,7 +144,6 @@ class Contact extends TPage // ...
}
-?>
</com:TTextHighlighter>
<p>
diff --git a/demos/blog-tutorial/protected/pages/Day2/CreateAR.page b/demos/blog-tutorial/protected/pages/Day2/CreateAR.page index 1d7838a2..99e91d5a 100755..100644 --- a/demos/blog-tutorial/protected/pages/Day2/CreateAR.page +++ b/demos/blog-tutorial/protected/pages/Day2/CreateAR.page @@ -1,178 +1,127 @@ -<com:TContent ID="Main">
-
-<h1>Creating Active Record Classes</h1>
-
-<p>
-We need to create two <a href="http://www.pradosoft.com/demos/quickstart/?page=Database.ActiveRecord">Active Record</a> classes, <tt>UserRecord</tt> and <tt>PostRecord</tt>, to represent data records in the <tt>users</tt> and <tt>posts</tt> tables, respectively. Active Record classes must extend from the base class <tt>ActiveRecord</tt>, and must define property names that matches with the field names of the corresponding table.
-</p>
-
-<p>
-To better organize our directories, we create a new directory <tt>protected/database</tt> to hold the class files. We also modify our application configuration by inserting the following lines. It is equivalent to adding the directory <tt>protected/database</tt> to PHP include_path, which allows us to use the classes without explicitly including them.
-</p>
-
-<com:TTextHighlighter CssClass="source" Language="xml">
-<paths>
- <using namespace="Application.database.*" />
-</paths>
-</com:TTextHighlighter>
-
-<p>
-Instead of writing the classes manually, we will use the <a href="http://www.pradosoft.com/demos/quickstart/?page=GettingStarted.CommandLine">PRADO command line tool</a> again to generate the classes for us.
-</p>
-
-<p>
-Under the <tt>blog</tt> directory, run the following command to enter into the interactive mode of the command line tool:
-</p>
-
-<com:TTextHighlighter CssClass="source cli" Language="text">
-php path/to/prado-cli.php shell .
-</com:TTextHighlighter>
-
-<p>
-We should see
-</p>
-
-<com:TTextHighlighter CssClass="source cli" Language="text">
-Command line tools for Prado 3.1.0.
-** Loaded PRADO appplication in directory "protected".
-PHP-Shell - Version 0.3.1
-(c) 2006, Jan Kneschke <jan@kneschke.de>
-
->> use '?' to open the inline help
-
->>
-</com:TTextHighlighter>
-
-<p>
-At the prompt, enter the following two commands to create <tt>UserRecord</tt> and <tt>PostRecord</tt> classes:
-</p>
-
-<com:TTextHighlighter CssClass="source cli" Language="text">
->> generate users Application.database.UserRecord
-
->> generate posts Application.database.PostRecord
-</com:TTextHighlighter>
-
-<p>
-Here we used the <a href="http://www.pradosoft.com/demos/quickstart/?page=Fundamentals.Components">namespace format</a> again to specify the classes to be created. The path <tt>Application.database.UserRecord</tt> indicates that we want the <tt>UserRecord</tt> class file to be <tt>protected/database/UserRecord.php</tt>.
-</p>
-
-<p>
-We should see the following directory structure with two new files under <tt>protected/database</tt>:
-</p>
-
-<img src="<%~ directories2.gif %>" class="output" />
-
-<p>
-If we check the <tt>PostRecord</tt> class file, we should see the following content.
-</p>
-
-<com:TTextHighlighter CssClass="source" Language="php">
-class PostRecord extends TActiveRecord
-{
- const TABLE='posts';
- public $post_id;
- public $author_id;
- public $create_time;
- public $title;
- public $content;
- public $status;
-
- public static function finder($className=__CLASS__)
- {
- return parent::finder($className);
- }
-}
-</com:TTextHighlighter>
-
-<p>
-As we see, for each field in the <tt>posts</tt> table, the class has a corresponding data member. The constant <tt>TABLE</tt> specifies the table name for the <tt>PostRecord</tt>. The static method <tt>finder()</tt> allows us to perform query and retrieve post data in terms of <tt>PostRecord</tt> objects.
-</p>
-
-<p>
-We can use the command line tool to do some testing with our newly created Active Record classes. Still in the interactive mode of the command line tool, we enter a PHP statement and should see the following. Interested readers may try some other PHP statements, such as <tt>UserRecord::finder()->findAll()</tt>.
-</p>
-
-<com:TTextHighlighter CssClass="source cli" Language="text">
->> PostRecord::finder()->findAll()
-array
-(
- [0] => PostRecord#1
- (
- [post_id] => '1'
- [author_id] => 'admin'
- [create_time] => '1175708482'
- [title] => 'first post'
- [content] => 'this is my first post'
- [status] => '0'
- [TActiveRecord:_readOnly] => false
- [TActiveRecord:_connection] => null
- [TComponent:_e] => array()
- )
-)
-</com:TTextHighlighter>
-
-<h1>Relationship Between Posts and Users</h1>
-<p>
-Recall that there was a foreign key relationship between the <tt>users</tt> and <tt>posts</tt> table. The entity-relationship diagram is shown below for convienence.
-</p>
-
-<img src="<%~ ER.gif %>" class="output" />
-
-<p>
-From the entity-relationship diagram above, we see that the <tt>posts</tt> table contains a field named <tt>author_id</tt>. This <tt>author_id</tt> field is a foreign key to the reference table <tt>users</tt>. In particular, the values in the <tt>author_id</tt> field should be of that from the <tt>users</tt> table's <tt>username</tt> field. One of the consequence of this relationship, thinking in terms of objects, is that each "post" belongs to an "author" and one "author" may have many "posts".
-</p>
-
-<p>
-We can model the relationship between <tt>posts</tt> and <tt>users</tt> table in Active Record by modifying the <tt>PostRecord</tt> and <tt>UserRecord</tt> classes as follows.
-</p>
-
-<com:TTextHighlighter CssClass="source" Language="php">
-class PostRecord extends TActiveRecord
-{
- //... properties and methods as before
-
- public $author; //holds an UserRecord
-
- public static $RELATIONS=array
- (
- 'author' => array(self::BELONGS_TO, 'UserRecord'),
- );
-}
-</com:TTextHighlighter>
-
-<p>
-The static <tt>$RELATIONS</tt> property of <tt>PostRecord</tt> defines that the property <tt>$author</tt> belongs to an <tt>UserRecord</tt>. In <tt>array(self::BELONGS_TO, 'UserRecord')</tt>, the first element defines the relationship type, in this case <tt>self::BELONGS_TO</tt>. The second element is the name of related record, in this case an <tt>UserRecord</tt>. The <tt>UserRecord</tt> is defined similarly below, the difference is that, the user record has many <tt>PostRecord</tt>s.
-</p>
-
-<com:TTextHighlighter CssClass="source" Language="php">
-class UserRecord extends TActiveRecord
-{
- //... properties and methods as before
-
- public $posts=array(); //holds an array of PostRecord
-
- public static $RELATIONS=array
- (
- 'posts' => array(self::HAS_MANY, 'PostRecord'),
- );
-}
-</com:TTextHighlighter>
-
-<p>
-An array of <tt>UserRecord</tt> with and its corresponding posts may be fetched as follows.
-</p>
-
-<com:TTextHighlighter CssClass="source" Language="php">
-$users = UserRecord::finder()->withPosts()->findAll();
-</com:TTextHighlighter>
-
-<com:TipBox>
-The method <tt>withXXX()</tt> (where XXX is the relationship property name, in this case, <tt>Posts</tt>) fetches the corresponding <tt>PostRecords</tt> using a second query (not by using a join). The <tt>withXXX()</tt> method accepts the same arguments as other finder methods of TActiveRecord, e.g. <tt>withPosts('status = ?', 0)</tt>.
-</com:TipBox>
-
-<p>
-Further detailed documentation can be found in the quickstart <a href="http://www.pradosoft.com/demos/quickstart/?page=Database.ActiveRecord">Active Record</a> docs.
-</p>
-
+<com:TContent ID="Main"> + +<h1>Creating Active Record Classes</h1> + +<p> +We need to create two <a href="http://www.pradosoft.com/demos/quickstart/?page=Database.ActiveRecord">Active Record</a> classes, <tt>UserRecord</tt> and <tt>PostRecord</tt>, to represent data records in the <tt>users</tt> and <tt>posts</tt> tables, respectively. Active Record classes must extend from the base class <tt>ActiveRecord</tt>, and must define property names that matches with the field names of the corresponding table. +</p> + +<p> +To better organize our directories, we create a new directory <tt>protected/database</tt> to hold the class files. We also modify our application configuration by inserting the following lines. It is equivalent to adding the directory <tt>protected/database</tt> to PHP include_path, which allows us to use the classes without explicitly including them. +</p> + +<com:TTextHighlighter CssClass="source" Language="xml"> +<paths> + <using namespace="Application.database.*" /> +</paths> +</com:TTextHighlighter> + +<p> +Instead of writing the classes manually, we will use the <a href="?page=GettingStarted.Wsat">PRADO Web Site Administration Tool</a> to generate the classes for us. +So we need to modify again our application configuration in the services section like follows: +</p> + + <p class="block-content"> +<com:TTextHighlighter CssClass="source" Language="xml"> +<services> + ... + <service id="wsat" class="System.Wsat.TWsatService" Password="my_secret_password" /> +</services> +</com:TTextHighlighter> +</p> + +<p class="block-content"> + Then you are ready to go to: http://localhost/yoursite/index.php?wsat=TWsatLogin where you should see + the following page: +</p> +<img src="<%~wsat_login.png%>" style="width: 700px;" /> +<p class="block-content"> + In the text field you need to type the password previosly specified in the service inclusion. This + is part of a basic security system to avoid undesirable persons to use this tool. +</p> + + <p class="block-content"> + In order to generate AR classes you need to go to: http://localhost/divermania/index.php?wsat=TWsatGenerateAR + by clicking the proper links in the welcome page. Then you should see the following page: +</p> +<img src="<%~blog_wsat_generate_ar.png%>" style="width: 700px;" /> + +<p> + In the <tt>Output Folder</tt> field we used the <a href="http://www.pradosoft.com/demos/quickstart/?page=Fundamentals.Components">namespace format</a> again, the path <tt>Application.database</tt> indicates that we want to put our class's files in the <tt>protected/database/</tt> folder. + The <tt>*</tt> in the <tt>Table Name</tt> field means that we want to generate all AR classes, you can specify a table name instead if you want to generate just a specific AR class. +</p> + +<p> +Afterward we should see the following directory structure with two new files under <tt>protected/database</tt>: +</p> + +<img src="<%~ directories2.gif %>" class="output" /> + +<p> +If we check the <tt>PostRecord</tt> class file, we should see something similar to the following content: +</p> + +<com:TTextHighlighter CssClass="source" Language="php"> +class PostRecord extends TActiveRecord +{ + const TABLE='posts'; + + public $post_id; + public $author_id; + public $create_time; + public $title; + public $content; + public $status; + + public static function finder($className=__CLASS__) + { + return parent::finder($className); + } + + public static $RELATIONS = array ( + 'author' => array(self::BELONGS_TO, 'UserRecord', 'author_id') + ); + + public function __toString() + { + return $this->title; + } +} +</com:TTextHighlighter> + +<p> +As we see, for each field in the <tt>posts</tt> table, the class has a corresponding data member. The constant <tt>TABLE</tt> specifies the table name for the <tt>PostRecord</tt>. The static method <tt>finder()</tt> allows us to perform query and retrieve post data in terms of <tt>PostRecord</tt> objects. +</p> + +<h1>Relationship Between Posts and Users</h1> +<p> +Recall that there was a foreign key relationship between the <tt>users</tt> and <tt>posts</tt> table. The entity-relationship diagram is shown below for convienence. +</p> + +<img src="<%~ ER.gif %>" class="output" /> + +<p> +From the entity-relationship diagram above, we see that the <tt>posts</tt> table contains a field named <tt>author_id</tt>. This <tt>author_id</tt> field is a foreign key to the reference table <tt>users</tt>. In particular, the values in the <tt>author_id</tt> field should be of that from the <tt>users</tt> table's <tt>username</tt> field. One of the consequence of this relationship, thinking in terms of objects, is that each "post" belongs to an "author" and one "author" may have many "posts". +</p> + +<p> +The static <tt>$RELATIONS</tt> property of <tt>PostRecord</tt> defines that the property <tt>$author</tt> belongs to an <tt>UserRecord</tt>. In <tt>array(self::BELONGS_TO, 'UserRecord')</tt>, the first element defines the relationship type, in this case <tt>self::BELONGS_TO</tt>. The second element is the name of related record, in this case an <tt>UserRecord</tt>. +</p> + +<p> +An array of <tt>UserRecord</tt> with and its corresponding posts may be fetched as follows. +</p> + +<com:TTextHighlighter CssClass="source" Language="php"> +$users = UserRecord::finder()->withPosts()->findAll(); +</com:TTextHighlighter> + +<com:TipBox> +The method <tt>withXXX()</tt> (where XXX is the relationship property name, in this case, <tt>Posts</tt>) fetches the corresponding <tt>PostRecords</tt> using a second query (not by using a join). The <tt>withXXX()</tt> method accepts the same arguments as other finder methods of TActiveRecord, e.g. <tt>withPosts('status = ?', 0)</tt>. +</com:TipBox> + +<p> +Further detailed documentation can be found in the quickstart <a href="http://www.pradosoft.com/demos/quickstart/?page=Database.ActiveRecord">Active Record</a> docs. +</p> + </com:TContent>
\ No newline at end of file diff --git a/demos/blog-tutorial/protected/pages/Day2/blog_wsat_generate_ar.png b/demos/blog-tutorial/protected/pages/Day2/blog_wsat_generate_ar.png Binary files differnew file mode 100644 index 00000000..433c1230 --- /dev/null +++ b/demos/blog-tutorial/protected/pages/Day2/blog_wsat_generate_ar.png diff --git a/demos/blog-tutorial/protected/pages/Day2/wsat_login.png b/demos/blog-tutorial/protected/pages/Day2/wsat_login.png Binary files differnew file mode 100644 index 00000000..dbe1ad8b --- /dev/null +++ b/demos/blog-tutorial/protected/pages/Day2/wsat_login.png |