如何通过命令行将命令发送到正在运行的应用程序

时间:2011-11-10 04:16:56

标签: vb.net

药膏!我想使用命令行参数退出我的GUI应用程序(vb.net 4)。我应该从命令行发送这个:

myapplication.exe quit

- 应该退出已经运行的应用程序实例。 现在,我有一个互斥锁检测,这样我一次只能运行一个应用程序实例。似乎如果我发送命令行,它将无法在已经运行的应用程序上运行;它只适用于正在发射的那个。

3 个答案:

答案 0 :(得分:1)

轻松向运行的应用程序实例发送消息

大家好!找到这篇不错的帖子here之后,寻找单个应用程序对第​​一个实例做一件事的方法,但第二个实例会导致第一个实例做其他事情。

这个值是你可以(使用你自己的额外编程)使用它来实现将命令行参数发送到正在运行的应用程序的效果。您实际上将使用应用程序的第二个实例将命令行参数作为消息发送到第一个实例。它在我的Windows XP上运行正常,但我对vb.net很新,所以如果你有任何改进,我想知道!

所以我改编了 anoriginalidea&#39> 很好的例子,下面是我的结果。这是这一切的基础,所以你只看到这个过程的要点。

它的工作原理如下:

  1. 首先,将此模块粘贴在您的应用程序中。
  2. 然后启动app1
  3. 您将收到一条消息," InterCom Server Reporting for Duty!"
  4. 现在启动app2 - 你会收到一条消息(它实际上来自app1!),说"我的名字是 真的鲍勃!"让你知道该功能被解雇了。
  5. 然后app2将退出(你告诉它在sub main中)和 然后app1将退出becuase app2告诉它退出InterComClient() 被叫了。
  6. 首先将此添加为您的子主 互斥锁将检查您的应用程序是否已经运行。

    Public Sub Main()
        Dim createdNew As Boolean = True
        Using mutex As New Mutex(True, "TestForKalatorMutexProcess", createdNew)
            If createdNew Then
                InterComServer()
                'BE SURE TO CHANGE myApplication TO YOUR PRIMARY FORM!
                Application.Run(new myApplication)
            Else
                InterComClient()
                application.exit()
            End If
        End Using
    End Sub
    

    现在将其添加到应用程序的模块中

    Imports System.Runtime.Remoting
    Imports System.Runtime.Remoting.Channels
    Imports System.Runtime.Remoting.Channels.ipc 'You have to add this as a reference!
    
    Public Module intercom
    #Region "-------------InterShared-------------------------------------"
    Public Interface ICommunicationService
        Sub SaySomething(ByVal text As String)
    End Interface
    #End Region
    
    #Region "-------------InterComClient-------------------------------------"
    'This will run on the second instance
    Public Sub InterComClient(ByRef intercommessage As String)
        Try
            Dim ipcCh As New IpcChannel("myClient")
            ChannelServices.RegisterChannel(ipcCh, False)
            Dim obj As ICommunicationService = DirectCast(Activator.GetObject(GetType(ICommunicationService), "ipc://IPChannelName/SreeniRemoteObj"), ICommunicationService)
            obj.SaySomething(intercommessage)
            Thread.Sleep(1000)
            ChannelServices.UnregisterChannel(ipcCh)
        Catch ex As Exception
            'If you use this as a way to exit your application, be sure to discard this exception
            'because the InterCom Server won't be running to receive the closing of the channel
            'and it will throw a "Pipe Ended" error that can't be solved.
            'To "discard" the error, simply catch it and don't do anything.
            'Dim errmsg As New Messenger("Exception in InterComClient" & vbCr & ex.Message)
        End Try
    End Sub
    #End Region
    
    #Region "-------------InterComServer-------------------------------------"
    Public Class CommunicationService
        Inherits MarshalByRefObject
        Implements ICommunicationService
        Public Sub SaySomething(ByVal whatmessage As String) Implements ICommunicationService.SaySomething
            msgbox("InterCom Client Heard this : " & whatmessage)
            Application.exit
        End Sub
    End Class
    
    Public Sub InterComServer()
        Dim ipcCh As IpcChannel
        ipcCh = New IpcChannel("IPChannelName")
        ChannelServices.RegisterChannel(ipcCh, False)
        RemotingConfiguration.RegisterWellKnownServiceType(GetType(CommunicationService), "SreeniRemoteObj", WellKnownObjectMode.Singleton)
        MsgBox("InterCom Server Reporting for Duty!")
    End Sub
    #End Region
    
    End Module
    

    <强> [更新]

    对于任何人来说,我已经在我的应用程序中使用了这段时间了一段时间,它看起来效果很好。

答案 1 :(得分:0)

如果您保持命令行打开输入并且只是按下Enter / Return键,该怎么办?然后,您可以检查是否通过了quit或其他程序命令。

答案 2 :(得分:0)

您需要的是设置某种形式的进程间通信。使用命令行参数启动第二个实例时,由于您的单实例互斥代码,它在终止自身之前,需要通知第一个实例并将参数传递给它。

现在可以说,如果你正在处理的 only 命令行参数将要退出,那么你可以改为在系统中运行正在运行的进程(参见System.Diagnotics.Process)并杀死第一个实例。