用户
 找回密码
 入住 CI 中国社区
搜索
查看: 4470|回复: 8
收起左侧

关于flock文件锁的问题

[复制链接]
发表于 2011-6-13 11:31:44 | 显示全部楼层 |阅读模式
多个进程同时写文件,我调用flock解决。
文件1 lock.php
$fp = fopen("lock.txt", "r+");
if (flock($fp, LOCK_EX)) { // do an exclusive lock
    ftruncate($fp, 0); // truncate file
} else {
    echo "Couldn't get the lock!";
}

while ( ! file_exists('xxx.txt')){
    sleep(3);
    fwrite($fp, "Write something here\n");
}

flock($fp, LOCK_UN); // release the lock
fclose($fp);

文件2,另一个写文件,writer.php
<?php
$fp = fopen("lock.txt", "r+");
fwrite($fp, "==============================\n");
fclose($fp);

我先执行文件1,php lock.php
这是,lock.txt这个文件应该已经被锁定了。
然后我再执行php writer.php
这时候,应该是由于lock.txt被锁定了,应该是不能写入了,但是事实是仍然能写入。。。请大家指点。。。
发表于 2011-6-13 12:08:07 | 显示全部楼层
这应该是运行时锁吧,会呗自动释放掉的,手册写的
On versions of PHP before 5.3.2, the lock is released also by fclose() (which is also called automatically when script finished)
可能你需要的是这个:http://cn.php.net/manual/en/function.chmod.php

发表于 2011-6-13 16:55:16 | 显示全部楼层
有辅助函数file的write方法,为什么不用呢?
 楼主| 发表于 2011-6-13 22:55:04 | 显示全部楼层
jeongee 发表于 2011-6-13 12:08
这应该是运行时锁吧,会呗自动释放掉的,手册写的
On versions of PHP before 5.3.2, the lock is released ...

但是我没有调用fclose啊,我一直在while循环里面啊。。。
 楼主| 发表于 2011-6-13 22:55:20 | 显示全部楼层
spt119 发表于 2011-6-13 16:55
有辅助函数file的write方法,为什么不用呢?

什么意思?请指教。。。
发表于 2011-6-14 00:43:27 | 显示全部楼层
楼主注意看一下 http://cn.php.net/manual/zh/function.flock.php
其中有一段:
在部分操作系统中 flock() 以进程级实现。当用一个多线程服务器 API(比如 ISAPI)时,可能不可以依靠 flock() 来保护文件,因为运行于同一服务器实例中其它并行线程的 PHP 脚本可以对该文件进行处理。
 楼主| 发表于 2011-6-14 11:20:03 | 显示全部楼层
Hex 发表于 2011-6-14 00:43
楼主注意看一下 http://cn.php.net/manual/zh/function.flock.php
其中有一段:

我没有用多线程服务器api,我直接用的是cli
应该是这样,我第二个php程序去写文件的时候,应该也要先去获取锁,这样就能停住了,告知文件被锁住了。。。
发表于 2011-6-14 12:03:08 | 显示全部楼层
mahone 发表于 2011-6-14 11:20
我没有用多线程服务器api,我直接用的是cli
应该是这样,我第二个php程序去写文件的时候,应该也要先去获 ...

cli 的话每次启动一个 PHP 就是一个新的进程。
根据你的情况看,这个锁不能跨进程。
这应该是 PHP 的运行机制决定的。
 楼主| 发表于 2011-6-15 11:55:47 | 显示全部楼层
Hex 发表于 2011-6-14 12:03
cli 的话每次启动一个 PHP 就是一个新的进程。
根据你的情况看,这个锁不能跨进程。
这应该是 PHP 的运行 ...

hex给我发的网址,我看了下,下面的第一个回帖,有个代码================
LOCK_NB seems to be checked and works fine in Windows, too, in PHP 5.3.3.

For instance, try concurrently running two instances of the following script (via the CLI). The second prints "Didn't quite get the lock..." as expected, whereas w/o the LOCK_NB flag, it just hangs.

<?php
$x = fopen("flocktest.txt", "w");
if (flock($x, LOCK_EX|LOCK_NB)) {
    print "No problems, I got the lock, now I'm going to sit on it.";
    while (true)
        sleep(5);
} else {
    print "Didn't quite get the lock. Quitting now. Good night.";
}
fclose($x);
?>

================================
我开启2个cli进程去运行这个代码,如果去掉LOCK_NB这个锁,确实是会阻塞的。
也就是我前面说的,代码里面是要去flock一下,才会被锁住,否则应该就不会被锁住,应该是这样。

本版积分规则