Save This Page
Home » xmlbeans-2.4.0-src » org.apache.xmlbeans.impl.validator » [javadoc | source]
    1   /*   Copyright 2004 The Apache Software Foundation
    2    *
    3    *   Licensed under the Apache License, Version 2.0 (the "License");
    4    *   you may not use this file except in compliance with the License.
    5    *   You may obtain a copy of the License at
    6    *
    7    *       http://www.apache.org/licenses/LICENSE-2.0
    8    *
    9    *   Unless required by applicable law or agreed to in writing, software
   10    *   distributed under the License is distributed on an "AS IS" BASIS,
   11    *   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
   12    *   See the License for the specific language governing permissions and
   13    *  limitations under the License.
   14    */
   15   package org.apache.xmlbeans.impl.validator;
   16   
   17   import org.apache.xmlbeans.SchemaType;
   18   import org.apache.xmlbeans.SchemaTypeLoader;
   19   import org.apache.xmlbeans.XmlCursor;
   20   import org.apache.xmlbeans.XmlError;
   21   import org.apache.xmlbeans.XmlOptions;
   22   import org.apache.xmlbeans.impl.common.ValidatorListener;
   23   import org.apache.xmlbeans.impl.common.XmlWhitespace;
   24   import org.apache.xmlbeans.impl.common.QNameHelper;
   25   
   26   import javax.xml.namespace.QName;
   27   import javax.xml.stream.XMLStreamException;
   28   import javax.xml.stream.XMLStreamReader;
   29   import javax.xml.stream.Location;
   30   import javax.xml.stream.events.XMLEvent;
   31   import javax.xml.stream.util.StreamReaderDelegate;
   32   import java.util.ArrayList;
   33   import java.util.Collection;
   34   import java.util.List;
   35   
   36   /**
   37    * This class is a wrapper over a generic XMLStreamReader that provides validation.
   38    * There are 3 cases:
   39    * <br/> 1) the XMLStreamReader represents a document, it contains only one element document
   40    *          - in this case the user schema type should be null or it should be a document SchemaType
   41    * <br/> 2) the XMLStreamReader represents an xml-fragment (content only) - must have at least one user type or xsi:type
   42    * <br/>     a) it has an xsi:type - if user schema type is available it has to be a base type of xsi:type
   43    * <br/>     b) it doesn't have xsi:type - user must provide a schema type
   44    *         otherwise will error and will not do validation
   45    * <br/> 3) the XMLStreamReader represents a global attribute - i.e. user schema type is null and only one attribute
   46    * <br/>
   47    *
   48    * @author Cezar Andrei (cezar.andrei at bea.com)
   49    * Date: Feb 13, 2004
   50    */
   51   public class ValidatingXMLStreamReader
   52       extends StreamReaderDelegate
   53       implements XMLStreamReader
   54   {
   55       private static final String URI_XSI = "http://www.w3.org/2001/XMLSchema-instance";
   56       private static final QName XSI_TYPE = new QName(URI_XSI, "type");
   57       private static final QName XSI_NIL  = new QName(URI_XSI, "nil");
   58       private static final QName XSI_SL   = new QName(URI_XSI, "schemaLocation");
   59       private static final QName XSI_NSL  = new QName(URI_XSI, "noNamespaceSchemaLocation");
   60   
   61       private SchemaType _contentType;
   62       private SchemaTypeLoader _stl;
   63       private XmlOptions _options;
   64       private Collection _errorListener;
   65       protected Validator _validator;
   66       private final ElementEventImpl _elemEvent;
   67       private final AttributeEventImpl _attEvent;
   68       private final SimpleEventImpl _simpleEvent;
   69       private PackTextXmlStreamReader _packTextXmlStreamReader;
   70   
   71       private int _state;
   72       private final int STATE_FIRSTEVENT = 0;
   73       private final int STATE_VALIDATING = 1;
   74       private final int STATE_ATTBUFFERING = 2;
   75       private final int STATE_ERROR = 3;
   76   
   77       private List _attNamesList;
   78       private List _attValuesList;
   79       private SchemaType _xsiType;
   80   
   81       private int _depth;
   82   
   83       /**
   84        * Default constructor. Use init(...) to set the params.
   85        * See {@link #init}
   86        */
   87       public ValidatingXMLStreamReader()
   88       {
   89           super();
   90           _elemEvent = new ElementEventImpl();
   91           _attEvent = new AttributeEventImpl();
   92           _simpleEvent = new SimpleEventImpl();
   93           _packTextXmlStreamReader = new PackTextXmlStreamReader();
   94       }
   95   
   96       /**
   97        * Used in case of reusing the same ValidatinXMLStreamReader object
   98        * @param xsr The stream to be validated
   99        * @param startWithCurrentEvent Validation will start if true with the current event or if false with the next event in the stream
  100        * @param contentType The schemaType of the content. This can be null for document and global Att validation
  101        * @param stl SchemaTypeLoader context of validation
  102        * @param options Validator options
  103        * @param errorListener Errors and warnings listener
  104        */
  105       public void init(XMLStreamReader xsr, boolean startWithCurrentEvent, SchemaType contentType,
  106                        SchemaTypeLoader stl, XmlOptions options, Collection errorListener)
  107       {
  108           _packTextXmlStreamReader.init(xsr);
  109   
  110   //        setParent(xsr);
  111           setParent(_packTextXmlStreamReader);
  112           _contentType = contentType;
  113           _stl = stl;
  114           _options = options;
  115           _errorListener = errorListener;
  116   //        _elemEvent.setXMLStreamReader(xsr);
  117   //        _attEvent.setXMLStreamReader(xsr);
  118   //        _simpleEvent.setXMLStreamReader(xsr);
  119           _elemEvent.setXMLStreamReader(_packTextXmlStreamReader);
  120           _attEvent.setXMLStreamReader(_packTextXmlStreamReader);
  121           _simpleEvent.setXMLStreamReader(_packTextXmlStreamReader);
  122           _validator = null;
  123           _state = STATE_FIRSTEVENT;
  124           if (_attNamesList!=null)
  125           {
  126               _attNamesList.clear();
  127               _attValuesList.clear();
  128           }
  129           _xsiType = null;
  130           _depth = 0;
  131   
  132           if (startWithCurrentEvent)
  133           {
  134               int evType = getEventType();
  135               validate_event(evType);
  136           }
  137       }
  138   
  139       private static class PackTextXmlStreamReader
  140           extends StreamReaderDelegate
  141           implements XMLStreamReader
  142       {
  143           private boolean _hasBufferedText;
  144           private StringBuffer _buffer = new StringBuffer();
  145           private int _textEventType;
  146   
  147           void init(XMLStreamReader xmlstream)
  148           {
  149               setParent(xmlstream);
  150               _hasBufferedText = false;
  151               _buffer.delete(0, _buffer.length());
  152           }
  153   
  154           public int next()
  155               throws XMLStreamException
  156           {
  157               if (_hasBufferedText)
  158               {
  159                   clearBuffer();
  160                   return super.getEventType();
  161               }
  162   
  163               int evType = super.next();
  164   
  165               if (evType == XMLEvent.CHARACTERS || evType == XMLEvent.CDATA || evType == XMLEvent.SPACE)
  166               {
  167                   _textEventType = evType;
  168                   bufferText();
  169               }
  170   
  171               return evType;
  172           }
  173   
  174           private void clearBuffer()
  175           {
  176               _buffer.delete(0, _buffer.length());
  177               _hasBufferedText = false;
  178           }
  179   
  180           private void bufferText()
  181               throws XMLStreamException
  182           {
  183               if (super.hasText())
  184                   _buffer.append( super.getText());
  185   
  186               _hasBufferedText = true;
  187   
  188               while (hasNext())
  189               {
  190                   int evType = super.next();
  191   
  192                   switch (evType)
  193                   {
  194                   case XMLEvent.CHARACTERS:
  195                   case XMLEvent.CDATA:
  196                   case XMLEvent.SPACE:
  197                       if (super.hasText())
  198                           _buffer.append(super.getText());
  199   
  200                   case XMLEvent.COMMENT:
  201                       //ignore
  202                       continue;
  203                   default:
  204                       return;
  205                   }
  206               }
  207           }
  208   
  209           public String getText()
  210           {
  211               assert _hasBufferedText;
  212               return _buffer.toString();
  213           }
  214   
  215           public int getTextLength()
  216           {
  217               assert _hasBufferedText;
  218               return _buffer.length();
  219           }
  220   
  221           public int getTextStart()
  222           {
  223               assert _hasBufferedText;
  224               return 0;
  225           }
  226   
  227           public char[] getTextCharacters()
  228           {
  229               assert _hasBufferedText;
  230               return _buffer.toString().toCharArray();
  231           }
  232   
  233           public int getTextCharacters(int sourceStart, char[] target, int targetStart, int length)
  234           {
  235               assert _hasBufferedText;
  236               _buffer.getChars(sourceStart, sourceStart + length, target, targetStart);
  237               return length;
  238           }
  239   
  240           public boolean isWhiteSpace()
  241           {
  242               assert _hasBufferedText;
  243               return XmlWhitespace.isAllSpace(_buffer);
  244           }
  245   
  246           public boolean hasText()
  247           {
  248               if (_hasBufferedText)
  249                   return true;
  250               else
  251                   return super.hasText();
  252           }
  253   
  254           public int getEventType()
  255           {
  256               if (_hasBufferedText)
  257                   return _textEventType;
  258               else
  259                   return super.getEventType();
  260           }
  261       }
  262   
  263       private static class ElementEventImpl
  264           implements ValidatorListener.Event
  265       {
  266           private static final int BUF_LENGTH = 1024;
  267           private char[] _buf = new char[BUF_LENGTH];
  268           private int _length;
  269           private boolean _supportForGetTextCharacters = true;
  270   
  271           private XMLStreamReader _xmlStream;
  272   
  273           private void setXMLStreamReader(XMLStreamReader xsr)
  274           {
  275               _xmlStream = xsr;
  276           }
  277   
  278           // can return null, used only to locate errors
  279           public XmlCursor getLocationAsCursor()
  280           {
  281               return null;
  282           }
  283   
  284           public javax.xml.stream.Location getLocation()
  285           {
  286               return _xmlStream.getLocation();
  287           }
  288   
  289           // fill up chars with the xsi:type attribute value if there is one othervise return false
  290           public String getXsiType() // BEGIN xsi:type
  291           {
  292               return _xmlStream.getAttributeValue(URI_XSI, "type");
  293           }
  294   
  295           // fill up chars with xsi:nill attribute value if any
  296           public String getXsiNil() // BEGIN xsi:nil
  297           {
  298               return _xmlStream.getAttributeValue(URI_XSI, "nil");
  299           }
  300   
  301           // not used curently
  302           public String getXsiLoc() // BEGIN xsi:schemaLocation
  303           {
  304               return _xmlStream.getAttributeValue(URI_XSI, "schemaLocation");
  305           }
  306   
  307           // not used curently
  308           public String getXsiNoLoc() // BEGIN xsi:noNamespaceSchemaLocation
  309           {
  310               return _xmlStream.getAttributeValue(URI_XSI, "noNamespaceSchemaLocation");
  311           }
  312   
  313           // On START and ATTR
  314           public QName getName()
  315           {
  316               // avoid construction of a new QName object after the bug in getName() is fixed.
  317               if (_xmlStream.hasName())
  318                   return new QName(_xmlStream.getNamespaceURI(), _xmlStream.getLocalName());
  319               else
  320                   return null;
  321           }
  322   
  323           // On TEXT and ATTR
  324           public String getText()
  325           {
  326               _length = 0;
  327               addTextToBuffer();
  328               return new String( _buf, 0, _length );
  329   //            return _xmlStream.getText();
  330           }
  331   
  332           public String getText(int wsr)
  333           {
  334               return XmlWhitespace.collapse( _xmlStream.getText(), wsr );
  335           }
  336   
  337           public boolean textIsWhitespace()
  338           {
  339               return _xmlStream.isWhiteSpace();
  340           }
  341   
  342           public String getNamespaceForPrefix(String prefix)
  343           {
  344               return _xmlStream.getNamespaceURI(prefix);
  345           }
  346   
  347           private void addTextToBuffer()
  348           {
  349               int textLength = _xmlStream.getTextLength();
  350               ensureBufferLength(textLength);
  351   
  352               if (_supportForGetTextCharacters)
  353                   try
  354                   {
  355                       _length = _xmlStream.getTextCharacters(0, _buf, _length, textLength);
  356                   }
  357                   catch(Exception e)
  358                   {
  359                       _supportForGetTextCharacters = false;
  360                   }
  361   
  362               if(!_supportForGetTextCharacters)
  363               {
  364                   System.arraycopy(_xmlStream.getTextCharacters(), _xmlStream.getTextStart(), _buf, _length, textLength);
  365                   _length = _length + textLength;
  366               }
  367           }
  368   
  369           private void ensureBufferLength(int lengthToAdd)
  370           {
  371               if (_length + lengthToAdd>_buf.length)
  372               {
  373                   char[] newBuf = new char[_length + lengthToAdd];
  374                   if (_length>0)
  375                       System.arraycopy(_buf, 0, newBuf, 0, _length);
  376                   _buf = newBuf;
  377               }
  378           }
  379       }
  380   
  381       private static final class AttributeEventImpl
  382           implements ValidatorListener.Event
  383       {
  384           private int _attIndex;
  385           private XMLStreamReader _xmlStream;
  386   
  387           private void setXMLStreamReader(XMLStreamReader xsr)
  388           {
  389               _xmlStream = xsr;
  390           }
  391   
  392           // can return null, used only to locate errors
  393           public XmlCursor getLocationAsCursor()
  394           {
  395               return null;
  396           }
  397   
  398           public javax.xml.stream.Location getLocation()
  399           {
  400               return _xmlStream.getLocation();
  401           }
  402   
  403           // fill up chars with the xsi:type attribute value if there is one othervise return false
  404           public String getXsiType() // BEGIN xsi:type
  405           {
  406               throw new IllegalStateException();
  407           }
  408   
  409           // fill up chars with xsi:nill attribute value if any
  410           public String getXsiNil() // BEGIN xsi:nil
  411           {
  412               throw new IllegalStateException();
  413           }
  414   
  415           // not used curently
  416           public String getXsiLoc() // BEGIN xsi:schemaLocation
  417           {
  418               throw new IllegalStateException();
  419           }
  420   
  421           // not used curently
  422           public String getXsiNoLoc() // BEGIN xsi:noNamespaceSchemaLocation
  423           {
  424               throw new IllegalStateException();
  425           }
  426   
  427           // On START and ATTR
  428           public QName getName()
  429           {
  430               assert _xmlStream.isStartElement() : "Not on Start Element.";
  431               String uri = _xmlStream.getAttributeNamespace(_attIndex);
  432               QName qn = new QName(uri==null ? "" : uri, _xmlStream.getAttributeLocalName(_attIndex));
  433               //System.out.println("    Att QName: " + qn);
  434               return qn;
  435           }
  436   
  437           // On TEXT and ATTR
  438           public String getText()
  439           {
  440               assert _xmlStream.isStartElement() : "Not on Start Element.";
  441               return _xmlStream.getAttributeValue(_attIndex);
  442           }
  443   
  444           public String getText(int wsr)
  445           {
  446               assert _xmlStream.isStartElement() : "Not on Start Element.";
  447               return XmlWhitespace.collapse( _xmlStream.getAttributeValue(_attIndex), wsr );
  448           }
  449   
  450           public boolean textIsWhitespace()
  451           {
  452               throw new IllegalStateException();
  453           }
  454   
  455           public String getNamespaceForPrefix(String prefix)
  456           {
  457               assert _xmlStream.isStartElement() : "Not on Start Element.";
  458               return _xmlStream.getNamespaceURI(prefix);
  459           }
  460   
  461           private void setAttributeIndex(int attIndex)
  462           {
  463               _attIndex = attIndex;
  464           }
  465       }
  466   
  467       /**
  468        * This is used as implementation of Event for validating global attributes
  469        * and for pushing the buffered attributes
  470        */
  471       private static final class SimpleEventImpl
  472           implements ValidatorListener.Event
  473       {
  474           private String _text;
  475           private QName  _qname;
  476           private XMLStreamReader _xmlStream;
  477   
  478           private void setXMLStreamReader(XMLStreamReader xsr)
  479           {
  480               _xmlStream = xsr;
  481           }
  482   
  483           // should return null, getLocation will be used, used only to locate errors
  484           public XmlCursor getLocationAsCursor()
  485           { return null; }
  486   
  487           public javax.xml.stream.Location getLocation()
  488           {
  489               return _xmlStream.getLocation();
  490           }
  491   
  492           // fill up chars with the xsi:type attribute value if there is one othervise return false
  493           public String getXsiType() // BEGIN xsi:type
  494           { return null; }
  495   
  496           // fill up chars with xsi:nill attribute value if any
  497           public String getXsiNil() // BEGIN xsi:nil
  498           { return null; }
  499   
  500           // not used curently
  501           public String getXsiLoc() // BEGIN xsi:schemaLocation
  502           { return null; }
  503   
  504           // not used curently
  505           public String getXsiNoLoc() // BEGIN xsi:noNamespaceSchemaLocation
  506           { return null; }
  507   
  508           // On START and ATTR
  509           public QName getName()
  510           { return _qname; }
  511   
  512           // On TEXT and ATTR
  513           public String getText()
  514           {
  515               return _text;
  516           }
  517   
  518           public String getText(int wsr)
  519           {
  520               return XmlWhitespace.collapse( _text, wsr );
  521           }
  522   
  523           public boolean textIsWhitespace()
  524           { return false; }
  525   
  526           public String getNamespaceForPrefix(String prefix)
  527           {
  528               return _xmlStream.getNamespaceURI(prefix);
  529           }
  530       }
  531   
  532       /* public methods in XMLStreamReader */
  533   
  534       public Object getProperty(String s) throws IllegalArgumentException
  535       {
  536           return super.getProperty(s);
  537       }
  538   
  539       public int next() throws XMLStreamException
  540       {
  541           int evType = super.next();
  542   //        debugEvent(evType);
  543   
  544           validate_event(evType);
  545   
  546           return evType;
  547       }
  548   
  549       private void validate_event(int evType)
  550       {
  551           if (_state==STATE_ERROR)
  552               return;
  553   
  554           if (_depth<0)
  555               throw new IllegalArgumentException("ValidatingXMLStreamReader cannot go further than the subtree is was initialized on.");
  556   
  557           switch(evType)
  558           {
  559           case XMLEvent.START_ELEMENT:
  560               _depth++;
  561               if (_state == STATE_ATTBUFFERING)
  562                   pushBufferedAttributes();
  563   
  564               if (_validator==null)
  565               {
  566                   // avoid construction of a new QName object after the bug in getName() is fixed.
  567                   QName qname = new QName(getNamespaceURI(), getLocalName());
  568   
  569                   if (_contentType==null)
  570                       _contentType = typeForGlobalElement(qname);
  571   
  572                   if (_state==STATE_ERROR)
  573                       break;
  574   
  575                   initValidator(_contentType);
  576                   _validator.nextEvent(Validator.BEGIN, _elemEvent);
  577               }
  578   
  579               _validator.nextEvent(Validator.BEGIN, _elemEvent);
  580   
  581               int attCount = getAttributeCount();
  582               validate_attributes(attCount);
  583   
  584               break;
  585   
  586           case XMLEvent.ATTRIBUTE:
  587               if (getAttributeCount()==0)
  588                   break;
  589   
  590               if (_state == STATE_FIRSTEVENT || _state == STATE_ATTBUFFERING)
  591               {
  592                   // buffer all Attributes
  593                   for (int i=0; i<getAttributeCount(); i++)
  594                   {
  595                       // avoid construction of a new QName object after the bug in getName() is fixed.
  596                       QName qname = new QName(getAttributeNamespace(i), getAttributeLocalName(i));
  597   
  598                       if (qname.equals(XSI_TYPE))
  599                       {
  600                           String xsiTypeValue = getAttributeValue(i);
  601                           String uri = super.getNamespaceURI(QNameHelper.getPrefixPart(xsiTypeValue));
  602                           QName xsiTypeQname = new QName(uri, QNameHelper.getLocalPart(xsiTypeValue));
  603                           _xsiType = _stl.findType(xsiTypeQname);
  604                       }
  605   
  606                       if (_attNamesList==null)
  607                       {
  608                           _attNamesList = new ArrayList();
  609                           _attValuesList = new ArrayList();
  610                       }
  611                       // skip xsi:type xsi:nil xsi:schemaLocation xsi:noNamespaceSchemaLocation
  612                       if (isSpecialAttribute(qname))
  613                           continue;
  614   
  615                       _attNamesList.add(qname);
  616                       _attValuesList.add(getAttributeValue(i));
  617                   }
  618                   _state = STATE_ATTBUFFERING;
  619               }
  620               else
  621                   throw new IllegalStateException("ATT event must be only at the beggining of the stream.");
  622   
  623               break;
  624   
  625           case XMLEvent.END_ELEMENT:
  626           case XMLEvent.END_DOCUMENT:
  627               _depth--;
  628               if (_state == STATE_ATTBUFFERING)
  629                   pushBufferedAttributes();
  630   
  631               _validator.nextEvent(Validator.END, _elemEvent);
  632               break;
  633   
  634           case XMLEvent.CDATA:
  635           case XMLEvent.CHARACTERS:
  636               if (_state == STATE_ATTBUFFERING)
  637                   pushBufferedAttributes();
  638   
  639               if (_validator==null)
  640               {
  641                   if (_contentType==null)
  642                   {
  643                       if (isWhiteSpace()) // hack/workaround for avoiding errors for parsers that do not generate XMLEvent.SPACE
  644                           break;
  645   
  646                       addError("No content type provided for validation of a content model.");
  647                       _state = STATE_ERROR;
  648                       break;
  649                   }
  650                   initValidator(_contentType);
  651                   _validator.nextEvent(Validator.BEGIN, _simpleEvent);
  652               }
  653   
  654               _validator.nextEvent(Validator.TEXT, _elemEvent);
  655               break;
  656   
  657           case XMLEvent.START_DOCUMENT:
  658               _depth++;
  659               break;
  660   
  661           case XMLEvent.COMMENT:
  662           case XMLEvent.DTD:
  663           case XMLEvent.ENTITY_DECLARATION:
  664           case XMLEvent.ENTITY_REFERENCE:
  665           case XMLEvent.NAMESPACE:
  666           case XMLEvent.NOTATION_DECLARATION:
  667           case XMLEvent.PROCESSING_INSTRUCTION:
  668           case XMLEvent.SPACE:
  669               //ignore
  670               break;
  671   
  672           default:
  673               throw new IllegalStateException("Unknown event type.");
  674           }
  675       }
  676   
  677       private void pushBufferedAttributes()
  678       {
  679           SchemaType validationType = null;
  680   
  681           if (_xsiType!=null)
  682           {
  683               if (_contentType==null)
  684               {
  685                   validationType = _xsiType;
  686               }
  687               else
  688               {
  689                   // we have both _xsiType and _contentType
  690                   if (_contentType.isAssignableFrom(_xsiType))
  691                   {
  692                       validationType = _xsiType;
  693                   }
  694                   else
  695                   {
  696                       addError("Specified type '" + _contentType +
  697                           "' not compatible with found xsi:type '" + _xsiType + "'.");
  698                       _state = STATE_ERROR;
  699                       return;
  700                   }
  701               }
  702           }
  703           else
  704           {
  705               if (_contentType != null)
  706               {
  707                   validationType = _contentType;
  708               }
  709               else if (_attNamesList!=null)
  710               {
  711                   // no xsi:type, no _contentType
  712                   // this is the global attribute case
  713                   validationType = _stl.findAttributeType((QName)_attNamesList.get(0));
  714                   if (validationType==null)
  715                   {
  716                       addError("A schema global attribute with name '" + _attNamesList.get(0) +
  717                           "' could not be found in the current schema type loader.");
  718                       _state = STATE_ERROR;
  719                       return;
  720                   }
  721                   // if _attNamesList.size() > 1 than the validator will add an error
  722               }
  723               else
  724               {
  725                   addError("No content type provided for validation of a content model.");
  726                   _state = STATE_ERROR;
  727                   return;
  728               }
  729           }
  730   
  731           // here validationType is the right type, start pushing all acumulated attributes
  732           initValidator(validationType);
  733           _validator.nextEvent(Validator.BEGIN, _simpleEvent);
  734   
  735           // validate attributes from _attNamesList
  736           validate_attributes(_attNamesList.size());
  737           _attNamesList = null;
  738           _attValuesList = null;
  739   
  740           _state = STATE_VALIDATING;
  741       }
  742   
  743       private boolean isSpecialAttribute(QName qn)
  744       {
  745           if (qn.getNamespaceURI().equals(URI_XSI))
  746               return qn.getLocalPart().equals(XSI_TYPE.getLocalPart()) ||
  747                   qn.getLocalPart().equals(XSI_NIL.getLocalPart()) ||
  748                   qn.getLocalPart().equals(XSI_SL.getLocalPart()) ||
  749                   qn.getLocalPart().equals(XSI_NSL.getLocalPart());
  750   
  751           return false;
  752       }
  753   
  754       /**
  755        * Initializes the validator for the given schemaType
  756        * @param schemaType
  757        */
  758       private void initValidator(SchemaType schemaType)
  759       {
  760           assert schemaType!=null;
  761   
  762           _validator = new Validator(schemaType, null, _stl, _options, _errorListener);
  763       }
  764   
  765       private SchemaType typeForGlobalElement(QName qname)
  766       {
  767           assert qname!=null;
  768   
  769           SchemaType docType = _stl.findDocumentType(qname);
  770   
  771           if (docType==null)
  772           {
  773               addError("Schema document type not found for element '" + qname + "'.");
  774               _state = STATE_ERROR;
  775           }
  776           return docType;
  777       }
  778   
  779       private void addError(String msg)
  780       {
  781           String source = null;
  782   //        Location location = null;
  783           Location location = getLocation();
  784   
  785           if (location != null)
  786           {
  787               source = location.getPublicId();
  788               if (source==null)
  789                   source = location.getSystemId();
  790   
  791               _errorListener.add(XmlError.forLocation(msg, source, location));
  792           }
  793           else
  794               _errorListener.add(XmlError.forMessage(msg));
  795       }
  796   
  797       protected void validate_attributes(int attCount)
  798       {
  799           for(int i=0; i<attCount; i++)
  800           {
  801               validate_attribute(i);
  802           }
  803       }
  804   
  805       protected void validate_attribute(int attIndex)
  806       {
  807           ValidatorListener.Event event;
  808           if (_attNamesList==null)
  809           {
  810               _attEvent.setAttributeIndex(attIndex);
  811               QName qn = _attEvent.getName();
  812               if (isSpecialAttribute(qn))
  813                   return;
  814   
  815               event = _attEvent;
  816           }
  817           else
  818           {
  819               _simpleEvent._qname = (QName)_attNamesList.get(attIndex);
  820               _simpleEvent._text = (String)_attValuesList.get(attIndex);
  821               event = _simpleEvent;
  822           }
  823   
  824           _validator.nextEvent(Validator.ATTR, event);
  825       }
  826   
  827       /**
  828        * @return Returns the validation state up to this point.
  829        * NOTE: At least one START ELEMENT should have been consumed for a valid value to be returned.
  830        */
  831       public boolean isValid()
  832       {
  833           if ( _state==STATE_ERROR || _validator==null)
  834               return false;
  835   
  836           return _validator.isValid();
  837       }
  838   
  839   //    /* for unit testing */
  840   //    public static void main(String[] args) throws FileNotFoundException, XMLStreamException
  841   //    {
  842   //        ValidatingXMLStreamReader valXsr = new ValidatingXMLStreamReader();
  843   //        for( int i = 0; i<args.length; i++)
  844   //        {
  845   //            validate(valXsr, args[i]);
  846   //        }
  847   //    }
  848   //
  849   //    private static void validate(ValidatingXMLStreamReader valXsr, String file)
  850   //        throws XMLStreamException, FileNotFoundException
  851   //    {
  852   //        Collection errors = new ArrayList();
  853   //        XMLStreamReader xsr = XMLInputFactory.newInstance().
  854   //            createXMLStreamReader(new FileInputStream(new File(file)));
  855   //        valXsr.init(xsr, null,
  856   //            XmlBeans.typeLoaderForClassLoader(ValidatingXMLStreamReader.class.getClassLoader()),
  857   //            null,
  858   //            errors);
  859   //
  860   //        while( valXsr.hasNext() )
  861   //        {
  862   //            valXsr.next();
  863   //        }
  864   //
  865   //        System.out.println("File '" + file + "' is: " + (valXsr.isValid() ? "Valid" : "INVALID") + "\t\t\t\t ----------");
  866   //        for (Iterator i = errors.iterator(); i.hasNext(); )
  867   //        {
  868   //            XmlError err = (XmlError)i.next();
  869   //            System.out.println("ERROR " + err.getSeverity() + " " + err.getLine() + ":" + err.getColumn() + " " +
  870   //                err.getMessage() + " ");
  871   //        }
  872   //    }
  873   //
  874   //    private void debugEvent(int evType)
  875   //    {
  876   //        switch(evType)
  877   //        {
  878   //        case XMLEvent.START_ELEMENT:
  879   //            System.out.println("SE     " + _elemEvent.getName());
  880   //            break;
  881   //        case XMLEvent.START_DOCUMENT:
  882   //            System.out.println("SDoc");
  883   //            break;
  884   //        case XMLEvent.END_ELEMENT:
  885   //            System.out.println("EE     " + _elemEvent.getName());
  886   //            break;
  887   //        case XMLEvent.END_DOCUMENT:
  888   //            System.out.println("EDoc");
  889   //            break;
  890   //        case XMLEvent.SPACE:
  891   //            System.out.println("SPACE");
  892   //            break;
  893   //        case XMLEvent.CDATA:
  894   //            System.out.println("CDATA");
  895   //            break;
  896   //        case XMLEvent.CHARACTERS:
  897   //            String c = _elemEvent.getText();
  898   //            System.out.println("TEXT     " + c);
  899   //            break;
  900   //
  901   //        case XMLEvent.ATTRIBUTE:      // global attributes
  902   //            System.out.println("ATT     count: " + _elemEvent._xmlStream.getAttributeCount());
  903   //            for(int i=0; i<_elemEvent._xmlStream.getAttributeCount(); i++)
  904   //            {
  905   //                System.out.println("\t\t" + _elemEvent._xmlStream.getAttributeNamespace(i) + ":" +
  906   //                    _elemEvent._xmlStream.getAttributeLocalName(i) + "  =  " +
  907   //                    _elemEvent._xmlStream.getAttributeValue(i));
  908   //            }
  909   //            break;
  910   //        case XMLEvent.COMMENT:
  911   //            System.out.println("COMMENT");
  912   //            break;
  913   //        case XMLEvent.DTD:
  914   //            System.out.println("DTD");
  915   //            break;
  916   //        case XMLEvent.ENTITY_DECLARATION:
  917   //            System.out.println("ENTITY_DECL");
  918   //            break;
  919   //        case XMLEvent.ENTITY_REFERENCE:
  920   //            System.out.println("ENTITY_REF");
  921   //            break;
  922   //        case XMLEvent.NAMESPACE:
  923   //            System.out.println("NS");
  924   //            break;
  925   //        case XMLEvent.NOTATION_DECLARATION:
  926   //            System.out.println("NOTATION_DECL");
  927   //            break;
  928   //        case XMLEvent.PROCESSING_INSTRUCTION:
  929   //            System.out.println("PI");
  930   //            break;
  931   //        }
  932   //    }
  933   }

Save This Page
Home » xmlbeans-2.4.0-src » org.apache.xmlbeans.impl.validator » [javadoc | source]