私はこれを数回行わなければならず、多くの異なる解決策を研究してきました。
私が最もエレガントで簡単に実行できるソリューションは、そのように実装できます。
1.シンプルなインターフェースを作成できるプロジェクトを作成する
インターフェースには、呼び出したいメンバーの署名が含まれます。
public interface IExampleProxy
{
string HelloWorld( string name );
}
このプロジェクトをクリーンで軽量に保つことが重要です。これは、両方AppDomain
が参照できるプロジェクトであり、参照できないようにします。Assembly
、クライアントアセンブリから別のドメインにロードする必要がをます。
2.次に、個別にロードするコードを含むプロジェクトを作成しますAppDomain
。
このプロジェクトは、クライアントプロジェクトと同様にプロキシプロジェクトを参照し、インターフェイスを実装します。
public interface Example : MarshalByRefObject, IExampleProxy
{
public string HelloWorld( string name )
{
return $"Hello '{ name }'";
}
}
3.次に、クライアントプロジェクトで、別のにコードをロードしますAppDomain
。
そこで、新しいを作成しますAppDomain
。アセンブリ参照のベースの場所を指定できます。プローブは、GACと現在のディレクトリおよびAppDomain
ベースロケーションにある依存アセンブリをチェックします。
// set up domain and create
AppDomainSetup domaininfo = new AppDomainSetup
{
ApplicationBase = System.Environment.CurrentDirectory
};
Evidence adevidence = AppDomain.CurrentDomain.Evidence;
AppDomain exampleDomain = AppDomain.CreateDomain("Example", adevidence, domaininfo);
// assembly ant data names
var assemblyName = "<AssemblyName>, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null|<keyIfSigned>";
var exampleTypeName = "Example";
// Optional - get a reflection only assembly type reference
var @type = Assembly.ReflectionOnlyLoad( assemblyName ).GetType( exampleTypeName );
// create a instance of the `Example` and assign to proxy type variable
IExampleProxy proxy= ( IExampleProxy )exampleDomain.CreateInstanceAndUnwrap( assemblyName, exampleTypeName );
// Optional - if you got a type ref
IExampleProxy proxy= ( IExampleProxy )exampleDomain.CreateInstanceAndUnwrap( @type.Assembly.Name, @type.Name );
// call any members you wish
var stringFromOtherAd = proxy.HelloWorld( "Tommy" );
// unload the `AppDomain`
AppDomain.Unload( exampleDomain );
必要に応じて、アセンブリをロードするにはさまざまな方法があります。このソリューションでは別の方法を使用できます。アセンブリ修飾名がある場合CreateInstanceAndUnwrap
は、アセンブリバイトをロードして型をインスタンス化object
し、プロキシ型に単純にキャストできるを返すため、または厳密に型指定されたコードにキャストできない場合は、動的言語ランタイムを使用して、返されたオブジェクトをdynamic
型付き変数に割り当て、そのメンバーを直接呼び出すだけです。
そこにあります。
これにより、クライアントプロジェクトが別の参照を持たないアセンブリをロードできます。 AppDomain
メンバーをクライアントから呼び出すことができます。
テストするには、Visual Studioの[モジュール]ウィンドウを使用します。クライアントアセンブリドメインと、そのドメインに読み込まれているすべてのモジュール、および新しいアプリドメインと、そのドメインに読み込まれているアセンブリまたはモジュールが表示されます。
重要なのは、どちらかがコード化されていることを確認することです MarshalByRefObject
か、シリアル化。
`MarshalByRefObjectを使用すると、ドメインの存続期間を設定できます。たとえば、プロキシが20分以内に呼び出されなかった場合にドメインを破棄したいとします。
これがお役に立てば幸いです。