2

在浏览器关闭、用户离开当前页面或会话到期之前,有什么方法可以锁定文件?

我有一个 java 应用程序,它从文本文件中读取注释,并允许用户通过 java 应用程序修改或添加更多注释到 pdf。完成后,他们单击“保存”,完整的注释文件将返回到其原始数据文件。

问题是两个人可以打开同一个注释文件并执行不同的更新。然后,每次保存时,它们都会覆盖现有文件,以便只保存第二个用户的更改。

理想的解决方案是让 1 个人“签出”文件进行编辑,进行修改,直到他们关闭窗口、离开页面或会话到期,然后文件将自动“签入”。在 C# 中有什么方法可以做到这一点?谢谢!

4

5 回答 5

0

那么没有简单的内置方法可以做到这一点,您可以做的是在与注释文件夹相同的文件夹中创建一个 {username}.lock 文件。然后在阅读或保存之前检查目录中是否有 .lock 文件。

如果有文件告诉用户它被锁定并且不能更新。显然,您需要确保删除 .lock 文件,否则在第一次访问后,没有人将能够访问注释文件。

于 2009-12-10T15:53:34.010 回答
0

真的没有很好的方法来做这样的锁。尽管您可以将代码放入 Session_End 以清除锁,但不能保证触发该事件。例如,服务器可能在会话期间崩溃。您将留下一个永久锁定的文件。

由于您想要简单,您可以考虑使用基于超时的锁定。当用户 A 开始编辑文件时,他们将获得 60 分钟(或您选择的任何时间段)的独占访问权限。您在数据存储中放置了一个条目,说最近的编辑锁定是针对用户 A 的,并且在下午 12:42 到期。用户 A 可以在那段时间内随意编辑。如果他之前完成了,他可以单击“完成”按钮删除锁定条目。您甚至可以给他一个“更多时间”按钮,将锁定到期时间戳更新为从现在起 60 分钟。

如果用户 B 出现并尝试编辑该文件,您的应用程序会检查列表并看到该文件已锁定到今天下午 12:42。如果用户 A 离开后永远无法完成,或者保存并忘记解锁,或者应用程序崩溃,您无需担心解锁或清理。用户 B 只需要等到 12:42 过去,然后您的应用程序将忽略现有的锁定条目,因为它已过期。

许多 wiki 使用与此类似的方法。它可能并不完美,但用户很容易理解,并且不需要任何操作员维护。

于 2009-12-11T16:16:32.970 回答
0

您可以将您的锁定代码Session_Start和您的释放代码放在Session_EndGlobal.asax 文件的方法中。然而,试图确定用户何时真正离开会话以便在不等待会话超时的情况下触发这些事件是很难检测到的,但可以通过 AJAX 和一些 Javascript 来完成。

例子

protected void Application_Start()
{
    Application("AnnotationFileLocked") = False;
}
...

protected void Session_End()
{
    if ((bool)Application("AnnotationFileLocked"))
    {
         // Session("UserName") could be set on Login
         if ((string)Application("AnnotationFileLockedBy") == (string)Session("UserName"))
         {
             Application("AnnotationFileLocked") = False;
             Application.Remove("AnnotationFileLockedBy");
         }
    }
}

然后在代码中的任何位置检查文件:

public void CheckOutFile()
{
    if (!(bool)Application("AnnotationFileLocked"))
    {
        Application("AnnotationFileLocked") = True
        Application("AnnotationFileLockedBy") = (string)Session("UserName");
        // do stuff
    }
}
于 2009-12-10T15:58:55.780 回答
0

如果两个用户能够编辑是应用程序的工作方式,那么为每个用户获取文件的临时副本进行编辑不是更有意义吗?

于 2009-12-10T15:59:00.350 回答
0

您可以使用我的库从多个应用程序访问文件。

您可以从 nuget 安装它:Install-Package Xabe.FileLock

如果您想了解更多信息,请查看 https://github.com/tomaszzmuda/Xabe.FileLock

ILock fileLock = new FileLock(file);
if(fileLock.Acquire(TimeSpan.FromSeconds(15), true))
{
    using(fileLock)
    {
        // file operations here
    }
}

fileLock.Acquire 方法只有在可以为该对象锁定文件独占时才会返回 true。但是上传文件的应用程序也必须在文件锁定中进行。如果对象不可访问,则方法返回 false。

因此,如果您想使用它,您可以在第一个用户打开文件以编辑并在会话过期或用户更改页面后处理它时创建锁。

于 2017-09-07T11:02:16.320 回答