【发布时间】:2011-06-02 19:33:36
【问题描述】:
我有一个 XSD 文件和一个 XML 文件,如何检查 XML 是否像 XSD 文件一样在正确的架构中?
我知道XmlDocument 类中有一个验证函数,但它需要一个事件处理程序
我只需要对或错。
附:我在 Visual Studio 2010 中工作。
【问题讨论】:
我有一个 XSD 文件和一个 XML 文件,如何检查 XML 是否像 XSD 文件一样在正确的架构中?
我知道XmlDocument 类中有一个验证函数,但它需要一个事件处理程序
我只需要对或错。
附:我在 Visual Studio 2010 中工作。
【问题讨论】:
您可以使用 XmlReaderSettings 类和 Create 方法创建一个验证 XmlReader 实例。
private bool ValidateXml(string xmlFilePath, string schemaFilePath, string schemaNamespace, Type rootType)
{
XmlSerializer serializer = new XmlSerializer(rootType);
using (var fs = new StreamReader(xmlFilePath, Encoding.GetEncoding("iso-8859-1")))
{
object deserializedObject;
var xmlReaderSettings = new XmlReaderSettings();
if (File.Exists(schemaFilePath))
{
//select schema for validation
xmlReaderSettings.Schemas.Add(schemaNamespace, schemaPath);
xmlReaderSettings.ValidationType = ValidationType.Schema;
try
{
using (var xmlReader = XmlReader.Create(fs, xmlReaderSettings))
{
if (serializer.CanDeserialize(xmlReader))
{
return true;
//deserializedObject = serializer.Deserialize(xmlReader);
}
else
{
return false;
}
}
}
catch(Exception ex)
{ return false; }
}
}
}
如果架构无效或无法反序列化xml,上述代码将抛出异常。 rootType 是等效类层次结构中根元素的类型。
示例:
架构位于:XML Schema Tutorial。将文件另存为D:\SampleSchema.xsd。
运行xsd.exe:
xsd.exe /c /out:D:\ "D:\SampleSchema.xsd"
/out选项指定输出目录,/c指定生成类的工具D:\SampleSchema.cs
//------------------------------------------------------------------------------
//
// This code was generated by a tool.
// Runtime Version:2.0.50727.4952
//
// Changes to this file may cause incorrect behavior and will be lost if
// the code is regenerated.
//
//------------------------------------------------------------------------------
using System.Xml.Serialization;
//
// This source code was auto-generated by xsd, Version=2.0.50727.3038.
//
///
[System.CodeDom.Compiler.GeneratedCodeAttribute("xsd", "2.0.50727.3038")]
[System.SerializableAttribute()]
[System.Diagnostics.DebuggerStepThroughAttribute()]
[System.ComponentModel.DesignerCategoryAttribute("code")]
[System.Xml.Serialization.XmlTypeAttribute(AnonymousType=true)]
[System.Xml.Serialization.XmlRootAttribute(Namespace="", IsNullable=false)]
public partial class note {
private string toField;
private string fromField;
private string headingField;
private string bodyField;
///
[System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
public string to {
get {
return this.toField;
}
set {
this.toField = value;
}
}
///
[System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
public string from {
get {
return this.fromField;
}
set {
this.fromField = value;
}
}
///
[System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
public string heading {
get {
return this.headingField;
}
set {
this.headingField = value;
}
}
///
[System.Xml.Serialization.XmlElementAttribute(Form=System.Xml.Schema.XmlSchemaForm.Unqualified)]
public string body {
get {
return this.bodyField;
}
set {
this.bodyField = value;
}
}
}
将该类添加到 Visual Studio 项目中。
对于上面的 xsd 示例,根类是 note。
调用方法,
bool isXmlValid = ValidateXml(@"D:\Sample.xml",
@"D:\SampleSchema.xsd",
@"http://www.w3.org/2001/XMLSchema",
typeof(note));
更多信息:
【讨论】:
你可以这样做。
public class XmlValidator
{
private bool _isValid = true;
public bool Validate(string xml)
{
_isValid = true;
// Set the validation settings as needed.
var settings = new XmlReaderSettings { ValidationType = ValidationType.Schema };
settings.ValidationFlags |= XmlSchemaValidationFlags.ProcessInlineSchema;
settings.ValidationFlags |= XmlSchemaValidationFlags.ProcessSchemaLocation;
settings.ValidationFlags |= XmlSchemaValidationFlags.ReportValidationWarnings;
settings.ValidationEventHandler += ValidationCallBack;
var reader = XmlReader.Create(new StringReader(xml), settings);
while(reader.Read())
{
// process the content if needed
}
return _isValid;
}
private void ValidationCallBack(object sender, ValidationEventArgs e)
{
// check for severity as needed
if(e.Severity == XmlSeverityType.Error)
{
_isValid = false;
}
}
}
class Program
{
static void Main(string[] args)
{
var validator = new XmlValidator();
var result =
validator.Validate(@"<?xml version=""1.0""?>
<Product ProductID=""1"" xmlns:xsi=""http://www.w3.org/2001/XMLSchema-instance"" xsi:noNamespaceSchemaLocation=""schema.xsd"">
<ProductName>Chairs</ProductName>
</Product>");
}
架构。
<?xml version="1.0"?>
<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<xsd:element name="Product">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="ProductName" type="xsd:string"/>
</xsd:sequence>
<xsd:attribute name="ProductID" use="required" type="xsd:int"/>
</xsd:complexType>
</xsd:element>
</xsd:schema>
【讨论】:
有一个非常简单的方法:
private void ValidationCallBack(object sender, ValidationEventArgs e)
{
throw new Exception();
}
public bool validate(string sxml)
{
try
{
XmlDocument xmld=new XmlDocument ();
xmld.LoadXml(sxml);
xmld.Schemas.Add(null,@"c:\the file location");
xmld.validate(ValidationCallBack);
return true;
}
catch
{
return false;
}
}
P.S : 我不是在 VS 中写的,所以可能会有不区分大小写的单词,但这段代码有效!
【讨论】: