如何在Delphi中设置SOAP元素的属性?

时间:2009-05-11 17:09:16

标签: web-services delphi soap attributes delphi-2009

在SOAP客户端请求中,标题需要以下行:

<NS2:Header Name="Foo">Bar<NS2:Header>

所以我写了一个有两个字符串属性的类:

  • Content属性 - 用于元素的值(“Bar”)
  • Name属性 - 用于属性的值(“Foo”)

Name属性的AS_ATTRIBUTE标志应指示它是XML“属性”。

   Header = class(TSoapHeader)
   private
     FContent: string;
     FName: string;
   published
     property Content: string read FContent write FContent;
     property Name: string read FName write FName stored AS_ATTRIBUTE;
   end;

并注册

   RemClassRegistry.RegisterXSClass(Header, MY_URI);
   RemClassRegistry.RegisterSerializeOptions(Header, [xoLiteralParam, 
xoSimpleTypeWrapper]);

xoLiteralTypWrapper选项指示该类应该只“包装”元素中的Content属性,而不是为其添加嵌套元素。

对于Name:=“Foo”和Content:=“Bar”,这将是SOAP请求中的结果XML代码:

<NS2:Header Name="Foo">
   <Content xsi:type="xsd:string">Bar</Content>
</NS2:Header>

属性位于正确的位置,但内容值位于嵌套标记中,不应该在此处。如果我从类定义中删除Name属性,则Content属性看起来很好,因为它是元素内容,如下所示:

<NS2:Header>Bar</NS2:Header>

这看起来像两个要求之间的冲突 - 如果我有 属性,我不会得到xoSimpleTypeWrapper样式。

1 个答案:

答案 0 :(得分:3)

我没试过这个,所以这是一个推测。尝试重写ObjectToSOAP和SOAPToObject方法。在帮助文件中,它说

  

覆盖ObjectToSOAP以自定义   你的应用程序转换的方式   TSOAPHeader后代的SOAP   表示。

同样,我没有在编译器上尝试过这个,但它可能如下所示:

function Header.ObjectToSOAP(RootNode, ParentNode: IXMLNode; 
  const ObjConverter: IObjConverter; const Name, URI: InvString; 
  ObjConvOpts: TObjectConvertOptions; out RefID: InvString): IXMLNode;  
begin 
  ObjConvOpts := ObjConvOpts + [ocoDontSerializeProps]; 
  Result := inherited ObjectToSOAP(RootNode, ParentNode, ObjConverter, Name, URI, ObjConvOpts, RefID); 
  Result.Text := FContent; 
  Result.Attributes['Name'] := FName;
end;