那么现有网站要提供webp支持如何来做呢?笔者主要从后端入手,解决后端将原有图像文件(png, jpeg)转webp的问题。
基本思路很简单,利用apache的重写策略,将图片请求重写为相应的webp图片,如果相应的webp文件不存在,则流转给脚本进行转换处理。
1、给站点vhost段配置如下重写规则:
rewriteCond %{REQUEST_FILENAME} (.+)\.(png|jpe?g) [NC] rewriteCond %1.webp -f [NC] rewriteCond %{HTTP_ACCEPT} image/webp [NC] rewriteRule (.+)\.(png|jpe?g) $1.webp rewriteCond %1.webp !-f [NC] rewriteCond %{HTTP_ACCEPT} image/webp [NC] rewriteRule (.+)\.(png|jpe?g) /2webp.php2、在网站目录下新建脚本2webp.php, 代码如下:
<?php class WebpConverter{ private $originFile; public function __construct($originFile) { $this->originFile = $originFile; } private function imageCreateFromAny($filepath) { $type = exif_imagetype($filepath); // [] if you don't have exif you could use getImageSize() $allowedTypes = array( 1, // [] gif 2, // [] jpg 3, // [] png 6 // [] bmp ); if (!in_array($type, $allowedTypes)) { return false; } switch ($type) { case 1 : $im = imageCreateFromGif($filepath); break; case 2 : $im = imageCreateFromJpeg($filepath); break; case 3 : $im = imageCreateFromPng($filepath); break; case 6 : $im = imageCreateFromBmp($filepath); break; } return $im; } private function commandExists($command) { $isWin = strtoupper(substr(PHP_OS, 0, 3)) === 'WIN'; $test = $isWin ? "where" : "which"; return is_executable(trim(shell_exec("$test $command"))); } public function save($targetFile = null){ $this->targetFile = $targetFile; if (!$this->targetFile) { $pathInfo = pathinfo($this->originFile); $this->targetFile = $pathInfo['dirname'] . DIRECTORY_SEPARATOR . $pathInfo['filename'] . '.webp'; } if (function_exists('imagewebp')) { //imagewebp 是GD库里面的函数,但是即使安装了GD库也不一定支持webp,编译php时需要指定相应的配置。 $img = $this->imageCreateFromAny($this->originFile); $result = imagewebp($img, $this->targetFile); imagedestroy($img); } else if (class_exists('Imagick')) { //需要安装Imagick扩展 $image = new Imagick($this->originFile); $image->setImageFormat('webp'); $image->setImageAlphaChannel(Imagick::ALPHACHANNEL_ACTIVATE); $image->setBackgroundColor(new ImagickPixel('transparent')); $result = $image->writeImage($this->targetFile); } else if ($this->commandExists('cwebp')) { //需要在服务器安装libwebp-dev工具包,tools工具下载。 $cmd = 'cwebp "' . $this->originFile . '" -o "'. $this->targetFile . '"'; exec($cmd, $output); } return $this; } public function flush(){ header('Content-Type: image/webp'); echo file_get_contents($this->targetFile); } } $requestURI = strtok($_SERVER['REQUEST_URI'], '?'); define('BASE_ROOT', __DIR__); if (is_file($originFile = BASE_ROOT . $requestURI)) { $convertor = new WebpConverter($originFile); $convertor->save()->flush(); } ?>