Bagaimana cara memastikan bahwa file JavaScript saya yang dikirimkan melalui CDN tidak diubah?

88

Saya sedang mengerjakan skenario di mana beberapa file JavaScript akan di-host di CDN. Saya ingin memiliki beberapa mekanisme sehingga ketika file ini diunduh di sisi pengguna, saya dapat memastikan bahwa file tersebut tidak dirusak dan memang berasal dari CDN yang ditentukan.

Saya memahami bahwa tugasnya sangat mudah jika saya menggunakan SSL, tetapi tetap saja, saya ingin memastikan bahwa file yang benar disajikan bahkan di HTTP tanpa SSL.

Sejauh yang saya bisa cari, tidak ada mekanisme seperti tanda tangan digital untuk file JavaScript yang didukung lintas platform. Mungkin itu tidak dibutuhkan?

Apakah ada beberapa metode bawaan browser untuk memverifikasi penulis file JavaScript? Apakah ada yang dapat saya lakukan untuk melakukan ini dengan cara yang aman?

baba26
sumber
13
Meskipun menurut saya pertanyaan ini menarik, bukankah ini di luar topik?
evolusionxbox
20
mengapa Anda menyajikan file di http?
njzk2
12
"Tapi kenapa tidak ada mekanisme seperti itu?" Karena itu sangat sulit . Setelah data Anda meninggalkan server Anda, itu bersulang. HTTPS membantu tetapi jika itu adalah koneksi HTTP biasa, validasi apa pun bisa gagal (atau lebih tepatnya - lulus). Serangan MITM hanya dapat mengubah tanda tangan yang Anda harapkan dan / atau tanda tangan dari apa yang Anda berikan sebelum browser memenuhi harapan tersebut. Jadi, ketika pengguna menerima beberapa muatan, itu akan dianggap benar-benar aman ... padahal belum tentu begitu.
VLAZ
4
"Tapi kenapa tidak ada mekanisme seperti itu?" Karena sudah ada solusi yang murah, efektif, dan dapat diterapkan secara luas di HTTPS.
Kevin Krumwiede
9
Ini mungkin harus ada di ServerFault atau Keamanan, karena ini benar-benar tentang melayani file dengan cara yang aman, dan hubungan apa pun dengan pemrograman hanya bersinggungan karena file tersebut kebetulan mewakili kode sumber.
underscore_d

Jawaban:

140

Faktanya, fitur seperti ini saat ini sedang disusun dengan nama Subresource Integrity . Perhatikan integrityatribut <script>tag. Meskipun belum sepenuhnya diadopsi secara keseluruhan , itu hanya memenuhi tujuan ini.

integrity

Berisi metadata sebaris yang dapat digunakan agen pengguna untuk memverifikasi bahwa sumber daya yang diambil telah dikirim tanpa manipulasi yang tidak terduga. Lihat Integritas Subresource.

Sumber

Subresource Integrity (SRI) adalah fitur keamanan yang memungkinkan browser memverifikasi bahwa file yang mereka ambil (misalnya, dari CDN) dikirim tanpa manipulasi yang tidak terduga. Ini berfungsi dengan memungkinkan Anda memberikan hash kriptografi yang harus cocok dengan file yang diambil.

Sumber


Contoh:

<script src="https://example.com/example-framework.js"
    integrity="sha384-oqVuAfXRKap7fdgcCY5uykM6+R9GqQ8K/uxy9rx7HNQlGYl1kPzQho1wx4JwY8wC"
    crossorigin="anonymous"></script>

Namun perlu diperhatikan bahwa ini tidak akan melindungi Anda dari serangan Man in the Middle jika Anda mentransfer sumber daya melalui HTTP biasa. Dalam kasus ini, kode hash dapat dipalsukan oleh penyerang, membuat pertahanan terhadap file skrip yang dimanipulasi menjadi tidak berguna.

Karena alasan ini, Anda harus selalu menggunakan koneksi HTTPS yang aman, bukan HTTP biasa, selain langkah-langkah keamanan yang dijelaskan di atas.

Timo
sumber
9
Saya pikir perlu disebutkan bahwa pemeriksaan integritas dapat dengan mudah dipalsukan dengan asumsi bahwa OP berencana untuk mengirim HTML mereka dalam HTTP serta file aset mereka. Jika situs mereka adalah HTTPS dan mereka ingin menyajikan aset melalui HTTP maka sebagian besar browser tidak akan menyukai ini dan mengabaikan aset HTTP secara diam-diam.
MonkeyZeus
3
@MonkeyZeus Ini hanya akan benar meskipun jika terjadi serangan MITM atau jika server kita sendiri dikompromikan, benar? Pemahaman saya adalah bahwa pertanyaan tersebut secara eksplisit menanyakan bagaimana mempertahankan CDN yang dikompromikan.
Timo
10
@TimoSta Persis! Tanpa pemeriksaan ini, jika Anda menyertakan skrip dari, misalnya, https://code.jquery.com/siapa pun yang menyusup code.jquery.comdapat menggunakan XSS situs Anda, terlepas dari apakah code.jquery.comsedang diakses melalui HTTPS atau tidak . Dengan pemeriksaan ini, penyerang hanya dapat mencegah skrip dimuat, bukan menggantinya dengan yang berbahaya.
Ajedi32
1
@MonkeyZeus Saya menambahkan catatan ke jawaban saya, menyatakan kekhawatiran Anda. Apakah Anda setuju dengan kata-katanya?
Timo
1
@TimoSta Sangat bagus, saya menyukainya! btw, saya memberi +1 bahkan sebelum saya mengirim komentar pertama saya :-)
MonkeyZeus
36

Kamu sedang mencari pemeriksaan integritas sub sumber .

Misalnya, inilah cuplikan CDN jQuery:

<script src="https://code.jquery.com/jquery-3.1.0.js"
        integrity="sha256-slogkvB1K3VOkzAI8QITxV3VzpOnkeNVsKvtkYLMjfk="
        crossorigin="anonymous"></script>
Brian
sumber
2
Sama sekali tidak berguna karena penyerang dapat mengubah bidang integritas pada saat yang sama memodifikasi skrip yang Anda unduh.
Lightness Races di Orbit
15
@LightnessRacesinOrbit: Tidak jika Anda mengontrol domain Anda sendiri yang diakses melalui HTTPS tetapi tidak mengontrolnya code.jquery.com. Ini dapat melindungi Anda dari gangguan code.jquery.com.
SilverlightFox
2
@SilverlightFox: Oke, sama sekali tidak berguna melawan serangan MITM *
Lightness Races di Orbit
@LangitRacesin Ya. Masih sangat berguna dan akan mencegah serangan ini misalnya: bleepingcomputer.com/news/security/…
Adrian Mouat
6

Penafian: Seperti biasa, Anda hanya boleh mempertimbangkan mekanisme ini untuk digunakan saat menggunakan https, karena dapat dengan mudah dinonaktifkan melalui MitM dengan http

Selain mekanisme dalam jawaban di atas, Anda juga dapat menggunakan header tanggapan http kebijakan keamanan konten di halaman induk.

http://www.html5rocks.com/en/tutorials/security/content-security-policy/

Kebijakan-Keamanan Konten: script-src 'sha256-qznLcsROx4GACP2dm0UCKCzCG-HiZ1guq6ZZDob_Tng ='

Ada beberapa hal yang perlu diperhatikan di sini. Awalan sha * - menentukan algoritma yang digunakan untuk menghasilkan hash. Dalam contoh di atas, sha256- digunakan. CSP juga mendukung sha384- dan sha512-. Saat membuat hash, jangan sertakan tag. Juga kapitalisasi dan spasi kosong, termasuk spasi kosong di depan atau di belakang.

Menggunakan Chrome 40 atau lebih baru, Anda dapat membuka DevTools lalu memuat ulang halaman Anda. Tab Konsol akan berisi pesan kesalahan dengan hash sha256 yang benar untuk setiap skrip sebaris Anda.

Mekanisme ini telah ada cukup lama, jadi dukungan browser sepertinya cukup bagus, pastikan untuk memeriksanya.

Selain itu, jika Anda ingin memastikan bahwa browser lama yang tidak sesuai tidak aman, Anda dapat menyertakan skrip pengalihan sinkron di bagian atas halaman yang tidak diizinkan oleh kebijakan.

Fabio Beltramini
sumber
telah ada selama beberapa waktu, tetapi dukungan browser tidak terlalu bagus. caniuse.com/subresource-integrity
Sp0T
@ Sp0t - Integritas subresumber (tentang tautan Anda) adalah mekanisme dalam jawaban lain. Jawaban saya adalah tentang kebijakan keamanan konten, yang memiliki dukungan yang jauh lebih baik
Fabio Beltramini
3

Ada poin penting tentang apa yang bisa dan tidak bisa dilakukan penandatanganan semacam ini. Ini dapat melindungi pengguna dari serangan hipotetis di mana seseorang memodifikasi kode Anda. Itu tidak dapat menjamin situs Anda bahwa kode Anda adalah kode yang sedang dijalankan. Dengan kata lain, Anda masih tidak bisa mempercayai apa pun yang datang ke situs Anda dari klien.

ddyer
sumber
2

Jika model musuh Anda mengizinkan penyerang untuk mengubah file JavaScript saat mereka dikirim dari CDN, maka model musuh Anda mengizinkan penyerang untuk mengubah sumber rujukan saat ia dikirimkan untuk menghapus setiap upaya verifikasi, untuk mengubah alamat sumber ke selain CDN, dan / atau untuk menghapus referensi ke JavaScript seluruhnya.

Dan jangan buka can of worm tentang bagaimana aplikasi Anda dapat menentukan apakah resolver pengguna menyelesaikan atau tidak dengan benar ke CDN melalui permintaan HTTP (atau mekanisme lain yang tidak memiliki rantai kepercayaan terverifikasi).

/ etc / hosts:

#  ...
1.2.3.4    vile-pirates.org    trustworthy.cdn
#  ...
Eric Towers
sumber
2
Kalimat pertama jelas tidak benar. Bagaimana jika halaman rujukan dimuat melalui HTTPS dan file JavaScript dimuat melalui HTTP-bukan-S?
pengguna253751
Atau bagaimana jika CDN itu sendiri dikompromikan, tetapi bukan server Anda?
Ajedi32
@ imibis: Saya memilih untuk menganggap OP tidak terlalu irasional untuk mengusulkan skenario seperti itu.
Eric Towers
1
@immibis Bukankah itu sebabnya browser umumnya tidak mengizinkan halaman HTTPS memuat JS melalui HTTP?
Barmar
1
@ imibis Saya mengatakan bahwa itu memperbaiki situasi yang bahkan tidak mungkin, karena browser melarangnya.
Barmar
1

Anda dapat memastikannya dengan Subresource Integrity. Banyak CDN publik menyertakan hash SRI dalam kode sematan yang ditawarkan di situs web CDN. Misalnya, di PageCDN, saat Anda mengklik file jquery di halaman CDN jQuery , Anda mendapatkan opsi untuk menyalin URL atau menggunakan tag skrip yang berisi hash SRI seperti di bawah ini:

<script src="https://pagecdn.io/lib/jquery/3.4.1/jquery.min.js" integrity="sha256-CSXorXvZcTkaix6Yvo6HppcZGetbYMGWSFlBw8HfCJo=" crossorigin="anonymous"></script>

Pada pemuatan halaman, browser akan mengeluarkan permintaan untuk sumber daya ini dan pada penyelesaian permintaan itu akan mencocokkan hash dari file yang diterima dengan yang diberikan sebagai nilai integritas dalam tag skrip. Jika kedua hash tidak cocok, browser akan membuang file jquery tersebut.

Saat ini, fitur ini didukung oleh 91% browser di seluruh dunia. Detail lebih lanjut tentang caniuse .

5377037
sumber