14 Apr 2010
Update 2011-12-02: karena masih aja banyak yang belum paham, saya tambahkan template pertanyaan di akhir artikel.
Sebagai programmer, setiap hari kita menghadapi software yang error. Bentuknya macam-macam, misalnya:
-
Aplikasi yang kita buat error
-
Peserta milis menggunakan framework X dan mengalami masalah
-
Rekan sesama programmer membutuhkan bantuan
-
dsb
Pada sebagian besar kasus, kita dengan senang hati akan membantu. Sudah menjadi sifat programmer untuk memiliki rasa keingintahuan yang tinggi dan senang terhadap teka-teki. Aplikasi yang error adalah teka-teki yang menarik.
Sayangnya, seringkali informasi error yang kita terima tidak lengkap sehingga butuh usaha tambahan untuk mengorek kejadian yang sebenarnya. Inilah yang membuat programmer seringkali keburu malas, sehingga akhirnya kegiatan solving error menjadi tidak fun lagi.
Berikut adalah beberapa tips untuk membuat laporan error yang baik, supaya programmer yang akan memecahkan masalah tersebut bisa segera bekerja dengan efektif.
Prinsip utama dalam melaporkan error adalah sebagai berikut
Programmer bukan Mama Loren Baby Djenar atau Ki Joko Bodo. Dia tidak bisa membaca pikiran ataupun melakukan telepati. Jadi jangan menganggap programmer melihat apa yang dilihat user. User harus menjelaskan apa yang dia lihat.
Jelaskan lokasinya
Seringkali si informan error berkata seperti ini,
Help, aplikasinya error nih
Nah, yang menerima informasi jelas bingung. Aplikasi yang mana?
Kalo client yang jadi informan, bisa jadi kita punya banyak project di sana.
Walaupun projectnya cuma satu, tapi aplikasi kan bisa terdiri dari banyak modul, screen, fitur, dsb.
Jadi, jelaskan di mana errornya. Di aplikasi apa, modul apa, screen yang mana. Terdengar simple, tapi nyatanya ada saja yang melewatkan hal pertama ini.
Mari kita lanjutkan.
Tujuan
Kita menggunakan aplikasi tentu ingin mencapai tujuan tertentu. Ingin menyimpan data customer, menampilkan laporan bulanan, dan lain sebagainya. Nah, tujuan ini harus disampaikan ke programmer. Soalnya sering terjadi percakapan seperti ini :
User (U) : Pak, fitur daftar produknya error.
Programmer (P) : Harusnya bisa kok, sudah kami test di sini tidak ada masalah.
U : Tapi saya coba tidak bisa
P : Coba jelaskan langkahnya
U : Saya buka menu daftar produk, muncul tabel berisi produk.
Kemudian saya klik dua kali nama produk dalam tabel, saya ganti isinya.
Setelah itu, saya tutup screennya.
Pas dibuka lagi, datanya tetap sama.
P : Lho, memangnya Ibu mau melakukan apa?
U : Saya mau edit harga produknya
P : Walah, bukan dari situ Bu. Gunakan menu edit produk
Nah, seringkali tujuan user tidak sesuai dengan fitur aplikasi. Jadi, beri tahukan tujuan user pada programmer.
Langkah Reproduksi
Begitu programmer akan mencoba memperbaiki error, dia akan mencoba mereproduksi error tersebut di komputernya sendiri. Nah di sinilah biasanya terjadi percakapan seperti ini :
U : Ini aplikasi error, tidak bisa simpan data
P : Oh, di sini saya coba bisa kok
U : Di sini tidak bisa
P : Di sini bisa
U : Tidak bisa
P : Bisa
dst
Akan lebih produktif kalau percakapannya seperti ini :
U : Ini aplikasi error, tidak bisa simpan data
P : Apa yang dilakukan?
U : Seperti ini :
- Buka screen Edit Produk
- Pilih kategori Komputer dan Elektronik
- Isi kode produk
- Isi nama produk
- Harga dikosongkan
- Tekan tombol simpan
Nah, dengan percakapan seperti ini, programmer bisa mengulangi apa yang dilakukan user.
Apakah langkah repro saja sudah cukup? Belum, masih ada 1 hal penting lainnya.
Harapan dan Kenyataan
Mari kita lanjutkan percakapan di atas.
U : Setelah ditekan tombol simpan, datanya tidak tersimpan.
P : Di tempat saya masuk kok ke database.
U : Di sini, setelah ditekan simpan tidak terjadi apa-apa
P : Maksudnya?
U : Ya harusnya kan ada pesan, “Data sudah tersimpan”
Ini tidak ada.
Nah, di sini harapan user adalah ada notifikasi dari aplikasi bahwa data sudah tersimpan. Tapi kenyataannya tidak ada notifikasi apa-apa dari aplikasi. User mengira ini error,
padahal programmer memang tidak menyediakan notifikasi tersebut, walaupun datanya sudah masuk ke database. Dari sini, programmer bisa menambahkan notifikasi sesuai harapan user.
Jadi, harapan dan kenyataan harus disampaikan pada programmer.
Environment
Ini maksudnya adalah kondisi di mana aplikasi dijalankan, seperti
Sering terjadi aplikasi error hanya di Linux saja, atau di Mac saja, tapi berjalan lancar di Windows. Atau sebaliknya. Dengan memberi informasi ini, programmer bisa lebih terarah dalam mencari kesalahan dalam kode program.
Demikian juga dengan versi aplikasi dan aplikasi lain yang terinstal. Seringkali sudah diketahui bahwa aplikasi kita tidak kompatibel dengan versi library tertentu, versi OS tertentu, atau dengan aplikasi lain. Misalnya seperti ini :
Tanya (T) : Saya instal Tomcat tapi error
Jawab (J) : Errornya gimana?
T : Katanya port 8080 tidak bisa digunakan.
J : Apakah ada webserver lain yang terinstal?
T : Web server sih tidak ada, saya cuma install database Oracle saja.
J : Oh, Oracle itu membawa web server sendiri, jalannya juga di 8080.
Coba matikan Oraclenya, atau ganti port Tomcat ke angka lain.
Demikian beberapa tips melaporkan error.
Berikut ringkasannya :
-
Jelaskan Lokasinya
-
Sebutkan Tujuan
-
Langkah Reproduksi
-
Harapan dan Kenyataan
-
Environment
Berikut template yang bisa digunakan untuk mengajukan pertanyaan.
Saya ingin …… (misal : mendeploy aplikasi di glassfish),
untuk itu saya melakukan langkah2 berikut :
- ….
- ….
- ….
Setelah saya lakukan langkah di atas, saya mengharapkan hasil sbb:
- …..
- …..
- …..
Tapi ternyata kok malah muncul hasil seperti ini :
- ….
- ….
- ….
Sebagai tambahan informasi, saya menggunakan :
- Sistem Operasi … versi …
- Bahasa Pemrograman … versi …
- Database … versi …
- Framework/Tools … versi …
Dengan mengikuti tips ini berarti Anda sudah membantu kami untuk membantu Anda.
:D
10 Mar 2010
Pertanyaan yang sering muncul dalam pengelolaan proyek software adalah, “Dokumen apa saja yang harus dibuat?”
Tidak ada jawaban absolut untuk pertanyaan ini, semuanya tergantung situasi dan kondisi. Bahkan di satu perusahaan yang sama, kelengkapan dokumen projectnya bisa saja berbeda antar project.
Dalam artikel ini, kita akan membahas bagaimana menentukan dokumen yang digunakan dalam project.
Disclaimer : Semua yang dijelaskan pada artikel ini ditulis berdasarkan pengalaman dan kebutuhan internal ArtiVisi. Kebutuhan Anda belum tentu sama dengan kami.
Pertama, kita harus tahu dulu latar belakang kenapa dokumen project dibutuhkan. Setidaknya ada beberapa kegunaan dokumen project, yaitu
-
sebagai media komunikasi di internal tim, dengan client, dengan manajemen, dan pihak lain yang berkepentingan (stakeholder)
-
sebagai catatan historis jalannya project
-
sebagai alat bantu untuk melihat kondisi terkini project (project visibility)
-
sebagai kontrak legal bila terjadi perselisihan
Setelah kita mengetahui apa saja kegunaan dokumen, mari kita teliti satu persatu berdasarkan fase dalam project.
Fase Sales
Biasanya pada saat ada tawaran project, kita akan membuat proposal yang relatif tebal (> 10 halaman). Kami di ArtiVisi saat ini sudah hampir tidak pernah membuat proposal project, karena beberapa alasan berikut :
Fungsi proposal sebenarnya adalah panduan awal untuk membuat agreement. Poin-poin yang ada di proposal akan dipindahkan ke agreement yang selanjutnya akan ditandatangani kedua belah pihak.
Kami menyederhanakan proposal menjadi quotation biasa, yang berisi informasi sbb :
Ada beberapa informasi yang biasa ada di proposal dan tidak ada di quotation, yaitu
-
teknologi yang digunakan. Biasanya client kami menurut saja apa solusi yang kita rekomendasikan. Kalaupun ada requirement khusus, akan ditulis di bagian requirement khusus di quotation
-
skema layer, tier, database diagram, dsb. Biasanya, implementasi internal aplikasi tidak perlu dipikirkan client. Client cukup menentukan what to be built, dan kami yang memikirkan how to build. Kalau client ingin ikut cawe-cawe urusan internal, biasanya kita tawarkan outsourcing programmer saja, bukan project software.
Selanjutnya, setelah quotation dinegosiasikan dan disetujui, tiba saatnya membuat agreement, atau perjanjian kerja sama. Ada beberapa poin yang dicantumkan dalam agreement, yaitu :
-
scope pekerjaan
-
out of scope
-
estimasi durasi
-
klausul keterlambatan delivery
-
termin pembayaran
-
klausul keterlambatan pembayaran
-
prosedur change management
Dari beberapa poin di atas, poin klausul keterlambatan delivery harus mendapat perhatian khusus. Keterlambatan delivery bisa terjadi karena banyak sekali sebab. Tidak semua diantaranya adalah kesalahan tim project. Oleh karena itu, kalau ada klausul seperti ini di agreement, tim project harus mengeluarkan effort ekstra untuk melakukan project tracking. Dengan demikian, bila terjadi keterlambatan, ada data yang lengkap mengenai riwayat dan penyebab keterlambatan tersebut.
Selesai bagian agreement, mari kita masuk ke tahap berikutnya.
Project Planning
Tujuan dari dilakukannya dokumentasi pada fase ini adalah untuk mengkomunikasikan bagaimana project akan berjalan, baik ke internal tim maupun ke client. Berikut informasi yang ada dalam project plan :
-
Milestone dan Delivery : list urutan delivery yang akan disampaikan, isi dari masing-masing delivery, dan estimasi tanggalnya
-
Daftar Task untuk Milestone berikut. Kita tidak melakukan breakdown untuk milestone lainnya, karena masih banyak ketidakpastiannya. Breakdown task hanya dilakukan untuk milestone yang ada di depan mata. Begitu suatu milestone akan selesai, baru dilakukan breakdown task untuk milestone selanjutnya.
-
Daftar Resiko Project : ini adalah hal-hal yang berpotensi menghambat jalannya project, seperti misalnya ada PIC client yang akan resign, teknologi yang belum familiar, dsb
Kami tidak membuat Gantt chart. Sebabnya karena Gantt chart sangat menekankan pada dependensi antar task. Sedangkan di project software, dependensi sangat mudah berubah. Misalnya, kita definisikan Modul B dikerjakan setelah Modul A. Ternyata karena PIC client di modul A sedang ada training di luar kota, diputuskan bahwa Modul B akan dikerjakan duluan. Atau, tadinya direncanakan skema database akan dikerjakan sebelum desain UI. Tapi ternyata karena satu dan lain hal, terpaksa UI dikerjakan duluan.
Hal-hal seperti ini cukup sering terjadi dalam project. Sehingga penggunaan Gantt chart justru akan merepotkan kita dalam mengupdate project plan. Kita tahu, semakin sulit dokumen diubah, semakin malas kita mengubahnya, dan akhirnya dokumen tersebut menjadi tidak up to date.
Project Tracking
Project tracking adalah kegiatan untuk memantau jalannya project. Dalam kegiatan ini, project manager melihat kemajuan project, mengidentifikasi masalah yang terjadi, dan mencarikan solusinya. Kalau masalah yang terjadi berada di luar kemampuan PM, dia akan melakukan eskalasi, yaitu meminta bantuan ke atasannya.
Di ArtiVisi, kita cuma menggunakan satu dokumen untuk melakukan project tracking, yaitu progress report mingguan, yang berisi informasi sbb:
-
Daftar task yang dikerjakan minggu ini dan statusnya, apakah sudah selesai, sedang dikerjakan, atau belum dimulai
-
Daftar task yang akan dikerjakan minggu depan
-
Daftar deliverable yang akan diberikan minggu depan
-
Resiko project saat ini. Daftar ini dibuat pada saat planning, terus menerus dipantau setiap minggu, dan dilaporkan statusnya
-
Masalah yang terjadi dalam project dan action plan yang dilakukan
-
Perubahan terhadap estimasi awal
Dokumen ini dibuat oleh PM setelah berkonsultasi dengan pasukannya, kemudian dikirim ke manajemen internal dan client. Dengan tidak adanya Gantt chart, kita tidak perlu mengeluarkan effort ekstra untuk mengupdate Gantt chart.
Fase Requirement
Pada fase ini, tim project menganalisa kebutuhan user sebagai patokan di fase coding. ArtiVisi cuma membuat satu dokumen pada fase ini, yaitu User Story. Dokumen user story berisi informasi sbb:
-
User Goal : tujuan yang ingin dicapai client dalam menggunakan fitur ini
-
Ijin Akses : security level untuk menjalankan fitur ini
-
Penjelasan : deskripsi naratif tentang fitur ini
-
Flow aplikasi : langkah-langkah untuk menjalankan fitur ini
-
Desain screen : screenshot prototype atau scan paper prototype
-
Rincian field : penjelasan masing-masing komponen dalam desain screen
-
Prasyarat : hal-hal yang harus terjadi/ada sebelum fitur ini bisa dijalankan
-
Kondisi awal : kondisi aplikasi (data, screen, dsb) sebelum fitur dijalankan
-
Kondisi akhir : kondisi aplikasi setelah fitur selesai dijalankan
-
Karakteristik khusus : kebutuhan khusus seperti response time, usability, dsb
-
Flow pengetesan : bagaimana cara mengetes fitur ini
-
Sign Off : persetujuan user bahwa deskripsi dalam fitur ini sudah sesuai keinginan
Nantinya akan ada banyak dokumen User Story sesuai jumlah fitur dalam aplikasi. Setelah User Story ditandatangani, semua perubahan harus melalui change procedure, yaitu dengan mengisi change request form. Berikut informasi yang ada di dalam change request form :
-
Penjelasan Perubahan : deskripsi dari apa saja yang ingin diubah
-
Alasan Perubahan : mengapa perubahan ini diajukan
-
Benefit : keuntungan bila perubahan diimplementasikan
-
Dampak : akibat terhadap durasi, effort, dokumen, source code bila perubahan jadi diimplementasikan
-
Estimasi : estimasi effort, durasi, cost untuk menjalankan perubahan ini
-
Approval : persetujuan manajemen baik kedua belah pihak terhadap perubahan ini
Fase Desain
Di fase desain biasanya kami mendesain beberapa hal berikut:
-
skema database
-
interkoneksi antar modul
-
protokol komunikasi
-
format data
Walaupun prosesnya dilakukan, tapi tidak ada dokumen permanen yang dihasilkan. Skema database misalnya. Desain dibuat di papan tulis, dan langsung ditulis dalam bentuk source code (SQL atau Hibernate mapping). Bila suatu saat diperlukan diagram, akan digenerate dengan tools dari database development. Protokol komunikasi dan format data akan dibuat di dokumen user story sebagai requirement internal.
Fase Coding
Pada fase ini, kita menghasilkan source code dan user manual.
Fase UAT
Pada fase ini, kita membuat dua dokumen, yaitu hasil pengetesan sesuai skenario di User Story dan Berita Acara UAT. Biasanya (tapi tidak selalu), berita acara dan hasil pengetesan digunakan sebagai lampiran penagihan.
Fase Implementasi
Pada fase ini, cuma satu dokumen yang dihasilkan, yaitu Berita Acara Serah Terima Aplikasi. Dokumen ini dibuat dan ditandatangani setelah kegiatan implementasi selesai dilakukan. Beberapa kegiatan dalam fase ini antara lain :
-
Instalasi Aplikasi
-
Training User
-
Deployment Aplikasi
-
Paralel Run
Demikian dokumentasi project yang kita buat selama project. Tidak terlalu banyak kan? Berikut daftarnya
-
Quotation
-
Agreement
-
Project Plan
-
Progress Report
-
User Story
-
Requirement Sign Off
-
Change Request Form (kalau perlu)
-
User Manual
-
Berita Acara UAT
-
Berita Acara Serah Terima Aplikasi
Kesimpulannya, buatlah dokumen sesuai kebutuhan, bukan sesuai hype yang sedang trend saat ini dan bukan juga sesuai warisan leluhur.
16 Feb 2010
Di berbagai milis yang saya ikuti, ada diskusi menarik yang muncul. Apa saja yang harus dilakukan untuk dalam project management? Bagaimana SOP (standard operating procedure) nya? Tools apa yang digunakan?
Saya sudah mencoba berbagai metodologi manajemen proyek sepanjang karir saya. Ala koboi di jaman jahiliah dulu, ala waterfall di perusahaan terdahulu, ala CMMI di BaliCamp, dan berbagai ala-ala lainnya. Sepanjang perjalanan tersebut, saya juga membaca tentang berbagai metodologi seperti XP, Scrum, Crystal, RUP, dsb.
Dari semuanya, tentu tidak ada metodologi yang bisa digunakan di semua kondisi. Segalanya serba tergantung keadaan. Walaupun demikian, hasil pengalaman bertahun-tahun tersebut sudah memberikan saya pemahaman tentang latar belakang di aturan-aturan CMMI maupun di metodologi lainnya. Begitu kita mendapatkan alasan dibalik aturan tersebut, kita bisa mengambil esensinya dan mengimplementasikannya dengan bentuk lain yang sesuai dengan situasi kita.
Berikut adalah manajemen proyek ala ArtiVisi.
Fase dan Siklus
Sebelum membahas lebih jauh tentang manajemen proyek, kita luruskan dulu beberapa istilah. Kita mengenal istilah fase dan siklus (lifecycle)
Fase adalah tahapan yang dilalui dalam membuat aplikasi. Biasanya, dalam satu fase akan terdiri dari banyak task.
Fase yang ada di internal ArtiVisi adalah sebagai berikut :
- Requirement Development
- Coding
- User Acceptance Test
- Implementasi
Keempat fase ini berjalan secara serial, artinya, fase coding baru bisa dimulai setelah requirement development selesai, dsb.
Mendengar ini, pembaca yang beraliran progresif revolusioner pasti langsung demo di Bundaran HI, “Waterfall is dead, long live Agile !!!”
Tunggu dulu sebentar, waterfall dan iteratif itu adalah lifecycle, bukan fase.
Lalu apa itu lifecycle? Lifecycle adalah urutan kita menjalankan fase tersebut di keseluruhan project. Bagaimana maksudnya ini?
Begini, misalnya kita membuat aplikasi akunting. Aplikasi ini terdiri dari beberapa modul yaitu; ledger, hutang/piutang, dan manajemen kas. Lifecycle waterfall adalah apabila kita menjalankan project dengan urutan seperti ini :
-
Project Planning
- Modul Ledger
- Modul Hutang/Piutang
- Modul Kas
-
Requirement Development
- Modul Ledger
- Modul Hutang/Piutang
- Modul Kas
-
Coding
- Modul Ledger
- Modul Hutang/Piutang
- Modul Kas
-
UAT
- Modul Ledger
- Modul Hutang/Piutang
- Modul Kas
-
Implementasi
- Modul Ledger
- Modul Hutang/Piutang
- Modul Kas
Lifecycle waterfall memang memiliki banyak kelemahan, apalagi kalau projectnya besar. Karena rentang waktu yang jauh antara fase requirement dan fase UAT, maka biasanya pada saat UAT user merasa kaget karena merasa aplikasi yang dibuat tidak sesuai ekspektasi. Entah karena user sudah lupa requirement yang dia bikin sendiri, ataupun karena proses bisnisnya memang sudah berubah.
Lifecycle yang dijalankan ArtiVisi adalah Staged Delivery, seperti yang dijelaskan di bukunya Steve McConnell berjudul Rapid Development. Berikut urutannya.
-
Global / High Level
- Project Planning
- Requirement Development
-
Modul Ledger
- Project Planning
- Requirement Development
- Coding
- UAT
- Implementasi
-
Modul Hutang/Piutang
- Project Planning
- Requirement Development
- Coding
- UAT
- Implementasi
-
Modul Kas
- Project Planning
- Requirement Development
- Coding
- UAT
- Implementasi
Pendekatan ini bukan waterfall, karena delivery-nya iteratif dan kecil-kecil. Satu modul biasanya berkisar 1 - 2 bulan saja, kira-kira sesuai dengan panjang sprint yang dianjurkan di metodologi Scrum. Tapi pendekatan ini juga bukan murni agile, karena ada global project planning dan requirement di awal. Untuk apa ada kegiatan itu? Tidak lain dan tidak bukan adalah untuk mengantisipasi interkoneksi antar modul.
Bila kita langsung mengambil salah satu modul untuk diiterasi, maka ada resiko modul tersebut tidak nyambung dengan modul lainnya. Memang bisa disambungkan, tapi nanti akan berkesan tambal sulam. Istilahnya Fred Brooks dalam Mythical Man Month, tidak ada Conceptual Integrity. Oleh karena itu kita perlu melakukan global requirement development untuk melihat interaksi antar modul.
Pembaca yang teliti mungkin juga akan bertanya, mengapa kita menggunakan istilah Requirement Development, bukannya Requirement Gathering? Ini karena untuk mendapatkan requirement, perlu usaha ekstra, tidak sekedar memungut (gathering) informasi di sana-sini. Seringkali kita harus menanyakan hal yang sama dari beberapa sudut pandang untuk mendapatkan apa maunya user. Di saat lain, kita harus bisa menebak fitur yang tersirat. Kalau user bilang, “Harus ada fitur untuk menyimpan data transaksi”, berarti tidak cuma ada screen edit dan list. Tapi juga harus ada fitur search berdasarkan tanggal, produk, nilai transaksi, dan atribut lainnya. Kadangkala ini juga berarti harus ada fitur untuk export/import ke format file lainnya. Jadi, untuk mendapatkan requirement, perlu proses development. Mulai dari sedikit, lalu diakumulasi, dan dikristalisasi sehingga benar-benar akurat dan lengkap. Jangan sampai ada yang ketinggalan.
Kelima fase yang dijelaskan di atas merupakan fase yang sekuensial. Artinya, satu fase dijalankan setelah fase lain selesai. Kita tidak bisa mulai implementasi sebelum UAT selesai. Well, bisa sih, tapi hasilnya tidak akan menyenangkan. Demikian juga, kalau belum selesai coding, ya jangan UAT dulu. Bisa sih maksain UAT, tapi tentu tidak akan menyenangkan. Begitu juga halnya kalau kita coding sebelum jelas requirementnya.
Selain fase yang sekuensial tersebut, ada juga serangkaian kegiatan yang harus kita lakukan secara kontinyu sepanjang project. Yaitu project tracking dan change management.
Project Tracking
Project tracking tidak sulit. Setiap minggu, harus ada orang yang melihat project plan dan membandingkan dengan kondisi sekarang. Task mana yang sudah selesai, mana yang sedang dikerjakan, mana yang sudah selesai. Kondisi sekarang ini direkap ke dalam satu laporan, 1-2 halaman, dan dilaporkan ke client dan manajemen. Di ArtiVisi, mengadopsi dari BaliCamp, selain rekap task juga disertakan rekap resiko dan masalah yang terjadi dalam proyek. Ini akan menjadi bahan diskusi dengan client, bagaimana cara memecahkan masalah tersebut, dan bagaimana mencegah resiko agar tidak berdampak merugikan.
Requirement Development
Sebelum membahas change management, kita bahas dulu requirement. Di ArtiVisi, requirement bentuknya adalah daftar screen aplikasi, biasanya dibuat dengan Netbeans. Kami tidak menggunakan format naratif seperti yang dianut beberapa organisasi dan dinamai User Requirement Specification (URS), Business Requirement Specification (BRS), atau Software Requirement Specification (SRS), User Story, atau istilah-istilah lainnya. Berdasarkan pengalaman, dokumen naratif membuat user malas berinteraksi. Untuk aplikasi shopping cart sederhana saja, bila dibuatkan *RS, akan menjadi lebih dari 20 halaman. Apalagi untuk aplikasi yang besar. Client akan malas membaca, dan akibatnya pada saat aplikasi dideliver hasilnya tidak sesuai ekspektasi, walaupun sesuai dengan *RS.
ArtiVisi menggunakan prototype aplikasi untuk requirement. Kita buatkan screen desktop ataupun web, diisi data hardcoded, dan sudah memiliki menu dan flow. Dari screen registrasi klik submit akan masuk screen konfirmasi, dst. Dengan menggunakan prototype yang bisa diisi dan diklik, user akan lebih bersemangat untuk berinteraksi, sehingga hasil requirement akan menjadi berkualitas. Pada fase requirement ini user bebas meminta modifikasi apapun asal masih dalam scope yang disepakati.
Setelah tidak ada lagi perubahan signifikan, semua screen dicapture, dimasukkan ke dokumen, dan diapprove client (sign off). Ini akan menjadi patokan dalam proses development, diantaranya digunakan oleh programmer untuk coding, dan technical writer untuk membuat user manual.
Change Management
Perubahan setelah sign off harus melalui prosedur change management. Ini gunanya agar progress project bisa terkendali. Sering sekali banyak project molor dan tidak selesai-selesai karena banyak perubahan ini itu yang tidak dikelola dengan baik sehingga tidak terlihat titik akhirnya.
Prosedur change management tidak rumit. Hanya terdiri dari tiga langkah saja, yaitu :
- Requester menjelaskan perubahan yang diminta, apa alasan yang mendasari perubahan
- Tim development menganalisa dampak perubahan, apakah ada coding yang berubah, user manual, test scenario, dsb. Output dari analisa ini adalah estimasi berapa tambahan waktu, tenaga, dan biaya untuk mengeksekusi perubahan ini
-
Manajemen di sisi client memutuskan berdasarkan estimasi tersebut, apakah perubahan ini akan :
- Dijalankan segera
- Ditunda ke iterasi berikut
- Ditolak, artinya tidak jadi dijalankan pada project ini, mungkin saja dijadikan project baru.
Dengan adanya proses ini, akan jelas berapa hari project akan mundur, dan berapa biaya tambahannya.
Demikian sharing tentang praktek yang kita gunakan di ArtiVisi. Metodologi ini cukup sederhana, sehingga bisa dijalankan bahkan di project yang one-man-show. Project manager dia, business analyst dia, programmer dia juga, training lagi-lagi dia, terima transferan tidak lain dan tidak bukan adalah dia juga. Di project berskala besar, metodologi ini juga cukup efektif untuk membuat project berjalan secara predictable.
Masih ada penjelasan lebih lanjut yang harus ditulis, diantaranya bagaimana cara menghitung (estimasi) project, dan bagaimana melakukan project planning dan tracking yang efektif. Ini akan dibahas di tulisan yang lain.
Bila ingin berkomentar atau berdiskusi, silahkan bergabung di milis it-project-indonesia@googlegroups.com dengan cara mengirim email kosong ke it-project-indonesia-subscribe@googlegroups.com
15 Jul 2009
Di mana kita harus menyimpan log output aplikasi kita? Tentunya kita ingin menggunakan lokasi yang dinamis sesuai dengan lokasi deployment. Misalnya, di Windows kita mungkin mendeploy aplikasi kita di
C:\Program Files\Apache Tomcat\webapps\aplikasi-saya
Sedangkan di Linux, kita mendeploy aplikasi di
/opt/apache-tomcat/webapps/aplikasi-saya
Dengan kemungkinan seperti di atas, bagaimana kita harus menulis konfigurasi log4j?
Mudah, bila kita menggunakan Spring MVC.
Kita bisa menggunakan Log4jConfigListener
yang disediakan Spring. Class ini memungkinkan kita menggunakan variabel di konfigurasi log4j kita. Kita mendaftarkan class ini di dalam web.xml
, sebelum ContextLoaderListener
, seperti ini :
<listener>
<listener-class>org.springframework.web.util.Log4jConfigListener</listener-class>
</listener>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
Dengan adanya Log4jConfigListener
ini, kita bisa menyebutkan lokasi konfigurasi log4j seperti ini :
<context-param>
<param-name>log4jConfigLocation</param-name>
<param-value>classpath:artivisi-log4j.properties</param-value>
</context-param>
Isi artivisi-log4j.properties
terlihat seperti ini :
# Konfigurasi kategori
log4j.rootLogger=INFO,fileout
# File output
log4j.appender.fileout=org.apache.log4j.DailyRollingFileAppender
log4j.appender.fileout.file=${webapp.root.path}/WEB-INF/logs/application.log
log4j.appender.fileout.datePattern='.'yyyy-MM-dd
log4j.appender.fileout.layout=org.apache.log4j.PatternLayout
log4j.appender.fileout.layout.conversionPattern=%d [%t] %p (%F:%L) %m%n
Perhatikan konfigurasi log4j.appender.fileout.file
. Kita menggunakan variabel ${webapp.root.path}
yang akan diisi dengan nilai lokasi deployment aplikasi web kita. Variabel ${webapp.root.path}
ini didefinisikan dalam web.xml sebagai berikut :
<context-param>
<param-name>webAppRootKey</param-name>
<param-value>webapp.root.path</param-value>
</context-param>
Dengan konfigurasi ini, kita dapat meletakkan log output kita di
C:\Program Files\Apache Tomcat\webapps\aplikasi-saya\WEB-INF\logs\application.log
bila kita mendeploy di Windows, dan di
/opt/apache-tomcat/webapps/aplikasi-saya/WEB-INF/logs/application.log
bila kita deploy di Linux.
Konfigurasi di atas bisa disederhanakan lagi bila kita mengikuti nilai default yang disediakan Spring, yaitu cukup seperti ini dalam web.xml
:
<listener>
<listener-class>org.springframework.web.util.Log4jConfigListener</listener-class>
</listener>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
Kemudian memberi nama file konfigurasi logger kita log4j.properties
yang berada di top level dalam classpath, dan berisi seperti ini :
# Konfigurasi kategori
log4j.rootLogger=INFO,fileout
# File output
log4j.appender.fileout=org.apache.log4j.DailyRollingFileAppender
log4j.appender.fileout.file=${webapp.root}/WEB-INF/logs/application.log
log4j.appender.fileout.datePattern='.'yyyy-MM-dd
log4j.appender.fileout.layout=org.apache.log4j.PatternLayout
log4j.appender.fileout.layout.conversionPattern=%d [%t] %p (%F:%L) %m%n
Nilai variabel ${webapp.root}
secara default akan diisi dengan lokasi deployment tanpa harus mengkonfigurasi webAppRootKey
03 Jul 2009
Dulu, kita sudah mencoba untuk membuat remoting service dengan menggunakan Spring Framework. Salah satu protokol yang digunakan adalah Spring HTTP Invoker. Untuk mempublish service dengan protokol ini, kita harus menggunakan servlet engine, misalnya Tomcat.
Akan tetapi, Sun Microsystem merilis Java versi 6 yang sudah dilengkapi dengan HTTP Server sederhana. Dengan memanfaatkan fitur ini, kita tidak perlu lagi menggunakan Tomcat hanya untuk mempublish service dengan HTTP Invoker. Ini akan sangat bermanfaat untuk aplikasi kecil yang ingin dipanggil oleh aplikasi lain.
Pada artikel ini, kita akan mempublish service dengan protokol HTTP Invoker pada HTTP Server yang disediakan oleh Sun JRE versi 6.
Di Netbeans, kita akan membuat tiga project, yaitu
-
remoting-shared : project ini menampung interface RemotingService, yang akan digunakan di client dan server
-
remoting-server : project ini yang akan mempublish service. Implementasi RemotingService juga ada di sini
-
remoting-client : project ini yang akan mengakses service yang dipublish remoting-server
Berikut screenshot Netbeans. Project remoting-server dan remoting-client memiliki dependensi terhadap remoting-shared.
Pertama, mari kita lihat dulu service interfacenya. Berikut adalah kode programnya.
package com.artivisi.tutorial.remoting.spring.service.api;
public interface RemotingService {
public String halo(String nama);
}
Kode program ini berada di project remoting-shared.
Berikutnya, kita lihat dulu di sisi client. Kita cuma butuh satu class untuk menjalankan aplikasi, yaitu ClientLauncher sebagai berikut.
package com.artivisi.tutorial.remoting.spring.client;
public class ClientLauncher {
private static final Logger log = Logger.getLogger(ClientLauncher.class.getName());
public static void main(String[] args) {
AbstractApplicationContext ctx =
new ClassPathXmlApplicationContext("client-ctx.xml", ClientLauncher.class);
ctx.registerShutdownHook();
RemotingService service = (RemotingService) ctx.getBean("remotingService");
String msg = service.halo("endy");
log.info("Pesan dari server : "+msg);
}
}
ClientLauncher akan membaca client-ctx.xml yang isinya seperti ini.
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd">
<!-- proxy dengan protokol HTTP Invoker -->
<bean id="remotingService"
class="org.springframework.remoting.httpinvoker.HttpInvokerProxyFactoryBean">
<property name="serviceUrl"
value="http://localhost:9090/RemotingService"/>
<property name="serviceInterface"
value="com.artivisi.tutorial.remoting.spring.service.api.RemotingService"/>
</bean>
</beans>
Seperti kita lihat di atas, client mengakses service yang ada di komputer lokal (localhost) di port 9090, dengan nama service RemotingService.
Selanjutnya, mari kita implement project remoting-server. Di sini ada implementasi RemotingService sebagai berikut
/*
* To change this template, choose Tools | Templates
* and open the template in the editor.
*/
package com.artivisi.tutorial.remoting.spring.service.impl;
@Service("remotingService")
public class RemotingServiceImpl implements RemotingService {
Logger log = Logger.getLogger(RemotingServiceImpl.class.getName());
public String halo(String nama) {
log.info("Terima dari client : "+nama);
return "Halo, "+nama;
}
}
Kemudian ada class untuk menjalankan aplikasi di sisi server. Berikut ServerLauncher.
package com.artivisi.tutorial.remoting.spring.server;
public class ServerLauncher {
public static void main(String[] args) {
AbstractApplicationContext ctx =
new ClassPathXmlApplicationContext("server-ctx.xml", ServerLauncher.class);
ctx.registerShutdownHook();
}
}
ServerLauncher membaca file konfigurasi server-ctx.xml. Inilah isinya.
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:p="http://www.springframework.org/schema/p"
xmlns:context="http://www.springframework.org/schema/context"
xsi:schemaLocation="
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-2.5.xsd">
<!-- menginstankan Sun HttpServer dalam JRE 6 -->
<bean class="org.springframework.remoting.support.SimpleHttpServerFactoryBean">
<property name="contexts">
<map>
<entry key="/RemotingService" value-ref="remotingServiceHttpInvoker"/>
</map>
</property>
<property name="port" value="9090" />
</bean>
</beans>
Pada blok konfigurasi pertama, kita menginstankan Sun HttpServer yang ada di JRE 6. HttpServer ini akan berjalan di port 9090, sesuai dengan yang kita konfigurasi di sisi client. Di sana terlihat bahwa URL /RemotingService akan ditangani oleh remotingServiceHttpInvoker. Berikut konfigurasinya
<!-- publish service dengan protokol HttpInvoker -->
<bean id="remotingServiceHttpInvoker"
class="org.springframework.remoting.httpinvoker.SimpleHttpInvokerServiceExporter"
p:service-ref="remotingService"
p:serviceInterface="com.artivisi.tutorial.remoting.spring.service.api.RemotingService"
/>
Selanjutnya, kita suruh Spring mendeteksi implementasi service kita secara otomatis, yaitu class yang ada anotasi @Service.
<context:component-scan base-package="com.artivisi"/>
Berikut adalah dependensi pustaka di project client.
Dan ini untuk di server.
Keseluruhan project akan terlihat seperti ini.
Semua library dapat diambil dari distribusi Spring Framework dan Repository SpringSource.
Coba jalankan ServerLauncher, kita akan melihat log seperti ini.
Jul 3, 2009 2:57:25 PM org.springframework.context.support.AbstractApplicationContext prepareRefresh
INFO: Refreshing org.springframework.context.support.ClassPathXmlApplicationContext@be2358: display name [org.springframework.context.support.ClassPathXmlApplicationContext@be2358]; startup date [Fri Jul 03 14:57:25 WIT 2009]; root of context hierarchy
Jul 3, 2009 2:57:26 PM org.springframework.beans.factory.xml.XmlBeanDefinitionReader loadBeanDefinitions
INFO: Loading XML bean definitions from class path resource [server-ctx.xml]
Jul 3, 2009 2:57:26 PM org.springframework.context.support.AbstractApplicationContext obtainFreshBeanFactory
INFO: Bean factory for application context [org.springframework.context.support.ClassPathXmlApplicationContext@be2358]: org.springframework.beans.factory.support.DefaultListableBeanFactory@f11404
Jul 3, 2009 2:57:26 PM org.springframework.beans.factory.support.DefaultListableBeanFactory preInstantiateSingletons
INFO: Pre-instantiating singletons in org.springframework.beans.factory.support.DefaultListableBeanFactory@f11404: defining beans [org.springframework.remoting.support.SimpleHttpServerFactoryBean#0,remotingServiceHttpInvoker,remotingService,org.springframework.context.annotation.internalCommonAnnotationProcessor,org.springframework.context.annotation.internalAutowiredAnnotationProcessor,org.springframework.context.annotation.internalRequiredAnnotationProcessor]; root of factory hierarchy
Jul 3, 2009 2:57:27 PM org.springframework.remoting.support.SimpleHttpServerFactoryBean afterPropertiesSet
INFO: Starting HttpServer at address 0.0.0.0/0.0.0.0:9090
Lalu jalankan ClientLauncher, inilah log yang muncul.
Jul 3, 2009 2:58:12 PM org.springframework.context.support.AbstractApplicationContext prepareRefresh
INFO: Refreshing org.springframework.context.support.ClassPathXmlApplicationContext@be2358: display name [org.springframework.context.support.ClassPathXmlApplicationContext@be2358]; startup date [Fri Jul 03 14:58:12 WIT 2009]; root of context hierarchy
Jul 3, 2009 2:58:12 PM org.springframework.beans.factory.xml.XmlBeanDefinitionReader loadBeanDefinitions
INFO: Loading XML bean definitions from class path resource [client-ctx.xml]
Jul 3, 2009 2:58:13 PM org.springframework.context.support.AbstractApplicationContext obtainFreshBeanFactory
INFO: Bean factory for application context [org.springframework.context.support.ClassPathXmlApplicationContext@be2358]: org.springframework.beans.factory.support.DefaultListableBeanFactory@d2906a
Jul 3, 2009 2:58:13 PM org.springframework.beans.factory.support.DefaultListableBeanFactory preInstantiateSingletons
INFO: Pre-instantiating singletons in org.springframework.beans.factory.support.DefaultListableBeanFactory@d2906a: defining beans [remotingService]; root of factory hierarchy
Jul 3, 2009 2:58:13 PM com.artivisi.tutorial.remoting.spring.client.ClientLauncher main
INFO: Pesan dari server : Halo, endy
Setelah ClientLauncher dijalankan, di log server akan muncul informasi sebagai berikut.
INFO: Terima dari client : endy
Demikianlah cara menggunakan embedded HttpServer. Selamat mencoba.