我有一个简单的缓存系统
if (file_exists($cache)) {
echo file_get_contents($cache);
// if coming here when $cache is deleting, then nothing to display
}
else {
// PHP process
}
我们定期删除过时的缓存文件,例如在1小时后删除所有缓存。虽然这个过程非常快,但我认为可以在if statement
和file_get_contents
进程之间删除缓存文件。
我的意思是,当if statement
检查缓存文件是否存在时,它是存在的;但是当file_get_contents
试图捕获它时,它就不再存在了(通过同步缓存删除进程删除)。
file_get_contents
锁定文件以避免读取过程中正在进行的删除过程。但是,当if statement
将process发送到第一个条件(在file_get_contents
开始之前)时,可以删除该文件。
有什么办法避免这种情况吗?缓存删除系统不同吗?
注意:I没有遇到任何实际问题,因为捕捉这个事件的可能性不大,但从逻辑上讲,它是可能的,并且应该发生在重负载上。
发布于 2012-11-07 17:58:36
如果失败,file_get_contents
将返回false,那么下面的内容如何:
if (($output = file_get_contents($filename)) === false){
// Do the processing.
$output = 'Generated content';
// Save cache file
file_put_contents($filename, $output);
}
echo $output;
顺便说一句,您可能想考虑使用fpassthru
,它更节省内存,特别是对于更大的文件。在大型文件(> 100 MB)上使用file_get_contents可能会导致问题(取决于您的配置)。
<?php
$fp = @fopen($filename, 'rb');
if ($fp === false){
// Generate output
} else {
fpassthru($fp);
}
发布于 2012-11-07 17:58:48
幸运的是,file_get_contents
在出错时返回FALSE
,因此您可以快速烘焙它,如:
if (FALSE !== ($buffer = file_get_contents())) {
echo $buffer;
return;
}
// PHP process
或者类似的。考虑到您想要放置@
操作符来隐藏有关不存在的文件的任何警告,这是一种快速和肮脏的方式:
if (FALSE !== ($buffer = @file_get_contents())) {
另一种选择是锁定,但这可能会阻止您的缓存删除不删除文件,如果您已经锁定了它。
然后左转就是拖住自己的缓存。这意味着在PHP中读取文件创建时间,检查它是否小于5分钟,然后进行文件删除处理(5分钟是示例性的),然后您就会知道该文件已经过时,并被替换为新内容。然后重新创建文件。否则,请读取文件,这可能比使用readfile
而不是file_get_contents
和echo
更好。
https://stackoverflow.com/questions/13275131
复制相似问题