in reply to Re: A Picture A Day
in thread A Picture A Day

The browser never sees it. This is a CGI header. The server interprets it as a request to go to that URL and start over. Thus, it'll even handle if-modified-since and last-modified correctly.

-- Randal L. Schwartz, Perl hacker

Replies are listed 'Best First'.
Re: Re: Re: A Picture A Day
by mortis (Pilgrim) on Dec 19, 2001 at 20:50 UTC
    Thanks for the clarification -- even CGI.pm's redirect() method doesn't print the status line:
    perl -MCGI -e 'print CGI->new({})->redirect("/foo/b ar.cgi");'
    gives:
    Status: 302 Moved
    location: /foo/bar.cgi
    
    
    This doesn't apply to nph CGI's, correct?

    I didn't know that. Thanks

      For nph (non-parsable-headers, or something like that) CGI's, you need to construct all headers yourself, giving full freedom over what is being sent. With normal CGI, the _server_ interprets your Status-header, and will use it instead of its default "200" (OK) status => the Status header is not sent to the user agent.
      With a nph CGI, you need to construct the first line of the response yourself.

      # Normal CGI (The Status line is optional, the server will try to be i +ntelligent and guess it) Status: 302 Found Location: foo <blank line> # NPH CGI HTTP/1.1 302 Found Location: foo <blank line>

      2;0 juerd@ouranos:~$ perl -e'undef christmas' Segmentation fault 2;139 juerd@ouranos:~$

Re: Re: Re: A Picture A Day
by Juerd (Abbot) on Dec 19, 2001 at 21:02 UTC
    The browser DOES see it. The webserver will add the status by itself, or takes it from the Status header.
    This means there'll be _two_ requests, one'll hit the request, one'll hit the image. If everything's fast enough, the user will never notice.

    a251111.upc-a.chello.nl - - [19/Dec/2001:16:55:17 +0100] "GET /test/te +st.cgi HTTP/1.1" 302 286 "-" "Mozilla/5.0 (compatible; Konqueror/2.2. +2; Linux 2.4.10-ac12; X11; i686; en)" a251111.upc-a.chello.nl - - [19/Dec/2001:16:55:18 +0100] "GET /test/te +st.txt HTTP/1.1" 304 - "-" "Mozilla/5.0 (compatible; Konqueror/2.2.2; + Linux 2.4.10-ac12; X11; i686; en)"
    The 302 status is "Found", which tells the browser to re-request using the URL in the Location-header.
    The 304 is "Not modified", telling my browser to use the cached version.

    2;0 juerd@serv:~/juerd.nl/juerd.nl/test$ cat test.cgi #!/usr/bin/perl print "Location: test.txt\n\n"; 2;0 juerd@serv:~/juerd.nl/juerd.nl/test$ cat test.txt; echo Hello world
    merlyn, perhaps you meant s/browser/user/; s/CGI/HTTP/; s/server/browser/?

    2;0 juerd@ouranos:~$ perl -e'undef christmas' Segmentation fault 2;139 juerd@ouranos:~$

      Not with Apache, CGI, and a proper absolute path that begins with a slash. The browser will never know it happens. There's something broken in your test.

      -- Randal L. Schwartz, Perl hacker

        You're right, having a slash there made Apache handle the redirect.
        Some further testing showed:
        1. Apache handles the redirect internally when the value of the Location header begins with a slash
        2. Apache doesn't handle it internally when it's a relative path
        3. Apache doesn't handle it internally when it's an absolute URL (m!^http://!)
        Update (200112191738+0200)
        While watching tv, suddenly it all became clear to me: a webserver simply cannot handle relative paths, because it doesn't handle paths! The webserver can only handle absolute requests, and then only on the current host (Which seems logical if you know what the request line is: GET /foo.html HTTP/1.1, no hostname in there! (The hostname is in the Host-header, or there isn't a hostname at all)).
        Browsers, however, CAN handle relative things, or should at least be able to. That's why Apache lets the browser handle "test.txt", but can handle "/test/test.txt" without asking the browser.

        Am I right now, or was this sudden brainstorm wrong too?

        2;0 juerd@ouranos:~$ perl -e'undef christmas' Segmentation fault 2;139 juerd@ouranos:~$