Kullanıcının tarayıcı geçmişine geri dönüp dönemeyeceği nasıl kontrol edilir


Yanıtlar:


119

Kısa cevap: Yapamazsınız.

Teknik olarak, mülkü kontrol edecek doğru bir yol var:

history.previous

Ancak, işe yaramaz. Buradaki sorun, çoğu tarayıcıda bunun bir güvenlik ihlali olarak kabul edilmesidir ve genellikle tanımsız döndürür .

history.length

Diğerlerinin önerdiği bir özelliktir ...
Ancak , tarihin tam olarak nerede olduğunu göstermediği için uzunluk tamamen çalışmaz . Ayrıca, her zaman aynı numaradan başlamaz. Örneğin, bir açılış sayfasına sahip olmayan bir tarayıcı 0'dan başlarken, açılış sayfası kullanan başka bir tarayıcı 1'den başlar.

alternatif metin

Çoğu zaman bir bağlantı eklenir:

history.back();

veya

 history.go(-1);

ve sadece geri dönemezseniz bağlantıyı tıklamanın hiçbir şey yapmaması beklenir.


Bu iyi bir bilgidir, ancak sorunu çözmez. Aslında herhangi bir tarayıcıda çalışan bazı kodları hazırlamak olurdu. Belki de ilk kullandığınız tarayıcıyı kontrol eden bir kod.
Santiago Bendavid

5
Söylediğim kesin bir cevap yok. Her yaklaşımın artılarını ve eksilerini söylüyorsunuz, ancak hangi tarayıcıyı kullandığınızı kontrol eden ve bir veya diğer kod parçalarını şartlı olarak yürüten bir komut dosyasının nasıl alınacağını değil.
Santiago Bendavid

'Bununla ilgili sorun, çoğu tarayıcıda bu bir güvenlik ihlali olarak kabul ediliyor' ile ne demek istediğimi anlayabilir miyim Başka bir iş parçacığındaki başka bir kullanıcı, müşterinin tarayıcı geçmişini alabilmenin güvenliği ihlal ettiğini belirtti, ancak açıklamıyor Neden. Güvenlik tehditleri nelerdir?
Kevin Chandra

Bir web sitesi, dolaylı kişisel bilgiler içerebilecek bir kullanıcının geçmişini bilmemelidir. Bir site, kullanıcının sitenin kendisinde ne yaptığını bilmek için izleme / çerezleri kullanabilir, ancak örneğin hangi bankayı kullandığımı, çocuklarımın hangi okula gittiğini vb. tarayıcılar bu mülke erişime izin vermez
McAden

84

Kontrol etmenin başka bir yolu var - yönlendireni kontrol edin. İlk sayfada genellikle boş bir yönlendiren bulunur ...

if (document.referrer == "") {
    window.close()
} else {
    history.back()
}

2
Yönlendiren, gizlilik nedeniyle gizlenebilir.
Kornel

11
Bir sayfa bir bağlantı tarafından yüklenmediğinde, ancak adres çubuğuna URL girildiğinde veya bir yer işareti yüklendiğinde yönlendiren her zaman boştur. Tarayıcı sekmesi / penceresi daha önce başka bir sayfa yüklediğinde, bu tür sayfaların bir geçmişi olabilir!
ygoe

1
Ancak çok sayfalı web sitesinde navigasyon için uygulanabilir bir çözüm
Dan

36
Yeni bir pencereyi zorlamak için target = "_ blank" ile bir pencere açılmışsa çalışmaz. Tarayıcıdaki geri düğmesi çalışmaz, ancak bir belge olacaktır.
Referrer

3
Güvenli (HTTPS) bir sayfadan güvensiz bir sayfaya (HTTP) geliyorsanız bu işe yaramaz, çünkü yönlendireni keser.
Kevin Borders

54

Kodum, tarayıcının bir sayfa geri gitmesine izin verir ve bu başarısız olursa bir yedek URL yükler. Ayrıca hashtag değişikliklerini de algılar.

Geri düğmesi kullanılamadığında, yedek URL 500 ms'den sonra yüklenir, bu nedenle tarayıcının bir önceki sayfayı yüklemek için yeterli zamanı vardır. Yedek URL'yi hemen sonra yüklemek window.history.go(-1);, tarayıcının yedek URL'yi kullanmasına neden olur, çünkü js komut dosyası henüz durmadı.

function historyBackWFallback(fallbackUrl) {
    fallbackUrl = fallbackUrl || '/';
    var prevPage = window.location.href;

    window.history.go(-1);

    setTimeout(function(){ 
        if (window.location.href == prevPage) {
            window.location.href = fallbackUrl; 
        }
    }, 500);
}

6
Bence bu gerçekten sorunun özünü, bir kişinin neden umursadığını ve bu konuda gerçekten güvenilir ve tutarlı bir şekilde neler yapılabileceğini gösteriyor.
Chris Marisic

1
Bu, geri düğmesinin bulunduğu URL'yi alıp kromdaki yeni bir sekmeye yapıştırıncaya kadar çalıştı. Geri düğmesine tıklamak boş bir sekmeye gönderilmesiyle sonuçlandı. :(
karlingen

2
Chrome'un varsayılan davranışı budur. Sayfayı "ziyaret ettiniz" chrome://newtabve böylece tarihe geri dönebilirsiniz.
redelschaap

Buna dikkat edin, çünkü yavaş bir ağ bağlantısı ile yedek url'ye oldukça düzenli olarak vurursunuz.
Mart'ta cameck

14

İşte böyle yaptım.

Bir boole ayarlamak için 'beforeunload' etkinliğini kullandım. Sonra 'ön yükün' tetiklenip tetiklenmediğini izlemek için bir zaman aşımı ayarladım.

var $window = $(window),
    $trigger = $('.select_your_link'),
    fallback = 'your_fallback_url';
    hasHistory = false;

$window.on('beforeunload', function(){
    hasHistory = true;
});

$trigger.on('click', function(){

    window.history.go(-1);

    setTimeout(function(){
        if (!hasHistory){
            window.location.href = fallback;
        }
    }, 200);

    return false;
});

Büyük tarayıcılarda çalışıyor gibi görünüyor (şimdiye kadar test edilmiş FF, Chrome, IE11).


1
Bu, sorunun en iyi yanıtıdır. Kolayca yerini alabilir window.location.href = fallbackile window.close()ve çok çalışıyor.
Vitani

13

Projelerimde kullandığım bir pasaj var:

function back(url) {
    if (history.length > 2) {
        // if history is not empty, go back:
        window.History.back();
    } else if (url) {
        // go to specified fallback url:
        window.History.replaceState(null, null, url);
    } else {
        // go home:
        window.History.replaceState(null, null, '/');
    }
}

FYI: Tarayıcı geçmişini yönetmek için History.js'yi kullanıyorum .


Geçmişi neden karşılaştırır. Uzunluk 2 ile?

Çünkü Chrome'un başlangıç ​​sayfası, tarayıcı geçmişindeki ilk öğe olarak sayılıyor.


history.lengthKullanıcının davranışları ve kullanıcının davranışları çok azdır :

  • Kullanıcı tarayıcıda yeni boş bir sekme açar ve ardından bir sayfa çalıştırır. history.length = 2ve back()bu durumda devre dışı bırakmak istiyoruz , çünkü kullanıcı boş sekmeye gidecek.
  • Kullanıcı daha önce bir yerdeki bir bağlantıyı tıklayarak sayfayı yeni sekmede açar . history.length = 1ve yine back()yöntemi devre dışı bırakmak istiyoruz .
  • Son olarak, kullanıcı birkaç sayfayı yeniden yükledikten sonra geçerli sayfaya gelir . history.length > 2ve şimdi back()etkinleştirilebilir.

Not: Kullanıcı harici web sitesinden bağlantıyı tıkladıktan sonra mevcut sayfaya geldiğinde durumu ihmal ediyorum target="_blank".

Not 2: document.referrer adresini yazarak web sitesini açtığınızda ve ayrıca web sitesi alt sayfaları yüklemek için ajax kullandığında boştur, bu nedenle ilk durumda bu değeri kontrol etmeyi bıraktım.


Bu yaklaşım benim için çok işe yaradı. Aslında yedekte kullandığım sayfalarım için statik yedek geri bağlantıları saklıyorum.
Greg Blass

Ancak, geri dönerseniz, history.length değişmez .. Yani, düzgün çalışmıyor
Ciprian Mocanu

Haklısın maalesef. Bu pasajı yalnızca "bir adım geri" yapısıyla kullanıyorum ...
gregmatys

12

bu hile yapıyor gibi görünüyor:

function goBackOrClose() {  

    window.history.back();
    window.close(); 

    //or if you are not interested in closing the window, do something else here
    //e.g. 
    theBrowserCantGoBack();

}

History.back () öğesini ve ardından window.close () öğesini çağırın. Tarayıcı geçmişe geri dönebiliyorsa, bir sonraki ifadeye ulaşamaz. Geri dönemezse pencereyi kapatır.

Ancak, sayfaya bir url yazarak ulaşılmışsa, firefox komut dosyasının pencereyi kapatmasına izin vermeyeceğini lütfen unutmayın.


3
Ben aksi takdirde history.back () çalıştırdıktan sonra yine kaçıyorum, bir sonraki ifadeyi çalıştırmak denemeden önce birkaç yüz milisaniye kadar bir gecikmeyle bir setTimeout kullanmadıkça çalışmıyor bu saptadığımız
Ken Fehling

Ben şahsen yaşamadım, hangi tarayıcıydı?
xtrahelp.com

Aşağıdaki cevap setTimeout fonksiyonu ile iyi çalışmıştı. ör .: setTimeout (function () {window.close ()}, 400);
gilchris

2
window.close()birçok modern tarayıcı tarafından güvenlik riski olarak kabul edilir. Bazıları bunu yapmanıza izin vermeyecek.
Rudi Kershaw

window.history.back () öğesinden sonra her şeyi yapabilirsiniz; ) (window.close; sadece bir örnektir
hariszaman

10

Dikkatli olun window.history.lengthçünküwindow.history.forward()

Yani belki window.history.length1'den fazla giriş olabilir, ancak geçmiş geri girişleri olmayabilir . Yani ateş ederseniz hiçbir şey olmazwindow.history.back()


9

Geri düğmesinin kullanılabilir olup olmadığını doğrudan kontrol edemezsiniz. Bakabilirsiniz history.length>0, ancak geçerli sayfanın önünde de sayfalar varsa bu geçerli olacaktır. Sadece geri düğmesinin kullanılamaz durumda olduğundan emin olabilirsiniz history.length===0.

Bu yeterince iyi değilse, yapabileceğiniz tek şey aramaktır history.back()ve sayfanız daha sonra yüklenirse geri düğmesi kullanılamaz! Geri düğmesi vasıtası eğer Tabii bu olan mevcut, sadece sayfadan uzak navigasyon ettik. Navigasyonu iptal etmek için onunloadizniniz yok, bu yüzden geri dönüşü durdurmak için yapabileceğiniz tek şey aslındaonbeforeunload , bu da büyük bir can sıkıcı istemin ortaya çıkmasına neden olur. Buna değmez.

Aslında, tarihle her şeyi yapmak normalde çok kötü bir fikirdir. Geçmişte gezinme, web sayfaları için değil tarayıcı kromu içindir. “Geri dön” bağlantıları eklemek genellikle değerinden daha fazla kullanıcı karışıklığına neden olur.


2
uzunluk hakkında - tüm tarayıcılarda o zaman bile. Bazı tarayıcılar geçerli sayfayı geçmiş öğesi olarak sayar ve 1'den başlar. Tarayıcı algılamayı dahil etmeniz gerekir.
McAden

Aslında her zaman olduğunu düşündüm 1! Bu 0bir beyin parçasıydı, tarayıcıların her zaman 1veya daha fazla yanıt vereceğini düşündüm . Opera ve IE başka türlü düşünüyor - iyi yakalama.
bobince

1
"Geçmişte gezinme, tarayıcı sayfaları için değil, web sayfaları içindir" - Kabul Edildi
Brian

5

history.lengthkullanıcının geçmişe geri dönüp dönemeyeceğini göstermediği için işe yaramaz. Ayrıca farklı tarayıcılar 0 veya 1 başlangıç ​​değerlerini kullanır - bu tarayıcıya bağlıdır.

Çalışma çözümü $(window).on('beforeunload'olay kullanmaktır , ancak sayfa ajax aracılığıyla yüklenir ve pencere geçmişini değiştirmek için pushState kullanırsa çalışacağından emin değilim.

Bu yüzden bir sonraki çözümü kullandım:

var currentUrl = window.location.href;
window.history.back();
setTimeout(function(){
    // if location was not changed in 100 ms, then there is no history back
    if(currentUrl === window.location.href){
        // redirect to site root
        window.location.href = '/';
    }
}, 100);

Benim için böyle çalışır: işlev goBackOrTo (targetUrl) {var currentUrl = window.location.href; window.history.go (1); setTimeout (function () {// konum 800 ms'de değiştirilmediyse, (currentUrl === window.location.href) {// site kök window.location.href = targetUrl yönlendirme yapamaz. }}, 800); }
alfonx

2

Aşağıdaki yaklaşımı buldum. Tarayıcının sayfadan ayrılmaya başlayıp başlamadığını saptamak için onbeforeunload olayını kullanır. Belirli bir zaman diliminde değilse, yalnızca yedeklemeye yönlendirilir.

var goBack = function goBack(fallback){
    var useFallback = true;

    window.addEventListener("beforeunload", function(){
      useFallback = false;
    });

    window.history.back();

    setTimeout(function(){
        if (useFallback){ window.location.href = fallback; }
    }, 100); 
}

Düğmesini kullanarak bu işlevi çağırabilirsiniz goBack("fallback.example.org").


1
Bunu en çok seviyorum, sadece window.onbeforeunload'un üzerine yazmaması windows.onbeforeunloadiçin olay dinleyicisine geçtim window.addEventListener("beforeunload", function (event) { useFallback = false; });.
MiChAeLoKGB

2

Burada ve burada cevap üzerine inşa . Bence, daha kesin cevap, bunun yeni bir sekmede yeni bir sayfa olup olmadığını kontrol etmektir.

Sayfanın geçmişi birden fazla ise, geçerli sayfanın önceki sayfasına geri dönebiliriz. Değilse, sekme yeni açılan bir sekmedir ve yeni bir sekme oluşturmamız gerekir.

Farklı bir şekilde, verilen cevaplara göre, referreryeni bir sekmenin hala bir yönlendiriciye sahip olacağı için bir kontrol etmiyoruz .

if(1 < history.length) {
    history.back();
}
else {
    window.close();
}

1
Teşekkür ederim. Günümü kurtardın :).
Bijay Yadav

1

Başka Orada yakın alınan mükemmel bir çözüm, başka SO cevap :

if( (1 < history.length) && document.referrer ) {
    history.back();
}
else {
    // If you can't go back in history, you could perhaps close the window ?
    window.close();
}

Birisi kullanırken işe yaramadığını, target="_blank"ancak Chrome'da benim için çalıştığını söylüyor.


0

tarayıcıda geri ve ileri düğmesi vardır. Bu soruya bir çözüm buldum. ancak tarayıcı ileri hareketini etkiler ve bazı tarayıcılarda hataya neden olur.

Şöyle çalışır: Tarayıcı, hiç açılmayan yeni bir URL açarsa, history.length büyür.

böylece hash'ı

  location.href = '#__transfer__' + new Date().getTime() 

hiç gösterilmemiş bir url almak için, o zaman history.length gerçek uzunluğu alacak.

  var realHistoryLength = history.length - 1

ama, Her zaman iyi çalışmaz, ve neden bilmiyorum, özellikle url otomatik hızlı atlamak zaman.


0

Bir çözüm bulmaya çalışıyordum ve bu alabileceğim en iyisi (ama harika çalışıyor ve burada bile bulduğum en kolay çözüm).

Benim durumumda, bir geri düğmesi ile geçmişe geri dönmek istedim, ancak kullanıcı açılan ilk sayfa uygulamamın bir alt sayfası olsaydı, ana sayfaya geri dönecekti.

Çözüm, uygulama yüklenir yüklenmez, sadece geçmiş durumunda bir değişiklik yaptım:

history.replaceState( {root: true}, '', window.location.pathname + window.location.hash)

Bu şekilde, sadece history.state.rootgeri dönmeden önce kontrol etmek gerekiyor . Doğruysa, bunun yerine bir geçmiş yapın:

if(history.state && history.state.root)
    history.replaceState( {root: true}, '', '/')
else
    history.back() 

Başka iyi bir kullanım durumu olduğunu düşünmüyorum. Uygulamanızın dışındaki geçmişi kontrol etmek istiyorsanız, belki de iyi bir fikir değildir.
Maxwell sc

-1
var fallbackUrl = "home.php";
if(history.back() === undefined)
    window.location.href = fallbackUrl;

bu süper kolay görünüyor ?! çeşitli tarayıcılarda test edildi mi?
benzkji

Chrome'da history.back()ise undefinedsadece boş sekme sayfasında
gregmatys

-2

Çözüm

'use strict';
function previousPage() {
  if (window.location.pathname.split('/').filter(({ length }) => length > 0).length > 0) {
    window.history.back();
  }
}

Açıklama

window.location.pathnamesize mevcut URI'yi verecektir. Mesela https://domain/question/1234/i-have-a-problemverecek /question/1234/i-have-a-problem. Daha fazla bilgi için window.location ile ilgili belgelere bakın .

Daha sonra, bu çağrı split()URI'nin tüm parçalarını bize verecektir. yani önceki URI'mızı alırsak benzer bir şeyimiz olur ["", "question", "1234", "i-have-a-problem"]. Daha fazla bilgi için String.prototype.split () ile ilgili belgelere bakın .

Geri arama, filter()ters eğik çizgi tarafından oluşturulan boş dizeyi filtrelemek için burada. Temel olarak yalnızca 1'den büyük bir uzunluğa (boş olmayan dize) sahip parça URI'sini döndürür. Yani bizim gibi bir şeyimiz olurdu ["question", "1234", "i-have-a-question"]. Bu şöyle yazılabilirdi:

'use strict';
window.location.pathname.split('/').filter(function(fragment) {
  return fragment.length > 0;
});

Daha fazla bilgi için Array.prototype.filter () ve Yıkım ataması hakkındaki belgelere bakın .

Şimdi, kullanıcı açıkken geri dönmeye çalışırsa https://domain/, if ifadesini tetiklemeyeceğiz ve bu yüzden window.history.back()yöntemi web sitemizde kalacak şekilde yöntemi tetiklemeyeceğiz . Bu URL, []uzunluğu olan 0ve 0 > 0yanlış olan eşdeğer olacaktır . Bu nedenle, sessizce başarısız oluyor. Tabii ki, bir şey kaydedebilir veya isterseniz başka bir işlem yapabilirsiniz.

'use strict';
function previousPage() {
  if (window.location.pathname.split('/').filter(({ length }) => length > 0).length > 0) {
    window.history.back();
  } else {
    alert('You cannot go back any further...');
  }
}

Sınırlamalar

Tabii ki, tarayıcı Geçmiş API'sını desteklemiyorsa bu çözüm çalışmaz . Bu çözümü kullanmadan önce hakkında daha fazla bilgi edinmek için belgelere bakın.


-5

Bunun işe yarayıp yaramadığından emin değilim, ama şunu deneyin:

<script type="text/javascript">

    function goBack() {
        history.back();
    }

    if (history.length > 0) { //if there is a history...
        document.getElementsByTagName('button')[].onclick="goBack()"; //assign function "goBack()" to all buttons onClick
    } else {
        die();
    }
</script>

Ve HTML'de bir yerde:

<button value="Button1"> //These buttons have no action
<button value="Button2">

DÜZENLE:

Yapabileceğiniz şey, tarayıcıların geri işlevini neleri desteklediğini araştırmak (hepsinin desteklediğini düşünüyorum) ve bu sayfada bulunan ve ayrıntılı olarak açıklanan standart JavaScript tarayıcı algılama nesnesini kullanmaktır . Daha sonra 2 farklı sayfanız olabilir: biri geri düğmesiyle uyumlu "iyi tarayıcılar" ve diğeri tarayıcılarını güncellemelerini söyleyen "kötü tarayıcılar" için


2
history.backbir işlevdir. history.length > 0O zaman geri dönüp history.back()
dönmediğini

3
Ayrıca []bir NodeList üzerinde bir anlam ifade etmez ve bir olay işleyicisine dize atayamazsınız.
bobince

-8

window.history.length0'a eşit olup olmadığını kontrol edin .


6
İyi bir yol değil, çünkü history.length tarihin neresinde olduğunuzu söylemiyor ...
Ron Reiter

@Ron Reiter: Evet, sanırım bu sorunun en iyi cevabı ve diğer yorumları bir yıldan uzun bir süre önce bunu zaten belirlemişti ...
Cristian Sanchez
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.