Pengantar Teks Penskripan Silang (XSS) dan Pertahanan JavaScript

Penskripan sesensi (XSS) adalah salah satu kerentanan keamanan web yang paling prevalent, secara konsisten menduduki peringkat dalam OWASP Top 10. Serangan XSS memungkinkan penyerang untuk menyuntikkan skrip sisi klien jahat ke dalam halaman web yang dilihat oleh pengguna lain. Skrip-skrip ini dapat mencuri token sesi, mengarahkan pengguna ke situs phishing, halaman deface, atau memasang malware. Sementara sanitisasi sisi server kritis, JavaScript memainkan peran pivotal pada klien samping untuk mendeteksi dan mencegah serangan. Artikel ini menyediakan panduan produksi yang komprehensif, siap menggunakan JavaScript untuk melindungi aplikasi Anda dari XSS.

Memahami Tiga Jenis XSS

Bekal menyelam ke pencegahan, sangat penting untuk memahami tiga kategori utama dari XSS: disimpan, dipantulkan, dan berbasis DOM. Masing-masing memerlukan pendekatan deteksi dan pencegahan yang sedikit berbeda.

XSS Tersimpan

Ketersimpanan (persisten) XSS terjadi ketika masukan berniat jahat disimpan secara permanen pada server (misalnya, dalam sebuah database, forum post, atau komentar) dan kemudian disajikan kepada pengguna tanpa sanitisasi yang tepat.Penyaringan muatan serangan dieksekusi dalam peramban dari siapa pun yang melihat konten yang disimpan.

XSS yang Dicerminkan Kecanduan

XSS yang dipantulkan oleh lenting terjadi ketika skrip jahat dipantulkan dari server web, biasanya melalui parameter URL atau penyerahan formulir. Penyerang mengelabui korban untuk mengklik link yang dibuat, dan kode yang disuntik segera dieksekusi. Tidak seperti XSS yang disimpan, muatan tidak bertahan.

XSS Berasaskan-DOM

XSS berbasis-DOM adalah kerentanan sisi klien murni. Muatan serangan memodifikasi lingkungan DOM dalam peramban korban. Kode jahat tidak pernah menyentuh server; berasal dari JavaScript sisi klien yang secara tidak aman menangani input pengguna (misalnya, membaca dari , , atau ).

Mengesankan Serangan XSS dengan JavaScript

Pengesanan gnomination adalah tentang identifikasi aktivitas yang mencurigakan sebelum kerusakan terjadi. JavaScript dapat memantau masukan pengguna, melacak mutasi DOM, dan memvalidasi data di titik masuk.Sementara deteksi sisi klien tidak dapat menangkap semua serangan (terutama jika para penyerang kerajinan meminta langsung ke server), ia menyediakan baris pertahanan pertama yang berharga.

Pengevalidasi dan Sanitasi Masukan

Selalu nazionale dan sanitize masukan pengguna di sisi klien sebelum diproses. Gunakan daripada untuk mencegah eksekusi skrip. Fungsi berikut strip karakter berbahaya dari string:

function sanitizeInput(input) {
 const div = document.createElement('div');
 div.textContent = input;
 return div.innerHTML;
}

Ini bekerja karena pengaturan tidak menafsirkan tag HTML; ini memperlakukan segala sesuatu sebagai teks biasa. Yang dihasilkan berisi versi escape dari karakter khusus HTML manapun (misalnya, , , ).

Pengirim DOM Monitoring Pengirim Unsur Mencurigakan

Penyerang anydon sering kali menyuntikkan tag atau pengendali acara (], ke dalam DOM. Menggunakan API, anda dapat menonton penyisipan unsur yang tak terduga. Contoh dasar:

const observer = new MutationObserver((mutations) => {
 mutations.forEach((mutation) => {
 mutation.addedNodes.forEach((node) => {
 if (node.nodeType === 1) { // element node
 if (node.tagName === 'SCRIPT') {
 console.warn('Potential XSS: a script element was injected via DOM.');
 node.remove(); // or log and analyze
 }
 // Check for dangerous attributes
 if (node.hasAttribute('onerror') || node.hasAttribute('onload')) {
 console.warn('Suspicious event handler attribute detected.');
 }
 }
 });
 });
});
observer.observe(document.body, { childList: true, subtree: true });

tools Caution: Pemblokiran skrip melalui dapat dilewati oleh penyerang pintar dan dapat mematahkan fungsionalitas yang sah. Gunakan ini sebagai alat pemantauan daripada mekanisme pencegahan primer.

URL dan Parameter Hash yang Sah

Untuk XSS berbasis-DOM, baca komponen URL dengan aman menggunakan dan hindari penyisipan nilai secara langsung ke HTML. Deteksi upaya untuk melewati kode executable:

const params = new URLSearchParams(window.location.search);
const userParam = params.get('name');
if (userParam && /[<>"'\/]/.test(userParam)) {
 console.warn('Potential XSS in parameter: ' + userParam);
 // Do not use this value in the DOM without encoding
}

Melarang Serangan XSS dengan JavaScript

Pencegahan violing memerlukan pendekatan multi-lapisan. JavaScript sendiri tidak dapat sepenuhnya mengamankan sebuah aplikasi, tetapi ketika dikombinasikan dengan sanitisasi backend yang tepat dan Content Security Policy (CSP), hal ini secara dramatis mengurangi risiko.

codekan Semua Data Terkendali-Pengguna Sebelum Sisipkan ke DOM

Aturan emas: jangan pernah memasukkan data yang tidak dipercaya langsung ke dalam DOM. Gunakan metode DOM yang aman dan bukan innerHTML.

Use atau

const userInput = getUserInput();
const safeText = document.createTextNode(userInput);
document.getElementById('output').appendChild(safeText);

Bila Anda Harus Menggunakan , Disucikan dengan Perpustakaan

Jika Anda benar-benar perlu untuk memberikan HTML (misalnya, dari editor teks kaya), bergantung pada perpustakaan sanitisasi terpercaya seperti DOMPurify[. DOMPurify adalah perpustakaan yang banyak digunakan, yang diuji pertempuran yang menghapus kode jahat sambil melestarikan HTML yang aman.

// Example with DOMPurify (install via npm or CDN)
const dirty = '<img src=x onerror="alert(1)">';
const clean = DOMPurify.sanitize(dirty);
document.getElementById('content').innerHTML = clean;

DOMPurify bekerja dengan menghurai input, stripping tag berbahaya dan atribut, dan mengembalikan hanya elemen yang diperbolehkan. View DOMPurify on GitHub].

Berilah Fungsi JavaScript Berbahaya

Beberapa metode dan properti JavaScript terkenal sebagai penyebab XSS. Hindari atau kendalikan dengan ketat:

  • [[GANDAFLT:0]]] — gunakan atau sanitaze yang benar.
  • , — aturan yang sama.
  • [[GANDAFLT:0]] — tidak pernah digunakan dengan masukan pengguna.
  • — dapat dieksploitasi jika ada masukan yang terkonkresi.
  • [[Eflat:0]] / dengan kode string[ — hindari; gunakan referensi fungsi sebagai gantinya.
  • [[GALALT:0]] konstruktor — analog untuk .

Kebijakan Keamanan Kandungan Implementasi Implementasi Konten (CSP) melalui JavaScript? Tidak Disarankan

CSP adalah sebuah mekanisme peramban yang membatasi skrip mana yang dapat dijalankan. Biasanya diatur melalui header HTTP, tetapi Anda juga dapat mengaturnya menggunakan tag atau melalui JavaScript dengan cara dinamis membuat elemen . Namun, pengaturan CSP dalam JavaScript kurang aman karena penyerang yang sudah memiliki beberapa kontrol dapat menonaktifkannya. Selalu lebih suka header HTTP. Jika Anda harus menggunakan JavaScript untuk menegakkan CSP (contoh, selama pengembangan), lakukan sangat awal dalam beban halaman:

const meta = document.createElement('meta');
meta.httpEquiv = 'Content-Security-Policy';
meta.content = "default-src 'self'; script-src 'self' 'unsafe-inline'"; // Be very careful with 'unsafe-inline'
document.head.appendChild(meta);

Untuk produksi, konfigurasi CSP di server web atau proksi terbalik Anda. MDN CSP dokumentasi menyediakan panduan komprehensif.

Ukur Keamanan Tambahan

Di luar taktik spesifik JavaScript, strategi pencegahan XSS lengkap mencakup langkah-langkah kritis ini:

  • [[EfolfsFLT:0]] Always validate di sisi server. Client-side validation dapat dihalau. Jangan pernah percaya data klien.
  • [[EfleksifT:0]]Gunakan header respons HTTP yang sesuai. , , dan terutama .
  • [[CUAL-LLT:0]]Output encode setiap kali anda meng-render data pengguna. Konteks: encode untuk entitas HTML, pengkodean URL, pengkodean string JavaScript, dll.
  • [[OGALFLT:0]]Keep dependen diperbarui. Vulnerable JavaScript library (contohnya, versi lama jQuery) adalah vektor XSS umum. Gunakan npm audit atau alat serupa.
  • [[LANFAILT:0]]Gunakan kerangka kerja dengan perlindungan bawaan-in XSS. React, Angular, dan Vue secara otomatis escape output secara default. Masih, berhati-hati dengan atau .
  • [[Eflat:0]]Implement a strict CSP. Hindari dan jika memungkinkan. Gunakan nonces atau hashes untuk skrip inline.

Contoh Dunia-Dunia: Rendering Komentar Aman

Perhatikan sebuah sistem komentar blog di mana pengguna mengirimkan pesan yang ditampilkan kepada orang lain. Seorang penyerang mungkin mencoba untuk menyisipkan . Berikut adalah pendekatan JavaScript yang terintegrasi dengan backend:

  1. [[Frontend sublith: Sanitize menggunakan sebelum dikirim ke server (tetapi server masih harus disanitif).
  2. [[NOLT:0]] Server mengembalikan data: Backend seharusnya HTML-encode teks komentar.
  3. Client rendering: Gunakan atau mesin template aman. Jangan pernah gunakan dengan data pengguna mentah.
function renderComment(comment) {
 const item = document.createElement('div');
 item.className = 'comment';
 const body = document.createElement('p');
 body.textContent = comment.body; // escaped by browser
 item.appendChild(body);
 document.getElementById('comments').appendChild(item);
}

Keberanian Anda

Setelah menerapkan pencegahan, ujilah aplikasi Anda menggunakan pemindai otomatis dan muatan manual. Vektor uji coba umum meliputi:

Gunakan alat pengembang peramban untuk memeriksa DOM dan memastikan muatan terlepas.

Kekecualian Kesimpulan

Skripsi lintas-site tetap menjadi ancaman serius, tetapi JavaScript menawarkan alat yang kuat untuk deteksi maupun pencegahan. Dengan memvalidasi masukan, memantau perubahan DOM, melarikan diri dari output, dan terintegrasi dengan perpustakaan yang kuat seperti DOMPurify, Anda dapat secara signifikan mengeraskan keamanan sisi klien Anda. Ingat bahwa langkah sisi klien bukanlah peluru perak; mereka melengkapi strategi yang dapat disebar pertahanan yang mencakup sanitisasi sisi server, header CSP, dan audit keamanan biasa. Tetap waspada, tes sering kali, dan menjaga perpustakaan Anda sampai saat ini.

Untuk pembacaan lebih lanjut, berkonsultasi dengan OWASSP XSS page dan OWASP XSS Prevention Cheat Sheet.