Using XML Schemas

| Questions |
| Usage Using Entities and CDATA Sections XML Schema API Changes to PSVI Accessing PSVI via XNI Accessing PSVI via DOM Accessing PSVI via SAX Parsing and analyzing an XML schema Using XSLoader to get an XSModel
| Answers |
| How do I validate against XML schema? |
| In this release, schema validation has been integrated with the regular SAXParser and DOMParser classes. No special classes are required to parse documents that use a schema. Each document that uses XML Schema grammars must specify the location of the grammars it uses by using an xsi:schemaLocation attribute if they use namespaces, and an xsi:noNamespaceSchemaLocation attribute otherwise. These are usually placed on the root / top-level element in the document, though they may occur on any element; for more details see XML Schema Part 1 section 4.3.2. Here is an example with no target namespace:
    <document
        xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance'
        xsi:noNamespaceSchemaLocation='document.xsd'>
        ...
    </document>
Here is an example with a target namespace. Note that it is an error to specify a different namespace than the target namespace defined in the Schema.
    <document
        xmlns='http://my.com'
        xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance'
        xsi:schemaLocation='http://my.com document.xsd'>
        ...
    </document>
Review the sample file, 'data/personal.xsd' for an example of an XML Schema grammar.
| How does the XML Schema processor treat entities and CDATA sections? |
| According to the XML Infoset the infoset items contributing to the [character information item] are: characters in the document, whether literally, as a character reference, or within a CDATA section, or within Entity Reference. The XML Schema specification "requires as a precondition for assessment an information set as defined in [XML-Infoset]" (Appendix D) and thus Xerces might attempt to normalize data in an entity reference or CDATA section. To preserve character data within entity references and CDATA sections, turn off http://apache.org/xml/features/validation/schema/normalized-value feature.
| Does Xerces provide access to the post schema validation infoset (PSVI)? |
| Xerces implements the XML Schema API specification that defines an API for accessing and querying the post schema validation infoset (PSVI) as defined in Contributions to the post-schema-validation infoset (Appendix C.2). This API also defines interfaces for loading XML schema documents. For more information please refer to the interfaces.
| The Xerces 2.6.2 release fixes a documentation bug in the XML Schema API. In particular in the XSModel interface the order of the parameters in getTypeDefinition, getNotationDeclaration, getModelGroupDefinition, getElementDeclaration, getAttributeDeclaration, getAttributeGroup methods have been changed from (String namespace, String name) to (String name, String namespace).
| What happened to the PSVI interfaces in org.apache.xerces.xni.psvi? |
| The PSVI interfaces which used to be part of the `org.apache.xerces.xni.psvi` and `org.apache.xerces.impl.xs.psvi` packages were modified and have been moved into the XML Schema API.
| How do I access PSVI via XNI? |
| From within an `XMLDocumentHandler`, one can retrieve PSVI information while in the scope of the document handler start/end element calls:
    import org.apache.xerces.xs.*;

    ...

    public void startElement(QName element, XMLAttributes attributes,
        Augmentations augs) {
        ElementPSVI elemPSVI = (ElementPSVI)augs.getItem("ELEMENT_PSVI");
        // get PSVI items of this element out of elemPSVI
        short attemp = elemPSVI.getValidationAttempted();
        short validity = elemPSVI.getValidity();
        ...
    }
| For more information, please refer to the API documentation for the XML Schema API.
The above code shows how to retrieve PSVI information after elements/attributes are assessed. The other kind of information PSVI offers is the property [schema information]. This property exposes all schema components in the schema that are used for assessment. These components and the schema itself are represented by interfaces in the `org.apache.xerces.xs` package. [schema information] property is only available on the `endElement` method for the validation root. When this method is called, information about various components can be retrieved by
    import org.apache.xerces.xs.*;

    ...

    public void endElement(QName element, Augmentations augs) {
        ElementPSVI elemPSVI = (ElementPSVI)augs.getItem("ELEMENT_PSVI");
        XSModel xsModel = elemPSVI.getSchemaInformation();
        // get a list of [namespace schema information information item]s,
        // one for each namespace.
        XSNamespaceItemList nsItems = xsModel.getNamespaceItems();
        ...

        // get an element declaration of the specified name and namespace
        XSElementDeclaration elemDecl = xsModel.getElementDeclaration
            (namespace, name);
        ...
    }
| How do I access PSVI via DOM? |
| Use the http://apache.org/xml/properties/dom/document-class-name property to set `org.apache.xerces.dom.PSVIDocumentImpl` as the implementation of the `org.w3c.dom.Document` interface. In the resulting DOM tree, you may cast `org.w3c.dom.Element` to the `org.apache.xerces.xs.ElementPSVI` and `org.w3c.dom.Attr` to the `org.apache.xerces.xs.AttributePSVI`.
    import org.apache.xerces.xs.ElementPSVI;
    import org.apache.xerces.xs.XSModel;
    import org.apache.xerces.xs.XSNamedMap;

    ...

    Document document = parser.getDocument();
    Element root = document.getDocumentElement();

    // retrieve PSVI for the root element
    ElementPSVI rootPSVI = (ElementPSVI)root;

    // retrieve the schema used in validation of this document
    XSModel schema = rootPSVI.getSchemaInformation();
    XSNamedMap elementDeclarations =
        schema.getComponents(XSConstants.ELEMENT_DECLARATION);

    // get schema normalized value
    String normalizedValue = rootPSVI.getSchemaNormalizedValue();
| How do I access PSVI via SAX? |
| The Xerces SAX parser also implements the `org.apache.xerces.xs.PSVIProvider` interface. Within the scope of the methods handling the start (`org.xml.sax.ContentHandler.startElement`) and end (`org.xml.sax.ContentHandler.endElement`) of an element, applications may use the `PSVIProvider` to retrieve the PSVI related to the element and its attributes.
    import org.apache.xerces.xs.PSVIProvider;
    import javax.xml.parsers.SAXParser;
    import javax.xml.parsers.SAXParserFactory;

    ...

    SAXParserFactory factory = SAXParserFactory.newInstance();
    SAXParser parser = factory.newSAXParser();
    PSVIProvider psviProvider = (PSVIProvider)parser;
| How do I parse and analyze an XML schema? |
| Please, refer to the Examining Grammars FAQ.
| Can I parse and query XML Schema components in memory? |
| Yes, the XML Schema API specification defines an interface called `XSLoader` which provides methods for loading XML Schema documents into an `XSModel`. The `XSImplementation` interface provides a method to create an `XSLoader` using the DOM Level 3 Bootstraping mechanism. An application can get a reference to an `XSImplementation` using the `getDOMImplementation` method on the `DOMImplementationRegistry` object with the feature string "XS-Loader". To create an `XSLoader` you need to do something like this:
    import org.w3c.dom.DOMImplementationRegistry;
    import org.apache.xerces.xs.XSImplementation;
    import org.apache.xerces.xs.XSLoader;

    ...

    // Get DOM Implementation using DOM Registry
    System.setProperty(DOMImplementationRegistry.PROPERTY,
        "org.apache.xerces.dom.DOMXSImplementationSourceImpl");
    DOMImplementationRegistry registry = DOMImplementationRegistry.newInstance();

    XSImplementation impl =
        (XSImplementation) registry.getDOMImplementation("XS-Loader");

    XSLoader schemaLoader = impl.createXSLoader(null);

    ...
In order to get access to DOM Level 3 functionality in Xerces, see this FAQ.