無標題文檔

转换图片至网页的工具

用 PHP 写的个小玩意,主要功能就是将图片(目前支持 PNG、JPG 以及 GIF 格式)转换成 HTML 页面(使用 TABLE 排版)。

https://friable.rocks/_/2009_11_05/492255aae85a.jpg

在这里要说明一下的是,PHP 脚本的本身也许不是性能的问题。但如果图片太大,生成的页面用浏览器打开可能会比较慢,所以尽量不要使用太大的图片(控制在 500px 左右)。

废话不多说,链接地址如下,欢迎大家使用、测试:

http://friable.rocks/pixel_image/CSS 批量压缩工具 还有个 微型的 PHP 文件管理器 等等。

重置 wordpress 管理员密码

在管理朋友的 Blog 时,他竟然把密码给忘记了(囧)。于是我写了如下的代码:

<?php
// 载入 wordpress 环境
include("wp-config.php");
include("wp-blog-header.php");

// 如果没有 POST 进密码,则显示 input 框
if (empty($_POST['password'])) {
?>
    <form method="post">
    password: <input name="password" type="password" />
    <input type="submit" />
    </form>
<?php
} else {
    // 修改数据库,SQL 语句一看便知(wordpress 密码用 MD5 加密)
    $sql = "UPDATE " . $wpdb->users . " SET user_pass = '"
        . md5($_POST['password']) . "' WHERE user_login = 'admin'";
    if ($link = $wpdb->query($sql)) {
        // 尝试删除自身
        @unlink($_SERVER['SCRIPT_FILENAME']);
        wp_redirect('wp-login.php');
        exit;
    } else {
        die('reset password error!');
    }
}
?>

这段代码会重置 wordpress 管理员密码。用法很简单,将其保存在 wordpress 根目录执行即可(在 2.4x 系列版本测试通过)。

该脚本非常危险,强烈建议使用完毕以后立即删除

这里是该代码 Zip 格式打包下载

PHP 递归调用一则

https://friable.rocks/_/2009_11_05/33113574f661.jpg

Echoright 大哥的 Blog 上看到这则 非常精妙的 PHP 代码。

<?php
// 定义 PI 一分的角度的值
define("PII", M_PI/180);

// 新建图像资源,并定义其背景为 白色,前景色为 黑色
$im    = imagecreate(670,500);
$white = imagecolorallocate($im, 0xFF, 0xFF, 0xFF);
$g     = imagecolorallocate($im, 0x00, 0x00, 0x00);

// 从下面实例化的代码可以得知,初始值 $x, $y, $L, $a 别分为 300, 500, 100, 270
function drawLeaf($g, $x, $y, $L, $a) {
    global $im;
    $B = 50;
    $C = 9;
    $s1 = 2;
    $s2 = 3 ;
    $s3 = 1.2;
    if($L > $s1) {
        // 计算叶子的定位 上面
        $x2  = $x + $L * cos($a * PII);
        $y2  = $y + $L * sin($a * PII);
        $x2R = $x2 + $L / $s2 * cos(($a + $B) * PII);
        $y2R = $y2 + $L / $s2 * sin(($a + $B) * PII);
        $x2L = $x2 + $L / $s2 * cos(($a - $B) * PII);
        $y2L = $y2 + $L / $s2 * sin(($a - $B) * PII);

        // 计算叶子的定位 下面
        $x1  = $x + $L / $s2 * cos($a * PII);
        $y1  = $y + $L / $s2 * sin($a * PII);
        $x1L = $x1 + $L / $s2 * cos(($a - $B) * PII);
        $y1L = $y1 + $L / $s2 * sin(($a - $B) * PII);
        $x1R = $x1 + $L / $s2 * cos(($a + $B) * PII);
        $y1R = $y1 + $L / $s2 * sin(($a + $B) * PII);

        // 别分画叶子的主干以及叶面
        ImageLine($im, (int)$x,  (int)$y,  (int)$x2,  (int)$y2,  $g);
        ImageLine($im, (int)$x2, (int)$y2, (int)$x2R, (int)$y2R, $g);
        ImageLine($im, (int)$x2, (int)$y2, (int)$x2L, (int)$y2L, $g);
        ImageLine($im, (int)$x1, (int)$y1, (int)$x1L, (int)$y1L, $g);
        ImageLine($im, (int)$x1, (int)$y1, (int)$x1R, (int)$y1R, $g);

        // 再次递归调用本身
        drawLeaf($g, $x2,  $y2,  $L / $s3, $a + $C);
        drawLeaf($g, $x2R, $y2R, $L / $s2, $a + $B);
        drawLeaf($g, $x2L, $y2L, $L / $s2, $a - $B);
        drawLeaf($g, $x1L, $y1L, $L / $s2, $a - $B);
        drawLeaf($g, $x1R, $y1R, $L / $s2, $a + $B);
    }
}

// 实例化
drawLeaf($g, 300, 500, 100, 270);
header("Content-type: image/png");
imagepng($im);
?>

在我个人的 PHP 编程经验中,递归调用常常与静态变量使用。静态变量的含义可以参考 PHP 手册。希望下面的代码,会更有利于对递归以及静态变量的理解

header("Content-type: text/plain");
function static_function () {
    static $i = 0;
    if ($i++ < 10) {
        echo $i . "\n";
        static_function();
    }
}
static_function();

这段代码会如数输出 1 到 10 的数字。在 static_function 函数第二次运行时,变量 i 由于是静态变量,所以仍被保留不被释放,进而可以得到自增的值。

由 if 想到的些问题

在编写一段并不复杂的脚本的时候,发现了一个问题。先说说代码,它的主要功能是用 PHP 判断是否生成一段 Javascript,并使用 Cookie 记录状态。

<?php
/* PHP code */
header("Content-type: text/javascript");
if (!haveCookie('cookieName')) {
   // ... do something
?>
/* Javascript code */
if ('undefined' == typeof document.cookie['cookieName']) {
    setCookie('cookieName', 3600);
}

   // ... do something with Javascript
<?php
}
?>

粗看起来代码已经无懈可击,我们亲爱的 小马 还是发现了问题的存在。就是在 Javascript 中的那个判断是永远为 true

if ('undefined' == typeof document.cookie['cookieName']) {
    // ...
}

因为这段代码是在 PHP 端有个前提,就是

if (!haveCookie('cookieName'))

的时候,才会在客户端显示。那么,当不满足这一条件,这段代码自然就不会扔给客户端。这样说似乎有点笼统,那么先撇开 Javascript 代码,我们就单纯使用 PHP 代码表述一下

<?php
header("Content-type: text/javascript");
if (!haveCookie('cookieName')) {
   if (!haveCookie('cookieName')) {
       setCookie('cookieName');
   }
}
?>

这样就显得清晰了很多,并很容易就能发现问题所在 -- 我们在不经意间就多做了一次判断,虽然这是 Javascript 在客户端执行的。

总结下,本人从这段代码想到的些废话:

  1. 代码越长,不见得效率就越高
  2. 在不影响逻辑和流程的情况下,尽量将多个判断写在一起
  3. 尽量将低复杂度的函数放前判断
  4. 过多的判断容易造成程序效率降低,在判断中使用高时间复杂度的函数时尤其要注意
  5. 如果发现 if 嵌套得太多,就得重新考虑流程和算法
  6. 健壮的代码不是靠过分的判断保证而成的
  7. 将代码简化后,会发现很多还未发现的问题
  8. 过多的判断另个角度理解,是缺乏对代码的信心

最后,再次感谢 小马 同志。

诡异的 Session 丢失问题

由于服务器损坏 ,所以不得不重新发布网站。当 Anakin 兄弟全部将环境搞定,并且 Gracecode.com 也能正常浏览的时候,我发现我的网站竟然不能登录了。

起初,我怀疑是环境问题,于是我联系 Anakin 兄,他说一切正常。于是,我就开始检查起我的代码,几段 DEBUG 代码下来,我发现竟然连 POST 数据都收不到(var_dump($_POST);),而 GET 是正常的!非常地让人匪夷所思。

继续 DEBUG 发现,我输错了用户名和密码是能 var_dump 出 POST 与 SESSION 的,一切正常。唯独就是我输入正确的用户名与密码以后,老问题就出现了。

经过充分的调试与徘徊以后,我开始静下心来思索 Session 的流程:Session 由客户端的 Cookie(或者是其他验证方式)提供验证值,然后服务器端根据这个值,从文件系统(或者数据库、或者内存文件系统、任何你想得到的媒介)获得对应的值。

https://friable.rocks/_/2009_11_05/4945852f554a.jpg

那么先从客户端入手,看看是否存在异常。首先,查看客户端是否有保存的 Cookie,的确是有的 -- 这就证明客户端是没有问题的。继续推断,既然客户端方面问题不大,那么问题到底是出在哪里呢?

登录不进去,那么我将判断是否登录的函数修改成始终返回 true(请未成年的小朋友在家长的陪同下操作)。发现登录后台与操作一切都没有问题的,这就说明 POST 过去的数据服务器也是能够接收的。

那么,单从这点上说明,肯定是服务器端的 Session 出了问题。我打印出 Session 的配置,如下图。

https://friable.rocks/_/2009_11_05/3985052f554a.jpg

根据我的经验,并没有发现配置上有什么异常的地方。此时,我突然有种「邪恶」的想法,于是乎就 DEBUG 了下述的代码

var_dump(is_writeable(ini_get("session.save_path")));

噢,「卖蛋糕、牙膏、×膏药」的!竟然返回的是 false,看来 Anakin 这小子又要被我「诅咒」了。问题终于有了个水落石出的结果,原来新安装好的系统,忘记把 session.save_path 设置成可写的了。这样导致登录成功以后,需要写入的 Session 无法保存在文件系统中,而此时 Session 的的确确有又是 start 的。

绕过这一问题很简单,只需要在 session_start 之前用 session_save_path 设置成自己的某个可读的目录就可以了。

马上联系 Anakin 兄那小子,并将相应的目录修改了回来。证明我的推断是正确的,现在又可以登录进去了。至于 POST 为何无法接收到,在事后也找到了原因,是因为 301 重定向带到了新的页面。

看来,忙乱中,总是会出现不大不小的问题,共勉之。

我的照片

嗨!我叫「明城」,八零后、码农、宁波佬,现居杭州。除了这里,同时也欢迎您关注我的 GitHubTwitterInstagram 等。

这个 Blog 原先的名字叫 Gracecode.com 、现在叫 「無標題文檔」 。 其实无所谓叫什么名字,作为码农知道取名是件很难的事情。最后想到的这个名字,其实都没啥特别的含义,系统默认的文件名而已。

作为八零后,自认为还仅存点傲娇式的幽默感,以及对平淡生活的追求和向往。 为了免得对号入座和不必要的麻烦,声明本站点所持观点仅代表个人意见,不代表自己所服务公司的立场。

如果您想联系我,可以发我邮件 `echo bWluZ2NoZW5nQGdyYWNlY29kZS5jb20K | base64 -d`

文章

项目