私はかなり大きなSOAPサービスと通信するためにDelphi XE2を使用しています。私は正常にwsdlをインポートし、すべてがうまく動作しています。しかし、私は同じようなコードをたくさん書いています。私は私のWebサービスを呼び出すジェネリックメソッドを持っていたいと思います。私はまた、今のように私のコードをマルチスレッド化するのは難しいと思います。なぜなら、私は各タイプの呼び出しごとにあまりにも多くのコードを書く必要があるからです。名前でSOAPメソッドを動的に呼び出す?
私は週末のプログラマーの方が多いので、デルファイの出入り口を習得するのは遠いですが、私は少なくとも私が望むことをするために使用しなければならないRTTIを公正に理解していると思います。
Webサービスには約700種類のメソッドがあり、それはかなり問題です。 WSDLから生成されたコードは以下のような方法があります。基本的には
function addPhone(const Params: addPhone): addPhoneResponse; stdcall;
function updatePhone(const Params: updatePhone): updatePhoneResponse; stdcall;
function getPhone(const Params: getPhone): getPhoneResponse; stdcall;
function removePhone(const Params: removePhone): removePhoneResponse; stdcall;
function listPhone(const Params: listPhone): listPhoneResponse; stdcall;
function addStuff(const Params: addStuff): addStuffResponse; stdcall;
function updateStuff(const Params: updateStuff): updateStuffResponse; stdcall;
...
... about 700 more of the above
、処理することができるものの約700の異なるタイプがあり、そしてそれらすべてのために、更新、追加、取得、削除、およびリストの方法があります。呼び出しごとに、対応するクラスがSOAPリクエストのパラメータとして使用されます。上記のように、対応するクラスもあります。
クラスは(非常に単純化された)のようになります。
addStuff = class
private
FStuff: string;
published
property stuff: string Index (IS_UNQL) read FStuff write FStuff;
end;
私は、Webサービスを呼び出すときに、私は、たとえば行います
procedure CreateStuff;
var
req: addStuff;
res: addStuffResponse;
soap: MyWebServicePort;
begin
// Use the function in the wsdl-generated code to create HTTPRIO
soap := GetMyWebServicePort(false,'',nil);
// Create Parameter Object
req := addPhone.Create;
req.stuff := 'test';
// Send the SOAP Request
res := soap.addStuff(req);
end;
(はい、私は試してみる必要があります知っています..finally and Free in there :-))
コード内のどこか別のメソッドを呼び出す必要があります。
procedure listStuff;
var
req: listStuff;
res: listStuffResponse;
soap: MyWebServicePort;
begin
// Use the function in the wsdl-generated code to create HTTPRIO
soap := GetMyWebServicePort(false,'',nil);
// Create Parameter Object
req := listPhone.Create;
req.stuff := 'test2';
// Send the SOAP Request
res := soap.listStuff(req);
end;
私はパラメータが常に私が呼び出すメソッドに相当する名前のクラスであることを知っているので、私は動的に呼び出しを呼び出すために以下のメタコードのようにすることができます。私はそれはいくつかのRTTIの魔法を必要と推測するが、私はそれを行うための方法を見つけることができたhave'nt:誰がどのように私のアイデアを持っています
soapRequest(VarOfTypeAddStuff,VarOfTypeAddStuffResponse)
soapRequest(VarOfTypeListStuff,VarOfTypeListStuffResponse)
...
:
procedure soapRequest(Param: Something; var Response: Something);
begin
soap := GetMyWebServicePort(false,'',nil);
Response := soap.DynamicInvoke(Param.ClassName, Param);
end
その後、私はのような何かを行うことができますWebサービスへの呼び出しを簡素化できますか?
誰もがそのような思い付くかどうかを確認するために興味深いものになるが、あなたを「隠す」の詳細を持っているように私は単なるラッパー・ルーチンを書きました。 – mj2008
@dahook:非常にうまく書かれた最初の投稿。投票した。ようこそ。 – RobertFrank