tags:

views:

315

answers:

2

I have a CGI script that generates a file on the server and then redirects the browser to that newly generated file.

#!/bin/bash
printf "Content-type: text/html\n\n";
cat /myspecialdir/foo > /httpd/foo.html
echo "<HTML><HEAD><BODY>"
echo "<META HTTP-EQUIV=\"CACHE-CONTROL\" CONTENT=\"NO-CACHE\">"
echo "<META HTTP-EQUIV=\"Refresh\" CONTENT=\"1; URL=/foo.html\">"
echo "</BODY></HEAD></HTML>"

The file /myspecialdir/foo contains some dynamic content that I want to be in /httpd/foo.html. I then want the script to redirect there after the generation of the new file.

The problem I have is that the script doesn't get new data on every hit from a browser. For example, if I visit http://myip/cgi-bin/genfoo.cgi the first time in IE the data gets generated and it gets redirected to foo.html. After that, if I go to the CGI page using the back button, it doesn't re-run and I get redirected to stale data.

How can I force the CGI script to execute even from the back button?

EDIT: I tried doing this with the HTTP headers approach, but this doesn't seem to be working. Here's the new script, am I missing something?

#!/bin/bash
cat /myspecialdir/foo > /httpd/foo.txt
printf "Pragma-directive: no-cache\n\n";
printf "Cache-directive: no-cache\n\n";
printf "Cache-control: no-cache\n\n";
printf "Pragma: no-cache\n\n";
printf "Expires: 0\n\n";
printf "Location: /foo.txt\n\n";
printf "Content-type: text/html\n\n";

All this does when I visit via IE is to print the headers in the page, like so:

Pragma-directive: no-cache

Cache-directive: no-cache

Cache-control: no-cache

Pragma: no-cache

Expires: 0

Location: /BACtrace.txt

Content-type: text/html

EDIT:

It turns out this was an issue with the HTTP server I was using (busybox v1.12.1). I was unable to send the HTTP headers as originally recommended, but I was able to get this to work with a combination of META tags and a setting in IE8 (Tools --> Internet Options --> Browsing History --> Settings Button --> check "Every time I visit a website").

The META tags I used are:

echo "<meta http-equiv=\"expires\" content=\"0\" />"
echo "<META HTTP-EQUIV=\"Pragma-directive\" CONTENT=\"no-cache\"/>"
echo "<META HTTP-EQUIV=\"Cache-directive\" CONTENT=\"no-cache\"/>"
echo "<META HTTP-EQUIV=\"Cache-control\" CONTENT=\"no-cache\"/>"
echo "<META HTTP-EQUIV=\"Pragma\" CONTENT=\"no-cache\"/>"
echo "<META HTTP-EQUIV=\"Refresh\" CONTENT=\"1; URL=/foo.txt\"/>"
+1  A: 

You need to tell the browser (and possible proxies) to disable caching of the file with the appropriate HTTP headers:

Pragma-directive: no-cache
Cache-directive: no-cache
Cache-control: no-cache
Pragma: no-cache
Expires: 0

Of course, you'll just add each these in your script like this:

printf "Pragma-directive: no-cache\r\n";

There's a fair bit of redundancy in these directives. All are probably not necessary, but it's good to make sure there's something all browsers and proxies out there understand.

Ville Laurikari
+1  A: 

This doesn't answer your question, so feel free to down vote, but you can make this much easier on yourself by doing:

#!/bin/bash

cat /myspecialdir/foo > /httpd/foo.html

printf "Location: /foo.html\n\n";

This sends a header to the browser telling it to redirect to /foo.html instead of having to load and parse the <meta> tags.

Edit: You should only send 1 \n at the end of each header. After the entire request, you send 2 of them, like this (broken out for clarity):

#!/bin/bash
cat /myspecialdir/foo > /httpd/foo.txt
printf "Pragma-directive: no-cache\n";
printf "Cache-directive: no-cache\n";
printf "Cache-control: no-cache\n";
printf "Pragma: no-cache\n";
printf "Expires: 0\n";
printf "Location: /foo.txt\n";
printf "\n";

(Also note that the Content-Type header isn't included)

Sean Bright
Sorry, Sean, but that doesn't redirect. All that does is print "Location: /foo.html" in the browser. Am I missing something?The new script is:#!/bin/ashcat /myspecialdir/foo > /httpd/foo.txtprintf "Location: /foo.txt\r\n";printf "Pragma-directive: no-cache\r\n"printf "Cache-directive: no-cache\r\n"printf "Cache-control: no-cache\r\n"printf "Pragma: no-cache\r\n"printf "Expires: 0\r\n"
Coleman
See my edit for details.
Sean Bright
Thanks for the clarification, Sean. It looks like the server I'm using (httpd from an older BusyBox) breaks this though because it automatically sends the Content-type: text/plain header which prevents my script from sending headers. So, unforutnately, I have to use META tags.
Coleman
I've marked this as the answer because of Sean's follow-up. Thanks!!!
Coleman