Saya sedang menulis aplikasi facebook berbasis iframe. Sekarang saya ingin menggunakan halaman html yang sama untuk membuat situs web normal serta halaman kanvas dalam facebook. Saya ingin tahu apakah saya dapat menentukan apakah halaman telah dimuat di dalam iframe atau langsung di browser?
javascript
facebook
iframe
akshat
sumber
sumber
Jawaban:
Browser dapat memblokir akses ke
window.top
karena kebijakan asal yang sama . Bug IE juga terjadi. Ini kode kerjanya:top
danself
keduanyawindow
objek (bersama denganparent
), jadi Anda melihat apakah jendela Anda adalah jendela teratas.sumber
window.self !== window.top
kembalitrue
ketika dijalankan dari dalam isiframe
, atauiframe
.Ketika dalam iframe dengan asal yang sama dengan induknya,
window.frameElement
metode mengembalikan elemen (misalnyaiframe
atauobject
) di mana jendela tertanam. Kalau tidak, jika menjelajah dalam konteks tingkat atas, atau jika kerangka induk dan anak memiliki asal yang berbeda, itu akan dievaluasinull
.Ini adalah Standar HTML dengan dukungan dasar di semua browser modern.
sumber
frameElement
akan melemparkan pengecualian SecurityError dalam iframe lintas asal, menurut W3C ( WHATWG mengatakan itu harus mengembalikan null sebagai gantinya). Jadi, Anda mungkin ingin membungkusnya dalam sebuahtry...catch
pernyataan.null
dan keluar dariiframe
Returns the element (such as <iframe> or <object>) in which the window is embedded, or null if the element is either top-level or is embedded into a document with a different script origin; that is, in cross-origin situations.
RoBorg benar, tetapi saya ingin menambahkan catatan tambahan.
Di IE7 / IE8 ketika Microsoft menambahkan Tab ke browser mereka, mereka merusak satu hal yang akan menyebabkan kekacauan dengan JS Anda jika Anda tidak hati-hati.
Bayangkan tata letak halaman ini:
Sekarang dalam bingkai "baz" Anda mengklik tautan (tanpa target, memuat dalam bingkai "baz") itu berfungsi dengan baik.
Jika halaman yang dimuat, mari kita menyebutnya special.html, gunakan JS untuk memeriksa apakah "itu" memiliki kerangka induk bernama "bar" itu akan mengembalikan true (diharapkan).
Sekarang katakanlah bahwa halaman special.html ketika dimuat, periksa kerangka induk (untuk keberadaan dan namanya, dan jika "bilah", ia memuat ulang dirinya sendiri dalam bingkai bilah. Misalnya
Sejauh ini bagus. Sekarang tiba bug.
Katakanlah daripada mengklik tautan asli seperti biasa, dan memuat halaman special.html dalam bingkai "baz", Anda mengekliknya di tengah atau memilih untuk membukanya di Tab baru.
Saat itu, tab baru dimuat ( tanpa bingkai induk sama sekali! ) IE akan memasuki lingkaran tanpa akhir pemuatan halaman! karena IE "menyalin" struktur frame dalam JavaScript sehingga tab baru TIDAK memiliki orangtua, dan orangtua itu MEMILIKI nama "bar".
Berita baiknya, adalah:
di tab baru itu mengembalikan true, dan dengan demikian Anda dapat menguji kondisi aneh ini.
sumber
window.parent
.Jawaban yang diterima tidak berfungsi untuk saya di dalam skrip konten dari Ekstensi Firefox 6.0 (Addon-SDK 1.0): Firefox mengeksekusi skrip konten di masing-masing: jendela tingkat atas dan di semua iframe.
Di dalam skrip konten saya mendapatkan hasil berikut:
Yang aneh tentang output ini adalah selalu sama terlepas apakah kode dijalankan di dalam iframe atau jendela tingkat atas.
Di sisi lain Google Chrome tampaknya hanya menjalankan script konten saya sekali dalam jendela tingkat atas, sehingga di atas tidak akan berfungsi sama sekali.
Apa yang akhirnya berhasil bagi saya dalam skrip konten di kedua browser adalah ini:
Tanpa iframe ini tercetak
0:0
, di jendela tingkat atas berisi satu frame yang dicetak1:1
, dan hanya dalam iframe dokumen yang dicetaknya0:1
.Ini memungkinkan ekstensi saya untuk menentukan di kedua browser apakah ada iframe yang ada, dan juga di Firefox jika dijalankan di dalam salah satu iframe.
sumber
document.defaultView.self === document.defaultView.top
atauwindow !== window.top
. Dalam skrip konten add-on SDK Firefox,self
objek global adalah objek yang digunakan untuk berkomunikasi dengan skrip utama.Saya tidak yakin bagaimana contoh ini bekerja untuk browser Web yang lebih lama, tetapi saya menggunakan ini untuk IE, Firefox dan Chrome tanpa dan mengeluarkan:
sumber
!(window===window.parent)
Saya menggunakan ini:
sumber
.indexOf("HTMLIFrameElement")
:?Gunakan fungsi javascript ini sebagai contoh tentang cara melakukannya.
sumber
Terbaik untuk sekarang Legacy Browser Frame Breaking Script
Solusi lain tidak berhasil untuk saya. Ini berfungsi di semua browser:
Salah satu cara untuk mempertahankan diri terhadap clickjacking adalah dengan memasukkan skrip "frame-breaker" di setiap halaman yang tidak boleh dibingkai. Metodologi berikut akan mencegah halaman web dibingkai bahkan di browser lama, yang tidak mendukung Header X-Frame-Options-Header.
Dalam elemen KEPALA dokumen, tambahkan berikut ini:
Pertama-tama terapkan ID ke elemen style itu sendiri:
Dengan cara ini, semuanya bisa ada dalam HEAD dokumen dan Anda hanya perlu satu metode / taglib di API Anda.
Referensi: https://www.codemagi.com/blog/post/194
sumber
sumber
Karena Anda bertanya dalam konteks aplikasi facebook, Anda mungkin ingin mempertimbangkan untuk mendeteksi ini di server ketika permintaan awal dibuat. Facebook akan memberikan banyak data querystring termasuk kunci fb_sig_user jika dipanggil dari iframe.
Karena Anda mungkin perlu memeriksa dan menggunakan data ini di aplikasi Anda, gunakan untuk menentukan konteks yang tepat untuk di-render.
sumber
Saya sebenarnya terbiasa memeriksa window.parent dan itu bekerja untuk saya, tetapi belakangan ini jendela adalah objek siklik dan selalu memiliki kunci induk, iframe atau tidak iframe.
Seperti komentar menyarankan membandingkan dengan window.parent bekerja keras. Tidak yakin apakah ini akan berfungsi jika iframe persis sama dengan laman web sebagai induk.
sumber
window.parent === window
adalah benar. Jadi jawaban Anda salah. Dan perbandingan ini dapat digunakan untuk memeriksa (setidaknya dalam chrome, tidak mengujinya di browser lain).Ini adalah kode kuno yang saya gunakan beberapa kali:
sumber
(parent.location == self.location)
parent.location
. Kalau tidak, pengecualian dilemparkanJika Anda ingin tahu apakah pengguna mengakses aplikasi Anda dari tab halaman facebook atau dari kanvas untuk memeriksa Permintaan yang Ditandatangani. Jika Anda tidak mendapatkannya, mungkin pengguna tidak mengakses dari facebook. Untuk memastikan konfirmasikan struktur bidang signed_request dan konten bidang.
Dengan php-sdk Anda bisa mendapatkan Permintaan yang Ditandatangani seperti ini:
Anda dapat membaca lebih lanjut tentang Permintaan yang Ditandatangani di sini:
https://developers.facebook.com/docs/reference/php/facebook-getSignedRequest/
dan di sini:
https://developers.facebook.com/docs/reference/login/signed-request/
sumber
Ini berakhir menjadi solusi paling sederhana bagi saya.
sumber
Tetapi hanya jika jumlah iframe berbeda di halaman Anda dan halaman yang memuat Anda di iframe. Jangan buat iframe di halaman Anda untuk mendapatkan jaminan 100% dari hasil kode ini
sumber
Tuliskan javascript ini di setiap halaman
Maka secara otomatis akan diarahkan ke halaman rumah.
sumber