[PHP] [原创] WordPress 使用Ajax钩子 wp_ajax_{$ACTION} 显示图像时图像破埙
首先介绍一下WordPress用于处理Ajax请求的钩子:
wp_ajax_{$ACTION} 和 wp_ajax_nopriv_{$ACTION}
在用户已经登录的时候执行前者,否则执行后者。
前端Ajax请求示例:
JavaScript
jQuery.ajax({
url: '<?php echo admin_url('admin-ajax.php') ?>',
data: {
action: 'my_action',
str: '123'
},
success: function(data){
alert(data);
}
});
这里使用了 admin_url('admin-ajax.php') 来确保获得正确的请求文件。
或者直接使用URL GET请求:
PHP
admin_url( 'admin-ajax.php' ) . '?action=my_action&str=123'
后台处理请求示例:
PHP
add_action( 'wp_ajax_my_action', 'my_action_handler' );
add_action( 'wp_ajax_nopriv_my_action', 'my_action_handler' );
function my_action_handler(){
$str = $_POST['str'];
$str .= '456';
echo $str;
exit;
}
这里为了方便,把两个钩子绑定到同个函数。
注意函数结尾需要加上 exit; 或者 wp_die(); ,因为 admin_ajax.php 默认会输出0
这样使用了自带的钩子函数,就不必创建一个新文件来处理请求。
进入正题:最近更新一个微信自定义图标插件,原先插件是使用一个php文件来显示一个大小调整后的图像。
PHP
<?php
if(isset($_GET['src'])){
$src = urldecode($_GET['src']);
}else{
exit;
}
$width = 300;
$height = 300;
resizeImg($src,$width,$height);
function resizeImg($src,$width,$height){
$arr = getimagesize($src);
header("Content-type: image/png");
$ext = pathinfo($src, PATHINFO_EXTENSION);
switch(strtolower($ext)){
case 'jpg':
case 'jpeg':
$src = imagecreatefromjpeg($src);
break;
case 'gif':
$src = imagecreatefromgif($src);
break;
case 'png':
$src = imagecreatefrompng($src);
break;
case 'wbmp':
$src = imagecreatefromwbmp($src);
break;
default:
exit;
}
//$src = imagecreatefromjpeg($src);
$image = imagecreatetruecolor($width, $height);
$bg = imagecolorallocate($image, 255, 255, 255);
imagefill($image, 0, 0, $bg);
imagecopyresampled($image, $src, 0, 0, 0, 0, $width, $height, $arr[0], $arr[1]);
imagepng($image);
imagedestroy($image);
}
?>
图像调用链接是:http://localhost/wordpress/wp-content/plugins/wechatshare/ws-resize.php?src=http%3A%2F%2Flocalhost%2Fwordpress%2Fwp-content%2Fuploads%2F2016%2F09%2F343.jpg
一切显示正常。然后想改用钩子的方式来显示图像:
PHP
add_action( 'wp_ajax_nopriv_resize_img', 'ws_resize_img' );
add_action( 'wp_ajax_resize_img', 'ws_resize_img' );
//resize
function ws_resize_img(){
if(isset($_GET['src'])){
$src = urldecode($_GET['src']);
}else{
exit;
}
$width = 300;
$height = 300;
$arr = getimagesize($src);
header("Content-type: image/png");
$ext = pathinfo($src, PATHINFO_EXTENSION);
switch(strtolower($ext)){
case 'jpg':
case 'jpeg':
$src = imagecreatefromjpeg($src);
break;
case 'gif':
$src = imagecreatefromgif($src);
break;
case 'png':
$src = imagecreatefrompng($src);
break;
case 'wbmp':
$src = imagecreatefromwbmp($src);
break;
default:
exit;
}
//$src = imagecreatefromjpeg($src);
$image = imagecreatetruecolor($width, $height);
$bg = imagecolorallocate($image, 255, 255, 255);
imagefill($image, 0, 0, $bg);
imagecopyresampled($image, $src, 0, 0, 0, 0,$width,$height,$arr[0], $arr[1]);
imagepng($image);
imagedestroy($image);
exit;
}
图像调用链接是:http://localhost/wordpress/wp-admin/admin-ajax.php?action=resize_img&src=http%3A%2F%2Flocalhost%2Fwordpress%2Fwp-content%2Fuploads%2F2016%2F09%2F343.jpg
然后发现图像怎么也显示不出来了,显示为一张破埙的图像。
在WordPress官方论坛发帖,发现有可能是 header already sent 错误,但是查看错误日志也没有发现有错。
后来直接F12查看对比了正常图像和破埙图像的数据,发现破埙图像的数据前面多了几个字符的输出。果然还是F12好用。
马上想到有可能是哪个插件输出了字符。
禁用掉所有插件只留下我的插件,一切正常了。
但是在实际环境中难免会有插件输出字符,不可能要求用户去禁用插件,所以只能自己去避免:
在 header("Content-type: image/png"); 前面加上两行:
PHP
ob_get_clean(); ob_clean();
问题就完美解决了。
附上更新后的WordPress自定义微信小图标插件:
已整合到单个PHP文件
http://www.qwqoffice.com/article-20.html
本文链接:https://www.qwqoffice.com/article.php?mod=view&tid=27
