모든 브라우저에서 웹 페이지 캐싱을 어떻게 제어합니까?


1552

조사에 따르면 모든 브라우저가 HTTP 캐시 지시문을 동일한 방식으로 존중하는 것은 아닙니다.

보안상의 이유로 우리는 우리의 응용 프로그램에서 특정 페이지를 캐시하지 않으려는 , 지금까지 웹 브라우저. 최소한 다음 브라우저에서 작동해야합니다.

  • Internet Explorer 6 이상
  • Firefox 1.5 이상
  • 사파리 3+
  • 오페라 9+
  • 크롬

우리의 요구 사항은 보안 테스트에서 비롯되었습니다. 웹 사이트에서 로그 아웃 한 후 뒤로 버튼을 누르고 캐시 된 페이지를 볼 수 있습니다.


ipad Safari의 경우 [this] [1]이 도움이됩니까? [1] : stackoverflow.com/questions/24524248/…
Bakhshi

가장 간단한 방법은 max-age = 10입니다. 페이지가 10 초 동안 캐시되므로 완벽하지 않습니다. 그러나 가장 작은 "헤더 스파게티"솔루션입니다. 또한 리버스 프록시를 사용하는 동적 웹 사이트에서 성능이 크게 향상되는 경우가 있습니다. (느린 PHP 스크립트는 10 초마다 한 번씩 호출 된 다음 리버스 프록시에 의해 캐시됩니다. 10 초에 한 번은 방문자 당 한 번보다 낫습니다)
Hello World


3
좋은 질문 감사합니다. 호기심을 위해 수신자가 "보안상의 이유로" 데이터를 저장하지 않도록하면서 일부 데이터를 전송하게하는 상황은 무엇입니까 ? 당신은 이미 그들을 보냈습니다!
회계사 م

1
@Accountant : 시나리오에서 사용자가 로그 아웃했습니다. 해당 User-Agent의 다음 사용자가 방금 로그 아웃 한 사람임을 보증 할 수있는 사람은 누구입니까?
Fabien Haddadi

답변:


2578

소개

언급 된 모든 클라이언트 (및 프록시)에서 작동하는 올바른 최소 헤더 세트 :

Cache-Control: no-cache, no-store, must-revalidate
Pragma: no-cache
Expires: 0

Cache-Control클라이언트와 프록시 (그리고 암시 적으로 옆에 일부 클라이언트에 의해 요구에 대한 HTTP 1.1 사양 당이다 Expires). 이는 Pragma선사 시대 클라이언트에 대한 HTTP 1.0 사양에 따릅니다. 이 Expires는 HTTP 1.0 클라이언트와 프록시 1.1 사양에 따라입니다. HTTP 1.1에서 Cache-Control우선권Expires 므로 결국 HTTP 1.0 프록시에만 적용됩니다.

와 함께 HTTPS를 통해 페이지를 제공 할 때 IE6 및 손상된 캐싱에 신경 쓰지 않으면을 no-store생략 할 수 Cache-Control: no-cache있습니다.

Cache-Control: no-store, must-revalidate
Pragma: no-cache
Expires: 0

IE6 또는 HTTP 1.0 클라이언트에 신경 쓰지 않는다면 (HTTP 1.1이 1997에 도입되었습니다) 생략 할 수 Pragma있습니다.

Cache-Control: no-store, must-revalidate
Expires: 0

HTTP 1.0 프록시에 관심이 없다면을 생략 할 수 Expires있습니다.

Cache-Control: no-store, must-revalidate

반면에 서버가 유효한 Date헤더를 자동으로 포함하면 이론적으로도 생략 Cache-Control하고 의존 할 Expires수 있습니다.

Date: Wed, 24 Aug 2016 18:32:02 GMT
Expires: 0

그러나 최종 사용자가 운영 체제 날짜를 조작하고 클라이언트 소프트웨어가이를 사용하는 경우 실패 할 수 있습니다.

위에서 언급 한 매개 변수가 지정된 경우 Cache-Control와 같은 다른 매개 변수 max-age는 관련이 없습니다 Cache-Control. Last-Modified여기에 대부분의 다른 답변에 포함 된 헤더는 단지 당신이 경우 흥미로운 실제로 원하는 요청을 캐시 당신이 전혀를 지정할 필요가 없습니다.

어떻게 설정합니까?

PHP 사용하기 :

header("Cache-Control: no-cache, no-store, must-revalidate"); // HTTP 1.1.
header("Pragma: no-cache"); // HTTP 1.0.
header("Expires: 0"); // Proxies.

Java Servlet 또는 Node.js 사용 :

response.setHeader("Cache-Control", "no-cache, no-store, must-revalidate"); // HTTP 1.1.
response.setHeader("Pragma", "no-cache"); // HTTP 1.0.
response.setHeader("Expires", "0"); // Proxies.

ASP.NET-MVC 사용

Response.Cache.SetCacheability(HttpCacheability.NoCache);  // HTTP 1.1.
Response.Cache.AppendCacheExtension("no-store, must-revalidate");
Response.AppendHeader("Pragma", "no-cache"); // HTTP 1.0.
Response.AppendHeader("Expires", "0"); // Proxies.

ASP.NET 웹 API 사용 :

// `response` is an instance of System.Net.Http.HttpResponseMessage
response.Headers.CacheControl = new CacheControlHeaderValue
{
    NoCache = true,
    NoStore = true,
    MustRevalidate = true
};
response.Headers.Pragma.ParseAdd("no-cache");
// We can't use `response.Content.Headers.Expires` directly
// since it allows only `DateTimeOffset?` values.
response.Content?.Headers.TryAddWithoutValidation("Expires", 0.ToString()); 

ASP.NET 사용 :

Response.AppendHeader("Cache-Control", "no-cache, no-store, must-revalidate"); // HTTP 1.1.
Response.AppendHeader("Pragma", "no-cache"); // HTTP 1.0.
Response.AppendHeader("Expires", "0"); // Proxies.

ASP.NET Core v3 사용

// using Microsoft.Net.Http.Headers
Response.Headers[HeaderNames.CacheControl] = "no-cache, no-store, must-revalidate";
Response.Headers[HeaderNames.Expires] = "0";
Response.Headers[HeaderNames.Pragma] = "no-cache";

ASP 사용 :

Response.addHeader "Cache-Control", "no-cache, no-store, must-revalidate" ' HTTP 1.1.
Response.addHeader "Pragma", "no-cache" ' HTTP 1.0.
Response.addHeader "Expires", "0" ' Proxies.

Ruby on Rails 또는 Python / Flask 사용 :

headers["Cache-Control"] = "no-cache, no-store, must-revalidate" # HTTP 1.1.
headers["Pragma"] = "no-cache" # HTTP 1.0.
headers["Expires"] = "0" # Proxies.

파이썬 / 장고 사용하기 :

response["Cache-Control"] = "no-cache, no-store, must-revalidate" # HTTP 1.1.
response["Pragma"] = "no-cache" # HTTP 1.0.
response["Expires"] = "0" # Proxies.

파이썬 / 피라미드 사용하기 :

request.response.headerlist.extend(
    (
        ('Cache-Control', 'no-cache, no-store, must-revalidate'),
        ('Pragma', 'no-cache'),
        ('Expires', '0')
    )
)

Go 사용하기 :

responseWriter.Header().Set("Cache-Control", "no-cache, no-store, must-revalidate") // HTTP 1.1.
responseWriter.Header().Set("Pragma", "no-cache") // HTTP 1.0.
responseWriter.Header().Set("Expires", "0") // Proxies.

아파치 .htaccess파일 사용하기 :

<IfModule mod_headers.c>
    Header set Cache-Control "no-cache, no-store, must-revalidate"
    Header set Pragma "no-cache"
    Header set Expires 0
</IfModule>

HTML4 사용하기 :

<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
<meta http-equiv="Pragma" content="no-cache">
<meta http-equiv="Expires" content="0">

HTML 메타 태그 및 HTTP 응답 헤더

HTML 페이지가 HTTP 연결을 통해 제공되고 헤더가 HTTP 응답 헤더와 HTML 태그 모두에 존재 하는 경우 HTTP 응답 헤더에 <meta http-equiv>지정된 것이 HTML 메타 태그보다 우선 한다는 점을 알아야 합니다. HTML 메타 태그는 file://URL을 통해 로컬 디스크 파일 시스템에서 페이지를 볼 때만 사용됩니다 . W3 HTML 사양 5.2.2 장 참조 . 웹 서버가 일부 기본값을 포함 할 수 있으므로 프로그래밍 방식으로 지정하지 않을 때는이 점을주의하십시오.

일반적으로, HTML 메타 태그를 지정 하지 않는 것이 좋습니다. 초보자의 혼동을 피하고 하드 HTTP 응답 헤더에 의존하십시오. 또한 특히 이러한 <meta http-equiv>태그는 HTML5에서 유효하지 않습니다 . 만 http-equiv에 나열된 값 HTML5 규격은 허용됩니다.

실제 HTTP 응답 헤더 확인

둘 중 하나를 확인하기 위해 웹 브라우저 개발자 도구 세트의 HTTP 트래픽 모니터에서 보거나 디버깅 할 수 있습니다. Chrome / Firefox23 + / IE9 +에서 F12를 누른 다음 "네트워크"또는 "넷"탭 패널을 연 다음 관심있는 HTTP 요청을 클릭하여 HTTP 요청 및 응답에 대한 모든 세부 정보를 확인할 수 있습니다. 아래 스크린 샷은 크롬에서이다 :

stackoverflow.com에 HTTP 응답 헤더를 표시하는 Chrome 개발자 툴셋 HTTP 트래픽 모니터

파일 다운로드시 해당 헤더를 설정하고 싶습니다.

우선,이 질문과 답변은 "파일 다운로드"(PDF, zip, Excel 등)가 아니라 "웹 페이지"(HTML 페이지)를 대상으로합니다. URI 경로 또는 쿼리 문자열 어딘가에 캐시 된 파일 형식 식별자를 사용하여 변경된 파일을 강제로 다시 다운로드하는 것이 좋습니다. 어쨌든 파일 다운로드에 캐시 없음 헤더를 적용하는 경우 HTTP 대신 HTTPS를 통해 파일 다운로드를 제공 할 때 IE7 / 8 버그에주의하십시오. 자세한 내용은 IE가 foo.jsf를 다운로드 할 수 없음을 참조하십시오 . IE는이 인터넷 사이트를 열 수 없습니다. 요청한 사이트를 사용할 수 없거나 찾을 수 없습니다 .


16
완료되지 않은 것 같습니다. IE 8 에서이 솔루션을 사용해 보았고 뒤로 버튼을 누르면 브라우저가 캐시 된 버전을로드한다는 것을 알았습니다.
Mike Ottum이

16
테스트 방법이 잘못되었을 수 있습니다. 페이지가 이미 캐시에 있었습니까? 헤더가 잘못되었거나 오버라이드되었을 수 있습니까? 어쩌면 당신은 잘못된 요청을보고 있었습니까? 기타
BalusC

8
실제로, 나는이 접근법이 불완전하고 IE8에 문제가 있거나 적어도 일부 상황에서 문제가 있음을 확인합니다. 특히, IE8을 사용하여 SSL을 통해 리소스를 가져 오는 경우 IE8은 리소스를 두 번째로 가져 오거나 (사용 된 헤더에 따라 첫 번째 시도 후) 가져 오기를 거부합니다. 예를 들어 EricLaw의 블로그를 참조하십시오 .
haylem

21
이것이 본질적으로 Bank of America가하는 일이라고 덧붙이고 싶습니다. 응답 헤더를보고이를 aspx로 변환하면 다음과 같은 작업을 수행합니다. Response.AppendHeader ( "Cache-Control", "no-cache, no-store, must-revalidate"); Response.AppendHeader ( "만료", "목, 1994 년 12 월 1 일 16:00:00 GMT"); 나는 그것이 그들에게 충분하다면 나에게 충분하다고 생각합니다.
John

8
@John : 헤더 만료는 HTTP 1.0 사양 의 예제 값입니다 . 작동하지만 정확히 타임 스탬프를 취하는 것은 다소 어리 석습니다.
BalusC

244

(이봐 요, 여러분 : 찾을 수있는 모든 헤더를 마음대로 복사하여 붙여 넣지 마십시오)

우선, 뒤로 버튼 기록은 캐시아닙니다 .

신선도 모델 (4.2 절)이 히스토리 메커니즘에 반드시 적용되는 것은 아닙니다. 즉, 히스토리 메커니즘은 만료 된 경우에도 이전 표시를 표시 할 수 있습니다.

이전 HTTP 사양에서는 단어가 더욱 강력 해져서 브라우저가 뒤로 버튼 기록에 대한 캐시 지시문을 무시하도록 명시 적으로 지시했습니다.

뒤로는 사용자 로그인 한 시간으로 되돌아갑니다 . 이전에 열린 URL로 이동하지 않습니다.

그러나 실제로 캐시는 매우 특정한 상황에서 뒤로 단추에 영향을 줄 수 있습니다.

  • 페이지 HTTPS를 통해 전달 되어야합니다 . 그렇지 않으면이 캐시 버스 팅을 신뢰할 수 없습니다. 또한 HTTPS를 사용하지 않는 경우 페이지는 여러 가지 방법으로 로그인 도용에 취약합니다.
  • 보내야합니다 Cache-Control: no-store, must-revalidate(일부 브라우저는 관찰 no-store하고 일부는 관찰 must-revalidate)

다음 중 어느 것도 필요하지 않습니다 .

  • <meta>캐시 헤더를 사용하면 전혀 작동하지 않습니다. 전혀 쓸모가 없습니다.
  • post-check/ pre-check캐치 가능한 리소스 에만 적용되는 IE 전용 지침입니다 .
  • 동일한 헤더를 두 번 또는 12 개로 보냅니다. 일부 PHP 스 니펫은 실제로 이전 헤더를 대체하므로 마지막 헤더 만 전송됩니다.

원하는 경우 다음을 추가 할 수 있습니다.

  • no-cache또는 max-age=0을 사용하면 리소스 (URL)를 "stale"로 만들고 최신 버전이있는 경우 브라우저에서 서버를 확인해야합니다 ( no-store이미 더 강력 함을 의미 함).
  • ExpiresHTTP / 1.0 클라이언트의 날짜가 과거와 같음 ( 요즘에는 실제 HTTP / 1.0 전용 클라이언트가 완전히 존재 하지는 않지만 ).

보너스 : 새로운 HTTP 캐싱 RFC .


1
로딩 시간과 관련하여 웹 사이트 성능에 부작용이 있습니까? no-store, no-cache, must-revalidate가 성능에 어떤 영향을 미칩니 까?
Raman Ghai

@RamanGhai 캐시를 비활성화하면 일반적으로 성능이 저하됩니다 (캐싱 비활성화에 대해 언급 한 세 가지 옵션 모두). CDN 및 ISP 프록시 (예 : 모바일 운영자가 일반적으로 사용하는)를 비효율적으로 만들 수 있습니다. 프록시 문제를 제외하고는 새로운 사용자에 의한 첫 번째로드에 해를 끼치 지 않지만 후속 탐색은 훨씬 느려질 수 있습니다.
Kornel

@porneL 당신은 우리가 보내야한다고 말합니다 Cache-Control: must-revalidate. 왜 보내지 Cache-Control: no-cache이후 no-cache이미 암시 must-revalidate? w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.9.1
Pacerier

3
의 관계 @Pacerier no-cache와 함께 must-revalidate캐시 사실이지만, 다시 역사는 캐시하지 않습니다. 히스토리 동작을 제어하기 위해 명시적인 브라우저must-revalidate .
Kornel

@porneL, 흠 원하는 행동이라고 말하는 지원 RFC가 있습니까?
Pacerier

103

@Kornel이 언급했듯이 원하는 것은 캐시를 비활성화하는 것이 아니라 기록 버퍼를 비활성화하는 것입니다. 다른 브라우저에는 히스토리 버퍼를 비활성화하는 미묘한 방법이 있습니다.

Chrome (v28.0.1500.95m)에서는으로 만이 작업을 수행 할 수 있습니다 Cache-Control: no-store.

FireFox (v23.0.1)에서는 다음 중 하나가 작동합니다.

  1. Cache-Control: no-store

  2. Cache-Control: no-cache (https 전용)

  3. Pragma: no-cache (https 전용)

  4. Vary: * (https 전용)

Opera (v12.15)에서는 Cache-Control: must-revalidate(https) 만 가능합니다.

Safari (v5.1.7, 7534.57.2)에서는 다음 중 하나가 작동합니다.

  1. Cache-Control: no-store
    <body onunload=""> html로

  2. Cache-Control: no-store (https 전용)

IE8 (v8.0.6001.18702IC)에서는 다음 중 하나가 작동합니다.

  1. Cache-Control: must-revalidate, max-age=0

  2. Cache-Control: no-cache

  3. Cache-Control: no-store

  4. Cache-Control: must-revalidate
    Expires: 0

  5. Cache-Control: must-revalidate
    Expires: Sat, 12 Oct 1991 05:00:00 GMT

  6. Pragma: no-cache (https 전용)

  7. Vary: * (https 전용)

위의 내용을 결합하면 Chrome 28, FireFox 23, IE8, Safari 5.1.7 및 Opera 12.15에서 작동하는이 솔루션을 제공합니다. Cache-Control: no-store, must-revalidate (https only)

Opera는 일반 http 페이지에 대한 히스토리 버퍼를 비활성화하지 않으므로 https가 필요합니다. 실제로 https를 얻을 수없고 Opera를 무시할 준비가 되었다면 최선의 방법은 다음과 같습니다.

Cache-Control: no-store
<body onunload="">

아래는 내 테스트의 원시 로그를 보여줍니다.

HTTP :

  1. Cache-Control: private, no-cache, no-store, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: 0
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Opera 12.15
    성공 : Chrome 28, FireFox 23, IE8, Safari 5.1.7

  2. Cache-Control: private, no-cache, no-store, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Opera 12.15
    성공 : Chrome 28, FireFox 23, IE8, Safari 5.1.7

  3. Cache-Control: private, no-cache, no-store, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: 0
    Pragma: no-cache
    Vary: *
    실패 : Safari 5.1.7, Opera 12.15
    성공 : Chrome 28, FireFox 23, IE8

  4. Cache-Control: private, no-cache, no-store, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    Pragma: no-cache
    Vary: *
    실패 : Safari 5.1.7, Opera 12.15
    성공 : Chrome 28, FireFox 23, IE8

  5. Cache-Control: private, no-cache, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: 0
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Chrome 28, FireFox 23, Safari 5.1.7, Opera 12.15
    성공 : IE8

  6. Cache-Control: private, no-cache, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Chrome 28, FireFox 23, Safari 5.1.7, Opera 12.15
    성공 : IE8

  7. Cache-Control: private, no-cache, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: 0
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Chrome 28, FireFox 23, Safari 5.1.7, Opera 12.15
    성공 : IE8

  8. Cache-Control: private, no-cache, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Chrome 28, FireFox 23, Safari 5.1.7, Opera 12.15
    성공 : IE8

  9. Cache-Control: no-store
    실패 : Safari 5.1.7, Opera 12.15
    성공 : Chrome 28, FireFox 23, IE8

  10. Cache-Control: no-store
    <body onunload="">
    실패 : Opera 12.15
    성공 : Chrome 28, FireFox 23, IE8, Safari 5.1.7

  11. Cache-Control: no-cache
    실패 : Chrome 28, FireFox 23, Safari 5.1.7, Opera 12.15
    성공 : IE8

  12. Vary: *
    실패 : Chrome 28, FireFox 23, IE8, Safari 5.1.7, Opera 12.15
    성공 : 없음

  13. Pragma: no-cache
    실패 : Chrome 28, FireFox 23, IE8, Safari 5.1.7, Opera 12.15
    성공 : 없음

  14. Cache-Control: private, no-cache, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Chrome 28, FireFox 23, Safari 5.1.7, Opera 12.15
    성공 : IE8

  15. Cache-Control: private, no-cache, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: 0
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Chrome 28, FireFox 23, Safari 5.1.7, Opera 12.15
    성공 : IE8

  16. Cache-Control: must-revalidate, max-age=0
    실패 : Chrome 28, FireFox 23, Safari 5.1.7, Opera 12.15
    성공 : IE8

  17. Cache-Control: must-revalidate
    Expires: 0
    실패 : Chrome 28, FireFox 23, Safari 5.1.7, Opera 12.15
    성공 : IE8

  18. Cache-Control: must-revalidate
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    실패 : Chrome 28, FireFox 23, Safari 5.1.7, Opera 12.15
    성공 : IE8

  19. Cache-Control: private, must-revalidate, proxy-revalidate, s-maxage=0
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Chrome 28, FireFox 23, IE8, Safari 5.1.7, Opera 12.15
    성공 : 없음

HTTPS :

  1. Cache-Control: private, max-age=0, proxy-revalidate, s-maxage=0
    Expires: 0
    <body onunload="">
    실패 : Chrome 28, FireFox 23, IE8, Safari 5.1.7, Opera 12.15
    성공 : 없음

  2. Cache-Control: private, max-age=0, proxy-revalidate, s-maxage=0
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    <body onunload="">
    실패 : Chrome 28, FireFox 23, IE8, Safari 5.1.7, Opera 12.15
    성공 : 없음

  3. Vary: *
    실패 : Chrome 28, Safari 5.1.7, Opera 12.15
    성공 : FireFox 23, IE8

  4. Pragma: no-cache
    실패 : Chrome 28, Safari 5.1.7, Opera 12.15
    성공 : FireFox 23, IE8

  5. Cache-Control: no-cache
    실패 : Chrome 28, Safari 5.1.7, Opera 12.15
    성공 : FireFox 23, IE8

  6. Cache-Control: private, no-cache, max-age=0, proxy-revalidate, s-maxage=0
    실패 : Chrome 28, Safari 5.1.7, Opera 12.15
    성공 : FireFox 23, IE8

  7. Cache-Control: private, no-cache, max-age=0, proxy-revalidate, s-maxage=0
    Expires: 0
    Pragma: no-cache
    Vary: *
    실패 : Chrome 28, Safari 5.1.7, Opera 12.15
    성공 : FireFox 23, IE8

  8. Cache-Control: private, no-cache, max-age=0, proxy-revalidate, s-maxage=0
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    Pragma: no-cache
    Vary: *
    실패 : Chrome 28, Safari 5.1.7, Opera 12.15
    성공 : FireFox 23, IE8

  9. Cache-Control: must-revalidate
    실패 : Chrome 28, FireFox 23, IE8, Safari 5.1.7
    성공 : Opera 12.15

  10. Cache-Control: private, must-revalidate, proxy-revalidate, s-maxage=0
    <body onunload="">
    실패 : Chrome 28, FireFox 23, IE8, Safari 5.1.7
    성공 : Opera 12.15

  11. Cache-Control: must-revalidate, max-age=0
    실패 : Chrome 28, FireFox 23, Safari 5.1.7
    성공 : IE8, Opera 12.15

  12. Cache-Control: private, no-cache, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Chrome 28, Safari 5.1.7
    성공 : FireFox 23, IE8, Opera 12.15

  13. Cache-Control: private, no-cache, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: 0
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Chrome 28, Safari 5.1.7
    성공 : FireFox 23, IE8, Opera 12.15

  14. Cache-Control: no-store
    실패 : Opera 12.15
    성공 : Chrome 28, FireFox 23, IE8, Safari 5.1.7

  15. Cache-Control: private, no-cache, no-store, max-age=0, proxy-revalidate, s-maxage=0
    Expires: 0
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Opera 12.15
    성공 : Chrome 28, FireFox 23, IE8, Safari 5.1.7

  16. Cache-Control: private, no-cache, no-store, max-age=0, proxy-revalidate, s-maxage=0
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    Pragma: no-cache
    Vary: *
    <body onunload="">
    실패 : Opera 12.15
    성공 : Chrome 28, FireFox 23, IE8, Safari 5.1.7

  17. Cache-Control: private, no-cache
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    Pragma: no-cache
    Vary: *
    실패 : Chrome 28, Safari 5.1.7, Opera 12.15
    성공 : FireFox 23, IE8

  18. Cache-Control: must-revalidate
    Expires: 0
    실패 : Chrome 28, FireFox 23, Safari 5.1.7,
    성공 : IE8, Opera 12.15

  19. Cache-Control: must-revalidate
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    실패 : Chrome 28, FireFox 23, Safari 5.1.7,
    성공 : IE8, Opera 12.15

  20. Cache-Control: private, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: 0
    <body onunload="">
    실패 : Chrome 28, FireFox 23, Safari 5.1.7,
    성공 : IE8, Opera 12.15

  21. Cache-Control: private, must-revalidate, max-age=0, proxy-revalidate, s-maxage=0
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    <body onunload="">
    실패 : Chrome 28, FireFox 23, Safari 5.1.7,
    성공 : IE8, Opera 12.15

  22. Cache-Control: private, must-revalidate
    Expires: Sat, 12 Oct 1991 05:00:00 GMT
    Pragma: no-cache
    Vary: *
    실패 : Chrome 28, Safari 5.1.7
    성공 : FireFox 23, IE8, Opera 12.15

  23. Cache-Control: no-store, must-revalidate
    실패 :
    성공 하지 못함 : Chrome 28, FireFox 23, IE8, Safari 5.1.7, Opera 12.15


3
나는 이것이 2 년 전에 게시되었다는 것을 알고 있지만 재미있는 읽을 거리였습니다. 이 문제는 몇 달 동안 나를 미치게 만들었습니다. 몸은 실제로 캐시 제어를 처리하는 방법을 알고있는 것 같습니다. 나는 몇 사람을 사용하는 것을 <body onunload="">보았지만 실제 문제를 해결하는 방법과 비슷합니다. .htaccess를 사용하고 헤더를 그런 식으로 수정하려고 시도했지만 HTTPS를 사용하면 그렇게 작동합니까? 문제가 가장 많이 제기되는 곳은 주로 사파리입니다.
Jordan

4
@Jordan, 위의 로그 당 HTTPS가있는 경우 추가 Cache-Control: no-store하면 트릭이 수행됩니다. <body onunload="">HTTPS가없는 경우에만 필요합니다.
Pacerier

37

web.config 경로가 유용하다는 것을 알았습니다 (답을 추가하려고했지만 여기에 게시되지 않은 것 같습니다)

<configuration>
<system.webServer>
    <httpProtocol>
        <customHeaders>
            <add name="Cache-Control" value="no-cache, no-store, must-revalidate" />
            <!-- HTTP 1.1. -->
            <add name="Pragma" value="no-cache" />
            <!-- HTTP 1.0. -->
            <add name="Expires" value="0" />
            <!-- Proxies. -->
        </customHeaders>
    </httpProtocol>
</system.webServer>

그리고 동일한 작업을 수행하는 express / node.js 방법이 있습니다.

app.use(function(req, res, next) {
    res.setHeader('Cache-Control', 'no-cache, no-store, must-revalidate');
    res.setHeader('Pragma', 'no-cache');
    res.setHeader('Expires', '0');
    next();
});

web.config의 경우 동적으로 / requirejs를 사용하여로드되는 스크립트에 대해서만 사용자 정의 헤더를 적용하도록 약간 수정합니다. 스크립트가 클라이언트 폴더에 있다고 가정하면 <location path = "client"> ..... </ location>
Ibrahim ben Salah

누가 궁금해하는 사람 web.conf: ASP.NET웹 응용 프로그램 의 기본 설정 및 구성 파일입니다 . 루트 디렉토리에있는 XML 문서입니다. ( 위키 ).
다른

27

이 페이지의 모든 답변에 여전히 문제가 있음을 발견했습니다. 특히, 나는 뒤로 버튼을 눌렀을 때 IE8이 캐시 된 버전의 페이지를 사용하는 것을 멈추지 않을 것입니다.

많은 연구와 테스트 끝에 필자가 실제로 필요한 유일한 헤더는 다음과 같습니다.

캐시 제어 : 저장소 없음
Vary : *

Vary 헤더에 대한 설명은 http://www.w3.org/Protocols/rfc2616/rfc2616-sec13.html#sec13.6을 확인 하십시오.

IE6-8, FF1.5-3.5, Chrome 2-3, Safari 4 및 Opera 9-10에서 이러한 헤더로 인해 페이지 링크를 클릭하거나 URL을 넣을 때 서버에서 페이지를 요청했습니다 주소 표시 줄에 직접. 1 월 10 일 현재 사용중인 모든 브라우저의 약 99 %가 여기 에 해당합니다.

IE6 및 Opera 9-10에서 뒤로 버튼을 누르면 캐시 된 버전이 계속로드됩니다. 내가 테스트 한 다른 모든 브라우저에서 서버에서 새로운 버전을 가져 왔습니다. 지금까지 뒤로 버튼을 눌렀을 때 해당 브라우저가 캐시 된 버전의 페이지를 반환하지 않는 헤더 세트를 찾지 못했습니다.

업데이트 : 이 답변을 작성한 후 웹 서버가 자신을 HTTP 1.0 서버로 식별하고 있음을 깨달았습니다. 내가 나열한 헤더는 HTTP 1.0 서버의 응답이 브라우저에 의해 캐시되지 않도록하기위한 올바른 헤더입니다. HTTP 1.1 서버의 경우 BalusC 's answer를 참조하십시오 .


4
이것은 IE8의 뒤로 버튼에서 작동합니다! 다른 제안에서 모든 것을 시도한 후에 "Vary : *"헤더를 추가하는 것은 사용자가 뒤로 버튼을 누를 때 IE8이 페이지를 다시로드하도록 할 수있는 유일한 방법입니다. 그리고 이것은 않습니다 1.1 서버 / HTTP 작업을.
coredumperror

onPageShow 이벤트가 "persisted"속성 (Safari에 필요)으로 트리거 될 때 BarlusC에서 제안한 헤더와 window.location.reload ()를 호출하는 JS 스 니펫과 결합하면 테스트 한 모든 브라우저에서 사용자가 뒤로 버튼을 사용할 때 서버.
coredumperror

1
@CoreDumpError, JavaScript가 활성화되어 있다고 가정해서는 안됩니다.
Pacerier

@Pacerier 2010 년에 답을 썼을 때, 이것은 서버가 자체적으로 HTTP 1.0 서버로 식별되는 Safari와 Opera의 최신 버전에서 작동했습니다. 불행히도 더 이상 쉽게 테스트 할 수있는 방법이 없으므로 이러한 브라우저의 최신 버전에 대해 확실한 것을 말할 수는 없습니다.
Chris Vasselli

테스트 한 브라우저 버전은 무엇입니까?
Pacerier

21

약간의 연구 끝에 우리는 대부분의 브라우저를 다루는 것으로 보이는 다음 헤더 목록을 만들었습니다.

ASP.NET에서는 다음 스 니펫을 사용하여이를 추가했습니다.

Response.ClearHeaders(); 
Response.AppendHeader("Cache-Control", "no-cache"); //HTTP 1.1
Response.AppendHeader("Cache-Control", "private"); // HTTP 1.1
Response.AppendHeader("Cache-Control", "no-store"); // HTTP 1.1
Response.AppendHeader("Cache-Control", "must-revalidate"); // HTTP 1.1
Response.AppendHeader("Cache-Control", "max-stale=0"); // HTTP 1.1 
Response.AppendHeader("Cache-Control", "post-check=0"); // HTTP 1.1 
Response.AppendHeader("Cache-Control", "pre-check=0"); // HTTP 1.1 
Response.AppendHeader("Pragma", "no-cache"); // HTTP 1.0 
Response.AppendHeader("Expires", "Mon, 26 Jul 1997 05:00:00 GMT"); // HTTP 1.0 

http://forums.asp.net/t/1013531.aspx 에서 발견


36
@bart : 더 번거롭지 만 1997 년 7 월 26
일은

5
Cache-Control: no-cacheCache-Control: private충돌 - 당신이 모두 함께 얻을해서는 안 : 전자는 후자하지 캐시에 프록시를 알 수 있지만 브라우저가 자신의 개인 사본을 보유 할 수 있습니다, 전혀 캐시에 브라우저와 프록시를하지 알려줍니다. 브라우저가 어떤 설정을 따를 지 잘 모르겠지만 브라우저와 버전간에 일관되지는 않습니다.
Keith

사전 확인 및 사후 확인을 사용하지 마십시오. blogs.msdn.com/b/ieinternals/archive/2009/07/20/…
EricLaw

이것은 나를 위해 작동하지 않았습니다-asp.net 4.5를 사용하면 코드가 실행되지만 필요한 결과를 얻지 못합니다. 나는 이것을 따라야했다 : stackoverflow.com/questions/22443932/…
Andy

8

응답에 pragma 헤더를 사용하는 것은 아내 이야기입니다. RFC2616은 요청 헤더로만 정의합니다.

http://www.mnot.net/cache_docs/#PRAGMA


4
이것은 스펙을 넘어서야하는 좋은 예입니다. 사양이 항상 명확하다면 StackOverflow와 같은 사이트에는 별다른 의미가 없습니다. 에서 마이크로 소프트 노 캐시 헤더 : HTTP 1.0 서버와의 호환성을 위해 Internet Explorer는 HTTP Pragma의 특별한 사용을 지원합니다. 클라이언트가 보안 연결 (https : //)을 통해 서버와 통신하고 서버가 응답과 함께 Pragma : no-cache 헤더를 반환하면 Internet Explorer는 응답을 캐시하지 않습니다.
michaelok

@michaelok : 당신의 참조는 유효하지만 더 큰 요점을 놓치고 있습니다. 적절한 Cache-Control / Expires를 설정하면 pragma가 필요 없습니다.
EricLaw

8

면책 조항 : @BalusC의 답변을 읽는 것이 좋습니다. 다음 캐싱 튜토리얼을 읽은 후 : http://www.mnot.net/cache_docs/ (나도 읽어 보는 것이 좋습니다), 나는 그것이 정확하다고 생각합니다. 그러나 역사적 이유로 (내가 직접 테스트했기 때문에) 아래에 원래 답변을 포함시킵니다.


나는 PHP에 대해 '허용 된'답변을 시도했지만 나에게는 효과가 없었습니다. 그런 다음 약간의 연구를 수행하고 약간의 변형을 발견하고 테스트하여 작동했습니다. 여기있어:

header('Cache-Control: no-store, private, no-cache, must-revalidate');     // HTTP/1.1
header('Cache-Control: pre-check=0, post-check=0, max-age=0, max-stale = 0', false);  // HTTP/1.1
header('Pragma: public');
header('Expires: Sat, 26 Jul 1997 05:00:00 GMT');                  // Date in the past  
header('Expires: 0', false); 
header('Last-Modified: '.gmdate('D, d M Y H:i:s') . ' GMT');
header ('Pragma: no-cache');

작동합니다. 문제는 헤더의 동일한 부분을 두 번 설정할 때 false헤더 함수에 대한 두 번째 인수로 전송되지 않으면 헤더 함수가 단순히 이전 header()호출을 덮어 쓰는 것 입니다. 설정 때, Cache-Control하나 하나에 모든 인수를 넣어하지 않는 경우, 예를 들어, header()함수 호출, 그는이 같은 작업을 수행해야합니다 :

header('Cache-Control: this');
header('Cache-Control: and, this', false);

보다 자세한 문서는 여기를 참조 하십시오 .


14
이것은 신화로 가득합니다. 사전 점검 및 사후 점검은 IE 전용이며 캐시 된 응답에만 관련되며 0 값은 작동하지 않습니다. max-stale은 서버 응답 헤더가 아닌 프록시 요청 헤더입니다. 만료는 단일 값만 허용합니다. 둘 이상의 헤더가 무시됩니다.
Kornel

1
@porneL, 이러한 신화를 올바르게 다루는 경쟁 답변을 제출 하시겠습니까?
Oddthinking

@Oddthinking, stackoverflow.com/questions/49547/… 는 경쟁 답변입니다.
Mike Ottum이

@Pacerier 네, 면책 조항에서 말하는 것처럼 BalusC의 답변을 사용하십시오.
Steven Oxley

8

ASP.NET Core의 경우 간단한 미들웨어 클래스를 작성하십시오.

public class NoCacheMiddleware
{
    private readonly RequestDelegate m_next;

    public NoCacheMiddleware( RequestDelegate next )
    {
        m_next = next;
    }

    public async Task Invoke( HttpContext httpContext )
    {
        httpContext.Response.OnStarting( ( state ) =>
        {
            // ref: http://stackoverflow.com/questions/49547/making-sure-a-web-page-is-not-cached-across-all-browsers
            httpContext.Response.Headers.Append( "Cache-Control", "no-cache, no-store, must-revalidate" );
            httpContext.Response.Headers.Append( "Pragma", "no-cache" );
            httpContext.Response.Headers.Append( "Expires", "0" );
            return Task.FromResult( 0 );
        }, null );

        await m_next.Invoke( httpContext );
    }
}

그런 다음에 등록하십시오 Startup.cs

app.UseMiddleware<NoCacheMiddleware>();

나중에 어딘가에 이것을 추가하십시오

app.UseStaticFiles();

문자열 리터럴 "Cache-Controls", "Pragma"및 "Expires"대신 Microsoft.Net.Http.Headers.HeaderNames의 상수를 사용하는 것이 좋습니다.
Victor Sharovatov

7

이러한 지침은 보안 위험을 완화하지 않습니다. 이들은 실제로 UA가 정보를 유지하지 못하도록 휘발성 정보를 새로 고치도록 의도되어 있습니다. 이 비슷한 질문을 참조하십시오 . 최소한 라우터, 프록시 등이 캐싱 지시문도 무시하지 않을 것이라는 보장은 없습니다.

더 긍정적으로 말하면 컴퓨터에 대한 물리적 액세스, 소프트웨어 설치 등에 관한 정책은 보안 측면에서 대부분의 회사보다 훨씬 앞서 있습니다. 이 정보의 소비자가 일반인 인 경우 정보가 컴퓨터에 닿으면 해당 컴퓨터가 본인의 책임이 아니라 자신의 책임 임을 이해하는 데 도움이됩니다 .


7

IE6에 버그가 있습니다

"Cache-Control : no-cache"를 사용하더라도 "Content-Encoding : gzip"이있는 컨텐츠는 항상 캐시됩니다.

http://support.microsoft.com/kb/321722

IE6 사용자의 gzip 압축을 비활성화 할 수 있습니다 ( "MSIE 6"의 사용자 에이전트 확인)


6

HTTP 1.1 용 RFC에 따르면 올바른 방법은 다음에 대한 HTTP 헤더를 추가하는 것입니다.

캐시 제어 : 캐시 없음

이전 브라우저는 HTTP 1.1을 제대로 준수하지 않으면이를 무시할 수 있습니다. 그것들을 위해 당신은 헤더를 시도 할 수 있습니다 :

프라 그마 : 캐시 없음

이것은 HTTP 1.1 브라우저에서도 작동합니다.


1
사양은 재확인없이 응답을 재사용해서는 안된다는 것을 나타냅니다. Cache-Control : no-store는 응답이 캐시에 저장되지 않았 음을 나타내는 공식적인 방법입니다.
AnthonyWJones

6

1995 년에 수정 된 http 헤더를 특정 날짜로 설정하면 일반적으로 트릭을 수행합니다.

예를 들면 다음과 같습니다.

만료 : Wed, 1995 년 11 월 15 일 04:58:08 GMT
최종 수정 : 1995 년 11 월 15 일 (수) 04:58:08 GMT
캐시 제어 : 캐시 없음, 재확인

1
오래 지속되는 Last-Modified 설정은 휴리스틱 재확인으로 인해 캐시 된 응답을 더 오래 사용할 수있게하는 것 외에는 캐싱에 영향을 미치지 않습니다.
EricLaw

6

헤더 함수에 대한 PHP 문서는 오히려 완전한 예 (타사에서 기여)이 있습니다

    header('Pragma: public');
    header("Expires: Sat, 26 Jul 1997 05:00:00 GMT");                  // Date in the past   
    header('Last-Modified: '.gmdate('D, d M Y H:i:s') . ' GMT');
    header('Cache-Control: no-store, no-cache, must-revalidate');     // HTTP/1.1
    header('Cache-Control: pre-check=0, post-check=0, max-age=0', false);    // HTTP/1.1
    header ("Pragma: no-cache");
    header("Expires: 0", false);

11
이것은 분명히 잘못입니다. Expires, Cache-control 및 Pragma에 대한 header ()에 대한 두 번째 호출은 이전에 설정된 값을 완전히 덮어 씁니다.
Kornel

1
@porneL : 이전 값을 무시하지 말라고 2 번째 매개 변수로 false를 전달하므로 이전에 설정 한 값을 덮어 쓰지 않습니다.
Julien Palard

1
@JulienPalard 내 의견을 작성한 후 답변이 편집되었습니다. 여전히 의미가 없습니다.
Kornel

9 이전의 IE에서 작업하려면 여러 캐시 제어 헤더를 보내지 마십시오. 사전 확인 또는 사후 확인을 보내지 마십시오. blogs.msdn.com/b/ieinternals/archive/2009/07/20/…
EricLaw

6

SSL을 통한 IE6-IE8 및 MS Office 파일의 cache : no-cache 헤더 및 이와 유사한 값의 다운로드 문제가 발생하는 경우 POST : 요청시 cache : private, no-store 헤더 및 반환 파일을 사용할 수 있습니다. 효과가있다.


6

내 경우에는 크롬으로 문제를 해결합니다.

<form id="form1" runat="server" autocomplete="off">

보안상의 이유로 사용자가 버튼을 다시 클릭하면 이전 양식 데이터의 내용을 지워야합니다.


mozilla 19.x 브라우저 문제도 코드 스 니펫으로 해결되었습니다. autocomplete = "off". 감사합니다.
Satya

5

II7에서 전송되지 않는 캐시 헤더에 대한 많은 질문으로 인해 IIS7 +에서 허용되는 답변이 작동하지 않는 것 같습니다.

등등

허용되는 답변은 어떤 헤더를 설정해야하는지에 대한 것이지만, 어떻게 설정해야하는지에는 맞지 않습니다. 이 방법은 IIS7에서 작동합니다.

Response.Cache.SetCacheability(HttpCacheability.NoCache);
Response.Cache.AppendCacheExtension("no-store, must-revalidate");
Response.AppendHeader("Pragma", "no-cache");
Response.AppendHeader("Expires", "-1");

첫 번째 줄은 Cache-control로 설정 되고 no-cache두 번째 줄은 다른 속성을 추가합니다no-store, must-revalidate


이것은 나를 위해 작동합니다 :Response.Cache.SetAllowResponseInBrowserHistory(false); Response.Cache.SetCacheability(HttpCacheability.NoCache); Response.Cache.SetNoStore(); Response.Cache.SetRevalidation(HttpCacheRevalidation.AllCaches);
Vilx-

4

Pragma : no-cache를 설정하여 모든 브라우저에서 가장 일관되고 최상의 결과를 얻었습니다.


4

BalusC가 제공 한 답변의 헤더는 브라우저의 뒤로 버튼을 사용할 때 Safari 5 (및 이전 버전)도 브라우저 캐시의 내용을 표시하지 못하게하지 않습니다. 이를 방지하는 방법은 빈 onunload 이벤트 핸들러 속성을 body 태그에 추가하는 것입니다.

<body onunload=""> 

이 해킹은 Safari에서 백 포워드 캐시를 손상시킵니다 . 뒤로 버튼을 클릭 할 때 크로스 브라우저 onload 이벤트가 있습니까?


쿨, 나는 그것을 테스트했고 이것은 실제로 Safari (5.1.7)에서는 작동하지만 Opera에서는 작동하지 않습니다.
Pacerier

4

또한 캐싱을 활성화 ExpiresDefault하기 위해 .htaccess파일을 사용하는 경우 파일 을 다시 설정해야합니다 .

ExpiresDefault "access plus 0 seconds"

그런 다음 ExpiresByType캐시하려는 파일의 특정 값을 설정 하는 데 사용할 수 있습니다 .

ExpiresByType image/x-icon "access plus 3 month"

PHP 등의 동적 파일이 브라우저에 캐시되어 있고 그 이유를 알 수없는 경우에도 유용 할 수 있습니다. 확인하십시오 ExpiresDefault.


3

헤더 외에도 https 를 통한 페이지 게재를 고려 하십시오 . 많은 브라우저는 기본적으로 https를 캐시하지 않습니다.


3
//In .net MVC
[OutputCache(NoStore = true, Duration = 0, VaryByParam = "*")]
public ActionResult FareListInfo(long id)
{
}

// In .net webform
<%@ OutputCache NoStore="true" Duration="0" VaryByParam="*" %>

2

BalusC- > 답변 을 완료하려면 perl을 사용하는 경우 CGI를 사용하여 HTTP 헤더를 추가 할 수 있습니다.

펄 사용하기 :

Use CGI;    
sub set_new_query() {
        binmode STDOUT, ":utf8";
        die if defined $query;
        $query = CGI->new();
        print $query->header(
                        -expires       => 'Sat, 26 Jul 1997 05:00:00 GMT',
                        -Pragma        => 'no-cache',
                        -Cache_Control => join(', ', qw(
                                            private
                                            no-cache
                                            no-store
                                            must-revalidate
                                            max-age=0
                                            pre-check=0
                                            post-check=0 
                                           ))
        );
    }

아파치 httpd.conf 사용

<FilesMatch "\.(html|htm|js|css|pl)$">
FileETag None
<ifModule mod_headers.c>
Header unset ETag
Header set Cache-Control "max-age=0, no-cache, no-store, must-revalidate"
Header set Pragma "no-cache"
Header set Expires "Wed, 11 Jan 1984 05:00:00 GMT"
</ifModule>

참고 : html META를 사용하려고 할 때 브라우저는 무시하고 페이지를 캐시했습니다.


0

누군가가 동적 콘텐츠 만 캐시하지 못하게하려면 추가 헤더를 프로그래밍 방식으로 추가해야한다고 지적하고 싶습니다.

캐시없는 헤더를 추가하기 위해 프로젝트의 구성 파일을 편집했지만 정적 콘텐츠 캐싱도 비활성화되었으므로 일반적으로 바람직하지 않습니다. 코드에서 응답 헤더를 수정하면 이미지 및 스타일 파일이 캐시됩니다.

이것은 명백하지만 여전히 언급 할 가치가 있습니다.

그리고 또 다른주의. HttpResponse 클래스의 ClearHeaders 메소드를 사용하는 데주의하십시오. 무모하게 사용하면 멍이들 수 있습니다. 나에게 준 것처럼.

ActionFilterAttribute 이벤트를 리디렉션 한 후 모든 헤더를 지우면 TempData 저장소의 모든 세션 데이터와 데이터가 손실됩니다. 리디렉션이 수행 될 때 액션에서 리디렉션하거나 헤더를 지우지 않는 것이 더 안전합니다.

두 번째로 ClearHeaders 메서드를 사용하지 않는 것이 좋습니다. 헤더를 개별적으로 제거하는 것이 좋습니다. 그리고 Cache-Control 헤더를 올바르게 설정하려면이 코드를 사용하고 있습니다.

filterContext.HttpContext.Response.Cache.SetCacheability(HttpCacheability.NoCache);
filterContext.HttpContext.Response.Cache.AppendCacheExtension("no-store, must-revalidate");

0

나는 <head><meta>요소에 운이 없었습니다 . HTML 캐시 외부에서 HTTP 캐시 관련 매개 변수를 직접 추가하면 실제로 효과가 있습니다.

web.py web.header호출을 사용하는 Python의 샘플 코드 는 다음과 같습니다. 개인적으로 관련없는 유틸리티 코드를 의도적으로 수정했습니다.

    웹 가져 오기
    수입 시스템
    개인 유틸리티 가져 오기

    myname = "main.py"

    URL = (
        '/', 'main_class'
    )

    메인 = web.application (urls, globals ())

    render = web.template.render ( "templates /", base = "layout", cache = False)

    main_class (객체) 클래스 :
        데프 GET (self) :
            web.header ( "캐시 제어", "캐시 없음, 저장 없음, 재확인")
            web.header ( "프 래그 마", "캐시 없음")
            web.header ( "만료", "0")
            render를 반환합니다.

        데프 POST (자체) :
            msg = "POSTed :"
            양식 = web.input (함수 = 없음)
            web.header ( "캐시 제어", "캐시 없음, 저장 없음, 재확인")
            web.header ( "프 래그 마", "캐시 없음")
            web.header ( "만료", "0")
            return render.index_laid_out (인사말 = msg + form.function)

    __name__ == "__main__"인 경우 :
        nargs = len (sys.argv)
        # 파이썬 프로그램 이름 뒤에 충분한 인수가 있는지 확인하십시오
        만약 nargs! = 2 :
            LOG-AND-DIE ( "% s : 명령 줄 오류, nargs = % s는 2"이어야합니다, myname, nargs)
        # TCP 포트 번호가 숫자인지 확인하십시오
        시험:
            tcp_port = int (sys.argv [1])
        e와 같은 예외를 제외하고 :
            LOG-AND-DIE ( "% s : tcp_port = int (% s) 실패 (정수 아님)", myname, sys.argv [1])
        # 모든 것이 잘됩니다!
        JUST-LOG ( "% s : 포트 % d에서 실행 중", myname, tcp_port)
        web.httpserver.runsimple (main.wsgifunc (), ( "localhost", tcp_port))
        main.run ()


몇 년 동안 사이트에 있었던 답변에서 이미 여러 번 다루어지지 않았습니까?
Martin Tournoij

META 지시문은 Internet Explorer 및 Edge 18 이하 버전에서 작동합니다. 최신 브라우저는이를 지원하지 않습니다. crbug.com/2763
EricLaw

0

캐싱에 대한 사례 연구 링크를 참조하십시오.

http://securityevaluators.com/knowledge/case_studies/caching/

기사에 따르면 요약 Cache-Control: no-store은 Chrome, Firefox 및 IE 에서만 작동합니다. IE는 다른 컨트롤을 허용하지만 Chrome 및 Firefox는 허용하지 않습니다. 이 링크는 개념 증명을 캐싱하고 문서화 한 기록과 함께 잘 읽습니다.


0

내 대답이 간단하고 어리석게 들리는 지 확실하지 않으며 아마도 오래 전에 이미 알려졌지만 누군가가 이전 페이지를보기 위해 브라우저 뒤로 버튼을 사용하지 못하게하는 것이 목표 중 하나이므로 다음을 사용할 수 있습니다.

window.location.replace("https://www.example.com/page-not-to-be-viewed-in-browser-history-back-button.html");

물론 전체 사이트에서 구현할 수는 없지만 적어도 일부 중요 페이지에서는 그렇게 할 수 있습니다. 도움이 되었기를 바랍니다.


-1

IIS에서 전체 앱 가져 오기 대신 개별 파일을 설정하기 위해 위치 블록을 사용할 수 있습니다.

 <location path="index.html">
    <system.webServer>
      <httpProtocol>
        <customHeaders>
          <add name="Cache-Control" value="no-cache" />
        </customHeaders>
      </httpProtocol>
    </system.webServer>
  </location>
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.