Tutorial Form PHP Part 6: Validasi Form untuk Mencegah Cross-site Scripting dan HTML injection

Di dalam tutorial Form PHP sebelumnya, kita telah membahas cara melalakukan pengecekan variabel form apakah telah tersedia untuk diproses (dengan fungsi isset()), apakah variabel tersebut kosong (dengan fungsi empty()), atau apakah variabel form tersebut memiliki tipe data tertentu.

Masih berkaitan dengan proses validasi form, kali ini kita akan membahas tentang cara mencegah user untuk memasukkan kode 'khusus' seperti JavaScript atau kode HTML kedalam form. Dalam tutorial kali ini kita akan mempelajari Cara Validasi Form untuk Mencegah Cross-site Scripting dan HTML injection.


Pengertian Cross-site Scripting dan HTML injection

Cross-site Scripting atau sering disingkat dengan XSS adalah jenis serangan ke sebuah situs dengan cara 'menyisipkan' kode script (biasanya JavaScript) ke dalam sebuah situs. Hal ini hanya akan berhasil jika situs tersebut memiliki fitur untuk menampilkan kembali isian form ke web browser, seperti form komentar. Sedangkan HTML injection adalah istilah yang lebih spesifik kepada cara 'menyisipkan' kode HTML kedalam sebuah situs.

Sebagai programmer web, penanganan untuk Cross-site Scripting maupun HTML injection merupakan hal yang sangat penting, terutama dalam pembuatan kode form dengan PHP. Karena form pada dasarnya dapat diinput oleh siapa saja, maka kita perlu memproteksi situs dari kode-kode berbahaya yang bisa diinput oleh user melalui form.


Contoh Cross-site Scripting dan HTML injection

Agar lebih memahami maksud dari Cross-site Scripting dan HTML injection, kita akan coba menginputnya melalui contoh halaman form.html dan proses.php dari tutorial sebelumnya.

Silahkan buka halaman form kita (form.html), lalu input kode dibawah ini kedalam dalam salah satu kotak inputan form:

<script>alert('Selamat datang di duniailkom')</script>

Dan anda akan mendapati tampilan berikut:

Tampilan Script Injection pada halaman FormTampilan tersebut adalah hasil dari kode JavaScript yang baru saja kita input melalui form. Kode tersebut dapat berjalan karena pada halaman proses.php kita langsung menampilkan data yang diinput oleh user tanpa melakukan proses filter.

Hal ini sangat berbahaya karena dengan kode JavaScript seseorang bisa melakukan 'hampir segalanya' dengan situs kita. Tidak hanya sekedar menampilkan ucapan selamat seperti kode diatas, tetapi seseorang juga bisa merubah background, mengubah tampilan seluruh web, bahkan mengarahkan pengunjung ke situs lain (redirect).

Hasil diatas saya peroleh menggunakan web browser mozilla firefox. Ketika saya menggunakan google chrome, tampilan javascript tersebut tidak muncul karena google chrome memiliki mekanisme 'pencegahan' kode javascript internal ketika diinput melalui form.

Sebagai contoh lainnya, seseorang bisa menginput kode berikut ke dalam kotak input nama:

Dunia <br> <br> <br> <br> <br> <br> <br> <br> <br> <br> Ilkom

Tampilan HTML Injection pada halaman FormWalaupun kode diatas tidak mengandung script, namun kode HTML tersebut akan membuat tampilan hasil form menjadi berantakan (bayangkan jika kita memiliki halaman yang berisi tabel berisi nama-nama seluruh user, dan kode diatas akan menghancurkan desain web yang telah dirancang).


Cara Mencegah Cross-site Scripting dan HTML injection

Salah satu cara sederhana untuk menghindari Cross-site Scripting dan HTML injection adalah dengan membuat karakter-karakter yang memiliki 'makna' di dalam HTML dan JavaScript untuk diubah menjadi named entity, yaitu menkonversi karakter khusus seperti < menjadi &lt;, dan karakter > menjadi &gt;. Atau cara lainnya adalah dengan menghilangkan sama sekali seluruh tag HTML atau script dari inputan user.

Penjelasan lebih lanjut tentang named entity (dan juga numeric entity) karakter HTML pernah kita bahas pada tutorial Cara Memasukkan Karakter Khusus ke dalam HTML.

Untuk kedua keperluan ini, PHP memiliki fungsi htmlspecialchars() dan fungsi strip_tags().

Fungsi htmlspecialchars() akan mengkonversi 4 karakter 'khusus' HTML menjadi named entity sehingga tidak akan di 'proses' oleh web browser. Keempat karakter tersebut adalah: <, >, & dan  ". Keempat karakter khusus inilah yang membuat web browser akan menerjemahkan sebuah string menjadi kode HTML/JavaScript.

Sedangkan fungsi strip_tags() akan menghapus seluruh tag HTML dari inputan user.

Sebagai contoh, kita akan mengupdate halaman proses.php agar bisa mencegah seseorang menyisipkan Cross-site Scripting dan HTML injection. Berikut adalah perintah PHP pada file proses.php:

<?php
if (isset($_GET['nama']) AND isset($_GET['email']))
{
   $nama=$_GET['nama'];
   $email=$_GET['email'];
   $nama=htmlspecialchars($nama);
   $email=strip_tags($email);
}
else
{
   die("Maaf, anda harus mengakses halaman ini dari form.html");
}
 
if(empty($nama))
{
   die("Maaf, anda harus mengisi nama");
}
else
{
   if (is_numeric($nama))
   {
      die("Maaf, nama harus berupa huruf");
   }
   else
   {
      echo "Nama: $nama <br /> Email: $email";
   }
}  
?>

Di dalam kode diatas, saya hanya menambahkan fungsi htmlspecialchars() untuk variabel $nama, dan fungsi strip_tags () untuk variabel $email.

Untuk mengujinya, silahkan anda coba memasukkan kode JavaScript kita sebelumnya ke dalam kotak input nama, yakni:

<script> alert('Selamat datang di duniailkom')</script>

dan nilai berikut ke dalam kotak input email:

Dunia <br> <br> <br> <br> <br> <br> <br> <br> <br> <br> Ilkom

Validasi Inputan Form untuk Mencegah HTML Injection pada halaman FormKemudian perhatikan hasil tampilan dari proses.php. Seperti yang dirancang, kali ini hasil inputan tersebut akan difilter agar lebih aman.Hasil Validasi Inputan Form untuk Mencegah HTML Injection pada halaman Form

Jika anda melihat kode yang dihasilkan, maka akan terlihat bahwa fungsi htmlspecialchars() akan mengubah

<script> alert('Selamat datang di duniailkom')</script>

menjadi

&lt;script&gt; alert('Selamat datang di duniailkom')&lt;/script&gt;

Perhatikan bahwa karakter khusus seperti < dan > telah diubah menjadi named entity.

Sedangkan untuk kotak inputan email, seluruh tag <br> telah di filter dan dihapus secara otomatis.


Validasi dengan htmlspecialchars atau strip_tags?

Pilihan apakan menggunakan fungsi htmlspecialchars() atau strip_tags() tergantung kepada alur logika form yang kita buat. Untuk isian form seperti user_name, email, dan alamat akan lebih aman jika kita tidak membolehkan tag HTML sama sekali (menggunakan fungsi strip_tags()), namun untuk kotak form komentar, mungkin kita akan membolehkan beberapa tag untuk diproses seperti tag <b>, tag <i>, atau mungkin juga tag <a>.

Fungsi strip_tags() memiliki argumen kedua yang bisa diisi dengan tag-tag HTML apa saja yang 'dibolehkan'. Jika kita membolehkan tag <a>, <b> dan tag <i> untuk variabel $komentar, maka penulisannya bisa dibuat menjadi:

$komentar=strip_tags($komentar, '<a><b><i>').

Sedangkan untuk fungsi htmlspecialchars(), jika anda ingin karakter tanda kutip ( ' ) juga diubah menjadi named entity, kita bisa menambahkan 1 argumen optional untuk fungsi htmlspecialchars(), dengan pilihan ENT_QUOTES. Sehingga dalam contoh variabel $nama, kita bisa menulisnya menjadi:

$nama=htmlspecialchars($nama, ENT_QUOTES);

Dengan demikian, jika diinput:

<script>alert('Selamat datang di duniailkom')</script>

Akan diproses menjadi:

&lt;script&gt; alert(&#039;Selamat datang di duniailkom&#039;)&lt;/script&gt;

Perhatikan bahwa karakter kutip ( ' ) diganti menjadi kode &#039.


Mengenal Fungsi htmlentities()

Selain fungsi htmlspecialchars() dan fungsi strip_tags(), dalam pembahasan mengenai validasi dan karakter entity HTML, PHP masih memiliki 1 lagi fungsi yang sering dipakai, yakni fungsi htmlentities().

Fungsi htmlentities() akan mengkonversi seluruh karakter khusus di dalam sebuah string menjadi entity, tidak hanya karakter <, >, & dan " seperti pada fungsi htmlspecialchars(). Fungsi htmlentities() akan memproses karakter khusus lain seperti: ™, ©, ®, atau Σ menjadi named entity.

Sebagai contoh, berikut adalah hasil konversi fungsi htmlentities():

<?php
   $string = "Hâäållòó Dunìaîlkom™©";
   echo htmlentities($string);
?>

Dan berikut adalah hasilnya:

Tutorial PHP - contoh cara pengunaan fungsi htmlentities() PHPSeperti yang terlihat bahwa fungsi htmlentities() akan mengubah seluruh karakter khusus menjadi named entity HTML.


Dalam tutorial kali ini, kita telah membahas penggunaan fungsi htmlspecialchars(), fungsi strip_tags() dan fungsi htmlentities() untuk membuat form kita lebih aman. Dalam tutorial berikutnya, kita akan membahas trik dalam menampilkan pesan kesalahan di halaman form.html, bukan di halaman proses.php seperti yang kita tampilkan pada tutorial ini dan tutorial form PHP sebelumnya.

48 Comments

  1. khoiro zamzami
    28 Dec 14
    • Andre
      29 Dec 14
  2. roronoa zoro
    15 Mar 15
    • Andre
      18 Mar 15
  3. Anonymous
    14 Sep 15
    • Andre
      16 Sep 15
      • jaka
        17 Dec 15
        • Andre
          20 Dec 15
  4. anonymous
    05 Dec 15
  5. Ari
    16 Feb 16
    • Andre
      16 Feb 16
  6. Anonymous
    05 Mar 16
    • Andre
      05 Mar 16
  7. Joko
    04 May 16
    • Andre
      05 May 16
  8. ira
    18 Jul 16
    • Andre
      26 Nov 16
  9. Kio
    26 Nov 16
  10. Triadjie
    29 Nov 16
    • Andre
      29 Nov 16
  11. Likhin
    14 Jan 17
    • Andre
      15 Jan 17
  12. Budi
    19 Jan 17
    • Andre
      04 Feb 18
  13. Huda Mustaqim
    18 Jan 18
    • Andre
      19 Jan 18
  14. Joe
    04 Feb 18
    • Andre
      04 Feb 18
      •  
        06 Feb 18
  15.  
    04 Feb 18
    • Joe
      04 Feb 18
      • Andre
        04 Feb 18
        • Joe
          06 Feb 18
  16. Joe
    06 Feb 18
  17. Ihsanul FIkri
    18 Aug 18
    • Andre
      19 Aug 18
  18. Anonymous
    08 Jan 19
  19. Raska
    22 Mar 19
    • Andre
      23 Mar 19
  20. melia
    05 Sep 19
    • Andre
      05 Sep 19
  21. melia
    05 Sep 19
  22. Anonymous
    26 Aug 20
  23. Boy
    02 Mar 21
    • Andre
      03 Mar 21
  24. Anonymous
    28 Jun 22

Add Comment

Leave a Reply to Ihsanul FIkri Cancel reply