|
16番会議室「玉石混淆みんなで作るSample蔵」に寄せられたサンプル
"DCOM(Remote Automation)をやる"
なんだかよくわからないものの筆頭である DCOM をやってみました.
1.用意したもの
Delphi3.1J Pro版 C/S版は要りません
WindowsNT4.0(SP3) サーバ(95でもできるらしい)
Windows95 クライアント.OSR2でなくてもよい
95用DCOMモジュールをwww.microsoft.com/japanから拾ってくる
マシン同士はTCP/IPでつないである.
2.下準備
・ クライアントの95にDCOMをインストールする.既に入っていれば不要.
<レジストリの確認>
HKEY_LOCAL_MACHINE
SOFTWARE
Microsoft
OLE
EnableDCOM = "Y"
EnableRemoteConnection = "Y"
・ サーバにするNTのRPC Service,DCOMを有効にする
<レジストリの確認>
HKEY_LOCAL_MACHINE
SOFTWARE
Microsoft
OLE
EnableDCOM = "Y"
EnableRemoteConnection = "Y"
Dcomcnfg.exeを使う.なんか動きがいまいちだけど(-_-;)
3.DCOMサーバアプリケーションの作成
・普通にアプリケーションの新規作成をする
・オートメーションオブジェクトの新規作成をする
・タイプライブラリエディタが出てくるので,適当にメソッドの宣言を
作り,更新ボタンを押すとXXXX_TLB.pasとUnit2.pasが出来る.
・下記の例のようにサーバとなるクラス(IMyServerはIDispatchの派生)の
中身を詰め込む.
・コンパイルしてサーバとクライアント両方のマシン上で一回実行して
レジストリにオブジェクトの情報を登録させる
・IDispatch(OLEAutomation)に関する引数の型の制限に注意.
・クライアントが誰でも実行できるようにするには,Dcomcnfg.exeでセキュリ
ティの設定をしただけでは駄目.サーバの実行をAdministratorsグループの
ユーザーに決めておくと,できる.
・ciMultiInstanceの場合,上記の場合サーバプロセスはひとつだけ起動する.
複数のマシンから別々のアカウントでログインしてもサーバプロセスは1個.
一方TMyServerのインスタンスは,Create要求の数だけ生成される.
・ciSingleInstanceだと,クライアントアプリのインスタンスごとに
それぞれサーバが立ち上がるのをタスクマネージャで見れる.
・コンパネ/サービス/RPC Serviceをダブルクリックして「デスクトップとの
対話」を許可しておくと,サーバが走っている間はサーバマシンの画面に
サーバーアプリのフォームが現れ,さわることが可能になる.
・念のため NT をリブート.
・スレッドがどうのこうのというのはまだ意味不明...
--------------------------------------------------------------------------
unit unit1
省略 Editを一個貼り付けておく
--------------------------------------------------------------------------
unit Unit2;
interface
uses
Windows, SysUtils, ComObj, ActiveX, MyServerPrj_TLB, Forms;
type
TMyServer = class(TAutoObject, IMyServer)
protected
procedure Beep; safecall;
procedure GetText(out S: WideString); safecall;
end;
implementation
uses ComServ, Unit1;
var
Count: integer;
procedure TMyServer.Beep;
begin
MessageBeep(0);
end;
procedure TMyServer.GetText(out S: WideString);
begin
inc(Count);
S := InttoStr(Count) + ' time(s) of GetText.' + Form1.Edit1.Text;
end;
initialization
TAutoObjectFactory.Create(
ComServer, TMyServer, Class_MyServer, ciMultiInstance);
end.
------------------------------------------------------------------------
unit MyServerPrj_TLB;
省略
------------------------------------------------------------------------
4.クライアントアプリケーションの作成
・普通にアプリケーションの新規作成をする.
・サーバで使っているXXXX_TLBユニットをusesして新しいインターフェース
宣言を取り込み,下記のようにDCOMオブジェクトの生成とメソッド呼出をする
・できたクライアントアプリをクライアントマシンで実行する.
-----------------------------------------------------------------------
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
ComObj, StdCtrls, MyServerPrj_TLB;
type
TForm1 = class(TForm)
Button1: TButton;
Label1: TLabel;
Edit1: TEdit; // DCOMサーバを走らせるコンピュータ名を書き込む
Label2: TLabel;
procedure Button1Click(Sender: TObject);
private
{ Private 宣言 }
Obj: IUnknown; // クライアントを閉じるまでオブジェクトを保持
public
{ Public 宣言 }
end;
var
Form1: TForm1;
implementation
{$R *.DFM}
procedure TForm1.Button1Click(Sender: TObject);
var
S: WideString;
Intf: IMyServer;
begin
if Obj = nil then begin
Obj := CreateRemoteComObject( Edit1.Text,
ProgIDToClassID('MyServerPrj.MyServer') );
end;
Intf := Obj as IMyServer;
Intf.Beep; // サーバのマシンでBeep音が鳴る!!
Intf.GetText(S); // ボタンを押した回数がサーバに蓄えられている
Label1.Caption := S;
end;
end.
--------------------------------------------------------------------------
5.余談
IDispatchでないとクライアントでInterfaceが取得できないというのは
なにか忘れているせいだと思うが,C/Sに付いてるClientDataSetコンポで使う
IProviderもIDispatchの派生にしてある所を見ると理由があるのだろう.
参考書には肝心なこと(最低何と何をすればDCOMできるのか?)がさっぱり
書いてないのでほとんど無意味(-_-;
「DCOMデプロイメントガイド」翔泳社
「DCOMガイドブック」オーム社
TN(CQJ01721)
Original document by TN 氏 ID:(CQJ01721)
ここにあるドキュメントは NIFTY SERVEの Delphi Users' Forum の16番会議室「玉石混淆みんなで作るSample蔵」に投稿されたサンプルです。これらのサンプルはボーランド株式会社がサポートする公式のものではありません。また、必ずしも動作が検証されているものではありません。これらのサンプルを使用したことに起因するいかなる損害も投稿者、およびフォーラムスタッフはその責めを負いません。使用者のリスクの範疇でご使用下さい。
Copyright 1996-2002 Delphi Users' Forum
|