我的c#web应用程序中有一个锁定,阻止用户在启动后运行更新脚本。
我在想我会在我的母版页中发布通知,让用户知道数据还不是全部。
目前我这样做是锁定的。
protected void butRefreshData_Click(object sender, EventArgs e)
{
Thread t = new Thread(new ParameterizedThreadStart(UpdateDatabase));
t.Start(this);
//sleep for a bit to ensure that javascript has a chance to get rendered
Thread.Sleep(100);
}
public static void UpdateDatabase(object con)
{
if (Monitor.TryEnter(myLock))
{
Updater.RepopulateDatabase();
Monitor.Exit(myLock);
}
else
{
Common.RegisterStartupScript(con, AlreadyLockedJavaScript);
}
}
我不想做
if(Monitor.TryEnter(myLock))
Monitor.Exit(myLock);
else
//show processing labal
正如我想象的那样,当它实际上没有运行时,它可能会显示通知。
我可以使用替代品吗?
编辑:
大家好,非常感谢您的建议!不幸的是我无法让他们工作......
然而,我将这两个想法结合起来,并提出了我自己的解决方案。它似乎工作到目前为止,但我必须等待这个过程完成......
好的,这似乎有效,我将Repopule方法分解为它自己的类。
public static class DataPopulation
{
public static bool IsUpdating = false;
private static string myLock = "My Lock";
private static string LockMessage = @"Sorry, the data repopulation process is already running and cannot be stopped. Please try again later. If the graphs are not slowly filling with data please contact your IT support specialist.";
private static string LockJavaScript = @"alert('" + LockMessage + @"');";
public static void Repopulate(object con)
{
if (Monitor.TryEnter(myLock))
{
IsUpdating = true;
MyProjectRepopulate.MyProjectRepopulate.RepopulateDatabase();
IsUpdating = false;
Monitor.Exit(myLock);
}
else
{
Common.RegisterStartupScript(con, LockJavaScript);
}
}
}
掌握我做的事
protected void Page_Load(object sender, EventArgs e)
{
if (DataPopulation.IsUpdating)
lblRefresh.Visible = true;
else
lblRefresh.Visible = false;
}
答案 0 :(得分:3)
(假设您知道在处理停止后立即显示此通知的竞争条件......)
您可以切换到CountdownEvent。这与ManualResetEvent
类似,但也提供CurrentCount和IsSet属性,可用于确定是否正在处理某些内容。
答案 1 :(得分:2)
探索Autoresetevents和ManualResetevents。您可以让生成的线程设置事件并检查主线程中的事件以显示消息。
答案 2 :(得分:2)
如果只是通过回调方法设置一个指示主动锁定的某个volaltile bool属性怎么样?
答案 3 :(得分:2)
butRefreshData_Click()
{
lock(myLock)
{
if (isbusy) {/*tell user*/}
}
}
UpdateDatabase(object con)
{
lock(myLock)
{
if (isbusy) {/*tell user*/ return;}
else {isbusy = true;}
}
Updater.RepopulateDatabase();
lock(myLock)
{
isBusy = false;
}
}
注意:您应该将UpdateDatabase
包装在try-finally中,以避免在抛出异常时isBusy
被卡住为真。
答案 4 :(得分:-1)
正如我想象的那样轻微 它可能会显示的可能性 实际上没有通知 运行
总是有可能发送“Working ...”消息,然后立即完成作业。你有什么应该在逻辑上工作。
public static void UpdateDatabase(object con)
{
if (Monitor.TryEnter(myLock))
{
System.Diagnostics.Debug.WriteLine("Doing the work");
Thread.Sleep(5000);
Monitor.Exit(myLock);
System.Diagnostics.Debug.WriteLine("Done doing the work");
}
else
{
System.Diagnostics.Debug.WriteLine("Entrance was blocked");
}
}