【问题标题】:How do I include a CDATA section in a WCF client webservice call in .Net?如何在 .Net 中的 WCF 客户端 Web 服务调用中包含 CDATA 部分?
【发布时间】:2015-06-11 07:02:06
【问题描述】:

我被要求创建一个 wcf 客户端来访问我无法修改的自定义 java web 服务。我需要使用 webservice 方法,例如:

<s:Envelope xmlns:s="http://www.w3.org/2003/05/soap-envelope">
  <s:Body xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
    <createDocument xmlns="http://www.dummyUrl.com/javaws">
      <version>
        ...
        <metadata>
          <attribute name="ConfigName">ConfigurationTemplateForModuleX</attribute>
          <attribute name="ConfigValue">This is a configuration string</attribute>
        </metadata>
        ...
      </version>
    </createDocument>
  </s:Body>
</s:Envelope>

在属性“ConfigValue”中,我通常需要保存字符串,但我还需要能够将节点内的整个 XML 文档保存为 CDATA,例如:

        ...
        <metadata>
          <attribute name="ConfigName">ConfigurationTemplateForModuleX</attribute>
          <attribute name="ConfigValue">
          <![CDATA[
            <?xml version="1.0" encoding="UTF-8" standalone="yes"?>
            <config>
               <title>Config Template for Module X</title>
               ...
            </config>
          ]]>
          </attribute>
        </metadata>
        ...

我创建了一个对我的 Visual Studio 项目的服务引用,并创建了代理类,我可以使用第一个代码部分中描述的 web 服务,但问题是我想要包含在请求被自动编码,因此不再可用,因为我无法更改目标 Web 服务:

 &lt;![CDATA[
   &lt;?xml version=&quot;1.0&quot; encoding=&quot;UTF-8&quot; standalone=&quot;yes&quot;?&gt;
   &lt;config&gt;
     &lt;title&gt;Config Template for Module X&lt;/title&gt;
     ...
   &lt;/config&gt;
 ]]&gt;

我需要以某种方式修改 XML-Text 属性的序列化,或者抑制编码。

你有什么想法可以解决这个问题吗?

【问题讨论】:

    标签: c# .net web-services wcf cdata


    【解决方案1】:

    一种不是很好但可行的解决方案是修改生成的 C# 服务引用。在该类型的部分类中,我看到如下内容:

    public partial class tKeyValuePair : object, System.ComponentModel.INotifyPropertyChanged
    {
        
        private string keyField;
        
        private string valueField;
        
        /// <remarks/>
        [System.Xml.Serialization.XmlAttributeAttribute(DataType="NMTOKEN")]
        public string key
        {
            get
            {
                return this.keyField;
            }
            set
            {
                this.keyField = value;
                this.RaisePropertyChanged("key");
            }
        }
        
        /// <remarks/>
        [System.Xml.Serialization.XmlTextAttribute()]
        public string Value
        {
            get
            {
                return this.valueField;
            }
            set
            {
                this.valueField = value;
                this.RaisePropertyChanged("Value");
            }
        }
    

    提示!我使用以下命令行创建了引用,因为生成的代码与 Visual Studio 服务引用不同:

    svcutil http://server/service?wsdl /nologo /d:C:\temp\ /enableDataBinding /wrapped
    

    当我将“公共字符串值”和“私有字符串值字段”的参考代码修改为 XmlNode[] 类型时,可以通过 C# 代码创建一个 XmlNode 数组,其中包含一个 XmlNode,其内容为 Text或 CDATA 的内容,如:

    XmlNode test = new XmlCDataSection("text in cdata");
    

    如果您打算将有效的 XML 作为 CData 包含在内,这也适用。

    【讨论】:

      【解决方案2】:

      将 XML 转换为 Base64 字符串并进行传输。在接收端进行简单的重新转换将为您提供正确的 XML 字符串。

      【讨论】:

      • 配置的接收端或消费者是一个不受我控制的内部java组件。
      • 我解决了这个问题,但在不同的层面。我得到了在服务器端使用 jaxb 的信息,因此内容是 html 编码还是包含在 CDATA 中是无关紧要的。下面的答案中描述了另一种解决方案 - 但您提供的链接非常有帮助。
      猜你喜欢
      • 2017-07-02
      • 1970-01-01
      • 2010-10-16
      • 1970-01-01
      • 1970-01-01
      • 2014-09-04
      • 2011-04-25
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多