- 最后更新
我正在关注MySQL 教程中的自动分区维护,该教程详细介绍了基于日期范围删除和添加 mySQL 表分区的通用方法。
这个想法是您可以在一定时间后自动抛弃旧表数据,并根据需要为当前数据创建新的表分区。
但是,由于我的站点可能会托管在“共享”提供程序包上,因此我似乎无法使用 mySQL 事件。
因此,我正在交叉使用第一个教程中描述的存储过程,并使用另一种方法来调用它们,该方法使用此 Stack Overflow 答案中详述的方法,并进行了一些修改:Mysql 的分区维护脚本
在我的本地测试机器上,我想将 PHP 脚本作为Webmin的 CRON 作业运行。
当我从Adminer(具有与 phpMyAdmin 类似的功能)运行存储过程时,使用mySQL 测试数据库,它们按预期执行 - 分区被删除,整个过程需要几分钟才能完成。
但是,当我从 Webmin 将修改后的 PHP 脚本作为 CRON 作业运行时,似乎什么也没发生。没有错误,但脚本会立即返回“OK”。
同样,当我从 LAMP 机器的 shell 运行脚本时,它会立即返回“OK”。
这是 PHP 脚本:
#!/usr/bin/env php
<?php
$connection = mysqli_connect('localhost', 'my_username', 'my_password', 'employees');
$result = mysqli_query($connection, "CALL perform_partition_maintenance('employees', 'titles', 3, 216, 5)") or die('Query fail: ' . mysqli_error($connection));
if ($result)
echo "OK";
else
echo "FAIL";
mysqli_close($connection);
对于我可能出错的任何建议,我将不胜感激。
更新
根据尼克的建议,我一直在添加很多调试语句。我走了一条稍微不同的路线,因为它更容易做 - 很多新的“into outfile”语句。
但我所观察到的让我感到困惑。存储过程的一小部分如下:
OPEN cur1;
read_loop: LOOP
FETCH cur1 INTO current_partition_name;
IF done THEN
LEAVE read_loop;
END IF;
IF ! @first AND p_seconds_to_sleep > 0 THEN
SELECT CONCAT('Sleeping for ', p_seconds_to_sleep, ' seconds');
SELECT SLEEP(p_seconds_to_sleep);
END IF;
SELECT CONCAT('Dropping partition: ', current_partition_name);
...
SET @first = FALSE;
END LOOP;
CLOSE cur1;
这一切都是从 Geoff Montee 页面上的 web 教程中获取的,未经修改,并且在其他上下文中完美地工作(即,在 Adminer 中,从 sql 控制台 - 只是没有与 PHP 脚本结合使用)。但是,当我注释掉上面写着的行时:
SELECT CONCAT('Dropping partition: ', current_partition_name);
一切正常,但是当我把那条线放回去时,脚本会窒息。我无法理解这一点。特别是因为 - 在测试中 - 我正在将“current_partition_name”写到磁盘上的文件中,用于循环的前三个迭代,并且在这种情况下引用字符串不会导致任何问题。这很奇怪。
这个另一个(显然未解决的)stackoverflow 问题听起来有些相似。