我的环境是:Windows,MSSQL和PHP 5.4。
我的场景:我正在执行一个小型外壳脚本,该脚本从我想要的数据库中创建完整的备份到临时文件夹,然后将其移至新位置。
备份良好,文件是在我的临时文件夹中创建的。然后,我将其重命名为第二个文件夹,有时还可以,有时它找不到源文件。
当然,在这一点上,我知道我可以跳过临时位置,但是找不到文件困扰我的实际问题。为什么如此随机,并且可能还会影响我在此之前编写的其他文件功能...我还需要控制文件如何以及何时移动到目标。
基本代码很简单(尽管这是我实际代码的简化版本,因为我怀疑任何人都会对我的错误处理/记录条件感兴趣):
$query = "use test; backup database test to disk '//server01/temp/backups/file.bak', COMPRESSION;";
if($SQLClass->query($query)) {
$source="////server01//temp//backups//file.bak";
$destination="////server02//storage//backups//file.bak";
if(!rename($source , $destination)) {
//handleError is just a class function of mine that logs and outputs errors.
$this->handleError("Moving {$source} to {$destination} failed.");
}
}
else {
die('backup failed');
}
我尝试的是:
- 我在它之前添加了一个file_exists,并且当重命名时找不到源文件。
- 由于找不到文件,copy()和unlink()也无法正常工作
- 尝试过clearstatcache()
- SQL备份完成后尝试睡眠(10)
这些根本没有帮助。我和Google似乎对下一步该怎么做或尝试。当然,我可以进行一些shell_execect,但这不会消除我对早期产品的担忧。
我只是在尝试多次运行命令时才注意到这个问题。ClearStatCache()无法触摸的文件名是否有某种缓存?它似乎与某种幽灵文件现象有关,其中PHP迟到了文件系统内容或此类。
我将感谢有关接下来要做什么的任何想法,如果您读到这么远,谢谢:)。
您可以尝试调用系统的copy
命令。当我必须在两个NFS共享之间复制文件时,我曾经有像您这样的问题(在Linux框上)。它只是不时失败,没有明显的原因。我切换到cp
(Windows复制的模拟)问题已经消失了。
肯定不是完美的,但对我有用。
它可能与缓存相关,或者MySQL进程尚未发布该文件。MySQL将文件将文件转移到另一个 temp文件中,首先将文件移至您的 temp文件夹。当文件移动时,其他过程可能无法访问。
首先,当出现错误时,我将尝试在temp dir中 glob()
。也许您注意到它还没有完成。
您还尝试实现诸如10个重试迭代之类的东西,并有所延迟?
$notMoved = 0;
while($notMoved < 10){
$source="////server01//temp//backups//file.bak";
$destination="////server02//storage//backups//file.bak";
if(!rename($source , $destination)) {
//handleError is just a class function of mine that logs and outputs errors.
if ($notMoved++ < 10){
sleep(20);
} else {
$this->handleError("Moving {$source} to {$destination} failed.");
break;
}
}else{
break;
}
}
绕过问题:
- 不要倾倒并移动
- 移动然后转储: - )
(OFC。当时您的备份商店将是一个)
$source="////server01//temp//backups//file.bak";
$destination="////server02//storage//backups//file.bak";
if(!rename($source , $destination)) {
//handleError is just a class function of mine that logs and outputs errors.
$this->handleError("Moving {$source} to {$destination} failed.");
}
$query = "use test; backup database test to disk '//server01/temp/backups/file.bak', COMPRESSION;";
if($SQLClass->query($query)) {
//done :-)
}
else {
die('backup failed');
}
尝试
$source = "\server01tempbackupsfile.bak";
$destination = "\server02storagebackupsfile.bak";
$content = file_get_content($source);
file_put_contents($destination, $content);