代码之家  ›  专栏  ›  技术社区  ›  amrox

使用Cocoa中的xsd文件验证XML模式?

  •  2
  • amrox  · 技术社区  · 15 年前

    我能穿过 xmllint ,这可能会起作用,但我正在寻找一种不启动外部任务的方法。

    3 回复  |  直到 8 年前
        1
  •  4
  •   0xced    7 年前

    如果您的xml文档没有对xml模式的引用,您应该自己添加它,然后使用NSXMLDocument进行验证 validateAndReturnError: 方法。

    下面是一个如何调整xml文档以引用xsd的示例。显然,您必须修改这段代码,以获得对本地xsd文件的引用。

    NSError *error = nil;
    NSURL *xmlURL = [NSURL URLWithString:@"http://www.xmlschema.info/PO.xml"];
    
    NSXMLDocument *document = [[NSXMLDocument alloc] initWithContentsOfURL:xmlURL options:NSXMLNodeOptionsNone error:NULL];
    
    NSXMLNode *noNamespaceSchemaLocation = [NSXMLNode attributeWithName:@"xsi:noNamespaceSchemaLocation" stringValue:@"http://www.xmlschema.info/PO.xsd"];
    NSXMLElement *rootElement = [document rootElement]; 
    NSMutableArray *rootAttributes = [[rootElement attributes] mutableCopy];
    [rootAttributes replaceObjectAtIndex:1 withObject:noNamespaceSchemaLocation];
    [rootElement setAttributes:rootAttributes];
    
    BOOL isValid = [document validateAndReturnError:&error];
    
    if (isValid)
        NSLog(@"document is valid");
    else
        NSLog(@"document is invalid: %@", [error localizedDescription]);
    

    供参考:

    内容 http://www.xmlschema.info/PO.xml

    <?xml version="1.0"?>
    <purchaseOrder orderDate="1999-10-20" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="C:\microsite_images\po.xsd">
        <shipTo country="US">
            <name>Alice Smith</name>
            <street>123 Maple Street</street>
            <city>Mill Valley</city>
            <state>CA</state>
            <zip>90952</zip>
        </shipTo>
        <billTo country="US">
            <name>Robert Smith</name>
            <street>8 Oak Avenue</street>
            <city>Old Town</city>
            <state>PA</state>
            <zip>95819</zip>
        </billTo>
        <comment>Hurry, my lawn is going wild</comment>
        <items>
            <item partNum="872-AA">
                <productName>Lawnmower</productName>
                <quantity>1</quantity>
                <USPrice>148.95</USPrice>
                <comment>Confirm this is electric</comment>
            </item>
            <item partNum="926-AA">
                <productName>Baby Monitor</productName>
                <quantity>1</quantity>
                <USPrice>39.98</USPrice>
                <shipDate>1999-05-21</shipDate>
            </item>
        </items>
    </purchaseOrder>
    

    http://www.xmlschema.info/PO.xsd

    <xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema">
    
      <xsd:annotation>
        <xsd:documentation xml:lang="en">
         Purchase order schema for Example.com.
         Copyright 2000 Example.com. All rights reserved.
        </xsd:documentation>
      </xsd:annotation>
    
      <xsd:element name="purchaseOrder" type="PurchaseOrderType"/>
    
      <xsd:element name="comment" type="xsd:string"/>
    
      <xsd:complexType name="PurchaseOrderType">
        <xsd:sequence>
          <xsd:element name="shipTo" type="USAddress"/>
          <xsd:element name="billTo" type="USAddress"/>
          <xsd:element ref="comment" minOccurs="0"/>
          <xsd:element name="items"  type="Items"/>
        </xsd:sequence>
        <xsd:attribute name="orderDate" type="xsd:date"/>
      </xsd:complexType>
    
      <xsd:complexType name="USAddress">
        <xsd:sequence>
          <xsd:element name="name"   type="xsd:string"/>
          <xsd:element name="street" type="xsd:string"/>
          <xsd:element name="city"   type="xsd:string"/>
          <xsd:element name="state"  type="xsd:string"/>
          <xsd:element name="zip"    type="xsd:decimal"/>
        </xsd:sequence>
        <xsd:attribute name="country" type="xsd:NMTOKEN"
                       fixed="US"/>
      </xsd:complexType>
    
      <xsd:complexType name="Items">
        <xsd:sequence>
          <xsd:element name="item" minOccurs="0" maxOccurs="unbounded">
            <xsd:complexType>
              <xsd:sequence>
                <xsd:element name="productName" type="xsd:string"/>
                <xsd:element name="quantity">
                  <xsd:simpleType>
                    <xsd:restriction base="xsd:positiveInteger">
                      <xsd:maxExclusive value="100"/>
                    </xsd:restriction>
                  </xsd:simpleType>
                </xsd:element>
                <xsd:element name="USPrice"  type="xsd:decimal"/>
                <xsd:element ref="comment"   minOccurs="0"/>
                <xsd:element name="shipDate" type="xsd:date" minOccurs="0"/>
              </xsd:sequence>
              <xsd:attribute name="partNum" type="SKU" use="required"/>
            </xsd:complexType>
          </xsd:element>
        </xsd:sequence>
      </xsd:complexType>
    
      <!-- Stock Keeping Unit, a code for identifying products -->
      <xsd:simpleType name="SKU">
        <xsd:restriction base="xsd:string">
          <xsd:pattern value="\d{3}-[A-Z]{2}"/>
        </xsd:restriction>
      </xsd:simpleType>
    
    </xsd:schema>
    
        2
  •  2
  •   Nic Gibson    15 年前

    here . 我自己也用过这个。

        3
  •  1
  •   Todd Ditchendorf    15 年前

    纽特是对的。我有一些使用libxmlxsdapi的开源Cocoa代码。

    项目在这里:

    http://code.google.com/p/cocoatron/

    - (void)doXSDValidation:(xmlDocPtr)source;
    

    在此文件中:

    http://code.google.com/p/cocoatron/source/browse/trunk/ValidateXMLDocuments/Validate%20XML%20Documents.m