Xóa bộ đệm trong JavaScript


179

Làm cách nào để xóa bộ đệm của trình duyệt bằng JavaScript?

Chúng tôi đã triển khai mã JavaScript mới nhất nhưng chúng tôi không thể lấy mã JavaScript mới nhất.

Lưu ý biên tập: Câu hỏi này được nhân đôi ở những nơi sau đây và câu trả lời trong câu hỏi đầu tiên có lẽ là tốt nhất. Câu trả lời được chấp nhận này không còn là giải pháp lý tưởng.

Làm cách nào để buộc trình duyệt tải lại các tệp CSS / JS được lưu trong bộ nhớ cache?

Làm cách nào tôi có thể buộc khách hàng làm mới tệp JavaScript?

Tự động tải lại dữ liệu nguồn / json cục bộ


5
Điều này làm tôi bối rối: "Chúng tôi đã triển khai mã javascript mới nhất nhưng chúng tôi không thể nhận được mã javascript mới nhất"
ví dụ như tôi

14
Tôi đoán ý bạn là, làm thế nào để buộc các trình duyệt máy khách sử dụng phiên bản javascript mới nhất của bạn chứ không phải phiên bản được lưu trong bộ nhớ cache của chúng - trong trường hợp đó bạn cần câu trả lời của Greg. Nếu bạn muốn biết làm thế nào để làm điều đó trong trình duyệt của riêng bạn, đó là câu trả lời của David Johnstone.
Stewol


4
Một cách tiếp cận phổ biến là đính kèm một ?version=xxxtệp được liên kết với JS thông qua bước xây dựng. Mỗi bản dựng mới sẽ yêu cầu một phiên bản mới của tệp JS.
Juan Mendes

1
@JuanMendes Điều này không phải lúc nào cũng hoạt động. Bước tương tự này được đề xuất khi mọi người gặp vấn đề khi cố gắng xem favicon mới nhất. Nó chỉ không được đảm bảo để làm việc.
uSeRnAmEhAhAhAhA 30/03/2016

Câu trả lời:


202

Bạn có thể gọi window.location.reload (đúng) để tải lại trang hiện tại. Nó sẽ bỏ qua mọi mục được lưu trong bộ nhớ cache và truy xuất các bản sao mới của trang, css, hình ảnh, JavaScript, v.v. từ máy chủ. Điều này không xóa toàn bộ bộ đệm, nhưng có tác dụng xóa bộ đệm cho trang bạn đang truy cập.

Tuy nhiên, chiến lược tốt nhất của bạn là phiên bản đường dẫn hoặc tên tệp như được đề cập trong các câu trả lời khác nhau. Ngoài ra, hãy xem Revving Filenames: không sử dụng chuỗi truy vấn vì lý do không sử dụng ?v=nlàm sơ đồ phiên bản của bạn.


6
Ồ cảm ơn nhé! Điều này cũng hoạt động tốt đối với Bộ đệm ứng dụng HTML5 được tải từ tệp cache.manifest. Tôi đã có một bảng kê khai cũ không bị xóa khỏi bộ nhớ, vì vậy một trình duyệt được lưu trong bộ nhớ cache sẽ không hiển thị các tệp mới hơn. Tôi đã gõ cái này trong bảng điều khiển javascript và hoạt động tốt. Cảm ơn!
JayCrossler

2
nhưng điều chỉnh bằng cách thay đổi tên tệp ... bạn sẽ không giữ tất cả các phiên bản trước đó chứ? nếu không, bạn sẽ nhận được rất nhiều lần thử thất bại từ các công cụ tìm kiếm và không đọc các phiên bản cũ hơn (hoặc hình ảnh được đánh dấu / liên kết)
Rodolfo

1
Làm thế nào mà tôi không nghĩ về điều đó, xe tăng bạn
osdamv

1
Đây có giống như người dùng nhấp vào nút refresh không?
GMsoF

2
@Manuel Nó sẽ chỉ vô hiệu hóa việc truy cập trang từ bộ đệm của url chính xác mà bạn đã gọi location.reload (true) trên. Nó không bao giờ xóa trang gốc khỏi bộ đệm vì nó chỉ đơn giản gắn dấu thời gian vào yêu cầu mới và nếu có các cuộc gọi khác được thực hiện không đồng bộ bởi trang này, các yêu cầu đó sẽ KHÔNG bị vô hiệu hóa các hành vi bộ đệm của chúng. Ví dụ. Nếu bạn làm mới một trang có tải lại (đúng) tải một số html và trang đó có tập lệnh thực hiện cuộc gọi ajax thứ hai để có nhiều html hơn để hiển thị trên cùng một trang, yêu cầu thứ hai sẽ không bị tắt bộ đệm.
J. Schei

114

Bạn không thể xóa bộ nhớ cache bằng javascript. Một cách phổ biến là nối số sửa đổi hoặc dấu thời gian được cập nhật lần cuối vào tệp, như sau:

myscript.123.js

hoặc là

myscript.js?updated=1234567890


9
Tuy nhiên, xin lưu ý rằng nhiều proxy sẽ không lưu trữ tệp khi tệp có chuỗi truy vấn. Xem câu trả lời của Kevin Hakanson .
chiborg

4
Làm cách nào để xóa bộ nhớ cache khi toàn bộ HTML đã được lưu vào bộ đệm? Nó sẽ không ảnh hưởng ngay cả khi số phiên bản được thêm vào do HTML được lưu trong bộ nhớ cache. Xin vui lòng trợ giúp
Nandakumar

Nếu tôi không thể xóa một mục bộ đệm, thì tại sao MDN nói rằng tôi có thể? Tôi đang thiếu gì? Tôi đã thử những gì MDN nói nhưng không có may mắn.
Sнаđошƒаӽ

41

Hãy thử thay đổi src của tệp JavaScript? Từ đây:

<script language="JavaScript" src="js/myscript.js"></script>

Về điều này:

<script language="JavaScript" src="js/myscript.js?n=1"></script>

Phương pháp này sẽ buộc trình duyệt của bạn tải một bản sao mới của tệp JS.


N = 1 làm gì?
KyelJmD

nó không làm gì cả ngoại trừ một cái gì đó khác biệt. nó có thể là? 12345 hoặc? Kyle
Oneezy

Vì vậy, tên tập tin cần phải được thay đổi quá? Hay chỉ là đường dẫn src cần được thay đổi?
Fred A

20

Khác với bộ nhớ đệm mỗi giờ hoặc mỗi tuần, bạn có thể lưu trữ theo dữ liệu tệp.

Ví dụ (trong PHP):

<script src="js/my_script.js?v=<?=md5_file('js/my_script.js')?>"></script>

hoặc thậm chí sử dụng thời gian sửa đổi tập tin:

<script src="js/my_script.js?v=<?=filemtime('js/my_script.js')?>"></script>

3
Tôi có thể xác minh tôi hiểu chính xác điều này không?: Với tùy chọn 1, khi tệp thay đổi, hàm băm kiểm tra md5 thay đổi, sau đó thay đổi url. Trình duyệt thấy một url mới và bắt đầu tải tệp mới. Dữ liệu get được thêm vào url bị máy chủ bỏ qua. Nếu đó là trường hợp, slick chết tiệt.
Colin Brogan

1
Ngoài ra, MD5-ing có phải toàn bộ bộ xử lý tệp không? Tôi đang xem xét làm điều này cho từng tệp css và js, nhưng tôi không muốn thấy tốc độ máy chủ đạt được điều này.
Colin Brogan

2
Sử dụng tổng kiểm tra là một ý tưởng tốt, nhưng nó nên được thực hiện ngay. Tính toán nó mỗi yêu cầu cho mỗi tệp sẽ đánh dấu hiệu suất của bạn đáng kể. Chuỗi truy vấn không tốt cho bộ nhớ đệm quá, xem các câu trả lời khác. Cách sử dụng đúng là nối thêm tổng kiểm tra (một phần của?) Hoặc số phiên bản vào tên tệp và thay vào đó sử dụng tên mới này (bạn có thể sử dụng tập lệnh xây dựng để thực hiện việc này một cách tự động khi triển khai). Xem lẩm bẩm , revusemin .
Frizi

10

Bạn cũng có thể buộc mã được tải lại mỗi giờ, như thế này, trong PHP:

<?php
echo '<script language="JavaScript" src="js/myscript.js?token='.date('YmdH').'">';
?>

hoặc là

<script type="text/javascript" src="js/myscript.js?v=<?php echo date('YmdHis'); ?>"></script>

1
xin chào, "v" và "mã thông báo" nghĩa là gì?
GMsoF

4
@GMsoF chỉ là một tham số get bổ sung được sử dụng (trong trường hợp này) để báo cho trình duyệt biết đó là một tệp "khác". Vì vậy, trình duyệt sẽ loại bỏ phiên bản được lưu trong bộ nhớ cache và tải phiên bản này thay thế. Điều này thường được sử dụng với "ngày sửa đổi cuối cùng" của một tập tin. Tôi hy vọng điều này có ý nghĩa ;-)
Jelmer

6

đặt cái này ở cuối mẫu của bạn:

var scripts =  document.getElementsByTagName('script');
var torefreshs = ['myscript.js', 'myscript2.js'] ; // list of js to be refresh
var key = 1; // change this key every time you want force a refresh
for(var i=0;i<scripts.length;i++){ 
   for(var j=0;j<torefreshs;j++){ 
      if(scripts[i].src && (scripts[i].src.indexOf(torefreshs[j]) > -1)){
        new_src = scripts[i].src.replace(torefreshs[j],torefreshs[j] + 'k=' + key );
        scripts[i].src = new_src; // change src in order to refresh js
      } 
   }
}

1
vui lòng cung cấp một số giải thích về giải pháp của bạn
Gabriel Espinoza

@GabrielEspinoza anh tải lại các tệp bằng cách sử dụng javascript, điều này làm cho bộ nhớ cache được cập nhật.
Neo Morina

6

thử dùng cái này

 <script language="JavaScript" src="js/myscript.js"></script>

Về điều này:

 <script language="JavaScript" src="js/myscript.js?n=1"></script>

5

Đây là một đoạn của những gì tôi đang sử dụng cho dự án mới nhất của tôi.

Từ bộ điều khiển:

if ( IS_DEV ) {
    $this->view->cacheBust = microtime(true);
} else {
    $this->view->cacheBust = file_exists($versionFile) 
        // The version file exists, encode it
        ? urlencode( file_get_contents($versionFile) )
        // Use today's year and week number to still have caching and busting 
        : date("YW");
}

Từ góc nhìn:

<script type="text/javascript" src="/javascript/somefile.js?v=<?= $this->cacheBust; ?>"></script>
<link rel="stylesheet" type="text/css" href="/css/layout.css?v=<?= $this->cacheBust; ?>">

Quá trình xuất bản của chúng tôi tạo ra một tệp có số sửa đổi của bản dựng hiện tại. Điều này hoạt động bằng cách mã hóa URL tệp đó và sử dụng nó như một bộ đệm bộ đệm. Khi không thành công, nếu tệp đó không tồn tại, số năm và tuần được sử dụng để bộ đệm vẫn hoạt động và nó sẽ được làm mới ít nhất một lần một tuần.

Ngoài ra, điều này cung cấp khả năng xóa bộ đệm cho mỗi lần tải trang trong khi ở môi trường phát triển để các nhà phát triển không phải lo lắng về việc xóa bộ đệm cho bất kỳ tài nguyên nào (javascript, css, ajax cuộc gọi, v.v.).


5

hoặc bạn chỉ có thể đọc tệp js bằng máy chủ với file_get_contets và sau đó đặt echo trong tiêu đề nội dung js


4

Có lẽ "xóa bộ nhớ cache" không dễ như mong muốn. Thay vì xóa bộ nhớ cache trên trình duyệt của tôi, tôi nhận ra rằng việc "chạm" vào tệp sẽ thực sự thay đổi ngày của tệp nguồn được lưu trong máy chủ (Đã kiểm tra trên Edge, Chrome và Firefox) và hầu hết các trình duyệt sẽ tự động tải xuống bản sao mới nhất của whats trên máy chủ của bạn (mã, đồ họa bất kỳ đa phương tiện quá). Tôi khuyên bạn chỉ nên sao chép các tập lệnh mới nhất trên máy chủ và giải pháp "thực hiện cảm ứng" trước khi chương trình của bạn chạy, vì vậy nó sẽ thay đổi ngày của tất cả các tệp vấn đề của bạn thành ngày và giờ mới nhất, sau đó nó tải xuống một bản sao mới vào trình duyệt của bạn:

<?php
    touch('/www/control/file1.js');
    touch('/www/control/file2.js');
    touch('/www/control/file2.js');
?>

... phần còn lại của chương trình của bạn ...

Tôi phải mất một thời gian để giải quyết vấn đề này (vì nhiều trình duyệt hoạt động khác nhau với các lệnh khác nhau, nhưng tất cả đều kiểm tra thời gian của tệp và so sánh với bản sao đã tải xuống trong trình duyệt của bạn, nếu ngày và giờ khác nhau, sẽ làm mới), Nếu bạn Không thể đi đúng hướng, luôn có một giải pháp hữu ích và tốt hơn cho nó. Trân trọng và cắm trại vui vẻ.


1
Tôi thích cách tiếp cận này, nhưng có lẽ tôi đang thực hiện điều này trong khu vực sai? Có ai biết nơi để thêm cái này trong một thiết lập WordPress không? Tôi đã thêm nó vào tệp tin.php, với các liên kết trực tiếp đến các tệp JavaScript và CSS, nhưng tôi vẫn phải tải lại một cách khó khăn để những thay đổi được chú ý.
flipflopmedia

1
Những gì bạn cần làm là ở thư mục wordpress html chính của bạn, chỉnh sửa tệp index.php của bạn để gọi hoặc thực thi lệnh Touch () cho các tệp mà bạn cần được làm mới và tải xuống. Tôi gặp vấn đề với các bức ảnh nhỏ và các tập tin js bị kẹt trong bộ nhớ cache. Tôi đã thử hầu hết các phương pháp được mô tả để giải phóng khỏi bộ nhớ, nhưng cách tốt nhất là tải một phương thức mới đúng hiện tại. Bạn có thể hoàn thành điều đó bằng cách chỉ thực hiện "Chạm vào" vì nó không sửa đổi bất cứ điều gì trên tệp, chỉ cập nhật thời gian và ngày hiện tại để đánh lừa trình duyệt của bạn để nghĩ rằng phiên bản khác của tệp và sự cố đã được khắc phục. Hoạt động trên hầu hết các trình duyệt
Luis H Cabrejo

3

Tôi đã có một số rắc rối với mã được đề xuất bởi yboussard. Vòng lặp j bên trong không hoạt động. Đây là mã sửa đổi mà tôi sử dụng thành công.

function reloadScripts(toRefreshList/* list of js to be refresh */, key /* change this key every time you want force a refresh */) {
    var scripts = document.getElementsByTagName('script');
    for(var i = 0; i < scripts.length; i++) {
        var aScript = scripts[i];
        for(var j = 0; j < toRefreshList.length; j++) {
            var toRefresh = toRefreshList[j];
            if(aScript.src && (aScript.src.indexOf(toRefresh) > -1)) {
                new_src = aScript.src.replace(toRefresh, toRefresh + '?k=' + key);
                // console.log('Force refresh on cached script files. From: ' + aScript.src + ' to ' + new_src)
                aScript.src = new_src;
            }
        }
    }
}

3

Nếu bạn đang sử dụng php có thể làm:

 <script src="js/myscript.js?rev=<?php echo time();?>"
    type="text/javascript"></script>

5
Câu hỏi này không chỉ được hỏi bốn năm trước, nó còn có câu trả lời tốt hơn, ngay cả khi nó không được chấp nhận.

3
Ngoài ra, phương pháp này sẽ tải xuống lại tệp mỗi lần bất kể số sửa đổi thực tế hoặc các thay đổi được thực hiện đối với tệp, điều này sẽ vô hiệu hóa hoàn toàn bộ đệm ẩn.
Antti29

2

Cache.delete () có thể được sử dụng cho chrome, firefox và opera mới.


Đây không phải là một phần của API của nhân viên dịch vụ sao?
BanksySan

@BanksySan từ các tài liệu MDN:You don't have to use it in conjunction with service workers, even though it is defined in the service worker spec.
Madbreaks

2

Xin vui lòng không cung cấp thông tin không chính xác. Api bộ đệm là một loại bộ đệm khác nhau từ bộ đệm http

Bộ đệm HTTP được kích hoạt khi máy chủ gửi các tiêu đề chính xác , bạn không thể truy cập bằng javasvipt.

Mặt khác, api bộ nhớ cache được kích hoạt khi bạn muốn, nó hữu ích khi làm việc với nhân viên dịch vụ để bạn có thể giao cắt yêu cầu và trả lời nó từ loại bộ đệm này xem: ilustration 1 ilustration 2 khóa học

Bạn có thể sử dụng những đồ công nghệ này để luôn có một nội dung mới trên người dùng của bạn:

  1. Sử dụng location.reload (đúng) điều này không hiệu quả với tôi, vì vậy tôi sẽ không giới thiệu nó.
  2. Sử dụng api Cache để lưu vào bộ đệm và giao yêu cầu với nhân viên dịch vụ , hãy cẩn thận với cái này vì nếu máy chủ đã gửi tiêu đề bộ đệm cho các tệp bạn muốn làm mới, trước tiên trình duyệt sẽ trả lời từ bộ đệm HTTP, và nếu nó không tìm thấy nó, thì nó sẽ vào mạng, vì vậy bạn có thể kết thúc với và tập tin cũ
  3. Thay đổi url từ các tệp stactics của bạn, tôi khuyên bạn nên đặt tên cho nó bằng cách thay đổi nội dung tệp của bạn, tôi sử dụng md5 và sau đó chuyển đổi nó thành chuỗi và url thân thiện, và md5 sẽ thay đổi theo nội dung của tệp, ở đó bạn có thể tự do gửi tiêu đề bộ đệm HTTP đủ lâu

Tôi sẽ giới thiệu người thứ ba xem


2

Bạn cũng có thể vô hiệu hóa bộ nhớ đệm trình duyệt với các thẻ meta HTML, chỉ cần đặt các thẻ html vào phần đầu để tránh trang web bị lưu trong khi bạn đang mã hóa / kiểm tra và khi hoàn tất, bạn có thể xóa các thẻ meta.

(trong phần đầu)

<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"/>

Làm mới trang của bạn sau khi dán phần này vào đầu và cũng nên làm mới mã javascript mới.

Liên kết này sẽ cung cấp cho bạn các tùy chọn khác nếu bạn cần chúng http://cristian.sulea.net/blog/disable-browser-caching-with-meta-html-tags/

hoặc bạn chỉ có thể tạo một nút như vậy

<button type="button" onclick="location.reload(true)">Refresh</button>

nó làm mới và tránh bộ nhớ đệm nhưng nó sẽ ở đó trên trang của bạn cho đến khi bạn hoàn thành kiểm tra, sau đó bạn có thể gỡ nó ra. Tùy chọn nắm tay là điều tốt nhất tôi điều.


1

Tôi có xu hướng phiên bản khung của mình sau đó áp dụng số phiên bản cho đường dẫn kịch bản và kiểu

<cfset fw.version = '001' />
<script src="/scripts/#fw.version#/foo.js"/>

3
OP đã không đề cập đến Coldfusion.
marctrem

@VijayDev 404 cho liên kết của bạn
smarber 17/03/2017

1
window.parent.caches.delete("call")

đóng và mở trình duyệt sau khi thực thi mã trong bàn điều khiển.


1
Xin vui lòng giải thích, "cuộc gọi" trong đoạn mã trên là gì?
Anand Rockzz

@AnandRockzz không thể, cache api chỉ là một loại bộ đệm mới có thể được quản lý bằng javascipt, vì vậy để xóa một cái gì đó từ đó, bạn đã lưu nó trước khi xem developer.mozilla.org/en-US/docs/ Web / API / Cache
John Balvin Arias


0

Nguyên nhân khiến bộ đệm của trình duyệt cùng một liên kết, bạn nên thêm một số cuối ngẫu nhiên của url. new Date().getTime()tạo ra một số khác nhau

Chỉ cần thêm new Date().getTime()kết thúc của liên kết như cuộc gọi

'https://stackoverflow.com/questions.php?' + new Date().getTime()

Đầu ra: https://stackoverflow.com/questions.php?1571737901173


Chào mừng đến với SO! Câu trả lời của bạn không rõ ràng. Hãy chỉnh sửa nó. Loại trả lời này, dựa trên liên kết, nên được nhận xét chỉ trong trường hợp liên kết biến mất.
David García Bodego
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.