2014-10-09 297 views
2

我有一個.net WinForms應用程序,它將插件(dll)加載到它們自己的AppDomain中,每個dll都使用domain.CreateInstanceAndUnwrap()獲取它自己的AppDomain。我想要的是,這些對象永遠保持連接(直到應用程序停止)。
InitialLeaseTime是5分鐘,但我找不到方法來改變它。 .. 我嘗試遠程對象的覆蓋InitializeLifetimeService():MarshalByRefObject生命週期

Public Overrides Function InitializeLifetimeService() As Object 
    Return Nothing 
End Function 

在這裏,我得到一個Typeload的異常,稱這將打破繼承規則。 添加

<SecurityPermissionAttribute(SecurityAction.Demand, Flags:=SecurityPermissionFlag.Infrastructure)> 
<SecuritySafeCritical> 

不會改變任何東西。

然後:

​​3210

不這樣做既沒有,因爲保薦人(這裏沒有顯示)的莫名其妙的更新()方法不會被調用。

調用

lease.Renew(TimeSpan.FromMinutes(300)) 

直接改變CurrentLeaseTime不過租約的不InitialLeaseTime。

最後我打過電話的共享(靜態)屬性LeaseTime,這實際上導致了在租賃期開始CurrentLeaseTime的變化,但再次的InitialLeaseTime,這似乎是在5分鐘後結束,我的遠程對象被gc化:

LifetimeServices.RenewOnCallTime = System.TimeSpan.FromMinutes(300) 

任何幫助表示讚賞, Thx!

回答

2

不知道發生了什麼事情,但在這裏它是如何工作

var sponsor = new Sponsor(); // manages lifetime of the object in otherDomain 
var target = otherDomain.CreateInstanceFromAndUnwrap(assemblyFilename, typeFullName) 
    as MarshalByRefObject; 

var lease = target.InitializeLifetimeService() as ILease; 
lease.Register(sponsor); 

在這種情況下,您保留引用目標(明顯)和贊助這是唯一重要的。贊助商是管理訂閱類:

class Sponsor : MarshalByRefObject, ISponsor 
{ 
    public bool Release { get; set; } 

    public TimeSpan Renewal(ILease lease) 
    { 
     // if any of these cases is true 
     if (lease == null || lease.CurrentState != LeaseState.Renewing || Release) 
      return TimeSpan.Zero; // don't renew 
     return TimeSpan.FromSeconds(1); // renew for a second, or however long u want 
    } 
} 

當你用它做,簡單的設置發佈到true的贊助商,讓他走了。您也可以通過在贊助商上實施IDisposable來解決這個問題,如果這讓您感到尷尬。

+0

嗨,謝謝!使用你的解決方案,贊助商的Renewal()方法現在被調用。但是當我返回TimeSpan.FromHours(1)時,它有時會起作用,有時不起作用。我已經嘗試了很多,但無法弄清楚...... btw:lease.CurrentState在續訂()內始終處於「活動」狀態,而不是「續訂」。 – Lukas 2014-10-09 17:53:43

+0

更新:現在工作。我引用了遠程對象中的其他對象,這些對象也從MarshalByRefObject繼承。這些物體的租賃也必須更新。 – Lukas 2014-10-10 19:17:01