如何为OIOUBL标准XML序列化的ID属性指定非string类型?
解决OIOUBL XML序列化中ID元素类型冲突问题
你遇到的问题是因为同一个XML命名空间urn:oasis:names:specification:ubl:schema:xsd:CommonBasicComponents-2下的<cbc:ID>元素被映射到了System.String和自定义TaxSchemeId两种不同CLR类型,导致XmlSerializer无法解析。下面是几个可行的解决办法:
方案1:统一使用带属性的通用ID类(推荐)
OIOUBL里大部分<cbc:ID>元素都带有schemeID这类属性,直接用string类型没法承载属性,还会和自定义ID类冲突。可以定义一个通用类封装带属性的字符串,统一所有<cbc:ID>元素的CLR类型:
[XmlType(Namespace = "urn:oasis:names:specification:ubl:schema:xsd:CommonBasicComponents-2")] public class IdentifiedString { [XmlAttribute("schemeID")] public string SchemeID { get; set; } [XmlText] public string Value { get; set; } } // TaxScheme类中使用这个通用类 public class TaxScheme { [XmlElement(ElementName = "ID", Namespace = "urn:oasis:names:specification:ubl:schema:xsd:CommonBasicComponents-2")] public IdentifiedString ID { get; set; } }
后续所有需要带schemeID的<cbc:ID>都用这个IdentifiedString类,纯字符串ID也可以用它(忽略SchemeID属性即可),从根源上避免类型冲突。
方案2:用XmlChoiceIdentifier区分不同ID类型
如果必须同时保留string和自定义TaxSchemeId两种ID类型,可以通过标识枚举告诉序列化器如何区分:
// 定义枚举标记ID类型 public enum IdTypeChoice { StringID, TaxSchemeID } public class YourClass { [XmlChoiceIdentifier("IdType")] [XmlElement(ElementName = "ID", Namespace = "urn:oasis:names:specification:ubl:schema:xsd:CommonBasicComponents-2", Type = typeof(string))] [XmlElement(ElementName = "ID", Namespace = "urn:oasis:names:specification:ubl:schema:xsd:CommonBasicComponents-2", Type = typeof(TaxSchemeId))] public object ID { get; set; } [XmlIgnore] public IdTypeChoice IdType { get; set; } }
这种方式需要维护枚举和类型映射,适合场景较少的情况,但复杂度比方案1高。
方案3:为不同ID指定不同元素名(不推荐)
如果可以违反OIOUBL规范(不建议),可以给不同类型的ID指定不同的XML元素名,但这会导致生成的XML不符合标准,仅作为应急方案。
验证序列化效果
以方案1为例,初始化并序列化的代码:
var taxScheme = new TaxScheme { ID = new IdentifiedString { SchemeID = "urn:oioubl:id:taxschemeid-1.1", Value = "63" } }; var serializer = new XmlSerializer(typeof(TaxScheme)); using var writer = new StringWriter(); serializer.Serialize(writer, taxScheme); var xml = writer.ToString();
生成的XML会完全符合目标格式:
<TaxScheme xmlns:cbc="urn:oasis:names:specification:ubl:schema:xsd:CommonBasicComponents-2"> <cbc:ID schemeID="urn:oioubl:id:taxschemeid-1.1">63</cbc:ID> </TaxScheme>
内容的提问来源于stack exchange,提问作者Сереженька
相关产品推荐
相关产品推荐

