感谢 Timiz0r ,我已经解决了这个问题,但这是多步骤的,所以我在这里详细说明完整的解决方案;原来的问题如下。首先,我将ILS功能改为:
Public Overrides Function InitializeLifetimeService() As Object
Return Nothing
End Function
然后我将其包含在计划以及 A 中。正如 Timiz0r 指出的那样, Form 继承了 MarshalByRefObject ,所以我不必在我的主类上包含一个Inherits语句(已经继承了< EM>表格的)。这是件大事,因为我最初没有包含它。接下来,我将AppDomain设置更改为:
Dim _ADomain As AppDomain = AppDomain.CreateDomain(Name)
Dim item As New A
item = CType(_ADomain.CreateInstanceAndUnwrap(GetType(A).Assembly.FullName, GetType(A).FullName), A)
通过这些更改,我现在可以根据需要使用DLL COM对象的单独实例。
我正在编写一个创建对象列表的应用程序,每个对象都引用一个DLL,并且每个对象都放在自己的AppDomain中,以防止DLL的实例相互干扰。采取另一种方式:
所有这些都很好,但是在设置域时,对InitializeLifetimeService的调用不受尊重......有点儿。等待默认的5分钟并调用我的A之后,我收到RemoteException错误。但是,添加一些Try / Catch语句,我发现我可以到达有问题的A,但它在尝试RaiseEvent时失败了。此外,似乎DLL对象本身被删除(或者它在尝试RaiseEvent时也会失败,它经常这样做)。
According to this article,AppDomain中的覆盖应自动创建一个未过期的租约。所以我试试这个:
_ADomain = AppDomain.CreateDomain(Name)
_ADomain.InitializeLifetimeService()
Dim item As A
item = CType(_ADomain.CreateInstanceAndUnwrap(GetType(A).Assembly.FullName, GetType(A).FullName), A)
没有骰子。根据{{3}},重写InitializeLifetimeService并返回Nothing将执行相同的操作。所以,在A类中,我做:
<SecurityPermissionAttribute(SecurityAction.Demand, _
Flags:=SecurityPermissionFlag.Infrastructure)> _
Public Overrides Function InitializeLifetimeService() As Object
Return Nothing
End Function
然而,没有任何反应。所以,经过another MSDN article,我试着设置一个长租约:
<SecurityPermissionAttribute(SecurityAction.Demand, _
Flags:=SecurityPermissionFlag.Infrastructure)> _
Public Overrides Function InitializeLifetimeService() As Object
Dim lease As ILease = CType(MyBase.InitializeLifetimeService(), ILease)
If lease.CurrentState = LeaseState.Initial Then
lease.InitialLeaseTime = TimeSpan.FromDays(5)
lease.SponsorshipTimeout = TimeSpan.FromDays(5)
lease.RenewOnCallTime = TimeSpan.FromDays(5)
End If
Return lease
End Function
部分问题似乎是我从未在初始状态下获得A.但是,如果我使用之前的设置并且总是返回Nothing,这应该不是问题,对吧?不幸的是,在做这类事情的例子方面几乎没有什么,所以我可能做错了。我很想知道如何处理这个问题,如果我无法解决这个问题,整个项目都是徒劳的。
我应该提到(第三方,闭源)DLL不可序列化,并且极不可能继承MarshalByRefObject。这就是为什么我将类放入AppDomain而不是DLL,但可能是问题的一部分。
yet another article可能是相关的,但设置与我正在做的不同,它适用于C#,我在脑海中转换为VB时遇到了麻烦。
答案 0 :(得分:4)
我已经有一段时间了,因为我实现了类似的东西,但我认为你需要A
,以及带有事件处理程序的类,继承自{{1}并提供一个不会过期的MarshalByRefObject
。
另外,如果在进行上述更改后ILease
方法中返回null并不起作用,请参阅我用来提供非过期ILease的代码:
InitializeLifetimeService
我无法记住使用上述代码而不是返回null的原因。我想我会提供它以防万一。