Desain Table untuk replikasi

  Hi, sudah lama blog ini tidak saya update, tentu saja alasan paling utama adalah kesibukan. Klise sekali ya, jadi ingat para blogger yang lain, selalu memakai alasan yang sama, sibuk.

Baiklah, topik kita kali ini adalah desain tabel yang akan di pergunakan untuk replikasi. Replikasi data ditempat kita adalah Master to Master, artinya setiap lokasi dapat melakukan update data dan masing masing lokasi akan melakukan sinkronisasi dengan lokasi lainnya. Desain tabel ini berdasarkan pengalaman yang kita miliki selama ini, yaitu :

  • Primary Key
    • Setiap record yang tercatat harus memiliki primary key, yang dapat dipergunakan untuk identifikasi unik record tersebut. Tingkat ke-unik-annya harus mempertimbangkan kode lokasi dan kode perusahaan.
    • Dengan pertimbangan di atas, pada saat replikasi, kita yakin bahwasannya data setiap record itu adalah unik, tidak akan mungkin tercampur / bertabrakan dengan data dari lokasi lainnya.
    • Contoh primary key nya :
      • A1   : A untuk kode lokasi, 1 untuk no urut data
      • XA1 : X untuk kode perusahaan, A untuk kode lokasi, 1 untuk no urut data.
  • Tanggal Pembuatan
    • Kita harus mencatat juga kapan record tersebut di catat di dalam tabel. Umumnya kita kombinasikan dengan constraint DEFAULT.
    • Contoh untuk Postgresql dan Oracle :
      • created_date timestamp default NOW()
      • created_by numeric(8)
  • Tanggal Perubahan
    • Kita juga harus mencatat kapan record tersebut berubah/diubah di dalam tabel. Pencatatannya dilakukan pada saat kita menjalankan perintah UPDATE atau REPLACE.
    • Contoh untuk Postgresql dan Oracle :
      • modified_date timestamp
      • modified_by numeric(8)

ID yang unik adalah suatu keharusan, sementara untuk tanggal Pembuatan dan perubahan sebagai data pendukung terhadap status record tersebut. Tentusaja data pendukungnya dapat bertambah sesuai kebutuhan, tetapi kolom kolom yang diatas itu adalah keharusan di tempat kita. Jadi standard DDL untuk tabel yang akan di replikasi seperti berikut :

<!-- Center Pane -->
Create Table Master_tbl
( id varchar(16),
  ...
  ...
  created_date timestamp default NOW(),
  created_by numeric(8),
  modified_date timestamp,
  modified_by numeric(8),
  contraint master_tbl_pk primary key (id)
);

Bagaimana dengan teman teman ?

Replikasi melambat setelah tabel reorganize dengan CTAS

  Teman teman pasti tahu kalau saya memakai Bucardo untuk replikasi. Nah kejadian terakhir yang saya alami dengan bucardo berhubungan dengan tabel reorganisasi. Begini ceritanya.

Saya memiliki 3 server yang saya pergunakan untuk master to master replication dan hanya salah satu server saja yang di pergunakan sebagai server transaksi utama, lainnya untuk keperluan backup dan baca data. Nah saat saya melakukan analisa terhadap server untuk keperluan backup dan data ini, saya menemukan beberapa tabel yang ukurannya 3x lebih besar dari asalnya di server transaksi utama. Saya cek apakah mungkin tabelnya ter-fragmentasi atau tidak. Ternyata benar ada fragmentasi disana.

Akhirnya tabel yang ter-fragmentasi itu saya betulkan dengan metode CTAS. Berhasil. Salah satu tabel tersebut setiap malamnya melakukan update data sekitar 150k records. Jadi kalau dengan bucardo akan menjadi 300K records. Saya berkeyakinan bahwa semuanya akan lancar.

Esoknya, hari ke 1, sewaktu saya memonitor ZABBIX, ini adalah tools di linux untuk melihat kondisi server, saya mendapati bahwa dua server dimana saya melakukan CTAS kemarin cpu-load-nya sangat tinggi. Itu selesai setelah 6 Jam process, baru load nya turun drastis. Langsung saja saya curiga, mungkin itu terjadi karena tabel yang kemarin saya CTAS. Kemudian saya coba matikan bucardo-nya dan berharap esok hari zabbix akan memberikan laporan yang lebih baik.

Esoknya, hari ke 2, pagi pagi langsung saya lihat kondisi Zabbix, ternyata benar, load selama 12 jam terakhir rendah sekali. Jadi saya berkesimpulan bahwa load yang tinggi kemarin itu karena Bucardonya. Saya remove tabel tabel yang kemarin saya CTAS dari daftar tabel yang di replikasi di bucardo. Kemudian bucardo saya start lagi untuk menyelesaikan semua data data yang belum di replikasi. Dalam 3 jam ke depan Zabbix menunjukan kalau 2 server tersebut sibuk, karena menyelesaikan transaksi bucardo. Setelah itu rendah kembali, normal seperti sedia kala.,

Nah, saya browsing mencari jawaban mengenai hal ini, tetapi masih belum juga ketemu jawabannya. Mengapa setelah tabel tersebut di CTAS, process bucardo di  tabel tersebut jadi lebih lambat. Apakah ada teman teman yang memiliki pengalaman seperti ini ? mohon info nya.

Bucardo : Mengatur object dalam sync

  Sekarang  bucardo sudah berjalan dengan lancar. Kadang kala kita perlu mengatur object postgresql di dalam bucardo sync. Object ini adalah table dan sequence. Kedua object ini dapat kita tambahkan atau kita hapus.

Contoh yang saya miliki adalah sebagai berikut :

  • Table A, ingin saya replikasi dari db1 ke db2, tetapi tidak untuk db3.
  • Sequence B, ingin saya replikasi dari db1 ke db3, tetapi tidak untuk db2.

Berikut langkah langkah untuk menambah suatu object ke dalam sync :

  • stop bucardo
  • bucardo add table schema.nama_table herd=my_herd
  • bucardo add sequence schema.nama_sequence herd=my_herd
  • bucardo validate sync my_sync
  • start bucardo

Dan untuk menghapus, langkah langkah nya sebagai berikut :

  • stop bucardo
  • bucardo remove table schema.nama_table
  • bucardo remove sequence schema.nama_sequence
  • bucardo validate sync my_sync
  • start bucardo

Jika setelah menghapus suatu object, kita menemukan pesan errod di dalam file log, seperti ini :

“(23143) [Mon Dec 3 13:18:24 2012] VAC Warning! VAC was killed at line 6486: DBD::Pg::st pg_result failed: ERROR: relation “bucardo.delta_265672″ does not exist”

artinya ada object postgresql yang secara fisik sudah tidak ada di postgresql tetapi masih terdaftar di dalam sistem bucardo. Mengapa ini dapat terjadi ? bucardo yang kita pakai bukan versi stabil, masih versi beta atau alpha. Tenang saja, kita bisa memperbaikinya kan.

Untuk membetulkannya:

  • bucardo stop
  • login ke db1
  • cek melalui perintah
    • select * from pg_class where oid = 265672
  • jika tidak ada hasilnya, berarti object memang tidak ada.
  • delete from bucardo.bucardo_delta_targets where tablename = 265672
  • if no result…. ulang step ke db yang lainnya  ..dan seterusnya
  • bucardo start

Bagaimana pengalaman anda dengan bucardo ? mohon infonya.

Bucardo Server Down

  Yup betul. Pagi ini saya mendapati server bucardo saya mati. Hardware error. Saya coba restart server, selalu terhenti dengan pesan kesalahan ada pada perangkat keras. Sedikit panik sih, tetapi harus tetap tenang.  Saya hitung pilihan yang saya punya.

  • 1 Mesin DB slave
  • Tidak ada backup database bucardo
  • Server DB Master dan Server DB Slave masih berfungsi.

Pilihan yang ada adalah install bucardo di mesin DB Slave, dan register ulang semua tabel yang akan di replikasi. Seharusnya proses registrasi ulang ini dapat di hindari, tetapi karena saya tidak punya backup database bucardo, jadi harus registrasi ulang. Kalau ini berjalan, saya harus ikutkan database bucardo dalam skema backup saya.

Ada sedikit kekhawatiran dalam hati, jangan jangan bucardo nya tidak mau replikasi karena saya install database bucardo yang baru. Dalam hati berharap semoga bucardo nya tetap dapat melakukan replikasi.

So, setelah install ulang bucardo di mesin DB Slave, registrasi ulang, maka sekarang saatnya untuk start bucardo. Sambil berharap harap cemas, saya start bucardo dan tail -f log.bucardo.

Ternyata berjalan normal, tanpa kurang suatu apapun. L E G A.

Bagaimana dengan teman teman, ada memiliki pengalaman seperti ini ?

Bucardo : Mengubah stuktur table

  Setelah memakai Bucardo sekaian lama, saya memiliki kebutuhan untuk merubah struktur tabel. Menambah kolom, merubah tipe data, melebarkan kolom, atau menambah constraint. Proses ini harus dilakukan dengan kondisi tidak ada proses replikasi yang sedang berjalan atau dengan kata lain Bucardo harus berhenti.

Berikut adalah langkah langkah merubah struktur tabel :

  • Matikan Bucardo
    • bucardo stop
  • Ubah stuktur tabel di semua lokasi
    • psql -h 192.168.0.2 -U postgres
    • alter table my_table add column ….
    • alter table add constraint my_constraint …
    • Ulangi hingga semua lokasi memiliki struktur table yang sama
  • Jalankan Bucardo kembali
    • Bucardo Start

Setelah itu kita hanya perlu memonitor file log.bucardo, jikalau tidak ada error berarti proses perubahan struktur tabel berhasil dilakukan. Silahkan mencoba.

Bucardo : Menambah Server ke dalam Replikasi Master To Master

  Beberapa waktu yang lalu, saya memutuskan untuk menambahkan 1 server lagi kedalam replikasi master to master yang saya pergunakan. Saya memakai Bucardo untuk menangani replikasi master to master. Performancenya cukup memuaskan saya. Nah saat ini saya merasa perlu untuk menambah 1 server lagi untuk membagi beban kerja di server.

Pada awalnya tujuan memakai 2 server hanya untuk keperluan berbagi beban server dan backup di dalam 1 lokasi gedung, ternyata diperjalanannya untuk lokasi kota yang lain perlu juga di bagi beban servernya dan backup jika sewaktu waktu jaringan antar kota terputus, sehingga tidak akan mengganggu transaksi lokal. Untuk instalasi awal replikasi master to master dengan bucardo dapat anda baca disini.

Informasi :

  • db1 memiliki ip address 192.16.0.1
  • db2 memiliki ip address 192.16.0.2
  • db1 dan db2 berada dalam 1 gedung
  • db3 memiliki ip address 192.16.1.3
  • db3 berada di kota yang berbeda

Nah berikut adalah langkah langkah untuk menambahkan Server Database db3  ke dalam replikasi :

  • Login ke Server Bucardo dan stop replikasinya.
    • bucardo stop
  • Login ke Server Applikasi dan stop semua applikasi yang terkoneksi ke Server Database
  • Login ke Server Database ke 1 , backup dan kirim Server Database ke 3
    • pg_dump -h 127.0.0.1 -U postgres my_database > my_database.dmp
    • scp my_database.dmp root@192.16.1.3:/root
  • Login ke Server Database ke 3, buat database baru, dan restore database backupnya
    • psql -h 127.0.0.1 -U postgres -c “create database my_database; ” template1
    • psql -h 127.0.0.1 -U postgres -d my_database < my_database.dmp
  • Login ke Server Bucardo, daftarkan Server Database ke 3, dan syncronize ulang
    • bucardo add db db3 dbname=eis dbhost=192.16.1.3 dbuser=postgres dbpass=password
    • bucardo remove sync db_sync
    • bucardo remove dbgroup db_group
    • bucardo add dbgroup db1:source db2:source db3:source
    • bucardo add sync db_sync herd=db_herd dbs=db_group
    • bucardo start
  • Kemudian check log.bucardo, kita akan menemukan pesan kesalahan seperti ini :
    • “(23143) [Mon Dec 3 13:18:24 2012] VAC Warning! VAC was killed at line 6486: DBD::Pg::st pg_result failed: ERROR: relation “bucardo.delta_265672? does not exist”
    • Tenang, pesan kesalahan ini terjadi karena kita melakukan restore database beserta object object bucardo dari server asal.
    • Setelah kita restore database dan kemudian bucardo kita start, maka bucardo akan melakukan proses sinkronisasi objectnya. Karena kita melakukan restore, tentu saja object id atau OID dari object table di server yang baru akan berbeda dengan object id dari server yang lama. Oleh karena itu, bucardo akan mendaftarkan ulang object table di server yang baru, sehingga kita harus menghapus object id yang lama secara manual.
    • Mari kita periksa table bucardo_delta_targets, disinilah object table di daftarkan.
      • select * from bucardo.bucardo_delta_targets;
    • Kita akan mendapati, daftar table dengan perbedaan di tanggal registrasi, di kolom cdate. Yang perlu kita lakukan adalah menghapus semua table yang memiliki tanggal cdate tidak sama dengan saat ini atau saat prosess restore.
      • delete from bucardo.bucardo_delta_targets where to_char(cdate,’dd/mm/yyyy’) <> to_char(now(),’dd/mm/yyyy’);
    • Setelah itu periksa kembali file log.bucardo, seharusnya pesan kesalahan sudah tidak muncul lagi.
  • Done

Nah, sekarang kita memiliki 3 server di dalam replikasi master to master kita, db1 dan db2 dalam 1 gedung, db3 berada di kota yang lain. Dengan cara ini, apabila terjadi putusnya jaringan antar kota, maka user di kota yang lain tetap dapat menjalankan applikasi. Dan pada saat jaringan tersambung kembali maka bucardo akan melakukan sinkronisasi data kembali. Bagaimana pendapat anda ?

Drop rubyrep object secara manual di PostgreSQL

  Selama saya melakukan test terhadap rubyrep, ada kejadian dimana saya harus menghapus object object milik rubyrep secara manual. Menggunakan perintah rubyrep uninstall gagal, karena tidak dapat berkomunikasi dengan salah satu servernya. Alhasil dengan terpaksa harus melakukan pembersihan secara manual.

Semua object object milik rubyrep, secara default memiliki nama depan yang diawali dengan awalan “rr_“. Object yang terinstal adalah trigger dan table.

Berikut langkah langkah melakukan drop rubyrep secara manual :

  • Login ke database postgresql dimana tabel tabel rubyrep terinstall
  • Dapatkan daftar trigger trigger yang dipergunakan rubyrep
SELECT 'DROP FUNCTION ' || ns.nspname || '.' || proname || '('
       || oidvectortypes(proargtypes) || ') CASCADE;'
FROM pg_proc 
INNER JOIN pg_namespace ns ON (pg_proc.pronamespace = ns.oid)
WHERE ns.nspname = 'public'  order by proname;
  • Copy Paste perintah drop function yang dimulai dengan awalan “rr_”  tersebut untuk menjalankan perintah drop tersebut.
  • Dapatkan daftar tabel tabel yang di pergunakan rubyrep
select 'DROP TABLE '||tablename||' CASCADE; ' 
from pg_tables 
where tablename ilike 'rr_%';
  • Copy Paste perintah drop tabel yang dimulai dengan awalan “rr_” tersebut untuk menjalankan perintah drop tersebut.
  • Done.
Nah, dengan cara ini maka semua tabel dan trigger milik rubyrep sudah hilang dari sistem. Silahkan mencoba.

Bucardo memakai parameter max_stack_depth

  Pagi ini saya menemukan error di dalam file log.bucardo yang menyatakan bahwa saya harus menaikkan paramter max_stack_depth di file konfigurasi postgresql.conf. Berikut potongan pesan errornya :

(9926) [Thu Sep  6 08:32:45 2012] KID Warning! Aborting due to exception for public.my_big_table:? Error was DBD::Pg::db do failed: ERROR:  stack depth limit exceeded\nHINT:  Increase the configuration parameter "max_stack_depth" (currently 2048kB), after ensuring the platform's stack depth limit is adequate. at /usr/local/share/perl/5.14.2/Bucardo.pm line 8131.

...

” Wah ini parameter apa ya ?” pikir saya. Terus terang saya belum pernah melihat secara mendetail fungsi dari parameter ini.

Menurut dokumentasi postgresql, parameter Max_Stack_Depth ini berfungsi untuk menaikkan kemampuan server dalam Execution Stack. Misalnya dalam pemrosesan fungsi fungsi rekursif seperti sub-query dan klausa IN. PostgreSQL akan memanggil parameter ini pada saat memproses fungsi fungsi rekursif itu saja, jadi tidak setiap saat. Nilai ideal dari parameter ini harusnya sama dengan nilai batasan ukuran stack di kernel linux, yang bisa diperoleh dengan menjalankan perintah ulimit -s.

$> ulimit -s

8192

Jika di komputer saya akan menghasilkan 8192. Nilai ulimit ini dalam kilobyte, ini artinya kernel saya memiliki batasan ukuran stack 8192 Kb atau 8M. Tetapi saya tidak akan menggunakan 8M ini, saya akan pakai setengahnya saja, 4M. Jikalau kita memaksa menaikkan nilai parameter ini diatas kemampuan kernel, 8M, maka sistem dapat menjadi lumpuh.

Setelah itu barulah saya merubah file konfigurasi postgresql.conf dan ubah parameter max_stack_depth.

$> vim /etc/postgresql/9.1/main/postgresql.conf 
...
max_stack_depth = 4M
...

Setelah itu server  postgresql di restart dan bucardo di start kembali. Problem selesai.

Instalasi Bucardo, master to master replikasi untuk database PostgreSQL

  Bucardo adalah software replikasi master to master untuk database Postgresql. Bucardo yang saya pergunakan adalah bucardo versi 5 beta, tepatnya versi 4.99.5 dan dapat di download dihalaman ini.  Sampai saat ini kecepatan replikasi yang dapat saya peroleh adalah > 200 record per detik untuk replikasi antar kota. Hasil ini dapat berbeda untuk jenis applikasi yang anda gunakan.

Konfigurasi yang saya miliki :

Berikut langkah langkah yang dilakukan untuk instalasi bucardo :

  • Backup database di server 1 dan extract di server 2, dengan ini maka kedua database tersebut memiliki struktur dan data yang identik.
  • Update package ubuntu dengan menambahkan beberapa package yang dibutuhkan

$> apt-get install make libdbi1 libdbi-perl libdbix-safe-perl libdbix-simple-perl libdbd-pg-perl libboolean-perl postgresql-contrib postgresql-plperl-9.1

  • Check nilai ulimit di kernel linux. Nilai ulimit ini akan di pergunakan untuk menentukan nilai parameter max_stack_depth di postgresql.

$> ulimit -s

8192

  • Berdasarkan infomasi diatas menghasilkan nilai 8192 Kb. Artinya saya dapat menaikan parameter max_stack_depth hingga 8M. Tetapi kita akan pakai setengahnya saja. Parameter max_stack_depth ini dipergunakan untuk memperbesar kemampuan query yang menggunakan klausa IN. Kemudian update file konfigurasi postgresqlnya.

$> vim /etc/postgresql/9.1/main/postgresql.conf

max_stack_depth = 4M

  • Install language plperlu di postgresql

$> psql -h 127.0.0.1 -U postgres
SQL> CREATE LANGUAGE PLPERLU;
SQL> CREATE LANGUAGE PLPGSQL;

  • Download Bucardo versi 5 Beta disini.
  • ekstrak file hasil download tersebut.
  • Kemudian lakukan kompilasi .

$> cd bucardo-4.99.5
$> perl Makefile.PL
$> make
$> sudo make install

  • Install Bucardo, dan ubah setting koneksinya seperti berikut

$> bucardo install

Current connection settings:
1. Host: 127.0.0.1
2. Port: 5432
3. User: postgres
4. Database: postgres
5. PID directory: /var/run/postgresql
Enter a number to change it, P to proceed, or Q to quit: P

$>

  • Check instalasi bucardo

$> bucardo –version

  • Tambahkan database ke bucardo

$> bucardo add db db1 dbname=mydatabase dbhost=192.16.0.1 dbuser=postgres dbpass=password
$> bucardo add db db2 dbname=mydatabase dbhost=192.16.0.2 dbuser=postgres dbpass=password

  • Daftarkan semua table dan sequence ke bucardo. Herd dapat dianalogikan sebagai kumpulan object database

$> bucardo add table all tables herd=db_herd
$> bucardo add sequence all sequences herd=db_herd

  • Daftarkan database yang ada didalam bucardo ke dalam database group

$> bucardo add dbgroup db_group db1:source db2:source

  • Sinkronisasi ke dua database tersebut untuk install triggernya dan start replikasi

$> bucardo add sync db_sync herd=db_herd dbs=db_group
$> bucardo start

  • Setelah start anda dapat melakukan testing insert, delete, update dari masing masing sisi server.
  • Perlu diingat yang di replikasikan adalah perintah DML yakni insert, update, delete.
  • Done.
Silahkan mencoba.

Dari RubyRep ke Bucardo

  Setelah beberapa saat rubyrep dipergunakan di server produksi kita, akhirnya saya putuskan untuk menghentikan pemakaian rubyrep dan beralih ke bucardo.

Rubyrep adalah produk replikasi untuk postgresql yang cukup baik. Dibuat oleh Arndt Lehmann. Instalasinya cukup mudah dengan setting yang flexible. Rubyrep juga dapat yang saya pergunakan adalah yang versi JRuby. Karena kemudahan instalasinya itulah maka saya mencoba rubyrep terlebih dahulu.

Bucardo adalah produk replikasi untuk postgresql juga. Awalnya dipergunakan di Backcounty.com pada tahun 2002 pada postgresql versi 7.2. Bucardo dirilis untuk umum tahun 2007 dan hingga saat ini versi stabil yang terakhir adalah versi 4. Untuk versi 5 masih beta dan sudah di kembangkan selama 3 tahun. Versi 5 inilah yang saya pergunakan untuk menggantikan rubyrep.

Alasan mengapa berhenti memakai rubyrep adalah murni karena rubyrep tidak cocok dengan arsitektur applikasi kita. Berikut alasan alasannya :

  • Tabel dengan banyak kolom, applikasi kita memiliki beberapa tabel yang memiliki banyak kolom, lebih dari 25 kolom, dan tabel tabel ini harus dapat direplikasikan ke server lain yang berada di luar kota.
  • Kecepatan replikasi, untuk tabel dengan banyak kolom, kecepatan replikasi antar kota dengan rubyrep hanya max 20 record, sementara dengan bucardo kecepatannya antara 200-250 record.

Rubyrep cukup bagus, hanya saja untuk arsitektur applikasi kita, rubyrep masih belum dapat bekerja optimal dibandingkan dengan bucardo. Jadi setelah membandingkan hasil test antara bucardo dan rubyrep, maka saya semakin mantab untuk beralih ke bucardo. Apabila anda memiliki pengalaman menggunakan bucardo, mohon infonya.