【发布时间】:2019-09-19 09:19:21
【问题描述】:
我需要验证一些通用传感器输入。要求是,验证不能在我的代码中进行,而是使用来自代码库外部的外部验证器(如 xsd),使用户能够交换验证逻辑而无需编码或重新编译应用程序。 我知道传感器输入仅对一种特定情况有效,因此希望从运行时存在且经过用户验证的类的实例生成 xsd,以获得有效的限制。
我尝试了来自this 问题的想法,但这仅适用于类型而不适用于类的实例。
因此我的问题是:有没有办法获取 C# 类的运行时实例并将其转换为将属性值作为唯一有效限制的 xsd?
更新:
澄清:我所拥有的是这样的课程:
public sealed class Sensor
{
public int Data { get; set; }
public int otherData { get; set; }
public int MoreData { get; set; }
}
该类在某处被实例化(例如,像这样):
var se = new Sensor()
{
Data = 5,
otherData = 10,
MoreData = 15
};
当我现在尝试使用以下函数创建 xsd 时:
var schemas = new XmlSchemas();
var exporter = new XmlSchemaExporter(schemas);
var mapping = new XmlReflectionImporter().ImportTypeMapping(typeof(Person));
exporter.ExportTypeMapping(mapping);
var schemaWriter = new StringWriter();
foreach (XmlSchema schema in schemas)
{
schema.Write(schemaWriter);
}
return schemaWriter.ToString();
我收到一些像这样的 xsd:
<?xml version="1.0" encoding="utf-8"?>
<xs:schema attributeFormDefault="unqualified" elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xs:element name="sensor">
<xs:complexType>
<xs:sequence>
<xs:element name="Data" type="xs:integer" />
<xs:element name="otherData" type="xs:integer" />
<xs:element name="moreData" type="xs:integer" />
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>
但这远不是我想要的。我想在其中内置适当的限制(它应该看起来像这样):
<?xml version="1.0" encoding="utf-8"?>
<xs:schema attributeFormDefault="unqualified" elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xs:element name="sensor">
<xs:complexType>
<xs:sequence>
<xs:element name="Data">
<xs:simpleType>
<xs:restriction base="xs:integer">
<xs:enumeration value="5"/>
</xs:restriction>
</xs:simpleType>
</xs:element>
<xs:element name="otherData">
<xs:simpleType>
<xs:restriction base="xs:integer">
<xs:enumeration value="10"/>
</xs:restriction>
</xs:simpleType>
</xs:element>
<xs:element name="moreData">
<xs:simpleType>
<xs:restriction base="xs:integer">
<xs:enumeration value="15"/>
</xs:restriction>
</xs:simpleType>
</xs:element>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:schema>
我显然可以继续将生成的文件加载到内存中,去除一些属性并更改 xsd 的外观,但这感觉不对,因为以下原因:
- 由我来定义 xsd 应该如何看起来像我带走的规则 我希望拥有的灵活性。
- 这种方法对我来说似乎很容易出错,因为它似乎基本上比直接字符串操作要好一些。
- 这个额外的代码会使我已经很大的代码变得更复杂和更难理解。
总结一下:我需要一个库或一个非常聪明的函数,它可以根据我在课堂上的 runitme 信息创建一个像上面那样的 xsd,而无需编写很多东西直接操作 xml 以避免对验证的未来使用容易出错或错误假设。
【问题讨论】:
-
xsd 是 xml 格式,因此您可以使用任何 xml 写入库创建架构。
-
您是否有一个让这一切变得简单的库?我真的不希望通过手动编码来生成 xsd 的复杂性。
-
有两个步骤 1) 枚举类的属性(参见:stackoverflow.com/questions/737151/…) 2)然后通过从步骤 1 获取属性来创建 xml/xsd。
-
@jdweng 请参阅我的更新以进行澄清。感谢您的帮助
标签: c# xsd runtime xsd-validation