Archive

Archive for March, 2008

Benchmark XCache

March 31st, 2008

Di blogdetik.com sudah terinstall xcache. Cuman waktu itu gak ngeliat performance enhancement yang significant. Karena lagi nganggur, coba-coba testing lagi pake ab dengan jumlah request 100000 dan konkurensi 1. Konkurensi gak diset banyak, karena memang buat ngecek dari sisi loading script php-nya aja, apa bener sih opcode cache benar-benar bekerja maksimal. Waktu pertama ditest tanpa xcache, memori yang dikonsumsi webserver hanya 9-10Mbs (php-cgi). Hasil benchmark ab-nya:

Concurrency Level:      1
Time taken for tests:   12344.642804 seconds
Complete requests:      100000
Failed requests:        0
Write errors:           0
Total transferred:      1460381792 bytes
HTML transferred:       1398600000 bytes
Requests per second:    8.10 [#/sec] (mean)
Time per request:       123.446 [ms] (mean)
Time per request:       123.446 [ms] (mean, across all concurrent requests)
Transfer rate:          115.53 [Kbytes/sec] received

Sedangkan kalo dipasang xcache, memori yang dikonsumsi webserver 12-22Mb (php-cgi). Hasil benchmark-nya:

Concurrency Level:      1
Time taken for tests:   5754.861240 seconds
Complete requests:      100000
Failed requests:        0
Write errors:           0
Total transferred:      1460381652 bytes
HTML transferred:       1398600000 bytes
Requests per second:    17.38 [#/sec] (mean)
Time per request:       57.549 [ms] (mean)
Time per request:       57.549 [ms] (mean, across all concurrent requests)
Transfer rate:          247.82 [Kbytes/sec] received

admin Benchmark, Server

Session…. Memcached….

March 31st, 2008

Yah, hari ini ngerjain session management via memcached. Karena gak yakin kalo server ini bila dipake lebih dari satu aplikasi webserver gak akan crash key (session_id) yang dipake, maka satu-satunya cara adalah nambahin parameter web_id di php.ini bagian session.save_path. Biar tiap aplikasi assign web_id sendiri-sendiri. Jadi kemungkinan tiap aplikasi web server yang generate session_id (yang dipake sebagai key di memcached) + web_id gak akan pernah sama. Berikut sedikit patch di source memcache_session.patch.

admin Server

Pake tcp loopback lebih cepet daripada unix socket… kok bisa

March 31st, 2008

Kalo dipikir-pikir, secara teori sih kecepatan transfer antara tcp dan unix socket, masih cepetan unix socket. Abis liat blog orang tentang perbandingan pake socket sama pake tcp, juga membuktikan kalo socket lebih cepat (di comment juga ada yang bilang sebaliknya). Aku coba buat konfigurasi yang sama untuk Nginx (nambah directive upstream dengan masing-masing unix socket yang di-create), dan merubah sedikit file cgi_main.c (php-5.2.5/sapi/cgi), dengan begitu instance child yang di-create akan mempunyai unix socket sendiri. Sebenarnya bisa dibuat instance php-cgi sendiri-sendiri sejumlah yang kita inginkan, terlepas dari cara spawn dari parent sejumlah PHP_FCGI_CHILDREN. Namun aku pikir nantinya akan ada masalah dengan modul xcache, karena xcache sharing opcode cache-nya pake shared memory file yang hanya bisa diliat di anak-anaknya php-cgi. Ya sudah, terpaksa ubah-ubah sedikit source php :( cgi_main.patch.

Dan ternyata hasilnya masih mengecewakan, gak ada penambahan performance, justru ada beberapa request dari hasil benchmark pakai ab yang failed. Yah….. gak sesuai harapan deh. Gak papa lah, paling gak hasil sedikit kerja bisa ada manfaatnya. Jadi kesimpulannya, pakai tcp socket aja…… (hm.. kalo pake pipe lebih cepet gak ya :D )

admin Benchmark, Server

Setting Wordpress MU di Nginx

March 27th, 2008

Habis coba test kecil-kecilan benchmark Apache dengan Nginx, ketahuan kalo diakses dengan jumlah konkurensi yang gede (lupa berapa spesifiknya), Nginx masih kuat merespon daripada Apache. Apache cenderung mereset koneksi jika udah kebanyakan request. Ini juga gak tau, emang bener gak settingan apache-nya… hehehe….

OK… Sekarang coba install Nginx. Sebenarnya udah dicoba sama temanku bagian sysnet, tapi waktu itu belum berani dimasukkan ke live, karena ada beberapa feature yang takutnya tidak didukung penuh oleh Nginx. Setelah dipikir2, sepertinya sih gak ada. Soalnya webserver dalam hal ini gak begitu banyak berperan di aplikasi WordpressMU, yang berperan banyak dari sisi PHP-nya. Cuman yang perlu diperhatikan itu fasilitas rewrite. Apache dengan Nginx punya cara penanganan yang berbeda dalam setting konfigurasi, maka dari itu penulis coba-coba belajar cara setting di Nginx.

Setelah tiga hari utak-atik rewrite di Nginx, akhirnya ketemu juga logika cara mainnya :D . Bingung sih baca manualnya di website Nginx, gak begitu jelas. Akhirnya coba-coba sendiri deh. Ada sih konfigurasi dapat dari googling, tapi masih ada masalah.

Nih hasil utak-atik konfigurasinya….

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
worker_processes 32;
daemon  off;
pid /var/run/nginx.pid;
events  {
                use epoll;
                worker_connections 1024;
                multi_accept on;
                epoll_events 512;
                accept_mutex_delay 10ms;
        }
http {
        include /opt/nginx/conf/mime.types;
        default_type  application/octet-stream;
        log_format main '$remote_addr - $remote_user [$time_local] '
                  '"$request" $status $body_bytes_sent "$http_referer" '
                  '"$http_user_agent" "$http_x_forwarded_for"';
        sendfile on;
        tcp_nopush        on;
        tcp_nodelay       on;
        gzip            on;
        gzip_http_version 1.0;
        gzip_comp_level 2;
        gzip_proxied any;
        gzip_types      text/plain text/html text/css application/x-javascript text/xml application/xml application/xml+rss text/javascript;

        server {
                listen       80;
                server_name  blog.com *.blog.com;
                access_log /var/log/nginx/access.fifo main;
                error_log /var/log/nginx/error.fifo info;
                client_max_body_size 20M;

                #-------- uploaded file -------------
                location ~ /files/ {
                        root /data/wpmu;
                        rewrite ^.*/files/(.*) /wp-content/blogs.php?file=$1 break; # get upload file
                        fastcgi_pass   127.0.0.1:8888;
                        fastcgi_index  index.php;
                        fastcgi_param  SCRIPT_FILENAME /data/wpmu/$fastcgi_script_name;
                        include        /opt/nginx/conf/fastcgi_params;
                }

                location ~* (/wp-content/avatars|/wp-content/cache/supercache/.+.html) {
                        root /data/wpmu;
                        expires 1h;
                        break;
                }

                location ~* ^.+.(html|jpg|jpeg|gif|png|ico|css|zip|tgz|gz|rar|bz2|doc|xls|exe|pdf|ppt|txt|tar|mid|midi|wav|bmp|rtf|js|swf)$ {
                        root /data/wpmu;
                        expires 30d;
                        break;
                }

                location / {
                        root   /data/wpmu;
                        index  index.php index.html index.htm;

                        #------- cache it, but do not supercache --------------
                        set $exist 0;
                        set $match 2;

                        if (-e $request_filename) {
                                set $exist 1;
                        }
                        # custom scripts, apart from wordpressmu
                        if ($uri ~ "^.*/(blogdir.php|blogstardir.php|blogcat.php|result.php|blognew.php).*$") {
                                set $match 1;
                        }

                        if ($match = $exist) {
                                break;
                        }

                        #------- supercache --------------
                        set $olduri $uri;
                        set $nosc 0;

                        rewrite ^ /wp-content/cache/supercache/$http_host/$uri/index.html;

                        if ($query_string ~ ".*s=.*") {
                                set $nosc 1;
                        }

                        if ($http_cookie ~ "^.*(comment_author_|wordpressuser|wp-postpass_).*$" ) {
                                set $nosc 1;
                        }

                        if (!-e $request_filename) {
                                set $nosc 1;
                        }

                        if ($nosc = 0) {
                                rewrite ^(.*) $1 last;
                        }

                        #------------------------------------
                        rewrite ^ $olduri;

                        if (-d $request_filename) {
                                rewrite ^(.*[^/])$ $1/ permanent;
                        }

                        if (!-e $request_filename) {
                                #permalink
                                rewrite ^ /index.php break;
                        }
                        break;

                        fastcgi_pass   127.0.0.1:8888;
                        fastcgi_index  index.php;
                        fastcgi_param  SCRIPT_FILENAME /data/wpmu/$fastcgi_script_name;
                        include        /opt/nginx/conf/fastcgi_params;
                }
        }
}

Di rewrite module ada rule “if”. Rule ini gak bisa di nested :( . Jadi masukin alurnya jadi bingung, sedikit akal-akalan. Intinya dalam rewrite itu, selama gak ada rule “break” atau “last ” diakhir line dalam satu directive location, maka pencarian akan dilanjutkan ke rule rewrite yang lain (masih dalam satu directive location). Jika sudah gak ketemu yang match, baru dilanjutkan di directive location lain. Variabel $uri akan berubah-ubah sesuai dengan hasil rule rewrite yang match. Sedangkan $request_uri merupakan original $uri ditambah dengan argumen.

Jika ada rule “last”, maka rewrite akan berhenti mencari rule rewrite selanjutnya di directive location-nya dia, dan mencari di directive location lain sampai ketemu match. Jika ingin benar-benar berhenti dan tidak akan melanjutkan mencari di directive location lain, maka pakai rule “break”.

Buat Wordpress MU sendiri, yang bikin pusing ini rule buat supercache. Tapi akhirnya berhasil, walaupun banyak akal-akalannya (liat sendiri aja). Ehmmm… belum cek keseluruhan… jadi 90% lah keberhasilannya ….hehehehe……..

Jika ada yang tahu cara efisiennya, kasih tau ya….

Updated: Ternyata yang lama masih kacau konfigurasinya… ketauan baru diproduction… hihihi.. sial

admin Server

Benchmark Session store antara NFS dan Memcached

March 24th, 2008

Coba ngetes benchmark session store pake file dan memcached.
Konfigurasi:
- 2 webserver buat ngetes centralized session store
- 1 server server nfs/memcached buat simpan session

Test:
Dibuat tes skrip pake jmeter. Intinya skrip put text di salah satu server webserver, simpan sessionid, terus di-get diserver webserver lainnya pake sessionid yang tersimpan. Jika centralized session bekerja, maka hasil yang di-get harus sama dengan yang di-put. Ukuran text yang dikirim dibagi 3, untuk 100 bytes, 1Kb, 10Kb, 100Kb.
Untuk nfs, masing2 webserver mounting ke server nfs ke direktori yang sama. Untuk memcached, pake bawaan patch rep-memcached (untuk coba replication memcached), sekalian test performance jika replication bekerja. Skrip melakukan operasi put dan get sejumlah 1000 kali dengan konkurensi 20 client.

Result Benchmark Session Store

Result:
Hasilnya dapat dilihat di gambar. Untuk NFS, nfsd berjalan dengan 8 proses dengan masing-masing menghabiskan 20-25% CPU. Sedangkan memcached dengan 2 proses (satu sebagai replication slave) menghabiskan 20-70% CPU. CPU load tertinggi berada di sisi master, sedangkan slave hanya memakan 20%.
Untuk 100 – 10Kb, memcached lebih unggul hampir 2 kali lipat dibanding NFS disegi performance (requests/second). Kemungkinannya karena memang NFS harus menghabiskan banyak waktu disisi I/O untuk read/write, sedangkan memcached tidak melibatkan disk I/O karena data disimpan di memori. Diatas 10 Kb, memcached mengalami penurunan performance, menjadi sama dengan NFS. Setting chunk_size di php.ini untuk memcached sudah ditinggikan 128Kb, supaya pas dengan ukuran size text, hasilnya tetap, hanya sedikit meningkatkan performance. Tapi kalau dilihat-lihat jarang yang menyimpan data di session store lebih dari 100Kb.

Nih, file-file buat ngetestnya : Session Test.zip

admin Benchmark, Server