XML 属性未获取命名空间前缀

     2023-04-12     290

关键词:

【中文标题】XML 属性未获取命名空间前缀【英文标题】:XML attribute not getting namespace prefix 【发布时间】:2021-12-14 00:41:24 【问题描述】:

我需要在序列化过程中生成以下 XML: (片段)

<IncidentEvent a:EventTypeText="Beginning" xmlns:a="http://foo">
  <EventDate>2013-12-18</EventDate>
  <EventTime>00:15:28</EventTime>
</IncidentEvent>

有问题的类如下所示:

public class IncidentEvent

    public string EventDate  get; set; 
    public string EventTime  get; set; 

    [XmlAttribute("EventTypeText", Namespace = "http://foo")]
    public string EventTypeText  get; set; 


似乎序列化程序注意到名称空间已在 xmlns: 根中声明,并且忽略了我的属性。我还尝试了以下方法:

[XmlRoot(Namespace = "http://foo")]
public class IncidentEvent

    public string EventDate  get; set; 
    public string EventTime  get; set; 

    private XmlSerializerNamespaces _Xmlns;

    [XmlNamespaceDeclarations]
    public XmlSerializerNamespaces Xmlns
    
        get
        
            if (_Xmlns == null)
            
                _Xmlns = new XmlSerializerNamespaces();
                _Xmlns.Add("ett", "http://foo");
            

            return _Xmlns;
        

        set
        
            _Xmlns = value;
        
    


    [XmlAttribute("EventTypeText", Namespace = "http://foo")]
    public string EventTypeText  get; set; 


这会产生以下 XML:

  <ett:IncidentEvent EventTypeText="Beginning" xmlns:ett="http://foo">
    <ett:EventDate>2013-12-18</ett:EventDate>
    <ett:EventTime>00:15:28</ett:EventTime>
  </ett:IncidentEvent>

这不是我想要的。元素不应该是前缀,属性应该是。需要什么才能让序列化程序了解我想要什么?

【问题讨论】:

【参考方案1】:

这可能是XmlSerializer 中的一个错误。

正如您所注意到的,即使XmlAttributeAttribute.Namespace 被显式设置,在某些情况下该属性也不会作为前缀。根据测试,当属性命名空间恰好与当前正在写入的元素的命名空间相同时,似乎会发生这种情况。

例如:

[XmlRoot(Namespace = "http://foo")]
public class IncidentEvent

    [XmlAttribute("EventTypeText", Namespace = "http://foo")]
    public string EventTypeText  get; set; 

序列化为以下 XML:

<q1:IncidentEvent EventTypeText="an attribute" xmlns:q1="http://foo" />

由于属性没有前缀,它实际上不在任何命名空间中,正如in the XML standard 所解释的那样:无前缀属性名称的命名空间名称始终没有值

但是,以下内容:

[XmlRoot(Namespace = "http://foo")]
public class IncidentEvent

    [XmlAttribute("EventTypeText", Namespace = "http://bar")]
    public string EventTypeText  get; set; 

使用正确前缀的属性进行序列化:

<q1:IncidentEvent p1:EventTypeText="an attribute" xmlns:p1="http://bar" xmlns:q1="http://foo" />

解决方法是显式设置[XmlAttribute(Form = XmlSchemaForm.Qualified)]。因此:

[XmlRoot(Namespace = "http://foo")]
public class IncidentEvent

    [XmlAttribute("EventTypeText", Namespace = "http://foo", Form = XmlSchemaForm.Qualified)]
    public string EventTypeText  get; set; 

序列化为

<q1:IncidentEvent q1:EventTypeText="an attribute" xmlns:q1="http://foo" />

根据需要。

【讨论】:

【参考方案2】:

我做了一些研究可能会得到以下答案的帮助

要使属性具有命名空间前缀,您必须指定与指定 http://foo 不同的命名空间标签。以下代码有望解决您的问题。在代码中,我删除了元素的命名空间并仅添加了属性。

public class IncidentEvent

    public string EventDate  get; set; 
    public string EventTime  get; set; 

    [XmlAttribute("EventTypeText", Namespace = "http://foo")]
    public string EventTypeText  get; set; 



class Program

    static void Main(string[] args)
    
        IncidentEvent xmlObj = new IncidentEvent()
        
            EventDate = "2012.12.01",
            EventTime = "1:00:00",
            EventTypeText = "Beginining"
        ;
        XmlSerializerNamespaces ns = new XmlSerializerNamespaces();
        ns.Add("ett", "http://foo");
        XmlSerializer serializer = new XmlSerializer(typeof(IncidentEvent));
        serializer.Serialize(Console.OpenStandardOutput(), xmlObj, ns);
        Console.WriteLine();
    

http://www.w3.org/TR/2009/REC-xml-names-20091208/#defaulting

【讨论】:

如果您需要将此对象序列化为另一个对象的子对象,这似乎会崩溃。当我在一种情况下对其进行测试时它运行良好,但我忘记了另一种情况。不过,很好的答案。【参考方案3】:

命名空间旨在区分具有相同名称的两个 XML 元素。由于不同的 XML 元素可以具有相同的属性名称但含义不同。因此,属性的名称空间标记没有任何优势,因为 XML 属性仅被视为“元素名称空间”的一部分。 在你的例子中

<ett:IncidentEvent EventTypeText="Beginning" xmlns:ett="http://foo">
    <ett:EventDate>2013-12-18</ett:EventDate>
    <ett:EventTime>00:15:28</ett:EventTime>
</ett:IncidentEvent>

EventTypeText 是命名空间 ett:IncidentEvent 的一部分 XML 命名空间请参考http://www.w3.org/TR/REC-xml-names/

【讨论】:

XML 需要针对我无法控制的 XSD 进行验证。我需要做的就是编写符合架构的 XML。我的第一个片段是手写的,但它确实有效。我只需要弄清楚如何让序列化程序做同样的事情。【参考方案4】:

我将把答案归功于 KKD,但我发现了另一种仍然会导致问题的场景。显然,如果要序列化的对象是另一个对象的子对象,如果父对象的命名空间与子对象的命名空间相同,则序列化程序假定您不需要显式声明子对象的命名空间。

 public class IncidentEvent : IXmlSerializable
 
    public string EventDate  get; set; 
    public string EventTime  get; set; 
    public string EventTypeText  get; set; 

    public System.Xml.Schema.XmlSchema GetSchema()
    
        return null;
    

    public void ReadXml(System.Xml.XmlReader reader)
    
        return null;
    

    public void WriteXml(System.Xml.XmlWriter writer)
    
        writer.WriteAttributeString("ex", "EventTypeText", "http://foo", EventTypeText);
    
 

通过实现 IXmlSerializable,我可以完全按照我需要的方式手动写出元素和属性。由于这是一种单向导出,因此除了 WriteXml 方法之外我不需要实现任何东西。

我仍然不确定这是否是最好的方式,但它目前有效。

【讨论】:

JAXB:为啥在生成的 xml 文档中未使用定义的命名空间前缀?

】JAXB:为啥在生成的xml文档中未使用定义的命名空间前缀?【英文标题】:JAXB:whyaredefinednamespaceprefixesnotusedingeneratedxmldocument?JAXB:为什么在生成的xml文档中未使用定义的命名空间前缀?【发布时间】:2021-04-0309:12:33【问题描述... 查看详情

访问没有命名空间前缀的 XML 中的特定标签属性

】访问没有命名空间前缀的XML中的特定标签属性【英文标题】:AccessSpecificTagAttributesinXMLwithNoNamespacePrefix【发布时间】:2021-09-2817:44:45【问题描述】:我有以下XML。(由于隐私原因,属性名称已更改)<?xmlversion="1.0"encoding="utf-8"... 查看详情

XML:一个命名空间前缀被声明为未声明,而事实上它是

】XML:一个命名空间前缀被声明为未声明,而事实上它是【英文标题】:XML:Anamespaceprefixisclaimedtobenotdeclaredwhenitfactitis【发布时间】:2011-01-0914:47:11【问题描述】:我们有一个Web服务,它返回一个非常简单的XML。<?xmlversion="1.0"?&... 查看详情

如何用前缀替换 xmlns 命名空间属性?

】如何用前缀替换xmlns命名空间属性?【英文标题】:HowcanIreplacexmlnsnamespaceattributeswithprefixes?【发布时间】:2017-07-2120:33:44【问题描述】:我一直在尝试用C#编写一个实用程序,它接受一个XML文件,从标签中删除xmlns属性,在根标... 查看详情

未定义命名空间前缀。如何自动定义它/忽略错误?

】未定义命名空间前缀。如何自动定义它/忽略错误?【英文标题】:Namespaceprefixisn\'tdefined.HowcanIdefineitautomatically/ignoreerror?【发布时间】:2016-07-1101:38:30【问题描述】:我制作了一个解析XML文件的PHP脚本,当我尝试解析它时,出... 查看详情

带有命名空间前缀的 TagSoup 属性

】带有命名空间前缀的TagSoup属性【英文标题】:TagSoupattributeswithnamespaceprefix【发布时间】:2011-05-0920:50:17【问题描述】:为了使用TagSoup解析xml响应,我正在扩展DefaultHandler,现在我遇到的问题是它忽略了方法中具有限定名称的... 查看详情

如何在 .NET 中的反序列化期间指定 XML 序列化属性以支持命名空间前缀?

】如何在.NET中的反序列化期间指定XML序列化属性以支持命名空间前缀?【英文标题】:HowdoIspecifyXMLserializationattributestosupportnamespaceprefixesduringdeserializationin.NET?【发布时间】:2010-11-1806:43:02【问题描述】:我有以下XML:<personxmln... 查看详情

Linq to Xml 和命名空间前缀

...文档。更准确地说,我正在尝试读取和写入文档的自定义属性。我目前在将前缀附加到XElement时遇到问题。我的代码如下:DimmainasXNameSpace="http://schemas.openxmlformats.o 查看详情

如何使用 lxml 在属性值中设置命名空间前缀?

】如何使用lxml在属性值中设置命名空间前缀?【英文标题】:howtosetanamespaceprefixinanattributevalueusingthelxml?【发布时间】:2010-09-1014:24:05【问题描述】:我正在尝试使用lxml创建XML模式。一开始是这样的:<xs:schemaxmlns="http://www.goo.c... 查看详情

XML 命名空间,为啥它们需要前缀?

】XML命名空间,为啥它们需要前缀?【英文标题】:XMLnamespaces,whyaretheyneccessaryforprefixes?XML命名空间,为什么它们需要前缀?【发布时间】:2013-06-1907:44:28【问题描述】:所以我一直在阅读w3schools上的命名空间,我知道它们是为... 查看详情

XML 序列化和命名空间前缀

】XML序列化和命名空间前缀【英文标题】:XMLSerializationandnamespaceprefixes【发布时间】:2011-01-2108:08:16【问题描述】:我正在寻找一种使用C#的方法,我可以将一个类序列化为XML并添加一个命名空间,但定义该命名空间将使用的前... 查看详情

使用命名空间前缀更新 XML 文件

】使用命名空间前缀更新XML文件【英文标题】:UpdateanXMLFileWithNamespacePrefix【发布时间】:2016-12-2304:38:41【问题描述】:我有一个带有命名空间的XML文件,我想通过添加更多项目来更新这个文件。这是我的XML文件结构:<?xmlversio... 查看详情

xml和schema命名空间详解

...空间是W3C推荐标准提供的一种统一命名XML文档中的元素和属性的机制。使用名称空间可以明确标识和组合XML文档中来自不同标记词汇表的元素和属性,避免了名称之间的冲突。  使用过DTD的人应该知道,命名冲突是DTD的一... 查看详情

Excel 到 XML 命名空间前缀自定义

】Excel到XML命名空间前缀自定义【英文标题】:ExceltoXMLNamespacePrefixCustomization【发布时间】:2016-07-1916:18:40【问题描述】:我正在使用Excel2013通过XML映射将数据从电子表格转换为XML格式。转换效果很好,但Excel将输出文件中的所有... 查看详情

XML 和 XSL 中的前缀命名空间处理由 XML 解析器返回错误

】XML和XSL中的前缀命名空间处理由XML解析器返回错误【英文标题】:PrefixednamespacehandlinginXMLandXSLreturnserrorbyXMLparser【发布时间】:2021-07-1614:57:14【问题描述】:我正在尝试使用XSLT处理XML/XSL。XML和部分XSL包含前缀名称空间。我的... 查看详情

Jackson XML - 使用命名空间前缀反序列化 XML

】JacksonXML-使用命名空间前缀反序列化XML【英文标题】:JacksonXML-deserializingXMLwithnamespaceprefixes【发布时间】:2013-05-0219:25:13【问题描述】:我正在使用JacksonXML插件(https://github.com/FasterXML/jackson-dataformat-xml),我不确定它是否受支持... 查看详情

使用 Scala 未定义 SAXParseException 命名空间 xml

...:57【问题描述】:我有一个SVG文档,并且SVG样式元素具有属性xml:space="preserve"。尝试使用Scala解析此文档时,堆栈跟踪会引发异常线程“主”org.xml.sax.SAXParseExce 查看详情

删除带有命名空间前缀的 xmlns 属性

】删除带有命名空间前缀的xmlns属性【英文标题】:Removexmlnsattributewithnamespaceprefix【发布时间】:2012-11-2821:49:30【问题描述】:这个问题是thisone的逻辑延续-现在假设XElement包含非默认命名空间中的元素:<Bodyxmlns="http://schemas.mic... 查看详情