Forum OpenACS Q&A: adding header to resource files: cache-control max-age=NNNN


How does one add a cache-control http header to files under /resources such as for css?

This is for latest Openacs 5.8 running on Naviserver.

I just ran a test via telnet, and it's not there:

GET /resources/xdcpm-base-css-v3.css HTTP/1.1

HTTP/1.1 200 OK
MIME-Version: 1.0
Server: NaviServer/4.99.6
Date: Fri, 13 Feb 2015 00:04:27 GMT
Last-Modified: Thu, 12 Feb 2015 23:32:15 GMT
Content-Type: text/css
Accept-Ranges: bytes
Content-Length: 11122
Connection: keep-alive

/*! normalize.css v3.0.2 | MIT License | */

kind regards,

it is a common local modification to alter rp_serve_resource_file (in acs-tcl/tcl/request-processor-procs.tcl) and add e.g.
    ns_setexpires [expr {60*60*24*30}]
right before "ns_returnfile 200 ...." to set expiration date to e.g. 30 days. Maybe we should add a kernel parameter for controlling this.

While you are on optimizing, and you are using NaviServer 4.99.6: you could activate the parameters zip_static and gzip_refresh in the ns/fastpath section of the config file. When you place a gzipped version of the css file right next to the css file, then the compressed version will be delivered, when the client is able to accept it. Whenever the source file is changed, naviserver will gzip the file on the fly such that the zipped und unzipped files are never out of sync.

Thank you, Gustaf.

Good idea to make it a parameter, since it is commonly preferred when delivering files to small/mobile devices.



The head version of OpenACS has now a package parameter for kernel named ResourcesExpireInterval for specifying the expiration interval for /resources/*. Per default, no expiration interval is set.
Excellent! Thank you, Gustaf.
Related with this but with Content Repository. I was looking to specify Expires: header to images (photo-album) and modify
/packages/acs-content-repository/tcl/revision-procs.tcl [See below]. Please take in mind that perhpas this is not the best solution.

Would it a good idea to add a ResourcesExpiralInterval to Content Repository Parameters?

index 88c68b7..6a690ab 100644
--- a/packages/acs-content-repository/tcl/revision-procs.tcl
+++ b/packages/acs-content-repository/tcl/revision-procs.tcl
@@ -57,6 +57,10 @@ ad_proc -public cr_write_content {
set content_length 0

+# Based on
+ ns_setexpires [expr {60*60*24*30}]
+ns_log warning "Setting Expires en $storage_type $revision_id"
switch $storage_type {
text {
set text [db_string write_text_content ""]

Dear Cesareo,

using expire for file in the content repository is much more problematic than for resources. When an end-user updates a file in the content-repository (say in file-storage, or wiki) then one expects that all user sees this change as well more or less immediately. With expires, people will see for a while the outdated files, which are served from local caches (unless they force a reload). Furthermore, the requirement of different applications of the content repository are different (e.g. photo-album, of different kind of file-storages). So having a single expire time for all usages of the file-storages is not advisable.

My case scenario is mainly with photo-album. So it would be a good idea to use a parameter per package.

I'll change it in my setup to use only inside photo-album. Thanks 😉

Just to keep documented here. I'm using it now in photo album to serve images (6 months cache)

diff --git a/packages/photo-album/www/images/index.vuh b/packages/photo-album/www/images/index.vuh
index ce37de7..2a567bd 100644
--- a/packages/photo-album/www/images/index.vuh
+++ b/packages/photo-album/www/images/index.vuh
@@ -18,6 +18,10 @@ if {[parameter::get -parameter CheckPermissionOnImageServeP] == "t"} {
permission::require_permission -object_id $image_id -privilege "read"

+# Based on
+# Six months expire
+ ns_setexpires [expr {60*60*24*30*6}]
if {[catch {cr_write_content -revision_id $image_id} errMsg]} {
if {$::errorCode eq "NOT_FOUND"} {