JQuery / Javascript kullanarak her türlü sayfa yenilemesini önleyin


93

Kullanıcı sayfama geldiğinde, sayfayı yenilemesini istemiyorum.

  1. Kullanıcı her zaman F5üstteki düğmeye basar veya yeniler. Bir uyarı almalı

    Sayfayı yenileyemezsiniz.

  2. Ayrıca, kullanıcı yeni bir sekme açarsa ve önceki sekmede aynı url'ye erişmeye çalışırsa bir uyarı almalıdır

    Aynı sayfayı 2 sekmede açamazsınız

Yine de bunu JavaScript veya jQuery kullanarak yapabilir miyim? Birinci nokta gerçekten önemli.


Broadcast Channel API ( developer.mozilla.org/en-US/docs/Web/API/Broadcast_Channel_API ) kullanarak algılayabilir ve sekmeler arasında iletişim kurmak için msg'ler gönderebilirsiniz. Böylece, bunu kullanarak aynı url'ye sahip birden fazla sekmeyi tespit edebilir ve diğer sekmeleri engelleyebilirsiniz.
aeXuser264

Yanıtlar:


195

# 1 aracılığıyla uygulanabilir window.onbeforeunload.

Örneğin:

<script type="text/javascript">
    window.onbeforeunload = function() {
        return "Dude, are you sure you want to leave? Think of the kittens!";
    }
</script>

Kullanıcıya mesaj istenir ve sayfada kalma veya yoluna devam etme seçeneği sunulur. Bu daha yaygın hale geliyor. Stack Overflow, bir gönderi yazarken bir sayfadan ayrılmaya çalışırsanız bunu yapar. Kullanıcının yeniden yüklemesini tamamen durduramazsınız, ancak yaparlarsa kulağa korkutucu gelebilir.

# 2 aşağı yukarı imkansızdır. Oturumları ve kullanıcı girişlerini takip etseniz bile, ikinci bir sekmeyi doğru şekilde algıladığınızı yine de garanti edemezsiniz. Örneğin, belki bir pencerem açık ve sonra kapatırım. Şimdi yeni bir pencere açıyorum. Birincisini zaten kapatmış olsam da, muhtemelen bunu ikinci bir sekme olarak algılarsınız. Artık kullanıcınız kapattığı için ilk pencereye erişemez ve siz onu reddettiğiniz için ikinci pencereye erişemez.

Aslında, bankamın çevrimiçi sistemi # 2'yi yapmak için gerçekten çok çalışıyor ve yukarıda açıklanan durum her zaman oluyor. Bankacılık sistemini tekrar kullanabilmek için genellikle sunucu tarafı oturumunun sona ermesini beklemem gerekir.


1
Onbeforeunload olayının Opera tarayıcısının sürümlerinde bulunmadığına dikkat edin.
WillyCornbread

1
Kullanıcı sayfada kalmayı seçerse bir şeyler yapmanın bir yolu var mı?
riship89

5
Bunun yerine, tarayıcılar arası uyumluluk ve kitaplık sorunlarını önlemek için window.addEventListener (bkz. Developer.mozilla.org/en-US/docs/Web/Events/beforeunload ) kullanmanız gerekse de hile yaptım .
Julien Bérubé

Bu sorunun eski olduğunu biliyorum, ancak gerçekten birden fazla oturumu önlemek istiyorlarsa, WebSockets kullanabilirler mi?
Meghan

1
@Sean - Evet ... gerçekten birden fazla oturumu önlemek istiyorsanız . Bir WebSocket durum bilgili, çift yönlü iletişim sağlayabilir. İstemci (muhtemelen) WebSocket bağlıyken aniden başka biri olmayacaktır, bu nedenle bu kullanıcıya bir belirteç atayabilmeli ve soket kapandığında bunu temizlemelisiniz. Ancak, kullanıcı aracısının beklenen davranışını hackliyor, bu yüzden muhtemelen kötü bir UX. Bunun gibi bir şeyin uygun olabileceği son derece az sayıda durum düşünebiliyorum (belki bir çevrimiçi oyun - birinin iki seviye 37 ölüm pençesi olarak oturum açmasını önlemek için ...).
Seth

34

Kullanıcının yenilemesini engelleyemezsiniz ve gerçekten denememelisiniz. Neden bu çözüme ihtiyacınız olduğuna geri dönmelisiniz , buradaki temel sorun nedir? Oradan başlayın ve sorunu çözmenin farklı bir yolunu bulun. Belki de neden bunu yapmanız gerektiğini düşündüğünüzün böyle bir çözüm bulmaya yardımcı olacağını düşünüyorsunuz.

Temel tarayıcı özelliklerini kırmak asla iyi bir fikir değildir, internetin% 99.999999999'undan fazlası F5 ile çalışır ve yenilenir, bu kullanıcının bir beklentisidir , kırmamanız gereken bir şey.


Sorun, sayfanın siebel uygulaması olmasıdır. ve bir kullanıcı bir oturumdayken yenile tuşuna bastığında, yeni bir oturum oluşturulur ve uygulama kilitlenir. bu yüzden kullanıcının yenilememesi gerekiyor.
pankaj

20
@pankaj - Bu, uygulama sitesinde düzeltilmelidir ve örneğin, kullanıcının oturumu sekmeler arasında paylaşması için çerezler.
Nick Craver

9
Buradan nereden geldiğinden emin değilim. İnternetteki sayısız site, kirli bir formunuz varsa tarayıcının yenilenmesini engeller ve değişikliklerinizi kaybedebileceğiniz konusunda sizi uyarır. Bunun neden "temel tarayıcı özelliklerini bozduğundan" emin değilim.
Siraris

1
@Siraris: Kesinlikle. Artı, kullanıcının kendi özel ağında olmasa bile kullanabileceği özel bir uygulama yapıyorum. Bu yüzden, çevrimdışı kullanım için her şeyi tarayıcı deposunda saklıyorum, ancak sayfayı yeniden yüklerse, tüm uygulama kaybolur. Çok "olağan" olmayabilir, ancak bu modern BT dünyasında giderek daha fazla olacak.
cslotty

16

F5 tuşunu devre dışı bırakmak iyi bir fikir olmasa da bunu JQuery'de aşağıdaki gibi yapabilirsiniz.

<script type="text/javascript">
function disableF5(e) { if ((e.which || e.keyCode) == 116 || (e.which || e.keyCode) == 82) e.preventDefault(); };

$(document).ready(function(){
     $(document).on("keydown", disableF5);
});
</script>

Umarım bu yardımcı olur!


29
CMD + R'nin olduğu OSX'e ne dersiniz? Veya basılacak bir düğmenin olduğu cep telefonu? Bunu bir çözüm olarak görmüyorum
ItalyPaleAle

14

CGI'nin ole günlerinde, çeşitli arka uç eylemlerini tetikleyecek birçok formumuz vardı. Gruplara gönderilen metin bildirimleri, yazdırma işleri, verilerin toplanması vb.

Kullanıcı "Lütfen bekleyin ... Biraz zaman alabilecek BÜYÜK bazı işler yapılıyor." Diyen bir sayfadaysa. REFRESH'i vurma olasılıkları daha yüksekti ve bu KÖTÜ olurdu!

NEDEN? Çünkü daha yavaş işleri tetikleyecek ve sonunda her şeyi batıracaktır.

Çözüm? Formlarını yapmalarına izin verin. Formlarını gönderdiklerinde ... İşinize başlayın ve onları beklemelerini söyleyen başka bir sayfaya yönlendirin.

Ortadaki sayfanın aslında işe başlamak için gereken form verilerini tuttuğu yer. WAIT sayfası ancak bir javascript geçmişi yok etme içeriyor. Böylece, bekledikleri sayfayı istedikleri kadar YENİDEN YÜKLEYebilirler ve bu WAIT sayfası yalnızca BEKLE'nin kendisi için gereken form verilerini içerdiğinden orijinal işi arka planda başlatmak için asla tetiklemeyecektir.

Umarım mantıklıdır.

Geçmiş yok etme işlevi ayrıca GERİ'yi tıklamalarını ve ardından yenilemelerini de engelledi.

Çok kusursuzdu ve kar amacı gütmeyen kuruluşun kapatılmasına kadar BİRÇOK YIL boyunca harika çalıştı.

Örnek: FORM GİRİŞİ - Tüm bilgilerini toplayın ve gönderildiğinde bu, arka uç işinizi tetikler.

Form girişinden YANIT - Statik bekleme sayfanıza ve / veya POST / GET'i başka bir forma (BEKLE sayfası) yönlendirme yapan HTML'yi döndürür.

BEKLE SAYFASI - Yalnızca bekleme sayfasıyla ilgili FORM verilerini ve en yakın geçmişi yok etmek için javascript'i içerir. Yalnızca en son sayfaları yok etmek için (-1 VEYA -2) gibi, ancak yine de orijinal FORM giriş sayfasına geri dönmelerine izin verir.

BEKLE sayfanıza geldiklerinde, istedikleri kadar REFRESH'e tıklayabilirler ve arka uçta orijinal FORM işini asla oluşturmazlar. Bunun yerine, WAIT sayfanız, işlerinin durumunu her zaman kontrol edebilmesi için META zamanlı yenilemeyi benimsemelidir. İşleri tamamlandığında, bekleme sayfasından istediğiniz yere yönlendirilirler.

Manuel olarak YENİLEME yapıyorlarsa ... Buraya iş durumlarının bir kontrolünü daha ekliyorlar.

Umarım yardımcı olur. İyi şanslar.


2
Bu şaşırtıcı ve bilgilendirici cevap için yeterince kredi almadınız. Teşekkür ederim!!
ShiningLight


3

2 numaralı sorun artık BroadcastAPI kullanılarak çözülebilir .

Şu anda yalnızca Chrome, Firefox ve Opera'da mevcut.

var bc = new BroadcastChannel('test_channel');

bc.onmessage = function (ev) { 
    if(ev.data && ev.data.url===window.location.href){
       alert('You cannot open the same page in 2 tabs');
    }
}

bc.postMessage(window.location.href);

2

Sayı (2), kullanıcının dahil olduğu her oturum için özel bir sinyal içeren bir soket uygulaması (websocket, socket.io, vb.) Kullanılarak mümkündür. Bir kullanıcı başka bir pencere açmaya çalışırsa, bir javascript işleyici kontrolüne sahip olursunuz sorun yoksa sunucuyla iletişime geçin ve ardından bir hata mesajıyla yanıt verin.

Ancak, mümkünse iki oturumu google docs gibi senkronize etmek daha iyi bir çözümdür.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.