Writing my first WordPress plugin – fixing the late header injection December 31, 2009
Posted by evilzenscientist in : evilzenscientist , add a commentI’ve been hand-hacking wp-includes/pluggable.php for several releases now. It just got old – so I decided to learn to write a real plugin to move the functionality of wp_redirect into my private plugin.
Here’s the issue. I have several sites that check that a user is logged in. These use runphp or exec-php so I can write/include PHP on the page:
<?php
/* Short and sweet */
global $user_level,$post,$user_login;
// get user information
get_currentuserinfo();
echo "Please wait … securing your connection …";
if ( $user_level == 0) {
// $user_level == 0 is anonymous or not logged in user
wp_redirect(get_option(‘siteurl’) . ‘/photos/sorry’);
}
else {
// $user_level >0 means they are logged in at least
wp_redirect(get_option(‘siteurl’) . ‘/wpg2′);
}
?>
The issue I’ve always had with this is that the standard wp_redirect writes the location information cleanly; because we are already in the page (and headers have already been written) Apache throws up and kills this:
[Thu Dec 31 04:51:18 2009] [error] [client 10.0.0.1] PHP Warning: Cannot modify header information – headers already sent by (output started at /www/foosite/wp-content/themes/regulus/header.php:5) in /www/foosite/wp-content/plugins/php-modify-headers-apache/php-modify-headers-apache.php on line 38, referer: http://foosite
The hand written fixes checked to see if headers had been sent; if so then do the naughty meta http-equiv refresh with the url instead.
if( !headers_sent() ) {
if ($is_IIS)
header("Refresh: 0;url=$location");
else
header("Location: $location");
} else
echo "<meta http-equiv='refresh' content='0;url=$location' />";
}
Testing the plugin now. Details later.
WordPress 2.9 – exec-php and header injection December 27, 2009
Posted by evilzenscientist in : evilzenscientist , 3 commentsUpgrades to WordPress 2.9 on several of the production blogs – and it’s the same old issue with php header injection.
I’ve blogged about this before – and raised a trac ticket. I’m probably going to write a plugin to solve this one for good.
Here’s the change – around line 863 of wp-includes/pluggable.php
/* ** Remove header injection piece - fix for exec-php ** evilzenscientist - 27 Dec 09 ** originally from 28 May 08 ** ref http://trac.wordpress.org/ticket/2860
       if ( $is_IIS ) {
               header("Refresh: 0;url=$location");
       } else {
               if ( php_sapi_name() != 'cgi-fcgi' )
                       status_header($status); // This causes problems on I
               header("Location: $location", true, $status);
       }
}
endif;
** */
/** added new header injection and refresh ** http://trac.wordpress.org/ticket/2860 ** evilzenscientist - 28 May 2008 */ if( !headers_sent() ) { if ($is_IIS) header("Refresh: 0;url=$location"); else header("Location: $location"); } else echo "<meta http-equiv='refresh' content='0;url=$location' />"; } endif; /** end of change */