繁体   English   中英

XmlSerializer产生没有命名空间前缀的XML

[英]XmlSerializer Producing XML With No Namespace Prefix

我必须创建一个带有所有元素前缀的XML文件,如下所示:

<ps:Request num="123" xmlns:ps="www.ladieda.com">
   <ps:ClientId>5566</ps:ClientId>
<ps:Request>

当我序列化对象时,C#很聪明,并且可以做到这一点:

<Request num="123" xmlns="www.ladieda.com">
   <ClientId>5566</ClientId>
<Request>

很好,因为ps:是不必要的。

但是,是否有一种方法可以强制C#序列化所有前缀?

我的序列化代码是这样的(对于传入对象pObject):

String XmlizedString = null;
MemoryStream memoryStream = new MemoryStream();
XmlSerializer xs = new XmlSerializer(pObject.GetType());
XmlTextWriter xmlTextWriter = new XmlTextWriter(memoryStream, Encoding.UTF8);

xs.Serialize(xmlTextWriter, pObject);
memoryStream = (MemoryStream)xmlTextWriter.BaseStream;
XmlizedString = UTF8ByteArrayToString(memoryStream.ToArray());
return XmlizedString;


private String UTF8ByteArrayToString(Byte[] characters)
{
    UTF8Encoding encoding = new UTF8Encoding();
    String constructedString = encoding.GetString(characters);
    return (constructedString);
}

首先,如果字符串的使用者正在处理XML,那么他们将不会在乎前缀,因为它对XML无关紧要。 也许他们不了解XML,并认为他们正在处理一个字符串(可能需要在每个元素上使用字符串“ ps:”)。

第二,您应该对代码进行一些更改:

XmlSerializer xs = new XmlSerializer(pObject.GetType());
using (MemoryStream memoryStream = new MemoryStream())
{
    XmlWriterSettings settings = new XmlWriterSettings()
    {
        Encoding = Encoding.UTF8
    };
    using (XmlWriter writer = XmlWriter.Create(memoryStream, settings))
    {
        xs.Serialize(writer, pObject);
    }
    return Encoding.UTF8.GetString(memoryStream.ToArray());
}

如果抛出异常,这将正确处理流和XmlWriter,停止使用不推荐使用的XmlTextWriter类,但仍返回包含为UTF-8编写的XML的字符串。

最后,要控制前缀,请参阅“如何:限定XML元素和XML属性名称”

XmlSerializerNamespaces myNamespaces = new XmlSerializerNamespaces();
myNamespaces.Add("ps", "www.ladieda.com");

XmlSerializer xs = new XmlSerializer(pObject.GetType());
using (MemoryStream memoryStream = new MemoryStream())
{
    XmlWriterSettings settings = new XmlWriterSettings()
    {
        Encoding = Encoding.UTF8
    };
    using (XmlWriter writer = XmlWriter.Create(memoryStream, settings))
    {
        xs.Serialize(writer, pObject, myNamespaces);
    }
    return Encoding.UTF8.GetString(memoryStream.ToArray());
}

还要检查XmlNamespaceDeclarationsAttribute。 注意:反序列化时,只会为您提供该元素定义的名称空间,而不会在父元素中定义名称空间。 如果您没有一致的根类型,请使用@John Saunders的XmlSerializer.Serialize()重载。

http://msdn.microsoft.com/zh-CN/library/system.xml.serialization.xmlnamespacedeclarationsattribute.aspx

在另一个问题中,@ John Saunders建议在控制WSDL中的xmlns时使用此属性: Wsdl(.net)中的命名空间前缀。

从MSDN示例:

// C#
using System;
using System.IO;
using System.Xml.Serialization;
[XmlRoot("select")]
public class Select {
    [XmlAttribute] public string xpath;
    [XmlNamespaceDeclarations] public XmlSerializerNamespaces xmlns;
}
public class Test {
    public static void Main(string[] args) {
       Select mySelect = new Select();
       mySelect.xpath = "myNS:ref/@common:y";
       mySelect.xmlns = new XmlSerializerNamespaces();
       mySelect.xmlns.Add("MyNS", "myNS.tempuri.org");
       mySelect.xmlns.Add("common", "common.tempuri.org");
       XmlSerializer ser = new XmlSerializer(typeof(Select));
       ser.Serialize(Console.Out, mySelect);
    }
}
// Output:
// <?xml version="1.0" encoding="IBM437"?>
// <select xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmln:xsi="http://www.w3.org/2001/XMLSchema-instance" 
// xmlns:common="common.tempuri.org" xmlns:MyNS="myNS.tempuri.org" xpath="myNS:ref/@common:y" />

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM