我在過去用Delphi編寫過Web服務,但大部分都非常簡單,只需要一些參數並向客戶端返回一個值。我正在處理的一項新服務要求我能夠發送和接收復雜類型。請看下面的類型在我的代碼中定義:TRemotable Descendant父成員不包含在由delphi web服務生成的WSDL中
TBaseRequest = Class(TRemotable)
private
FUsername: string;
FPassword: string;
published
Property Username: String read FUsername write FUsername;
Property Password: String read FPassword write FPassword;
End;
TBaseResponse = Class(TRemotable)
private
FStatusMessage: string;
FStatusCode: integer;
published
Property StatusMessage: string read FStatusMessage write FStatusMessage;
Property StatusCode: integer read FStatusCode write FStatusCode;
End;
TSepecialRequest = class(TBaseRequest)
private
FExtraParam: string;
published
Property ExtraParam: String read FExtraParam write FExtraParam;
end;
TSpecialResponse = class(TBaseResponse)
private
FExtraResult: string;
published
Property ExtraResult: String read FExtraResultwrite FExtraResult;
end;
所有這些類都與RemClassRegistry.RegisterXSClass registerd。
現在我也得到了接口中定義此WebService如下功能:
function SpecialMethod(request:TSepecialRequest): TSpecialResponse;
在服務代碼中,我可以很容易地訪問諸如用戶名和密碼的父類的屬性,但是如果我們看一下在生成的WSDL中,我們看到TSpecialRequest和TSpecialResponse類成員包含在模式部分中。
<xs:complexType name="TSpecialRequest">
<xs:complexContent>
<xs:extension base="TBaseRequest">
<xs:sequence>
<xs:element name="ExtraParam" type="xs:string"/>
</xs:sequence>
</xs:extension>
</xs:complexContent>
</xs:complexType>
<xs:complexType name="TSpecialResponse">
<xs:complexContent>
<xs:extension base="TBaseResponse">
<xs:sequence>
<xs:element name="ExtraResult" type="xs:string"/>
</xs:sequence>
</xs:extension>
</xs:complexContent>
</xs:complexType>
在WSDL此模式片段表明TSpecials是TBASE類的一些推廣和一切都很好除了TBASE類的能解密中不包括的模式。我希望這裏也有一個這樣的部分,但它缺失:
<xs:complexType name="TBaseRequest">
<xs:sequence>
<xs:element name="Username" type="xs:string"/>
<xs:element name="Password" type="xs:string"/>
</xs:sequence>
</xs:complexType>
<xs:complexType name="TBaseResponse">
<xs:sequence>
<xs:element name="StatusMessage" type="xs:string"/>
<xs:element name="StatusCode" type="xs:int"/>
</xs:sequence>
</xs:complexType>
但是,這個模式片段從生成的WSDL中缺少。這意味着任何嘗試使用此服務的客戶端將無法正確生成請求或解釋響應。例如,如果我試圖將geneated WSDL裝入WSDL進口商德爾福2009年,我得到了以下類:
TSpecialRequest = class(TRemotable)
private
FExtraParam: WideString;
published
property ExtraParam: WideString read FExtraParam write FExtraParam;
end;
TSpecialResponse = class(TRemotable)
private
FStatusMessage: WideString;
FStatusCode: Integer;
published
property StatusMessag: WideString read FStatusMessage write FStatusMessage;
property StatusCode: Integer read FStatusCode write FStatusCode;
end;
的結果是,客戶端代碼是不能做的事情一樣設定的用戶名和密碼成員應該是TSpecialRequest的一部分。
有沒有人有任何線索爲什麼會發生這種情況,或者我可以做些什麼?
如何使用Delphi IDE從Delphi類源代碼創建WSDL?直到現在我還沒有看到用Delphi 2009 Enterprise做這件事的方法(也許我應該讓它成爲一個新的SO問題:) – mjn 2010-06-04 17:42:15
它的離題和應該是一個新問題,但基本上當你創建一個SOAP服務器應用程序項目時將在其上添加一個TWSDLHTMLPublish組件的數據模塊。這個組件通過註冊的接口和遠程類,並添加生成一個WSDL。要訪問WSDL,必須將項目的已編譯DLL加載到ISAPI Web服務器(如IIS)中,然後使用URL(如http://server.com/project.dll),您將看到一個描述該服務的HTML頁面和鏈接到生成的WSDL。結果:基於在delphi代碼中定義的類的WSDL。 – 2010-06-05 21:09:22