Hari Kedua - Symfony advent calendar
======================================
Mensetup Data model
=====================
Diterjemahkan Oleh : [Wildan Maulana](mailto:wildan-maulana@fisika.ui.ac.id)
Sebelumnya di Symfony
---------------------
Selama tutorial yang panjang [hari pertama](1.txt) tetapi menarik, kita
sudah melihat bagaimana menginstall symfony framework, mensetup aplikasi
baru dan linkungan development, serta mengamankan code dengan source
version control. Ngomong-ngomong, code untuk aplikasi yang dibuat selama
hari pertama sudah terdapat pada repository SVN askeet di :
http://svn.askeet.com/
Objektif untuk hari kedua adalah untuk mendefinisikan apakah hasil akhirnya
dari segi fungsionalitas, membuat data model awal, dan mulai membuat code.
Ini termasuk menggenerate object-relational mapping dan menggunakannya
secara interaltif untuk membuat, mengambil dan mengupdate record di database
dengan application scaffolding.
Ini cukup banyal. Jadi, mari kita mulai !
The project unveiled
--------------------
Apa yang ingin Anda tahu ? Ini pertanyaan yang menarik. Ada banyak hal yang
menarik, seperti :
* What shall I do tonight with my girlfriend? (Apa yang harus saya lakukan
malam ini dengan kekasih saya ?)
* How can I generate traffic to my blog? (Bagaimana saya dapat menaikkan
traffic ke blog saya ?)
* What's the best web application framework? (Apakah web application
framework yang terbaik ? )
* What's the best affordable restaurant in Paris? (Restoran manakah yang
termurah plus terbaik di Paris ? )
* What's the answer to life, the universe, and everything? (Apakah jawaban
untuk hidup,alam semesta, dan segalanya ?)
Semua pertanyaan ini tidak hanya memiliki sebuah jawaban, dan jawaban
terbaiknya tentu saja bergantung pendapat orang. Bahkan, pertanyaan yang
hanya memiliki sebuah jawaban sering kurang menarik (seperti, berapa 1 +1 ?)
apalagi masalah macam ini ingin dipecahkan di web. Ini tidak adil.
Perkenalkan [askeet](http://www.askeet.com). Sebuah website yang didekasikan
untuk menolong orang mencari jawaban untuk pertanyaan mereka. Siapakah yang
akan menjawab pertanyaan-pertannyaan itu ? Setiap orang. Dan setiap orang
akan dapat merating jawaban orang lain, sehingga jawaban yang paling populer
akan lebih terlihat. Seiring bertambahnya pertanyaan, maka akan menjadi
mustahil untuk mengelompokkan pertanyaan-pertanyaan ini dalam kategori dan
subkategori, sehingga sebagai solusinya, pembuat pertanyaan akan dapat men
memberikan tag pada pertanyaannya dengan kata apapun yang ia suka, "à la" [del.icio.us](http://del.icio.us/).
Tentu saja, kepopuleran tag harus ditampilkan melalui tag bubble.
Jika seseorang ingin mengikuti jawaban ke suatu pertanyaan tertentu, dia
dapat mendaftarkan diri ke RSS feed pertanyaan ini. Semua fungsionalitas ini
harus elegan dan dan ringan, sehingga semua interaksi yang tidak terlalu
memerlukan halaman baru harus mamanfaatkan AJAX. Terakhir, back-end (bagian
administrasi) juga diperlukan untuk mengadministrasi pertanyaan dan jawaban
yang dilaporkan sebagai spam. atau menaikkan rating pertanyaan yang oleh
administrator dianggap menarik.
Kemudian Anda bertanya: Sudahkan Saya melihat website semacam ini di web ?
Yah.., kalau Anda sudah pernah melihatnya, maka Kami terperangkap, tapi jika
Anda menunjuk pada [faqts](http://www.faqts.com),
[eHow](http://www.ehow.com), [Ask Jeeves](http://www.ask.com) atau yang
mirip dengan ini semua, tanpa jawaban yang kolaboratif, tanpa AJAX, tanpa
RSS, dan tanpa tag, ini bukanlah website yang sama. Kita berbicara tentang
aplikasi web 2.0 disini.
Hal yang penting mengenai askeet adalah ia bukan hanya sebuah website, ia
adalah sebuah aplikasi yang dapat didownload oleh siapapun, menginstallnya
di rumah atau di intranet perusahaan, mengoptimalisasinya dan menambahkan
fiturnya juga. Source code nya akan di release dengan license open-source.
Kepala HR Anda mencari sebuah knowledge management system ? Anda ingin
mengikuti semua trik yang Anda pelajaru tentang cara memperbaiki mobil Anda
? Anda tidak ingin membuat bagian Frequently Asked Question dari website
Anda ? Ana tidak perlu mencari lagi, karena ada askeet. Yah .., ini akan
Ada, ini adalah hadiah Natal dari kami.
Dari mana harus memulai ?
--------------------------
Jadi bagaimana Anda akan memulai membuat aplikasi symfony Anda ? Ini
semuanya tergantung pada Anda ? Anda dapat menulis cerita, membuat rencana
main dan mencari rekan untuk melakuka pair programming (membuat program
secara berpasangan) jika Anda adalah pengadopsi [XP][1], atau menulis sebuah
spesifikasi detail dari website, beserta semua object, state, interaksi dan
lain-lainya, jika Anda adalah pengge,at [UML][2]
Tetapi tutorial ini bukanlah tentang teknik pengembangan aplikasi secara
umum, jadi kita akan mulai dengan relational data model sederhana, dan
menambahkan fitur yang lain satu persatu. Apa yang kita perlukan adalah
aplikasi yang dapat digunakan setiap akhir tutorial per hari, bukan
kumpulan code besar yang tidak pernah menghasilkan apa-apa. Dalam dunia yang
ideal, kita dapat menulis unti test untuk setiap fitur yang kita tambahkan,
tapi jujur saha, kita tidak akan memiliki cukup waktu untuk ini. Tetapi satu
hari tetap akan didekaasikan untuk membuat sebuah unit test, jadi tetaplah
membaca.
Untuk project ini, kita akan menggunakan database Mysql dengan tipe tabel
InnoDB untuk mengambil keuntungan adanya integrity constraint dan dukungan
transaksi. Kita dapat saja menggunakan database SQLite untuk langkah
pertama, untuk menghindari keperluan mensetting database yang sebenarnya
akan dipakai nanti. Ini hanya memerlukan beberapa perubahan kecil di file
`databases.yml`, yang akan kami sisakan untuk Anda selidiki sebagai latihan.
Data Model
----------
### Relational model
Tentu saja, akan ada tabel 'question' dan 'answer'. Kita juga akan perlu
tabel 'user', dan kita akan menyimpan ketertarikan user pada sebuah
pertanyaan di tabel 'interest', dan relevansi yang diberikan oleh seseorang
ke sebuah pertanyaan pada tabel 'relevancy'.
User harus diidentifikasi terlebih dahulu untuk menambahkan pertanyaan,
untuk merating jawaban yang berhubungan, atau untuk mendeklarasikan
ketertarikan pada suatu pertanyaan. User tidak perlu diidentifikasi untuk
menambahkan jawaban, tetapi jawaban akan selalu di link ke user sehingga
user dengan jawaban yang pupuler akan dapat dibedakan. Jawaban yang
dimasukkan tanpa identifikasi akan diperlihatkan sebagai kontribusi dari
generic user. yang bernama 'Anonymous Coward'. Akan lebih mudah untuk
memahaminya dengan entitty relationship diagram.

Perhatikan, kami mendeklarasikan field `created_at` untuk setiap tabel.
Symfont mengenal field macam ini dan akan mengeset nilainya dengan waktu
sistem yang sekarang ketika record itu dibuat. Sama juga dengan field
`updated_at` : Nilainya diset dengan sistem waktu setiap kali record diupdate.
### `schema.xml`
Relational model harus diterjemahkan ke file konfigurasi agar symfony dapat
memahaminya. Inilah tujuan dari file `schema.xml`, yang terletak pada
direktori `askeet/config/`. Ada dua cara untuk menulis file ini : dengan
tangan yaitu cara yang kita suka, atau dari database yang sudah ada. Kita
lihat terlebih dahulu solusi pertama :
Pertama-tama kita harus mengubah nama sample yang diinstall secara default.
$ svn rename config/schema.xml.sample config/schema.xml
Sintaks yang digunakan pada `schema.xml`, dijelaskan secara detail di
[Website Propel][3], sintaksnya relatif sederhana: Sintaks ini berbentuk
file XML, dimana tag `
` mengandung ``, `` dan
tag ``. Setelah Anda menulisnya sekali, Anda akan dapat menulis
semuanya. Berikut ini adalah `schema.xml` yang sesuai denan relational model
yang telah dijelaskan sebelumnya :
[xml]
Perhatikan pada file ini nama database nya diset menjadi `propel`. tanpa
peduli apa nama database sebenarnya. Parameter ini digunakan untuk melakukan
koneksi dari layer Propel ke framework symfony. Nama sebenarnya dari
database akan didefinisikan pada file konfigurasi `databases.yml` (lihat
dibawah).
Ada cara lain untuk membuat file `schema.xml` jika anda sudah memiliki
database. Jika Anda sudah familiar dengan tool design database yang grafis,
Anda akan lebih suka membuat schema dari database MySQL yang digenerate.
Sebelum Anda melakukan hal tersebut, Anda hanya perlu mengedit file
`propel.ini` yang terletal di direktori `askeet/config/` dan masukkan
setingan koneksi ke database Anda :
propel.database.url = mysql://username:password@localhost/databasename
...dimana `username`,`password`,`localhost`, dan `databasename` adalah
...setingan koneksi dari database Anda. Sekarang Anda dapat menggunakan
...perintah `propel-build-schema` (dari direktori askeet) untuk menggenerate
...`schema.xml` dari database.
$ symfony propel-build-schema
>**Catatan**: Beberapa tool ada yang bisa membantu Anda untuk membuat database
>secara grafis (misalnya [Fabforce DbDesigner](http://www.fabforce.net/dbdesigner4/)) dan menggenerate
>`schema.xml` secara langsung. (dengan [DB Designer 4 TO Propel Schema
>Converter](http://blog.tooleshed.com/docs/dbd2propel/transform.php)).
### Pembuatan model Object
Untuk menggunakan engine InnoDB, sebuah baris harus ditambahkan pada file
`propel.ini` di direktori `askeet/config/` :
propel.mysql.tableType = InnoDB
Setelah `schema.xml` dibuat, Anda dapat menggenerate model object yang
berdasarkan pada relational model. Pada symfony, object relational mapping
ini ditangani o;eh Propel, tetapi diegkapsulasi ke perintah symfony :
$ symfony propel-build-model
Perintah ini (yang perlu Anda gunakan dari direktori proyek askeet) akan
menggenerate clas-class yang berhubungan dengan semua tabel yang
didefinisikan pada schema, bersama dengan accesor standar(method `->get()` dan
`->set()`). Anda dapat melihat code yang digenerate ini pada direktori
`askeet/lib/model/om/`. Jika Anda bertanya-tanya kenapa ada dua buah class
per tabel, silahkan cek [bab
model](http://symfony-project.com/book/1_0/08-Inside-the-Model-Layer) pada buku
symfony. Class-class ini akan ditulis ulang kembali setiap kali anda
melakukan `build-model`, dan ini akan sering terjadi pada proyek ini. Jadi,
jika Anda ingin menambahkan method ke model object, Anda harus memodifikasi
class-class yang terletak di direktori `askeet/lib/model/` - class-class ini
merupakan warisan (inherit) dari class-class yang ada di `/om`.
Database
------------
### Koneksi
Sekarang symfony telah memiliki model object dari database, sekarang saatnya
mengkoneksikan proyek Anda dengan database MySQL. Pertama-tama, Anda harus
membuat sebuah database di MySQL:
$ mysqladmin -u youruser -p create askeet
Sekarang buka file konfigurasi `askeet/config/databases.yml`. Jika ini
adalah pertama kalinya Anda menggunakan symfony, Anda akan menemukan kalau
file konfigurasi symfony ditulis dalam [YAML][4]. Sintaks ini sangat
sederhana, tapi ada satu aturan yang sangat penting dalam file YAML: jangan
menggunakan tab, selalu gunakan spasi. Setelah Anda mengetahui hal ini, Anda
sudah siap untuk mengedit file dan menuliskam setingan koneksi yang benar ke
database Anda di bawah kategori `all:` :
all:
propel:
class: sfPropelDatabase
param:
phptype: mysql
host: localhost
database: askeet
username: youruser
password: yourpasswd
Jika Anda ingin tahu lebih banyak tentang konfigurasi symfony dan file YAML,
bacalah [bab Konfigurasi dalam
Praktek](http://www.symfony-project.com/book/1_0/19-Mastering-Symfony-s-Configuration-Files)
pada buku symfony.
### Build
Jika Anda tidak menulis file `schema.xml` dengan tangan, Anda mungkin telah
memiliki tabel-tabel ini di database Anda. Anda dapat melewatkan bagian ini.
Untuk Anda penggemar kwyboard, ini adalah sebuah kejutan. Anda tidak perlu
memnbuat tabel dab kolom pada MySQL database. Anda melakukannya sekali di
`schema.xml`, jadi symfony akan membuatkan semua statemen SQL untuk Anda:
$ symfony propel-build-sql
Perintah ini akan membuat `schema.xml` pada direktori `askeet/data/sql/`.
Gunakan perintah SQL ini pada MySQL:
$ mysql -u youruser -p askeet < data/sql/lib.model.schema.sql
Mengetes akses data melalui CRUD
---------------------------------
Sangatlah menyenanfkan melihat apa yang kita kerjakan itu berguna. Sampai
sekarang, browser Anda belum pernah digunakan, padahal kita seharusnnya
membuat aplikasi web...
Jadi mari kita membuat beberapa tenpale dan action symfony untuk
memanipulasi data di tabel 'question'. Ini akan memperbolehkan Anda untuk
membuat beberapa pertanyaan dan menampilkannya : .
Pada direktori `askeet/`, ketik :
$ symfony propel-generate-crud frontend question Question
Ini akan menngenerate scaffolding untuk module `question` pada aplikasi
`frontend` yang berdasarkan pada model object Propel `Question`, dengan
action Create Retrieve, Update Delete (yang disingkat dengan akronim CRUD).
Jangan binung: Scaffolding bukanlah aplikasi yang siap digunakan, melainkan
struktur dasar dimana dengan struktur dasar ini Anda dapat membangun
fitur-fitur baru, menambahkan business rule dan mengkostumisasi tampilannya.
Daftar semua action yang dibuat oleh generator CRUD adalah:
| Nama Action | Penjelasan
|--------------|------------
| list | menunjukkan semua record pada tabel
| index | diforward ke action list
| show | memperlihatkan semua field dalam suatu record
| edit | menampilkan sebuah form untuk membuat record baru atau mengedit data yang sudah ada
| update | memodifikasi sebuah record tergantung pada parameter yang diberikan di request, kemudian diforward ke show
| delete | mengahapus suatu record pada tabel
Anda dapat membaca tentang action-action yang digenerate pada [bab
scaffolding](http://www.symfony-project.com/book/1_0/14-Generators)
dari buku symfony.
Pada direktori, `askeet/apps/frontend/modules/`, perhatikan ada module baru,
yaitu `question`, coba browse source nya.
Setiap kali Anda perlu menambahkan class baru yang perlu autoloaded, jangan
lupa untuk membersihkan cache config (untuk mereload cache autoloading):
$ symfony cc frontend config
Anda sekarang dapat mengetesnya online dengan merequest:
http://askeet/question


Silahkan bermain-mainlah dengannya. Tambahkan beberapa pertanyaan,
mengeditnya, melist dan menghapusnya. Jika bekerja, maka ini berarti object
model telah benar, koneksi ke database benar, dan mapping antara relational
model antara database dan model symfony benat. Ini merupakan test
fungsional yang bagus.
Sampai Jumpa Besok
------------------
Anda tidak menulis sebaris kode PHP pun, tetapi Anda telah memiliki aplikasi
dasar untuk digunakan. Ini tidak buruk untuk hari kedua. Besok, kita akan
mulai menulis beberapa code untuk memiliki halaman selamat datang yang
menampilkan daftar pertanyaan.
Kita juga akan menambahkan data test ke database kami dengan menggunakan
batch process, dan mempelajari bagaimana meng-ekstend model.
Sekarang Anda tahu apa yang akan dilakukan oleh aplikasi, Anda mungkin bisa
membayangkan fitur tambahan yang dapat ditambahkan. Silahkan memberikan usul
tentang fitur yang ingin ditambahkan dengan menggunakan [mailing-list
askeet](mailto:askeet-subscribe@symfony-project.com), ide yang paling
populer akan menjadi tanbahan untuk hari ke 21 pada symfony advent calendar.
Silahkan melihat-lihat source tutorial hari ini (tag `release_day_2`) pada :
http://svn.askeet.com/tags/release_day_2
[1]: http://www.xprogramming.com/xpmag/whatisxp.htm "(XP) Extreme Programming Explained"
[2]: http://www.uml.org/ "Unified Modeling Language"
[3]: http://propel.phpdb.org/trac/ "Propel"
[4]: http://www.yaml.org/ "YAML"