Wednesday, March 30, 2005

Seperti XML, tetapi bukan

Ada yang bilang XML tidak benar-benar human readable, XML kurang efisien, karenanya beberapa orang membuat alternatif penggati XML yang lebih sederhana dan mudah. Tapi tetap saja XML memiliki kelebihan dari sisi iteroperability, kemudahan mendapatkan library untuk processing-nya (parser), kalaupun kurang simple sudah banyak tool (editor) untuk memanipulasi XML.

Beberapa alternatif pengganti XML diataranya:


Thursday, March 24, 2005

Java: Serialization Tutorial

- Suatu java object disimpan di memory dan dapat digunakan lagi selama JVM masih running

- Bagaimana menyimpan object agar masih bisa digunakan dilain waktu?

- Object serialization adalah proses penyimpanan suatu object pada kondisi tertentu dalam bentuk deretan byte (sequence of bytes) atau proses kebalikannya yaitu membuatnya kembali dari deretan byte menjadi object real dalam JVM

- Object serialization hanya menyimpan object's state. File class dari object serta method-method-nya tidak disimpan.

- Deretan byte tersebut dapat kemudian kita simpan menjadi suatu file atau dalam database atau ditransfer lewat jaringan.

- Suatu object yang dapat disimpan dan dibuat lagi (persit) harus dibuat menjadi persistance object.

- Object yang dapat disimpan dengan mekanisme object serialization disebut serializable object atau object tersebut bersifat serializable

- Untuk membuat object menjadi serializable, maka object tersebut ditandai dengan cara mengimplementasikan interface java.io.Serializable baik secara langsung ataupun tidak langsung (maksudnya secara hirarki object tersebut

- Contoh :
 import java.io.Serializable;
import java.util.Date;
import java.util.Calendar;
public class PersistentTime implements Serializable {
private Date time;
public PersistentTime() {
time = Calendar.getInstance().getTime();
}

public Date getTime() {
return time;
}
}

- Object diatas, karena telah meng-implement Serializable, dapat dibuat menjadi byte stream dan disimpan pada berbagai media misalnya file dalam disk.

- Interface Serializable merupakan interface kosong yang hanya sebuah interface penanda (marker)

- Untuk menyimpan atau mentransfer serializable object kita dapat menggunakan mentod ObjectOutputStream.writeObject(Object obj).

- ObjectOutputStream merupakan sebuah filter stream class yang dapat kita gunakan untuk menyimpan byte stream menjadi file atau ditransfer lewat network

- Contoh menyimpan object menjadi suatu file:
  import java.io.ObjectOutputStream;
import java.io.FileOutputStream;
import java.io.IOException;
public class FlattenTime {
public static void main(String [] args) {
PersistentTime time = new PersistentTime();
FileOutputStream fos = null;
ObjectOutputStream out = null;
try {
fos = new FileOutputStream("time.obj");
out = new ObjectOutputStream(fos);
out.writeObject(time);
out.close();
} catch(IOException ex) {
ex.printStackTrace();
}
}
}

contoh diatas akan menyimpan object menjadi suatu file bernama time.obj

- Contoh untuk membuat object dari persistance object
 import java.io.ObjectInputStream;
import java.io.FileInputStream;
import java.io.IOException;
import java.util.Calendar;

public class InflateTime {
public static void main(String [] args) {
PersistentTime time = null;
FileInputStream fis = null;
ObjectInputStream in = null;
try {
fis = new FileInputStream("time.obj");
in = new ObjectInputStream(fis);

// Recreate object
time = (PersistentTime)in.readObject();
in.close();
} catch(IOException ex) {
ex.printStackTrace();
} catch(ClassNotFoundException ex) {
ex.printStackTrace();
}
}
contoh diatas membuat object dari file bernama time.obj

- Proses untuk mendapatkan object dari sequence of bytes disebut proses deserialization

- Untuk mendapatkan real object kita harus melakukan casting menggunakan class aslinya dari object tersebut. Dalam contoh diatas adalah PersistentTime.

Karena sebenarnya persistance object hanya menyimpan state/property dari object itu saja

- Tidak semua object serializable, contohnya Thread, Socket, OutputStream dan subclass-nya.

- Bagaimana jika object yang serializable memiliki object yang tidak serializable?

Object tersebut harus ditandai dengan deklarasi "transient"

- Ketika object di-deserialize (dilakukan casting setelah byte stream dibaca) constructor dari object tersebut tidak dipanggil. Bagaimana jika ada proses yang penting yang ada di constructor object tersebut?

- Kita dapat membuat method tersendiri dan constructor memanggil method tersebut. Jika object di-deserialize maka kita harus secara manual memanggil method tersebut.

- Proses tersebut dapat diotomatisasi dengan mengimplementasikan method spesial berikut :
private void readObject(java.io.ObjectInputStream in)
throws IOException, ClassNotFoundException;
- Contoh :
  public class MyObject implements Serializable {

public MyObject() {
initialization();
}

private void initialization() {
// code constructor disini
}

private void readObject(java.io.ObjectInputStream in)
throws IOException, ClassNotFoundException {
in.defaultReadObject();

initialization();
}

}


- Kita dapat melakukan hal yang sama untuk proses serialization menggunakan method spesial berikut:
private void writeObject(java.io.ObjectOutputStream out)
throws IOException

- Method spesial readObject() dan writeObject() juga dapat digunakan untuk memastikan suatu proses dilakukan pada saat serialize atau deserialize.

Misalnya untuk keperluan security pada object yang disimpan maka setiap proses serialization object akan dienkrip terlebih dahulu dan didekrip saat proses deserialization

Contoh lain misalnya pada kasus suatu class serializable merupakan subclass dari class yang non-serializable. Untuk memastikan field dari parent class tersimpan dalam byte stream kita bisa menambahan code untuk menyimpan field dari parent class pasa method writeObject().
Lihat contoh code di:

http://java.sun.com/j2se/1.4.2/docs/guide/serialization/examples/nonserialsuper/sources.html

- Bagaimana jika suatu object yang merupakan subclass dari object yang Serializable tidak ingin bisa di-serialize atau di-deserialize? Gunakan method spesial tadi untuk melemparkan (throw) exception misalnya :
   throw new NotSerializableException("This object cannot be serialize");
- Saat object di-serialize, maka dibuat sebuah "fingerprint" yang disebut serialVersionUID berupa 64-bit data.

- Kita dapat membuat serialVersionUID sendiri dari awal pada serializable object dengan menambahkan field long bernilai sembarang seperti ini:
   static final long serialVersionUID = 4070409649129120458L;
- Jika suatu file dari persistance object disimpan kemudian object tersebut mengalami perubahan kecil, misalnya penambahan field (java code berubah), dan kita dapat mengatakan bahwa file dari persistance object yang disimpan masih kompatibel dengan object yang baru maka object baru tersebut harus diberikan serialVersionUID yang sama object yang lama.

Jika hal ini tidak dilakukan proses deserialization akan menghasilkan exception java.io.InvalidClassException.

- Untuk mengetahui serialVersionUID dari byte stream file, dapat digunakan tool "serialver" yang ada di JDK.

- The Externalizable Interface
....


- Links :
http://java.sun.com/developer/technicalArticles/Programming/serialization/
http://www.jguru.com/faq/subtopic.jsp?topicID=3341

Friday, March 18, 2005

WS-* spesification map

Kalau kita belajar web service maka kita akan dibingungkan dengan banyaknya spesifikasi/standar yang digunakan. Spesifikasi web service biasanya open sehingga mudah dipelajari tapi karena banyaknya perusahaan atau organisasi yang membuat spesifikasi yang kadang mirip, kita jadi dibingungkan dengan spesifikasi tersebut. Spesifikasi yang mirip biasanya mulcul karena memang merupakan solusi untuk masalah yang sama.

Jika ingin melihat bagaimana rumitnya spesifikasi web service, kita bisa lihat peta "Web Services & WS_* Specifications"

Selain itu juga kita bisa lihat Big Picture of the XML family Of Spesifications.

Wednesday, March 16, 2005

Java: Multi threading pada aplikasi JFC/Swing

  • User melakukan action pada Swing GUI komponen misalnya button
  • Action yang dieksekusi ditulis dalam method event listeners
  • Event listeners selalu dieksekusi dalam Event Dispatch Thread
  • Event Dispatch Thread bertanggung jawab untuk mengeksekusi semua event satu persatu.
  • Jika ada event yang prosesnya lama, event selanjutnya tidak akan dieksekusi sebelum proses tersebut selesai. Event yang belum dieksekusi akan menunggu di Event Queue.
  • Jika event yang belum dieksekusi adalah event yang mengubah tampilan GUI, maka GUI akan terlihat hang dan tidak responsif (frezee).
  • Komponen Swing memang tidak didesain secara default thread save, jadi implementasi yang salah bisa membuat aplikasi Swing
Solusi asynchronous (misalnya, SwingWorker 3) melakukan proses berikut:
  • Segera keluar dari listener method dengan mendelegasikan proses ke thread baru
  • Dengan bantuan class SwingWorker, thread baru yang mengerjakan task/event yang prosesnya lama
  • Menggunakan method SwingUtilities.invokeLater() untuk mengirimkan event baru ke Event Queue
  • Setelah worker thread menyelesaikan prosesnya, maka worker mengirimkan method finished() ke Event Queue
Solusi synchronous (misalnya, Spin dan Foxtrot) melakukan proses berikut:
  • Menggunakan worker thread
  • Event Dispatch Thread tidak keluar dari listener method, tapi melakukan dequeue events
  • Setelah time-consuming task selesai worker class memerintahkan Event Dispatch Thread untuk memberhentikan proses dequeue events dari Event QUeue

  • Kelebihan dengan solusi ini :Kode program lebih readable dan sederhana, exception handling yang lebih baik

Tuesday, March 15, 2005

PHP: NuSOAP dan DIME attachment

Butuh sending atau receiving DIME attachment pada web service manggunakan NuSOAP?

Saat ini saya sedang membuat sebuah class tambahan agar class soapclient dapat mendukung DIME attachment. Class ini dibuat seperti class soapclientmime pada file nusoapdime.php yang dibuat oleh Scott Nichol. Karena PEAR::SOAP sudah mendukung DIME attachment, maka dengan bantuan class Net_DIME dari PEAR maka pekerjaan ini jadi lebih mudah.

Saat ini create DIME attachment yang saya bikin untuk request (memmbuat DIME message untuk dikirim) sudah selesai. Inti perkerjaannya adalah disini :

function &_makeDIMEMessage(&$xml) {
// See class nusoap_base
$namespaces = 'http://schemas.xmlsoap.org/soap/envelope/';

// encode any attachments using DIME (see this link)
// now we have to DIME encode the message
$dime =& new Net_DIME_Message();
$msg =& $dime->encodeData($xml,$namespaces,NULL,NET_DIME_TYPE_URI);

// add the attachements
$c = count($this->requestAttachments);
for ($i=0; $i < $c; $i++) {
$attachment =& $this->requestAttachments[$i];
if ($attachment['data'] == '' && $attachment['filename'] <> '') {
if ($fd = fopen($attachment['filename'], 'rb')) {
$data = fread($fd, filesize($attachment['filename']));
fclose($fd);
} else {
$data = '';
}
$attachment['data'] = $data;
}
$msg .= $dime->encodeData($attachment['data'],
$attachment['contenttype'],
$attachment['cid'],
NET_DIME_TYPE_MEDIA);
}
$msg .= $dime->endMessage();
return $msg;
}
Selanjutnya agar NuSOAP support DIME attachment kita perlu penambahan kapabilitas untuk menerima response DIME message dan kapabilitas pada WSDL.

Friday, March 11, 2005

PHP: NuSOAP with certificate authentication

Dirjen Pajak Indonesia membuat Web Service untuk pelaporan pajak dari individu ataupun lembaga/perusahaan. Ini ide bagus, tapi sayang implementasinya kurang bagus. Saya tidak terlibat dengan project tersebut tapi setidaknya tau.

Web service yang dibuat tersebut disebut dengan eFiling (Electronic Filing System) yang maksudnya adalah layanan untuk mengirimkan Surat Pemberitahuan Pajak Tahunan (SPT) secara online. Web service tersebut dijual ke beberapa ASP (Application Service Provider), kemudian ASP tersebut membuat aplikasi sendiri yang mudah digunakan oleh masyarakat luas.

Implementasi web service tersebut menggunakan .NET, sayangnya pengembang proyek tidak memperhatikan interoperability dan kurang peduli dengan dokumentasi. Sehingga menyulitkan ASP untuk membuat aplikasinya. Walaupun saya bukan salah seorang dari ASP yang ada tapi saya tau sekali hal ini. Dengar-dengar proyek ini sudah berlangsung lama, lebih dari setahun dan hingga saat ini belum satu pun ASP yang benar-benar siap untuk menjual produk/layanannya ke masyarakat, padahal eFiling ini sudah diluncurkan oleh Presiden.

Tapi saya bukan ingin mengomentari proyek tersebut. Saya hanya memberikan highlight bahwa dalam pembangunan web service yang melibatkan banyak pihak yang menggunakannya masalah interoperability, dokumentasi dan keamanan sangatlah penting.

Implementasi web service ini cukup baik dilihat dari segi keamanan (security). eFiling menerapkan user authentication, XML-Encryption, XML Digital Signature (XML-Dsig), dan menggunakan SSL (HTTPS) dengan koneksi dedicated (antara ASP dan Dirjen Pajak). Keempat hal tersebut sudah cukup untuk membuat web service cukup aman.

User authentication yang digunakan adalah dengan mekanisme login menggunakan username dan password. XML-Encryption dan XML-DSig, karena standar yang umum/bebas dan gratis sudah banyak diimplementasikan. SSL dengan authentikasi sertifikat juga hal yang sudah biasa didunia web. Tapi sayangnya eFiling menggunakan DIME (Direct Internet Message Encapsultion) untuk mekanisme attachment pada SOAP. DIME adalah standar Microsoft, pernah disubmit ke IETF tapi tidak pernah menjadi RTF. Mekanisme attachment untuk web service, kita bisa menggunakan standar SOAP with attachments (Sw/A).

Implementasi web service client untuk eFiling ini akan sangat sulit jika kita ingin menggunakan PHP. Ini karena PHP tidak memiliki library yang memadai untuk standar-standar web service (WS-*). Setelah bersusah payah mencari-cari dengan google, akhirnya didapatkan NuSOAP sebagai kandidat utama untuk mencoba implementasi web service client untuk eFiling. Kenapa NuSOAP, karena library ini support koneksi dengan SLL dan authentication dengan digital certificate. Tapi ternyata NuSOAP tidak mendukung XML-Encryption dan XML-DSig dan DIME. Library PHP PEAR::SOAP mendukung DIME attachment dengan package DIME_Attachment tapi sayangnya tidak support authentication dengan digital certificate.

Tidak adanya library untuk XML-Encryption dan XML-DSig membuat aplikasi PHP harus dibuat saling beroperasi dengan aplikasi yang dibuat dengan bahasa lain yang memiliki library untuk kedua fungsi tersebut.

NuSOAP yang digunakan juga perlu mengalami perubahan untuk bisa sukses digunakan ketika authentication menggunakan digital certificate. Dibawah ini contoh code PHP menggunakan library nusoap.er.php (NuSOAP yang sudah dimodifikasi, saya akan upload code ini lain waktu) :
<html>
<head>
<title>DJP SOAP test</title>
</head>
<body>
<?
require_once('nusoap.er.php');

$soapclient = new soapclient('https://eFiling:1208/certReqWs/RegistrationService.asmx?WSDL','wsdl');

$username="";
$password="";
$certparams = array('cainfofile' => '/home/ejlp/htdocs/.cert/CADJP.cert',
'sslcertfile' => '/home/ejlp/htdocs/.cert/korupsipajak.cert.pem',
'sslkeyfile' => '/home/ejlp/htdocs/.cert/korupsipajak.key.pem',
'passphrase' => 'password');
$soapclient->setCredentials($username,$password,'certificate', $certparams);
ini_set("soap.wsdl_cache_enabled", "1");
$soapclient->create();

$err = $soapclient->getError();
if ($err) {
echo '<p><b>Create soapclient error: ' . $err . '</b></p>';
}

$proxy = $soapclient->getproxy();
$params = array( 'UserName' => 'test' , 'Password' => 'testpassword');
$results = $proxy->GetNPWP($params);

echo '<h3>Request:</h3> <xmp>'.$proxy->request.'</xmp>';
echo '<h3>Response:</h3> <xmp>'.$proxy->response.'</xmp>';
echo '<h3>Debug:</h3> <xmp>'.$proxy->debug_str.'</xmp>';
?>
</body>
</html>

Thursday, March 03, 2005

XML Signature

XML digital signature (XMLDsig) merupakan standar untuk memberikan digital signature pada data/dokumen xml.

XMLDsig merupakan rekomendasi dari W3C dan sudah mulai banyak digunakan pada web service sebagai salah satu standar untuk keamanan.

Dengan memberikan digital signature, data/dokumen xml dapat diverifikasi kebenarannya serta integritas datanya terpercaya.

XML digital signature adalah data signature dalam format xml yang distadarisasi. Karena formatnya xml dan jika digunakan untuk dokumen xml maka XML digital signature dapat ditempatkan dengan 3 macam cara yaitu:

1. Enveloped - Signature berada --sebagai element-- pada dokumen yang di tandai (signing)
2. Enveloping - dokumen XML yang di-signed berada didalam signature element
3. Detached - Signature berada terpisah dari signed data

Struktur XMLDsig adalah sebagai berikut:
  • SignedInfo: Isi yang di-sign
  • SignatureValue: Signed value
  • SignatureMethod: Algoritma yang digunakan mengkonvesi data yang dikanonikalisasi (canonicalized contents) kedalam bentuk SignatureValue
  • KeyInfo: Information key yang digunakan untuk validasi (opsional)
Catatan: Canocalization (C14N) adalah standar algoritma untuk memverifikasi kesamaan dokumen XML walaupun mungkin dua dokumen XML berbeda jika dibandingkan secara teks. Algoritma ini diperlukan untuk digital signature sedemikian sehingga dari dokumen XML yang kanonikal (sama) jika dilakukan hashing akan didapatkan hash value yang sama. Hash value tersebut akan menjadi informasi integritas data yang di-sign.

bersambung...

http://www.w3.org/Signature/

Followers