Make thumb.php give http redirects if given a file redirect
authorBrian Wolff <bawolff+wn@gmail.com>
Tue, 20 Aug 2013 20:29:23 +0000 (13:29 -0700)
committerBrian Wolff <bawolff+wn@gmail.com>
Tue, 27 Aug 2013 15:22:05 +0000 (09:22 -0600)
See bug 22390 for some of the background. Basically there's two
reasons why we want this:
* Hotlinkers to commons. We don't want to break their links when
we move a file (Wikimedia blog is a prominent hotlinker)
* Cached entires. On wikis using commons files, a file move doesn't
trigger HTMLCacheUpdate jobs for the downstream wiki (it only
triggers it on commons). This means that these pages will still
use the old version of the html (with img tags that have the old
url) until the next edit or purge action. But these urls won't
work as soon as the file is moved.

I'm pretty confident that redirects will work at this point
in the thumb stack, as the redirects for long file names work
fine (provided no thumb exists in swift with the wrong name).

Change-Id: I40350121cf902f66fcbd3cf788335a988fa7ee33

RELEASE-NOTES-1.22
thumb.php

index 8be6ecc..dfc972a 100644 (file)
@@ -200,6 +200,7 @@ production.
 * Add a mode parameter to <gallery> tag with potential options of "traditional",
   "nolines", "packed", "packed-overlay", or "packed-hover".
 * (bug 47399) A success message is now displayed after changing the password.
+* Make thumb.php give HTTP redirects for file redirects
 
 === Bug fixes in 1.22 ===
 * Disable Special:PasswordReset when $wgEnableEmail is false. Previously one
index 22a5b3d..2b68927 100644 (file)
--- a/thumb.php
+++ b/thumb.php
@@ -168,6 +168,48 @@ function wfStreamThumb( array $params ) {
 
        // Check the source file storage path
        if ( !$img->exists() ) {
+               $redirectedLocation = false;
+               if ( !$isTemp ) {
+                       // Check for file redirect
+                       if ( $isOld ) {
+                               // Since redirects are associated with pages, not versions of files,
+                               // we look for the most current version to see if its a redirect.
+                               $possibleRedirFile = RepoGroup::singleton()->getLocalRepo()->findFile( $img->getName() );
+                       } else {
+                               $possibleRedirFile = RepoGroup::singleton()->getLocalRepo()->findFile( $fileName );
+                       }
+                       if ( $possibleRedirFile && !is_null( $possibleRedirFile->getRedirected() ) ) {
+                               $redirTarget = $possibleRedirFile->getName();
+                               $targetFile = wfLocalFile( Title::makeTitleSafe( NS_FILE, $redirTarget ) );
+                               if ( $targetFile->exists() ) {
+                                       $newThumbName = $targetFile->thumbName( $params );
+                                       if ( $isOld ) {
+                                               $newThumbUrl = $targetFile->getArchiveThumbUrl( $bits[0] . '!' . $targetFile->getName(), $newThumbName );
+                                       } else {
+                                               $newThumbUrl = $targetFile->getThumbUrl( $newThumbName );
+                                       }
+                                       $redirectedLocation = wfExpandUrl( $newThumbUrl, PROTO_CURRENT );
+                               }
+                       }
+               }
+
+               if ( $redirectedLocation ) {
+                       // File has been moved. Give redirect.
+                       $response = RequestContext::getMain()->getRequest()->response();
+                       $response->header( "HTTP/1.1 302 " . HttpStatus::getMessage( 302 ) );
+                       $response->header( 'Location: ' . $redirectedLocation );
+                       $response->header( 'Expires: ' .
+                               gmdate( 'D, d M Y H:i:s', time() + 12 * 3600 ) . ' GMT' );
+                       if ( $wgVaryOnXFP ) {
+                               $varyHeader[] = 'X-Forwarded-Proto';
+                       }
+                       if ( count( $varyHeader ) ) {
+                               $response->header( 'Vary: ' . implode( ', ', $varyHeader ) );
+                       }
+                       return;
+               }
+
+               // If its not a redirect that has a target as a local file, give 404.
                wfThumbError( 404, "The source file '$fileName' does not exist." );
                return;
        } elseif ( $img->getPath() === false ) {