アウトオブプロセス ActiveX の SideBySide のシミュレーション
-
20-09-2019 - |
質問
私たちは、クライアント側の比較的複雑なアプリケーション (ActiveX / .net / Delphi / C++ / COM) を SxS を使用して適応させ、非管理展開と製品の古いバージョンからの分離を実現しています。
プロセスで使用するすべてのライブラリを記述したマニフェスト ファイルを登録せずに作成することで、.net ui、Delphi ui、proc で使用する COM サーバーなど、ほぼすべての in proc コンポーネントでこの目標を達成できました。 (ほぼ) いずれかのコンポーネントのクライアント上で。
そして、ここにほぼ部分があります:現時点では、アプリケーションは (C++ 部分から) プロセス外 ActiveX サーバー (Delphi ActiveX EXE) を呼び出し、そのアプリケーション自体がプロセス外 ActiveX サーバーの別のセット (サードパーティのプラグイン、ここには何でも入ります、Delphi、 C++、プロシージャ ActiveX EXE の外にあり、インターフェイスを実装しているものであれば何でも)。
みなさんご存じのとおり SxS は、プロセス外の ActiveX サーバーをサポートしません。そして、これらのオブジェクトをメインプロセスの proc com サーバーのように使用することはできません。そのためには、アプリケーションの大幅な書き換えが必要になり、最悪の場合、サードパーティのツールやベンダーによって使用される公開 API の中断が必要になるためです。許されない休憩。
私たちはつまずいてしまいました この記事 これは、別のプロセスで実行されている Internet Explorer ウィンドウから IHTMLDocument2 を抽出する方法を説明しています。そこで私たちはこのアプローチを思いつきました。
ActiveX をインプロセス サーバーとして実行するセカンダリ サテライト アプリケーション/プロセスを作成します。それでは、使用します LresultFromObject そして オブジェクトからの結果 ActiveX オブジェクトの参照をサテライト アプリケーションからメイン アプリケーション プロセスに転送します。サテライト アプリケーションには、SxS モードでの実行を可能にする独自のマニフェスト ファイルがあります。
この Delphi ActiveX EXE とサードパーティの AciveX EXE プラグイン間の通信にも同じアプローチが取られます。
代替ソリューションがありますが、現時点では、.net リモーティング クラスと .net com プロキシ クラスを使用して、com リクエストを .net に変換することで 2 つのプロセス間の通信チャネルを開くという上記の提案されたソリューションよりは好まれません。リモート処理を実行し、2 番目のプロセスで com に戻ります。
そこで次のような質問が生じます。
- このアプローチについてどう思いますか?
- 問題に対するより良い解決策はありますか?
解決
することは可能です。何が必要とされているか:
- アプリケーションは、COM に依存するのではなく、サーバー自体を起動する必要があります。レジストリによって提供される追加の間接指定は必要ありません。CreateProcess() を使用するだけです。
- サーバーは、CoRegisterClassObject() を使用して main() メソッドにクラス ファクトリを登録する必要があります。
- 重要:各ファクトリに使用される CLSID は、サービス インスタンスごとに一意になるように変更する必要があります。これにより、クライアントが正しいサーバーに接続できるようになります。プロセス ID とクラス ファクトリ CLSID を単に XOR します。クライアントはプロセス ID も知っているため、同じ変更を行うことができます。
- アプリケーションは、Sleep() 呼び出しを含むループ内で CoCreateInstance() を呼び出して、オブジェクト ファクトリが表示されるのを待つ必要があります。少なくとも 60 秒が経過するまでは失敗を宣言しないでください (これは私を悩ませました)。
- アプリケーションとサーバーの両方に、
<file>
各プロキシ/スタブ DLL の要素と<comInterfaceExternProxyStub>
リモートされる各インターフェイスの要素。
他のヒント
アレックス、
nobugzは右である、あなたはDelphiのオートメーションexeファイルの現在実行中のプロセスからのCOMオブジェクトのインスタンスを作成するために、実行中のオブジェクトテーブルにアクセスすることができます。
しかし、私は私が説明カント大きな問題を発見しました。この方法で作業するとき、私は唯一のバリアント発送方法を経由してオブジェクトにアクセスすることができます。
私のActive Xのexeファイルが登録されていない場合、私はインターフェイスを介してインスタンスにオブジェクトをしようとすると、基本的に、私は「インターフェイスがサポートされていません」というエラーが表示されます。例:
は、WebUpdate:IAutomation;
は、WebUpdate:= CoAutomation.Create。 < - 文句を言わない作業エラー
<時間>は、WebUpdate:バリアント;
は、WebUpdate:= CreateOleObject( 'WebUpdate.Automation')。 < - 作品ファイン
私が登録した場合は、問題REGSERVER使用してActive Xのexeファイルが消える!!
ゴー図!