001 package com.thaiopensource.validate.xerces;
002
003 import com.oxygenxml.validate.nvdl.NvdlProperty;
004 import com.thaiopensource.util.PropertyMap;
005 import com.thaiopensource.util.PropertyId;
006 import com.thaiopensource.validate.IncorrectSchemaException;
007 import com.thaiopensource.validate.Schema;
008 import com.thaiopensource.validate.SchemaReader;
009 import com.thaiopensource.validate.ValidateProperty;
010 import com.thaiopensource.validate.Option;
011 import com.thaiopensource.validate.xerces.SAXXMLErrorHandler;
012 import com.thaiopensource.validate.xerces.SchemaImpl;
013 import org.apache.xerces.parsers.CachingParserPool;
014 import org.apache.xerces.parsers.XMLGrammarPreparser;
015 import org.apache.xerces.util.SymbolTable;
016 import org.apache.xerces.util.SynchronizedSymbolTable;
017 import org.apache.xerces.util.XMLGrammarPoolImpl;
018 import org.apache.xerces.util.EntityResolverWrapper;
019 import org.apache.xerces.xni.XNIException;
020 import org.apache.xerces.xni.grammars.XMLGrammarDescription;
021 import org.apache.xerces.xni.grammars.XMLGrammarPool;
022 import org.apache.xerces.xni.parser.XMLInputSource;
023 import org.xml.sax.ErrorHandler;
024 import org.xml.sax.InputSource;
025 import org.xml.sax.SAXException;
026 import org.xml.sax.EntityResolver;
027
028 import java.io.IOException;
029 import java.io.StringReader;
030
031 class SchemaReaderImpl implements SchemaReader {
032 private static final PropertyId[] supportedPropertyIds = {
033 ValidateProperty.ERROR_HANDLER,
034 ValidateProperty.ENTITY_RESOLVER,
035 };
036 public Schema createSchema(InputSource in, PropertyMap properties)
037 throws IOException, SAXException, IncorrectSchemaException {
038 SymbolTable symbolTable = new SymbolTable();
039 XMLGrammarPreparser preparser = new XMLGrammarPreparser(symbolTable);
040 XMLGrammarPool grammarPool = new XMLGrammarPoolImpl();
041 preparser.registerPreparser(XMLGrammarDescription.XML_SCHEMA, null);
042 preparser.setGrammarPool(grammarPool);
043 ErrorHandler eh = ValidateProperty.ERROR_HANDLER.get(properties);
044 SAXXMLErrorHandler xeh = new SAXXMLErrorHandler(eh);
045 preparser.setErrorHandler(xeh);
046 EntityResolver er = ValidateProperty.ENTITY_RESOLVER.get(properties);
047 if (er != null)
048 preparser.setEntityResolver(new EntityResolverWrapper(er));
049 try {
050 preparser.preparseGrammar(XMLGrammarDescription.XML_SCHEMA, toXMLInputSource(in));
051 if (properties.contains(NvdlProperty.ATTRIBUTES_SCHEMA)) {
052 // Add a schema for virtual element.
053 String virtualElementSchema =
054 "<xs:schema xmlns:xs=\"http://www.w3.org/2001/XMLSchema\" targetNamespace=\"http://purl.oclc.org/dsdl/nvdl/ns/instance/1.0\">\n" +
055 " <xs:element name=\"virtualElement\">\n" +
056 " <xs:complexType>\n" +
057 " <xs:anyAttribute processContents=\"strict\"/>\n" +
058 " </xs:complexType>\n" +
059 " </xs:element>\n" +
060 "</xs:schema>";
061 XMLInputSource xin = new XMLInputSource(
062 "",
063 "",
064 "",
065 new StringReader(virtualElementSchema),
066 "UTF-8");
067 preparser.preparseGrammar(XMLGrammarDescription.XML_SCHEMA, xin);
068 }
069 }
070 catch (XNIException e) {
071 throw ValidatorImpl.toSAXException(e);
072 }
073 if (xeh.getHadError())
074 throw new IncorrectSchemaException();
075 return new SchemaImpl(new SynchronizedSymbolTable(symbolTable),
076 new CachingParserPool.SynchronizedGrammarPool(grammarPool),
077 properties,
078 supportedPropertyIds);
079 }
080
081 public Option getOption(String uri) {
082 return null;
083 }
084
085 private static XMLInputSource toXMLInputSource(InputSource in) {
086 XMLInputSource xin = new XMLInputSource(in.getPublicId(), in.getSystemId(), null);
087 xin.setByteStream(in.getByteStream());
088 xin.setCharacterStream(in.getCharacterStream());
089 xin.setEncoding(in.getEncoding());
090 return xin;
091 }
092 }