PHP和并发文件访问

时间:2008-11-16 06:58:37

标签: php file concurrency

我正在用PHP构建一个小型Web应用程序,它将一些信息存储在纯文本文件中。但是,我的应用程序的所有用户在某个特定时间点可以同时使用/修改此文本文件。

所以问题是。确保只有一个用户可以在任何给定时间点对文件进行更改的最佳方法是什么?

4 个答案:

答案 0 :(得分:22)

你应该锁定文件

    $fp = fopen("/tmp/lock.txt", "r+");

if (flock($fp, LOCK_EX)) {  // acquire an exclusive lock
    ftruncate($fp, 0);      // truncate file
    fwrite($fp, "Write something here\n");
    fflush($fp);            // flush output before releasing the lock
    flock($fp, LOCK_UN);    // release the lock
} else {
    echo "Couldn't get the lock!";
}

fclose($fp);

查看http://www.php.net/flock

答案 1 :(得分:11)

我的建议是使用SQLite。它快速,轻量级,存储在文件中,并具有防止并发修改的机制。除非您正在处理预先存在的文件格式,否则SQLite就是您的选择。

答案 2 :(得分:3)

你可以做一个提交日志的格式,类似维基百科的做法。

使用数据库,每次保存的更改都会在数据库中创建一个新行,这会使前一个记录变为冗余,并且增加值,然后您只需担心在保存阶段获取表锁。

至少如果两个并发的人碰巧编辑某些内容,这两种变化都会出现在历史记录中,并且任何输出到提交战争的人都可以复制到新版本中。

现在,如果您不想使用数据库,则必须担心备份每个可见文件的修订控制文件。

您可以在文件系统上放置修订控件(GIT / MERCURIAL / SVN),然后在保存阶段自动提交,

伪代码:

 user->save : 
   getWritelock(); 
   write( $file ); 
   write_commitmessage( $commitmessagefile ); # <-- author , comment, etc 
   call "hg commit -l $commitmessagefile $file " ; 
   releaseWriteLock(); 
 done.

至少这种方式当2个人同时进行重要提交时,两者都不会迷路。

答案 3 :(得分:2)

许多用户的单个文件确实不应该是您使用的策略我不认为 - 否则您可能需要实现一个(全局)访问点来监视当前是否正在编辑该文件。获取一个锁,进行修改,释放锁等。我会选择“没有人建议使用数据库(SQLite,如果你不想要完全装备RDBMS的开销)