Firefox 기록으로 돌아 가면 JavaScript가 실행되지 않습니다.


84

Firefox에서 뒤로 버튼을 사용하여 이전에 방문한 페이지로 이동하면 해당 페이지의 스크립트가 다시 실행되지 않습니다 .

거기에 어떤 수정 / 해결 방법 페이지를 두 번째로 볼 때 스크립트를 다시 실행해야하는가?

Google 크롬과 Internet Explorer에서 동일한 페이지를 테스트했으며 의도 한대로 작동합니다.


문제를 테스트하는 데 사용한 파일과 단계는 다음과 같습니다.

(0.html로 이동, 클릭하여 1.html로 이동, 뒤로 버튼)

0.html

<html><body>
<script>
  window.onload = function() { alert('window.onload alert'); };
  alert('inline alert');
</script>
<a href="1.html">Click Me!</a>
</body></html>

1.html

<html><body>
<p>Go BACK!</p>
</body></html>

답변:


92

window.onunload에서 호출 할 빈 함수를 설정합니다.

window.onunload = function(){}; 

예 :

<html><body>
<script type="text/javascript">
  window.onload = function() { alert('window.onload alert'); };
  window.onunload = function(){};
  alert('inline alert');
</script>
<a href="1.html">Click Me!</a>
</body></html>

출처 : http://www.firefoxanswer.com/firefox/672-firefoxanswer.html (보관 버전)


2
감사합니다. 작동합니다. 기본 onunload 처리기가 수행하는 작업에 대한 힌트가 있습니까? (예 : 여기서 일종의 기본 동작을 재정의하고 있습니까?)
Patonza

알겠습니다. 조사하겠습니다. 다시 한번 감사드립니다,이 문제는 :) 잠시 동안 저를 괴롭 히고있다
Patonza

FireFox가 왜 이것을 필요로하는지 아는 사람이 있지만 다른 브라우저는 필요하지 않습니까?
Pim Jager

7
당신은 아무것도 재정의하지 않습니다. 이것은 Firefox가 Back-Forward Cache (bfcache)에 페이지를 캐싱하지 못하게합니다. developer.mozilla.org/en/DOM/window.onunload developer.mozilla.org/En/Using_Firefox_1.5_caching
Chris Haas

1
안타깝게도 bfcache 중단 해야 하지만 여전히 이전 페이지를 기억하는 것 같습니다. 특히로드 된 iframe URL은 돌아갈 때 다시로드되며 생성 된 콘텐츠를 프레임에 배치해야하는 경우 크로스 브라우저가없는 것 같습니다. 새로 고치는 방법.
NoBugs

76

Firefox에서 뒤로 버튼을 사용하여 이전에 방문한 페이지로 이동하면 해당 페이지의 스크립트가 다시 실행되지 않습니다.

정확하고 좋은 일입니다.

Firefox (및 Safari 및 Opera)에서 링크를 누르면 다음 페이지로 이동하기 위해 페이지가 즉시 파괴되지 않습니다. 페이지를 그대로 유지하고보기에서 숨길뿐입니다. 뒤로 버튼을 누르면 문서를 다시로드하지 않고도 이전 페이지를 다시 볼 수 있습니다. 이것은 훨씬 더 빠르므로 사용자에게 더 부드러운 뒤로 / 앞으로 페이지 전환이 가능합니다.

이 기능을 bfcache 라고합니다 .

사용자가 이전에로드하고 사용하는 동안 페이지에 추가 한 모든 콘텐츠는 그대로 유지됩니다. 페이지 요소에 연결 한 모든 이벤트 처리기는 계속 연결됩니다. 설정 한 시간 제한 / 간격은 계속 활성화됩니다. 따라서 당신이 숨겨졌다가 다시 나타났다는 사실을 알아야 할 이유가 거의 없습니다. onload스크립트 코드를 다시 호출 하거나 인라인하는 것은 잘못된 것 입니다. 해당 함수에서 수행 한 바인딩 및 콘텐츠 생성은 동일한 콘텐츠에 대해 두 번째로 실행되어 잠재적으로 비참한 결과가 발생하기 때문입니다. (예 : document.write인라인 스크립트에서는 페이지가 완전히 파괴됩니다.)

에 쓰기 window.onunload가 영향을 미치는 이유 는 bfcache를 구현하는 브라우저가-언제 폐기 될지 알 필요가있는 페이지와의 호환성을 위해-언제 onunload발생하는지 알기 위해 관심이 있다고 선언하는 페이지 는 bfcache가 비활성화됩니다. 해당 페이지는 bfcache에서 가져 오는 대신 페이지로 돌아갈 때 새로로드됩니다.

따라서 설정 window.onunload= function() {};하면 실제로 수행하는 작업은 의도적으로 bfcache를 깨는 것입니다. 이로 인해 페이지 탐색 속도가 느려지므로 최후의 수단으로 사용하지 마십시오.

bfcache를 엉망으로 만들지 않고 사용자가 언제 페이지를 떠나거나 다시 돌아 왔는지 알아야하는 경우 대신 onpageshowonpagehide이벤트를 트랩 할 수 있습니다 .

window.onload=window.onpageshow= function() {
    alert('Hello!');
};

3
내 문제는 bfcache가 모든 페이지를 캐시하지 않기 때문에 js를 다시 실행하여 손실 된 콘텐츠를 다시 만들어야한다는 것입니다. 따라서 전체 페이지를 스 래싱하는 것은 괜찮을 수 있습니다. 어쨌든 window.onload 이벤트를 사용하지 않고 jQuery document.ready 이벤트를 사용하고 있습니다. document.ready를 계속 사용하고이 문제를 피할 수있는 방법을 알고 있습니까?
Patonza

bfcache는 일반적으로 남은 페이지를 그대로 반환해야합니다. 이전 페이지에서 돌아온 후 누락 된 내용은 무엇입니까? (테스트 케이스?) document.ready는 기본적으로 window.onload(일부 브라우저의 경우 어쨌든 동일한 이벤트)와 동일한 방식으로 작동 합니다.
bobince

14
그것은 캐시 된 것을 고려할 때 자바 스크립트를 다시 실행하지 않기 때문에 좋은 일이 아닙니다 ... 그러나 자바 스크립트가 이전에 변경 한 내용을 실제로 캐시하지는 않습니다. 자바 스크립트가 페이지로드시 요소에서 페이드 인하면 히스토리를 방문 할 때 다시 페이드되지 않습니다 ...하지만 다시 0 불투명도로 시작하여 자바 스크립트가 수행 한 작업을 취소합니다! 전부 아니면 아님. 자바 스크립트를 다시 실행하지 않고 캐시 된 상태로 표시하려면 자바 스크립트가 실행 된 후 페이지의 전체 상태를 캐시해야합니다!
Jimbo Jonny

1
@Jimbo : 테스트 케이스주세요. bfcache는 숨기기 / 표시를 통해 DOM의 정확한 상태를 보존하기위한 것입니다. 페이드 인 된 요소는 다른 스크립트를 실행하여 다시 숨기지 않는 한 페이지가 반환 될 때 불투명하게 유지됩니다.
bobince

1
@bobince-불투명도를 0으로 설정하는 CSS 파일로 요소를 만든 다음 jQuery를 사용하여 문서에서 페이드 인을 준비합니다. 히스토리로 돌아 가면 JS가 페이드 인 할 때 스타일 속성에 추가 한 불투명도 : 1을 유지하지 않고 스타일 시트 CSS (0)를 다시 적용합니다. 페이지를 처음 방문하면 요소가 0에서 1로 페이드 인됩니다. 다른 페이지로 이동하여 뒤로 치면 완전히 투명하게 표시됩니다.
Jimbo Jonny 2012

23

이벤트 의 persisted속성을 확인할 수 있습니다 pageshow. 초기 페이지로드시 false로 설정됩니다. 페이지가 캐시에서로드되면 true로 설정됩니다.

window.onpageshow = function(event) {
    if (event.persisted) {
        alert("From bfcache");
    }
};

어떤 이유로 jQuery에는 이벤트에이 속성이 없습니다. 그래도 원래 이벤트에서 찾을 수 있습니다.

$(window).bind("pageshow", function(event) {
    if (event.originalEvent.persisted) {
        alert("From bfcache");
    }
});

자바 스크립트와 jquery 버전을 모두 제공해 주셔서 감사합니다! 당신은 거기 끝에 닫기 대괄호를 놓쳤습니다 (이것은 신음이 아닙니다!). 나는 또한 다른 사람들을 위해 IE와 Chrome 보고서 .persisted는 상관없이 항상 거짓임을 주목할 것입니다.
Magnus Smith

Magnus가 언급했듯이 if 문을 제거하기 전까지는 Chrome에서 작동하지 않았습니다.
Justin

이것은 Chrome 58.0.3029.110 (64 비트) 및 FF 53.0.2 (64 비트)에서 변경없이 저에게 효과적이었습니다.
kmoser

1

아무것도하지 않는 "onunload"이벤트에 연결 :

<html><body>
<script type="text/javascript">
  window.onload = function() { alert('window.onload alert'); };
  window.onunload = function(){}; 
  alert('inline alert');
</script>
<a href="1.html">Click Me!</a>
</body></html>

확실하지, 나는까지 투표를 준 사람 같은 외모는이 질문에 대한 모든 답 ...을 downvoted
Patonza

페이지에 onunload 이벤트를 추가하면 실제로 페이지 전체가 캐시되는 것을 비활성화한다는 답변에 추가해야합니다. 이것은 단순히 JS를 다시 실행하게 만드는 것이 아니라 서버로드를 한 단계 높여줍니다. 이것은 실제로 가볍게 받아 들일 제안이 아니므로 신중하게 고려해야합니다.
dreagan

@dreagan, 이것은 bfcache를 비활성화하지만 반드시 HTTP 캐시를 비활성화하지는 않습니다. HTTP 캐시에는 완전히 다른 규칙 세트가 있습니다. 거기에 서버 측 절전 모드를 던지면 다시 클릭하는 동안 알 수 있습니다. Mozilla 는 BFCache 에 대한 FAQ 의 세 번째 질문에서 이에 대해 설명 합니다.
Chris Haas

나는 BFcache에 대해 이야기하고 있었는데, 그것을 지정해야했습니다. 그렇다고 OP에 결과를 알리지 않고 이와 같은 제안을해야한다는 의미는 아닙니다. 대안은 onpopstate 이벤트를 사용하여 javascript를 다시 시도하고 실행하는 것입니다.
dreagan

나는 아직도 내가 이해하는지 모르겠다. 클라이언트의 로컬 bfcache가 우회되면 왜 "서버로드가 한 단계 올라 갈까요?" 예, DOM을 다시 빌드해야하지만 HTML은 클라이언트 HTTP 캐시의 일부 여야합니다. 예, 추가 리소스를 다시로드해야하지만 이러한 리소스도 클라이언트의 HTTP 캐시에 포함되어야합니다. 에 관해서는 onpopstate,이 질문은 거의 오년 해당 이벤트 전 질문을 받았다 때 여전히 비교적 새로운이고 브라우저 지원은 매우 일관성이 있었다
크리스 하스

1

내가 아는 한 Firefox는 onLoad다시 이벤트를 발생시키지 않습니다 .

대신 여기이 링크를 기반으로 onFocus를 트리거해야합니다 .


그것을 테스트하고 windows.onfocus는 빈 window.onunload 핸들러를 설정하지 않아도 실제로 호출됩니다. onunload 설정은 약간 더 좋은 해결 방법이지만 .onfocus도 괜찮을 것입니다. 감사합니다 :)
Patonza 2010

1

사용자가 브라우저 기록을 사용하여 페이지로 다시 이동할 때 페이지가 JavaScript를 실행하도록하는 간단한 방법은 OnPopState 이벤트입니다. 이를 사용하여 홈페이지 ( https://fynydd.com ) 에서 비디오를 일시 중지하고 재생합니다 .

window.onpopstate = function() {

    // Do stuff here...
};

0

ajax 작업과 같은 경우 URL 변경 리스너를 사용할 수 있습니다.

$(window).on('hashchange', function() {
        ....
});
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.