KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > net > sf > dozer > util > mapping > vo > jaxb > employee > impl > runtime > SAXUnmarshallerHandlerImpl


1 //
2
// This file was generated by the JavaTM Architecture for XML Binding(JAXB) Reference Implementation, v1.0.4-b18-fcs
3
// See <a HREF="http://java.sun.com/xml/jaxb">http://java.sun.com/xml/jaxb</a>
4
// Any modifications to this file will be lost upon recompilation of the source schema.
5
// Generated on: 2006.10.05 at 10:03:40 CEST
6
//
7

8 package net.sf.dozer.util.mapping.vo.jaxb.employee.impl.runtime;
9
10 import java.util.ArrayList JavaDoc;
11 import java.util.Collections JavaDoc;
12 import java.util.Hashtable JavaDoc;
13 import java.util.Iterator JavaDoc;
14 import java.util.List JavaDoc;
15
16 import javax.xml.XMLConstants JavaDoc;
17 import javax.xml.bind.JAXBException;
18 import javax.xml.bind.UnmarshalException;
19 import javax.xml.bind.ValidationEvent;
20 import javax.xml.bind.ValidationEventHandler;
21
22 import org.xml.sax.Attributes JavaDoc;
23 import org.xml.sax.Locator JavaDoc;
24 import org.xml.sax.SAXException JavaDoc;
25 import org.xml.sax.SAXParseException JavaDoc;
26
27 import com.sun.xml.bind.JAXBAssertionError;
28 import com.sun.xml.bind.unmarshaller.Messages;
29 import com.sun.xml.bind.unmarshaller.Tracer;
30 import com.sun.xml.bind.util.AttributesImpl;
31
32 /**
33  * Implementation of {@link UnmarshallerHandler}.
34  *
35  * This object converts SAX events into unmarshaller events and
36  * cooridnates the entire unmarshalling process.
37  *
38  * @author
39  * <a HREF="mailto:kohsuke.kawaguchi@sun.com">Kohsuke KAWAGUCHI</a>
40  */

41 public class SAXUnmarshallerHandlerImpl
42     implements SAXUnmarshallerHandler, UnmarshallingContext
43 {
44     /**
45      * This flag is set to true at the startDocument event
46      * and false at the endDocument event.
47      *
48      * Until the first document is unmarshalled, we don't
49      * want to return an object. So this variable is initialized
50      * to true.
51      */

52     private boolean isUnmarshalInProgress = true;
53     
54     
55     
56     public SAXUnmarshallerHandlerImpl( UnmarshallerImpl _parent, GrammarInfo _gi ) {
57         this.parent = _parent;
58         grammarInfo = _gi;
59         startPrefixMapping("",""); // by default, the default ns is bound to "".
60
}
61     
62     private final GrammarInfo grammarInfo;
63     public GrammarInfo getGrammarInfo() { return grammarInfo; }
64     
65     /**
66      * Returns true if we should be collecting characters in the current element.
67      */

68     private final boolean shouldCollectText() {
69         return collectText[stackTop];
70     }
71     
72     public void startDocument() throws SAXException JavaDoc {
73         // reset the object
74
result = null;
75         handlerLen=0;
76         patchers=null;
77         patchersLen=0;
78         aborted = false;
79         isUnmarshalInProgress = true;
80         
81         stackTop=0;
82         elementDepth=1;
83     }
84     
85     public void endDocument() throws SAXException JavaDoc {
86         runPatchers();
87         isUnmarshalInProgress = false;
88     }
89     
90     public void startElement( String JavaDoc uri, String JavaDoc local, String JavaDoc qname, Attributes JavaDoc atts )
91             throws SAXException JavaDoc {
92         
93         // work gracefully with misconfigured parsers that don't support namespaces
94
if( uri==null )
95             uri="";
96         if( local==null || local.length()==0 )
97             local=qname;
98         if( qname==null || qname.length()==0 )
99             qname=local;
100         
101         if(result==null) {
102             // this is the root element.
103
// create a root object and start unmarshalling
104
UnmarshallingEventHandler unmarshaller =
105                 grammarInfo.createUnmarshaller(uri,local,this);
106             if(unmarshaller==null) {
107                 // the registry doesn't know about this element.
108
//
109
// the no.1 cause of this problem is that your application is configuring
110
// an XML parser by your self and you forgot to call
111
// the SAXParserFactory.setNamespaceAware(true). When this happens, you see
112
// the namespace URI is reported as empty whereas you expect something else.
113
throw new SAXParseException JavaDoc(
114                     Messages.format( Messages.UNEXPECTED_ROOT_ELEMENT2,
115                         uri, local, computeExpectedRootElements() ),
116                     getLocator() );
117             }
118             result = unmarshaller.owner();
119
120             pushContentHandler(unmarshaller,0);
121         }
122     
123         processText(true);
124     
125         getCurrentHandler().enterElement(uri,local,qname,atts);
126     }
127
128     public final void endElement( String JavaDoc uri, String JavaDoc local, String JavaDoc qname )
129             throws SAXException JavaDoc {
130         
131         // work gracefully with misconfigured parsers that don't support namespaces
132
if( uri==null )
133             uri="";
134         if( local==null || local.length()==0 )
135             local=qname;
136         if( qname==null || qname.length()==0 )
137             qname=local;
138         
139         processText(false);
140         getCurrentHandler().leaveElement(uri,local,qname);
141     }
142     
143     
144     
145     
146     
147     /** Root object that is being unmarshalled. */
148     private Object JavaDoc result;
149     public Object JavaDoc getResult() throws UnmarshalException {
150         if(isUnmarshalInProgress)
151             throw new IllegalStateException JavaDoc();
152         
153         if(!aborted) return result;
154         
155         // there was an error.
156
throw new UnmarshalException((String JavaDoc)null);
157     }
158
159     
160     
161 //
162
//
163
// handler stack maintainance
164
//
165
//
166
private UnmarshallingEventHandler[] handlers = new UnmarshallingEventHandler[16];
167     private int[] mementos = new int[16];
168     private int handlerLen=0;
169     
170     public void pushContentHandler( UnmarshallingEventHandler handler, int memento ) {
171         if(handlerLen==handlers.length) {
172             // expand buffer
173
UnmarshallingEventHandler[] h = new UnmarshallingEventHandler[handlerLen*2];
174             int[] m = new int[handlerLen*2];
175             System.arraycopy(handlers,0,h,0,handlerLen);
176             System.arraycopy(mementos,0,m,0,handlerLen);
177             handlers = h;
178             mementos = m;
179         }
180         handlers[handlerLen] = handler;
181         mementos[handlerLen] = memento;
182         handlerLen++;
183     }
184     
185     public void popContentHandler() throws SAXException JavaDoc {
186         handlerLen--;
187         handlers[handlerLen]=null; // this handler is removed
188
getCurrentHandler().leaveChild(mementos[handlerLen]);
189     }
190
191     public UnmarshallingEventHandler getCurrentHandler() {
192         return handlers[handlerLen-1];
193     }
194
195
196 //
197
//
198
// text handling
199
//
200
//
201
private StringBuffer JavaDoc buffer = new StringBuffer JavaDoc();
202     
203     protected void consumeText( String JavaDoc str, boolean ignorable ) throws SAXException JavaDoc {
204          if(ignorable && str.trim().length()==0)
205             // if we are allowed to ignore text and
206
// the text is ignorable, ignore.
207
return;
208         
209         // otherwise perform a transition by this token.
210
getCurrentHandler().text(str);
211     }
212     private void processText( boolean ignorable ) throws SAXException JavaDoc {
213         if( shouldCollectText() )
214             consumeText(buffer.toString(),ignorable);
215         
216         // avoid excessive object allocation, but also avoid
217
// keeping a huge array inside StringBuffer.
218
if(buffer.length()<1024) buffer.setLength(0);
219         else buffer = new StringBuffer JavaDoc();
220     }
221     
222     public final void characters( char[] buf, int start, int len ) {
223         if( shouldCollectText() )
224             buffer.append(buf,start,len);
225     }
226
227     public final void ignorableWhitespace( char[] buf, int start, int len ) {
228         characters(buf,start,len);
229     }
230
231
232
233     
234 //
235
//
236
// namespace binding maintainance
237
//
238
//
239
private String JavaDoc[] nsBind = new String JavaDoc[16];
240     private int nsLen=0;
241     
242     // in the current scope, nsBind[0] - nsBind[idxStack[idxStackTop]-1]
243
// are active.
244
// use {@link #elementDepth} and {@link stackTop} to access.
245
private int[] idxStack = new int[16];
246     
247     public void startPrefixMapping( String JavaDoc prefix, String JavaDoc uri ) {
248         if(nsBind.length==nsLen) {
249             // expand the buffer
250
String JavaDoc[] n = new String JavaDoc[nsLen*2];
251             System.arraycopy(nsBind,0,n,0,nsLen);
252             nsBind=n;
253         }
254         nsBind[nsLen++] = prefix;
255         nsBind[nsLen++] = uri;
256     }
257     public void endPrefixMapping( String JavaDoc prefix ) {
258         nsLen-=2;
259     }
260     public String JavaDoc resolveNamespacePrefix( String JavaDoc prefix ) {
261         if(prefix.equals("xml"))
262             return "http://www.w3.org/XML/1998/namespace";
263         
264         for( int i=idxStack[stackTop]-2; i>=0; i-=2 ) {
265             if(prefix.equals(nsBind[i]))
266                 return nsBind[i+1];
267         }
268         return null;
269     }
270     public String JavaDoc[] getNewlyDeclaredPrefixes() {
271         return getPrefixList( idxStack[stackTop-1] );
272     }
273
274     public String JavaDoc[] getAllDeclaredPrefixes() {
275         return getPrefixList( 2 ); // skip the default ""->"" mapping
276
}
277     
278     private String JavaDoc[] getPrefixList( int startIndex ) {
279         int size = (idxStack[stackTop]-startIndex)/2;
280         String JavaDoc[] r = new String JavaDoc[size];
281         for( int i=0; i<r.length; i++ )
282             r[i] = nsBind[startIndex+i*2];
283         return r;
284     }
285
286     
287     //
288
// NamespaceContext2 implementation
289
//
290
public Iterator JavaDoc getPrefixes(String JavaDoc uri) {
291         // wrap it into unmodifiable list so that the remove method
292
// will throw UnsupportedOperationException.
293
return Collections.unmodifiableList(
294             getAllPrefixesInList(uri)).iterator();
295     }
296     
297     private List JavaDoc getAllPrefixesInList(String JavaDoc uri) {
298         List JavaDoc a = new ArrayList JavaDoc();
299         
300         if( uri.equals(XMLConstants.XML_NS_URI) ) {
301             a.add(XMLConstants.XML_NS_PREFIX);
302             return a;
303         }
304         if( uri.equals(XMLConstants.XMLNS_ATTRIBUTE_NS_URI) ) {
305             a.add(XMLConstants.XMLNS_ATTRIBUTE);
306             return a;
307         }
308         if( uri==null )
309             throw new IllegalArgumentException JavaDoc();
310           
311         for( int i=nsLen-2; i>=0; i-=2 )
312             if(uri.equals(nsBind[i+1]))
313                 if( getNamespaceURI(nsBind[i]).equals(nsBind[i+1]) )
314                     // make sure that this prefix is still effective.
315
a.add(nsBind[i]);
316          
317         return a;
318     }
319
320     public String JavaDoc getPrefix(String JavaDoc uri) {
321         if( uri.equals(XMLConstants.XML_NS_URI) )
322             return XMLConstants.XML_NS_PREFIX;
323         if( uri.equals(XMLConstants.XMLNS_ATTRIBUTE_NS_URI) )
324             return XMLConstants.XMLNS_ATTRIBUTE;
325         if( uri==null )
326             throw new IllegalArgumentException JavaDoc();
327           
328         for( int i=idxStack[stackTop]-2; i>=0; i-=2 )
329             if(uri.equals(nsBind[i+1]))
330                 if( getNamespaceURI(nsBind[i]).equals(nsBind[i+1]) )
331                     // make sure that this prefix is still effective.
332
return nsBind[i];
333          
334         return null;
335     }
336
337      public String JavaDoc getNamespaceURI(String JavaDoc prefix) {
338          if( prefix.equals(XMLConstants.XMLNS_ATTRIBUTE) )
339              return XMLConstants.XMLNS_ATTRIBUTE_NS_URI;
340          if( prefix==null )
341              throw new IllegalArgumentException JavaDoc();
342         
343          return resolveNamespacePrefix(prefix);
344      }
345
346 //
347
//
348
// Attribute handling
349
//
350
//
351
/**
352      * Attributes stack.
353      */

354     private AttributesImpl[] attStack = new AttributesImpl[16];
355     /**
356      * Element nesting level.
357      */

358     private int elementDepth;
359     /**
360      * Always {@link #elementDepth}-1.
361      */

362     private int stackTop;
363     
364     /**
365      * Stack of collectText flag.
366      * False means text can be ignored for this element.
367      *
368      * Use {@link #elementDepth} and {@link #stackTop} to access the array.
369      */

370     private boolean[] collectText = new boolean[16];
371     
372     public void pushAttributes( Attributes JavaDoc atts, boolean collectTextFlag ) {
373         
374         if( attStack.length==elementDepth ) {
375             // reallocate the buffer
376
AttributesImpl[] buf1 = new AttributesImpl[attStack.length*2];
377             System.arraycopy(attStack,0,buf1,0,attStack.length);
378             attStack = buf1;
379             
380             int[] buf2 = new int[idxStack.length*2];
381             System.arraycopy(idxStack,0,buf2,0,idxStack.length);
382             idxStack = buf2;
383             
384             boolean[] buf3 = new boolean[collectText.length*2];
385             System.arraycopy(collectText,0,buf3,0,collectText.length);
386             collectText = buf3;
387         }
388         
389         elementDepth++;
390         stackTop++;
391         
392         // push the stack
393
AttributesImpl a = attStack[stackTop];
394         if( a==null )
395             attStack[stackTop] = a = new AttributesImpl();
396         else
397             a.clear();
398         
399         // since Attributes object is mutable, it is criticall important
400
// to make a copy.
401
// also symbolize attribute names
402
for( int i=0; i<atts.getLength(); i++ ) {
403             String JavaDoc auri = atts.getURI(i);
404             String JavaDoc alocal = atts.getLocalName(i);
405             String JavaDoc avalue = atts.getValue(i);
406             String JavaDoc aqname = atts.getQName(i);
407             
408             // work gracefully with misconfigured parsers that don't support namespaces
409
if( auri==null )
410                 auri="";
411             if( alocal==null || alocal.length()==0 )
412                 alocal=aqname;
413             if( aqname==null || aqname.length()==0 )
414                 aqname=alocal;
415
416             // <foo xsi:nil="false">some value</foo> is a valid fragment, however
417
// we need a look ahead to correctly handle this case.
418
// (because when we process @xsi:nil, we don't know what the value is,
419
// and by the time we read "false", we can't cancel this attribute anymore.)
420
//
421
// as a quick workaround, we remove @xsi:nil if the value is false.
422
if( auri=="http://www.w3.org/2001/XMLSchema-instance" && alocal=="nil" ) {
423                 String JavaDoc v = avalue.trim();
424                 if(v.equals("false") || v.equals("0"))
425                     continue; // skip this attribute
426
}
427             
428             // otherwise just add it.
429
a.addAttribute(
430                     auri,
431                     alocal,
432                     aqname,
433                     atts.getType(i),
434                     avalue );
435         }
436         
437         
438         // start a new namespace scope
439
idxStack[stackTop] = nsLen;
440         
441         collectText[stackTop] = collectTextFlag;
442     }
443     public void popAttributes() {
444         stackTop--;
445         elementDepth--;
446     }
447     public Attributes JavaDoc getUnconsumedAttributes() {
448         return attStack[stackTop];
449     }
450     /**
451      * @param uri,local
452      * has to be interned.
453      */

454     public int getAttribute( String JavaDoc uri, String JavaDoc local ) {
455         return attStack[stackTop].getIndexFast(uri,local);
456     }
457     public void consumeAttribute( int idx ) throws SAXException JavaDoc {
458         AttributesImpl a = attStack[stackTop];
459         
460         String JavaDoc uri = a.getURI(idx);
461         String JavaDoc local = a.getLocalName(idx);
462         String JavaDoc qname = a.getQName(idx);
463         String JavaDoc value = a.getValue(idx);
464
465         // mark the attribute as consumed
466
// we need to remove the attribute before we process it
467
// because the event handler might access attributes.
468
a.removeAttribute(idx);
469         
470         
471         getCurrentHandler().enterAttribute(uri,local,qname);
472         consumeText(value,false);
473         getCurrentHandler().leaveAttribute(uri,local,qname);
474     }
475     public String JavaDoc eatAttribute( int idx ) throws SAXException JavaDoc {
476         AttributesImpl a = attStack[stackTop];
477         
478         String JavaDoc value = a.getValue(idx);
479
480         // mark the attribute as consumed
481
a.removeAttribute(idx);
482         
483         return value;
484     }
485
486 //
487
//
488
// ID/IDREF related code
489
//
490
//
491
/**
492      * Submitted patchers in the order they've submitted.
493      * Many XML vocabulary doesn't use ID/IDREF at all, so we
494      * initialize it with null.
495      */

496     private Runnable JavaDoc[] patchers = null;
497     private int patchersLen = 0;
498     
499     public void addPatcher( Runnable JavaDoc job ) {
500         // re-allocate buffer if necessary
501
if( patchers==null )
502             patchers = new Runnable JavaDoc[32];
503         if( patchers.length == patchersLen ) {
504             Runnable JavaDoc[] buf = new Runnable JavaDoc[patchersLen*2];
505             System.arraycopy(patchers,0,buf,0,patchersLen);
506             patchers = buf;
507         }
508         patchers[patchersLen++] = job;
509     }
510     
511     /** Executes all the patchers. */
512     private void runPatchers() {
513         if( patchers!=null ) {
514             for( int i=0; i<patchersLen; i++ )
515                 patchers[i].run();
516         }
517     }
518
519     /** Records ID->Object map. */
520     private Hashtable JavaDoc idmap = null;
521
522     public String JavaDoc addToIdTable( String JavaDoc id ) {
523         if(idmap==null) idmap = new Hashtable JavaDoc();
524         idmap.put( id, getCurrentHandler().owner() );
525         return id;
526     }
527     
528     public Object JavaDoc getObjectFromId( String JavaDoc id ) {
529         if(idmap==null) return null;
530         return idmap.get(id);
531     }
532     
533
534
535 //
536
//
537
// Other SAX callbacks
538
//
539
//
540
public void skippedEntity( String JavaDoc name ) {
541     }
542     public void processingInstruction( String JavaDoc target, String JavaDoc data ) {
543         // just ignore
544
}
545     public void setDocumentLocator( Locator JavaDoc loc ) {
546         locator = loc;
547     }
548     public Locator JavaDoc getLocator() { return locator; }
549     
550     private Locator JavaDoc locator;
551
552
553 //
554
//
555
// error handling
556
//
557
//
558
private final UnmarshallerImpl parent;
559     private boolean aborted = false;
560     
561     public void handleEvent(ValidationEvent event, boolean canRecover ) throws SAXException JavaDoc {
562         ValidationEventHandler eventHandler;
563         try {
564             eventHandler = parent.getEventHandler();
565         } catch( JAXBException e ) {
566             // impossible.
567
throw new JAXBAssertionError();
568         }
569
570         boolean recover = eventHandler.handleEvent(event);
571         
572         // if the handler says "abort", we will not return the object
573
// from the unmarshaller.getResult()
574
if(!recover) aborted = true;
575         
576         if( !canRecover || !recover )
577             throw new SAXException JavaDoc( new UnmarshalException(
578                 event.getMessage(),
579                 event.getLinkedException() ) );
580     }
581   
582 //
583
//
584
// ValidationContext implementation
585
//
586
//
587
public String JavaDoc getBaseUri() { return null; }
588     public boolean isUnparsedEntity(String JavaDoc s) { return true; }
589     public boolean isNotation(String JavaDoc s) { return true; }
590
591
592 //
593
//
594
// debug trace methods
595
//
596
//
597
private Tracer tracer;
598     public void setTracer( Tracer t ) {
599         this.tracer = t;
600     }
601     public Tracer getTracer() {
602         if(tracer==null)
603             tracer = new Tracer.Standard();
604         return tracer;
605     }
606     
607     /**
608      * Computes the names of possible root elements for a better error diagnosis.
609      */

610     private String JavaDoc computeExpectedRootElements() {
611         String JavaDoc r = "";
612         
613         String JavaDoc[] probePoints = grammarInfo.getProbePoints();
614         for( int i=0; i<probePoints.length; i+=2 ) {
615             if( grammarInfo.recognize(probePoints[i],probePoints[i+1]) ) {
616                 if(r.length()!=0) r+=',';
617                 r += "<{"+probePoints[i]+"}"+probePoints[i+1]+">";
618             }
619         }
620         
621         return r;
622     }
623 }
624
Popular Tags