在.NET中,防止應用程序的多個實例同時運行的最佳方法是什麼?如果沒有「最佳」技術,那麼每種解決方案都需要考慮哪些問題?防止.NET中給定應用程序的多個實例?
回答
使用互斥鎖。上面使用GetProcessByName的例子之一有許多警告。下面是關於這個問題的好文章:
http://odetocode.com/Blogs/scott/archive/2004/08/20/401.aspx
[STAThread]
static void Main()
{
using(Mutex mutex = new Mutex(false, "Global\\" + appGuid))
{
if(!mutex.WaitOne(0, false))
{
MessageBox.Show("Instance already running");
return;
}
Application.Run(new Form1());
}
}
private static string appGuid = "c0a76b5a-12ab-45c5-b9d9-d693faa6e7b9";
http://en.csharp-online.net/Application_Architecture_in_Windows_Forms_2.0 - 單Instance_Detection_and_Management
本文簡單介紹瞭如何可以在其實例的數量創建控制Windows應用程序或只運行單一實例。這是商業應用程序非常典型的需求。已經有很多其他可能的解決方案來控制這一點。
http://www.openwinforms.com/single_instance_application.html
Hanselman有a post關於使用WinFormsApplicationBase類從Microsoft.VisualBasic程序集來做到這一點。
你必須使用的System.Diagnostics.Process。
通常它與一個名爲互斥完成(使用新的mutex(「你的應用程序名」,真正的),並檢查返回值),但也有一定的支撐班Microsoft.VisualBasic程序。 dll即can do it for you。
if (Process.GetProcessesByName(Process.GetCurrentProcess().ProcessName).Length > 1)
{
AppLog.Write("Application XXXX already running. Only one instance of this application is allowed", AppLog.LogMessageType.Warn);
return;
}
我認爲應該看到這個:http://odetocode.com/blogs/scott/archive/2004/08/20/the-misunderstood-mutex.aspx – SubmarineX 2014-04-30 08:26:35
@SubmarineX你如何確定這篇文章是正確的?它仍然是互斥之間的爭議和http://www.codeproject.com/Articles/4975/Easily-Create-A-Single-Instance-Application – 2014-07-23 07:48:49
驚人只需完美 感謝您的時間和精力 – 2015-04-20 08:52:19
使用Visual Studio 2005或2008年,當你創建一個項目的可執行文件,在「應用程序」面板中的屬性窗口中有一個名爲複選框「做單實例應用程序」,可以激活轉換該應用程序在單個實例應用程序上。
這裏是我正在談論的窗口的捕獲: 這是一個Visual Studio 2008的Windows應用程序項目。
我查找了你提到的這個複選框,對於我的C#/ WPF應用程序,並沒有任何。 – HappyNomad 2010-01-05 16:14:41
我沒有在我的VS 2008 C#/ WinForms應用程序的屬性中看到它。 – 2010-09-20 18:25:08
也不在VS2005中。他必須提到舊的VB工作室。 – nawfal 2011-08-24 14:38:22
這聽起來像有一些迄今已提出3種基本技術。
- 從Microsoft.VisualBasic.ApplicationServices.WindowsFormsApplicationBase類派生並將IsSingleInstance屬性設置爲true。 (我相信這裏的一個警告是,這將不適用於WPF應用程序,是嗎?)
- 使用一個已命名的互斥鎖並檢查它是否已被創建。
- 獲取正在運行的進程的列表並比較進程的名稱。 (這要求您的進程名稱相對於給定用戶計算機上運行的任何其他進程是唯一的。)
我錯過了任何注意事項?
以下是您需要確保只有一個實例正在運行的代碼。這是使用命名互斥體的方法。
public class Program
{
static System.Threading.Mutex singleton = new Mutex(true, "My App Name");
static void Main(string[] args)
{
if (!singleton.WaitOne(TimeSpan.Zero, true))
{
//there is already another instance running!
Application.Exit();
}
}
}
使用VB.NET! 編號:真的;)使用Microsoft.VisualBasic.ApplicationServices
;
從VB.Net的WindowsFormsApplicationBase爲您提供了一個「SingleInstace」屬性,這決定了其他情況下,讓只有一個實例運行。
[STAThread]
static void Main() // args are OK here, of course
{
bool ok;
m = new System.Threading.Mutex(true, "YourNameHere", out ok);
if (! ok)
{
MessageBox.Show("Another instance is already running.");
return;
}
Application.Run(new Form1()); // or whatever was there
GC.KeepAlive(m); // important!
}
來源:Ensuring a single instance of .NET Application
和:Single Instance Application Mutex
相同的答案@Smink並與一捻@Imjustpondering:
這是對於VB.Net
代碼Private Shared Sub Main()
Using mutex As New Mutex(False, appGuid)
If Not mutex.WaitOne(0, False) Then
MessageBox.Show("Instance already running", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error)
Return
End If
Application.Run(New Form1())
End Using
End Sub
這是代碼爲C#
private static void Main()
{
using (Mutex mutex = new Mutex(false, appGuid)) {
if (!mutex.WaitOne(0, false)) {
MessageBox.Show("Instance already running", "ERROR", MessageBoxButtons.OK, MessageBoxIcon.Error);
return;
}
Application.Run(new Form1());
}
}
(注:這是一個有趣的解決方案!它的工作原理,但使用不好的GDI +的設計來實現這一點。)
將圖像與您的應用程序並加載它在啓動時。保持它直到應用程序退出。用戶無法啓動第二個實例。 (當然互斥方案是乾淨多了)
private static Bitmap randomName = new Bitmap("my_image.jpg");
我在這裏嘗試了所有的解決方案,並沒有在我的C#.net 4.0項目的工作。希望可以幫到這裏有人爲我工作的解決方案:
private static string appGuid = "WRITE AN UNIQUE GUID HERE";
private static Mutex mutex;
當你需要檢查,如果應用程序已經在運行:
bool mutexCreated;
mutex = new Mutex(true, "Global\\" + appGuid, out mutexCreated);
if (mutexCreated)
mutex.ReleaseMutex();
if (!mutexCreated)
{
//App is already running, close this!
Environment.Exit(0); //i used this because its a console app
}
我需要關閉
作爲主類變量其他只有一些條件,這對我的目的很好運作
這對我純粹的C#工作。 try/catch是在循環過程中可能列表中的一個進程退出的時候。
using System.Diagnostics;
....
[STAThread]
static void Main()
{
...
int procCount = 0;
foreach (Process pp in Process.GetProcesses())
{
try
{
if (String.Compare(pp.MainModule.FileName, Application.ExecutablePath, true) == 0)
{
procCount++;
if(procCount > 1) {
Application.Exit();
return;
}
}
}
catch { }
}
Application.Run(new Form1());
}
在嘗試了多個解決方案後,我問了這個問題。我結束了使用的例子爲WPF這裏:http://www.c-sharpcorner.com/UploadFile/f9f215/how-to-restrict-the-application-to-just-one-instance/
public partial class App : Application
{
private static Mutex _mutex = null;
protected override void OnStartup(StartupEventArgs e)
{
const string appName = "MyAppName";
bool createdNew;
_mutex = new Mutex(true, appName, out createdNew);
if (!createdNew)
{
//app is already running! Exiting the application
Application.Current.Shutdown();
}
}
}
在App.xaml中:
x:Class="*YourNameSpace*.App"
StartupUri="MainWindow.xaml"
Startup="App_Startup"
1 - 創建程序的參考。CS - >
using System.Diagnostics;
2 - 投入void Main()
作爲代碼的第一行 - >
if (Process.GetProcessesByName(Process.GetCurrentProcess().ProcessName).Length >1)
return;
就是這樣。
只需使用StreamWriter
,這個怎麼樣?
System.IO.File.StreamWriter OpenFlag = null; //globally
和
try
{
OpenFlag = new StreamWriter(Path.GetTempPath() + "OpenedIfRunning");
}
catch (System.IO.IOException) //file in use
{
Environment.Exit(0);
}
一定限制應用程序的單一實例時要考慮安全性:
爲文章全文: https://blogs.msdn.microsoft.com/oldnewthing/20060620-13/?p=30813
我們使用一個名爲互斥用一個固定的名字來檢測 是否有另一個副本o f程序正在運行。但這也意味着攻擊者可以先創建互斥鎖,從而阻止我們的程序 運行!我怎樣才能防止這種類型的拒絕服務攻擊 ?
...
如果攻擊者在作爲 程序相同的安全上下文中運行的(或將要)在運行,那麼就沒有什麼可以做。 無論您想要確定您的程序的另一個副本 是否正在運行,「攻擊者」都可以模仿它。 由於它在正確的安全上下文中運行,因此它可以執行任何「真實」程序可以執行的操作。
...
顯然你不能保護自己的 相同的安全權限運行攻擊者,但你仍然可以保護自己免受 無特權的攻擊者在其它的安全權限運行。
嘗試在你的互斥量設置DACL,這裏的.NET方式: https://msdn.microsoft.com/en-us/library/system.security.accesscontrol.mutexsecurity(v=vs.110).aspx
- 1. 防止我的應用程序的多個實例
- 2. 防止啓動Java應用程序的多個實例
- 3. 如何防止Windows 10 XAML應用程序的多個實例?
- 4. 防止GTK應用程序的多個實例
- 5. 防止打開VB應用程序的多個實例
- 6. 防止Android應用程序開放的多個實例
- 7. 防止應用程序的多個實例
- 8. 防止android啓動應用程序的另一個實例
- 9. 跨平臺的方式,以防止打開應用程序的多個實例
- 10. PyQt防止應用程序的多個實例彈出相同的對話框
- 11. 如何防止我的macOS應用程序同時運行多個實例?
- 12. 打開文件時防止應用程序/活動的多個實例
- 13. 防止多實例應用程序環境中的重複條目
- 14. 如何防止HAProxy的多個實例?
- 15. jquery防止插件的多個實例
- 16. 防止對象的多個實例
- 17. 開始新的應用程序的實例,防止墓碑
- 18. 應用程序的多個實例
- 19. 應用程序的多個實例
- 20. Angularjs應用程序的多個實例
- 21. 如何防止我的應用程序創建新實例
- 22. 防止多個表單實例
- 23. 防止創建多個GUI實例
- 24. Docker中的多實例應用程序
- 25. Windows Phone多個應用程序實例
- 26. CreateProcessAsUser多個應用程序實例?
- 27. 多個Android應用程序實例
- 28. 如何防止vaadin應用程序實例干擾彼此?
- 29. 防止單個可執行文件的多個進程實例
- 30. .NET 4單一應用程序實例
我已經使用了幾年,但我現在希望更改爲基於互斥的解決方案。我有客戶報告這個問題,我懷疑它使用Remoting來做到這一點。 – 2009-06-18 08:28:43