douhuan6305 2014-06-15 01:38
浏览 64

.htaccess Rewriterule Regex仅适用于包含特定单词的文件

I have the following code in my .htaccess file which puts a watermark on all my WordPress uploads. I am trying to work out how I can change the Regex to make it only apply to files that end with a certain filename.

RewriteRule (.*)wp-content/uploads/(.*\.(jpe?g|gif|png))$ $1watermark.php?p=br&q=90&src=wp-content/uploads/$2

If there are files within the /uploads/ directory that end in example: ORIGINAL.jpg (full file name sunset-ORIGINAL.jpg) or ORIGINAL.gif, I want only those to have the watermark applied.

Is this something I can do with modifying the .htaccess Rewrite rule or should I be trying to achieve it inside the watermark.php file?

The code for watermark.php can be found here & below:

//we tell the server to treat this file as if it wore an image
header('Content-type: image/jpeg');
//image file path
$img = $_GET['src'];
//watermark position
$p = $_GET['p']; if(!$p) $p = 'br';
/*
p can be anything from the following list:
tl = top left
tc = top center
tr = top right
cl = center left
c = center of the image
cr = center right
bl = bottom left
bc = bottom center
br = bottom right
*/
//watermarked image quality
$q = $_GET['q'];
//if the quality field is missing or is not on the 0 to 100 scale then we set the quality to 93
if(!$q || $q<0 || $q>100) $q = '93';


$filetype = substr($img,strlen($img)-4,4);
$filetype = strtolower($filetype);
if($filetype == ".gif") $image = @imagecreatefromgif($img);
if($filetype == ".jpg") $image = @imagecreatefromjpeg($img);
if($filetype == ".png") $image = @imagecreatefrompng($img);
if (!$image) die();

//getting the image size for the original image
$img_w = imagesx($image);
$img_h = imagesy($image);
//if the filename has 150x150 in it's name then we don't apply the watermark
if (eregi("150x150", $img)) {
    imagejpeg($image, null, $q); die();
} else {
    $watermark = @imagecreatefrompng('watermark.png');
}
/*
//if you want to use the watermark only on bigger images then use this instead of the condition above
if ($img_w < "150") {//if image width is less then 150 pixels
    imagejpeg($image, null, $q); die();
} else {
    $watermark = @imagecreatefrompng('watermark.png');
}
*/

//getting the image size for the watermark
$w_w = imagesx($watermark);
$w_h = imagesy($watermark);

if($p == "tl") {
    $dest_x = 0;
    $dest_y = 0;
} elseif ($p == "tc") {
    $dest_x = ($img_w - $w_w)/2;
    $dest_y = 0;
} elseif ($p == "tr") {
    $dest_x = $img_w - $w_w;
    $dest_y = 0;
} elseif ($p == "cl") {
    $dest_x = 0;
    $dest_y = ($img_h - $w_h)/2;
} elseif ($p == "c") {
    $dest_x = ($img_w - $w_w)/2;
    $dest_y = ($img_h - $w_h)/2;
} elseif ($p == "cr") {
    $dest_x = $img_w - $w_w;
    $dest_y = ($img_h - $w_h)/2;
} elseif ($p == "bl") {
    $dest_x = 0;
    $dest_y = $img_h - $w_h;
} elseif ($p == "bc") {
    $dest_x = ($img_w - $w_w)/2;
    $dest_y = $img_h - $w_h;
} elseif ($p == "br") {
    $dest_x = $img_w - $w_w;
    $dest_y = $img_h - $w_h;
}

imagecopy($image, $watermark, $dest_x, $dest_y, 0, 0, $w_w, $w_h);
imagejpeg($image, null, $q);
imagedestroy($image);
imagedestroy($watermark);
  • 写回答

1条回答 默认 最新

  • douyin2962 2014-06-15 01:41
    关注

    Is this something I can do with modifying the .htaccess Rewrite rule or should I be trying to achieve it inside the watermark.php file?

    From an architectural standpoint, it’s better to just have the RewriteRule act on calling watermark.php and then add the robustness to watermark.php to differentiate which files should be acted on or ignored.

    The reason being as cool as .htaccess & related RewriteRule logic is, it really should only be used to quickly direct a web request from one thing to another. Adding a layer of “Is this file a JPEG? Okay, do this…” logic is a bit too much. It might be done, but the reality is it would all be better handled in one PHP script.

    And then within PHP you can add whatever robust levels of logic you best feel are need to decide if actions can be taken.

    Okay, looking at your code, look at these lines:

    $filetype = substr($img,strlen($img)-4,4);
    $filetype = strtolower($filetype);
    if($filetype == ".gif") $image = @imagecreatefromgif($img);
    if($filetype == ".jpg") $image = @imagecreatefromjpeg($img);
    if($filetype == ".png") $image = @imagecreatefrompng($img);
    if (!$image) die();
    

    $filetype is basically a file extension, right? And you only want to act on .gif, .jpg & .png files, right? Well look at this line:

    if (!$image) die();
    

    The logic to handle that is already there. This script will only act on files that are .gif, .jpg & .png files so there is no need to do any more work on that side.

    But I will say the logic in the script can be improved, but that is a whole other topic. As it stands, you are fine to send non-image files to this script since it will just die() if the file is not a .gif, .jpg & .png file anyway.

    EDIT: Okay, I saw in your comments you want the watermark.php script to only act on files that have the name ORIGINAL at the end of the name & before the extension, correct? Then you can modify watermark.php like this. First, find this line:

    //image file path
    $img = $_GET['src'];
    

    And then add a regex to check for the ORIGINAL at the end of .gif, .jpg & .png files like this:

    //image file path
    $img = $_GET['src'];
    // Check if the image has a '.gif', '.jpg' or '.png' extension.
    preg_match('/(?:ORIGINAL)\.(gif|jpg|png)$/', $img, $matches);
    if (empty($matches)) die();
    

    That said, this watermark.php has a major issue if you ask me: While it acts on GIF, JPEG & PNG files, the end product will all be a JPEG file as shown here on this line at the top:

    header('Content-type: image/jpeg');
    

    And this line at the bottom:

    imagejpeg($image, null, $q);
    

    Are you sure you want that? If I were you I would rework that code so a PNG stays a PNG, a GIF stays a GIF and a JPEG stays a JPEG. But that is out of the scope of this question & can be a nice project for you to tackle of you also feel the needs to be reworked.

    评论

报告相同问题?

悬赏问题

  • ¥15 我想咨询一下路面纹理三维点云数据处理的一些问题,上传的坐标文件里是怎么对无序点进行编号的,以及xy坐标在处理的时候是进行整体模型分片处理的吗
  • ¥15 CSAPPattacklab
  • ¥15 一直显示正在等待HID—ISP
  • ¥15 Python turtle 画图
  • ¥15 关于大棚监测的pcb板设计
  • ¥15 stm32开发clion时遇到的编译问题
  • ¥15 lna设计 源简并电感型共源放大器
  • ¥15 如何用Labview在myRIO上做LCD显示?(语言-开发语言)
  • ¥15 Vue3地图和异步函数使用
  • ¥15 C++ yoloV5改写遇到的问题