22

假设我有两个用 C# 编写的应用程序。第一个是引发名为“OnEmailSent”的事件的第三方应用程序。

第二个是我编写的自定义应用程序,我想以某种方式订阅第一个应用程序的“OnEmailSent”。

有什么方法可以将第二个应用程序附加到第一个应用程序的实例以侦听“OnEmailSent”事件?


因此,为了进一步澄清,我的具体情况是我们有一个用 c# 编写的自定义第三方应用程序,它引发了一个“OnEmailSent”事件。我们可以使用反射器看到事件存在。

我们想要做的是在该组件发送电子邮件时执行一些其他操作。

我们能想到的最有效的方法是能够使用安德斯建议的某种形式的 IPC,并监听第三方组件引发的 OnEmailSent 事件。

因为该组件是用 C# 编写的,所以我们正在考虑编写另一个 C# 应用程序,该应用程序可以将自己附加到正在执行的进程中,并且当它检测到 OnEmailSent 事件已被引发时,它将执行它自己的事件处理代码。


我可能遗漏了一些东西,但根据我对远程处理工作原理的理解,需要有一个服务器来定义客户端可以订阅的某种合同。

我更多地考虑有人编写了一个独立的应用程序,例如 Outlook,它公开了我想从另一个应用程序订阅的事件。

我想我正在考虑的场景是 .net 调试器以及它如何附加到执行程序集以在运行时检查代码。

4

6 回答 6

14

In order for two applications (separate processes) to exchange events, they must agree on how these events are communicated. There are many different ways of doing this, and exactly which method to use may depend on architecture and context. The general term for this kind of information exchange between processes is Inter-process Communication (IPC). There exists many standard ways of doing IPC, the most common being files, pipes, (network) sockets, remote procedure calls (RPC) and shared memory. On Windows it's also common to use window messages.

I am not sure how this works for .NET/C# applications on Windows, but in native Win32 applications you can hook on to the message loop of external processes and "spy" on the messages they are sending. If your program generates a message event when the desired function is called, this could be a way to detect it.

If you are implementing both applications yourself you can chose to use any IPC method you prefer. Network sockets and higher-level socket-based protocols like HTTP, XML-RPC and SOAP are very popular these days, as they allow you do run the applications on different physical machines as well (given that they are connected via a network).

于 2008-08-20T13:44:10.607 回答
3

您可以尝试Managed Spy并进行编程访问ManagedSpyLib

ManagedSpyLib 引入了一个名为 ControlProxy 的类。ControlProxy 是 System.Windows.Forms.Control 在另一个进程中的表示。ControlProxy 允许您获取或设置属性并订阅事件,就好像您在目标进程中运行一样。使用 ManagedSpyLib 进行自动化测试、事件记录以实现兼容性、跨进程通信或白盒测试。

但这可能对您不起作用,取决于 ControlProxy 是否可以以某种方式访问​​您在第三方应用程序中所追求的事件。

您也可以使用Reflexil

Reflexil 允许通过使用由 Jb EVAIN 编写的强大的 Mono.Cecil 库来修改 IL。Reflexil 作为 Reflector 插件运行,特别针对 IL 代码处理。它通过提出一个完整的指令编辑器并允许 C#/VB.NET 代码注入来实现这一点。

于 2008-08-20T13:12:46.563 回答
1

您可以使用远程处理或 WCF。请参阅http://msdn.microsoft.com/en-us/library/aa730857(VS.80).aspx#netremotewcf_topic7

于 2008-08-20T13:07:15.017 回答
0

来自该第三方应用程序的 OnEmailSent 事件的性质是什么?我的意思是,你怎么知道应用程序正在触发这样的事件?

如果打算进行进程间通信,你应该问自己的第一个问题是:真的有必要吗?

Without questioning your motives, if you really need to do interprocess communication, you will need some sort of mechanism. The list is long, very long. From simple WM_DATA messages to custom TCP protocols to very complex Web services requiring additional infrastructures.

This brings the question, what is it you are trying to do exactly? What is this third party application you have no control over?

Also, the debugger has a very invasive way of debugging processes. Don't expect that to be the standard interprocess mechanism used by all other applications. As a matter of fact, it isn't.

于 2008-08-20T13:21:01.957 回答
0

You can implement a similar scenario with SQL Server 2005 query change notifications by maintaing a persistent SqlConnection with a .NET application that blocks until data changes in the database.

See http://www.code-magazine.com/article.aspx?quickid=0605061.

于 2008-08-20T13:30:23.573 回答
0

also WM_COPYDATA might be possible, see https://social.msdn.microsoft.com/Forums/en-US/eb5dab00-b596-49ad-92b0-b8dee90e24c8/wmcopydata-event-to-receive-data-in-form-application?forum=winforms I'm using it for similar Purose (to notify that options have been changed)

In our C++/Cli-scenario (MFC-)programs communicate vith WM_COPYDATA with Information-String in COPYDATASTRUCT-Member lpData (Parameterlist like "Caller=xyz Receiver=abc Job=dosomething"). also a C#-App can receive WM_COPYDATA-messages as shown in the link. Sending WM_COPYDATA from C# (to known Mainframe-Handle) is done by a cpp/cli-Assembly, (I didnt proove how sending WMCOPYDATA can bei done in C#).

PS in Cpp/Cli we send AfxGetMainWnd()->m_hWnd as WPARAM of WMCOPYDATA-Message and in C# (WndProc) m.WParam can be used as adress to send WM_COPYDATA

于 2021-11-17T14:42:55.093 回答