From e219e587b360fd81b3b19f281b93ad4491ec1a9e Mon Sep 17 00:00:00 2001 From: Filipe Brandenburger Date: Thu, 3 Mar 2011 14:02:25 +0100 Subject: [PATCH] Support HTTP/1.1 307 redirects keep request method. --- NEWS | 2 ++ src/ChangeLog | 6 ++++++ src/http.c | 12 +++++++++++- src/retr.c | 13 +++++++++---- src/wget.h | 2 +- 5 files changed, 29 insertions(+), 6 deletions(-) diff --git a/NEWS b/NEWS index ff2ed06d..5a3cc2fa 100644 --- a/NEWS +++ b/NEWS @@ -57,6 +57,8 @@ Please send GNU Wget bug reports to . ** Now --adjust-extension does not modify the file extension if the file ends in .htm. + +** Support HTTP/1.1 307 redirects keep request method. * Changes in Wget 1.12 diff --git a/src/ChangeLog b/src/ChangeLog index 62302686..28aa1a59 100644 --- a/src/ChangeLog +++ b/src/ChangeLog @@ -1,3 +1,9 @@ +2010-11-20 Filipe Brandenburger (tiny change) + + * http.c (gethttp): Repeat a POST request on a 307 response. + * retr.c (retrieve_url): Use NEWLOCATION_KEEP_POST. + * wget.h: Define NEWLOCATION_KEEP_POST. + 2011-03-02 Tomasz Buchert (tiny change) * http.c (ensure_extension): Do not adjust the extension if the file diff --git a/src/http.c b/src/http.c index d7e55ca8..1aa9ef02 100644 --- a/src/http.c +++ b/src/http.c @@ -2323,6 +2323,15 @@ read_header: CLOSE_INVALIDATE (sock); xfree_null (type); xfree (head); + /* From RFC2616: The status codes 303 and 307 have + been added for servers that wish to make unambiguously + clear which kind of reaction is expected of the client. + + A 307 should be redirected using the same method, + in other words, a POST should be preserved and not + converted to a GET in that case. */ + if (statcode == HTTP_STATUS_TEMPORARY_REDIRECT) + return NEWLOCATION_KEEP_POST; return NEWLOCATION; } } @@ -2790,6 +2799,7 @@ Spider mode enabled. Check if remote file exists.\n")); ret = err; goto exit; case NEWLOCATION: + case NEWLOCATION_KEEP_POST: /* Return the new location to the caller. */ if (!*newloc) { @@ -2800,7 +2810,7 @@ Spider mode enabled. Check if remote file exists.\n")); } else { - ret = NEWLOCATION; + ret = err; } goto exit; case RETRUNNEEDED: diff --git a/src/retr.c b/src/retr.c index 1c587a2c..25c5dcf4 100644 --- a/src/retr.c +++ b/src/retr.c @@ -764,7 +764,7 @@ retrieve_url (struct url * orig_parsed, const char *origurl, char **file, proxy_url = NULL; } - location_changed = (result == NEWLOCATION); + location_changed = (result == NEWLOCATION || result == NEWLOCATION_KEEP_POST); if (location_changed) { char *construced_newloc; @@ -838,12 +838,17 @@ retrieve_url (struct url * orig_parsed, const char *origurl, char **file, } u = newloc_parsed; - /* If we're being redirected from POST, we don't want to POST + /* If we're being redirected from POST, and we received a + redirect code different than 307, we don't want to POST again. Many requests answer POST with a redirection to an index page; that redirection is clearly a GET. We "suspend" POST data for the duration of the redirections, and restore - it when we're done. */ - if (!post_data_suspended) + it when we're done. + + RFC2616 HTTP/1.1 introduces code 307 Temporary Redirect + specifically to preserve the method of the request. + */ + if (result != NEWLOCATION_KEEP_POST && !post_data_suspended) SUSPEND_POST_DATA; goto redirected; diff --git a/src/wget.h b/src/wget.h index 16269bf3..fce89e7a 100644 --- a/src/wget.h +++ b/src/wget.h @@ -353,7 +353,7 @@ typedef enum PROXERR, /* 50 */ AUTHFAILED, QUOTEXC, WRITEFAILED, SSLINITFAILED, VERIFCERTERR, - UNLINKERR + UNLINKERR, NEWLOCATION_KEEP_POST } uerr_t; /* 2005-02-19 SMS. -- 2.39.2