Project

General

Profile

1 17 jones
/**
2 203 jones
 *  '$RCSfile$'
3
 *    Purpose: A Class that handles the SAX XML events as they
4
 *             are generated from XML documents
5
 *  Copyright: 2000 Regents of the University of California and the
6
 *             National Center for Ecological Analysis and Synthesis
7
 *    Authors: Matt Jones, Jivka Bojilova
8 349 jones
 *    Release: @release@
9 17 jones
 *
10 203 jones
 *   '$Author$'
11
 *     '$Date$'
12
 * '$Revision$'
13 669 jones
 *
14
 * This program is free software; you can redistribute it and/or modify
15
 * it under the terms of the GNU General Public License as published by
16
 * the Free Software Foundation; either version 2 of the License, or
17
 * (at your option) any later version.
18
 *
19
 * This program is distributed in the hope that it will be useful,
20
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
21
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
22
 * GNU General Public License for more details.
23
 *
24
 * You should have received a copy of the GNU General Public License
25
 * along with this program; if not, write to the Free Software
26
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
27 17 jones
 */
28
29 75 jones
package edu.ucsb.nceas.metacat;
30 51 jones
31 17 jones
import java.sql.*;
32 638 bojilova
import java.io.StringReader;
33 17 jones
import java.util.Stack;
34 471 bojilova
import java.util.Vector;
35 821 bojilova
import java.util.Hashtable;
36 471 bojilova
import java.util.Enumeration;
37 18 jones
import java.util.EmptyStackException;
38 17 jones
39 185 jones
import org.xml.sax.Attributes;
40
import org.xml.sax.SAXException;
41 204 jones
import org.xml.sax.SAXParseException;
42 186 jones
import org.xml.sax.ext.DeclHandler;
43 185 jones
import org.xml.sax.ext.LexicalHandler;
44
import org.xml.sax.helpers.DefaultHandler;
45 17 jones
46 31 jones
/**
47
 * A database aware Class implementing callback bethods for the SAX parser to
48
 * call when processing the XML stream and generating events
49
 */
50 186 jones
public class DBSAXHandler extends DefaultHandler
51 471 bojilova
                          implements LexicalHandler, DeclHandler, Runnable {
52 17 jones
53 204 jones
   private boolean	atFirstElement;
54 243 jones
   private boolean	processingDTD;
55 204 jones
   private String 	docname = null;
56 135 jones
   private String 	doctype;
57
   private String 	systemid;
58 17 jones
   private boolean 	stackCreated = false;
59 471 bojilova
   private Stack 	  nodeStack;
60
   private Vector   nodeIndex;
61
   private Connection	  conn = null;
62 396 jones
   private DocumentImpl currentDocument;
63 185 jones
   private DBSAXNode    rootNode;
64 471 bojilova
   private String   action = null;
65
   private String   docid = null;
66 955 tao
   private String   revision = null;
67 471 bojilova
   private String   user = null;
68 802 bojilova
   private String[] groups = null;
69 680 bojilova
   private String   pub = null;
70 471 bojilova
   private Thread   xmlIndex;
71
   private boolean endDocument = false;
72 549 berkley
   private int serverCode = 1;
73 821 bojilova
   private Hashtable namespaces = new Hashtable();
74 17 jones
75 220 jones
   private static final int MAXDATACHARS = 4000;
76 691 bojilova
// DOCTITLE attr cleared from the db
77
//   private static final int MAXTITLELEN = 1000;
78 220 jones
79 31 jones
   /** Construct an instance of the handler class
80
    *
81
    * @param conn the JDBC connection to which information is written
82
    */
83 122 jones
   public DBSAXHandler(Connection conn) {
84 185 jones
     this.conn = conn;
85 204 jones
     this.atFirstElement = true;
86 243 jones
     this.processingDTD = false;
87 17 jones
88 185 jones
     // Create the stack for keeping track of node context
89
     // if it doesn't already exist
90
     if (!stackCreated) {
91
       nodeStack = new Stack();
92 471 bojilova
       nodeIndex = new Vector();
93 185 jones
       stackCreated = true;
94
     }
95 17 jones
   }
96 955 tao
97
  /** Construct an instance of the handler class
98 203 jones
    *
99
    * @param conn the JDBC connection to which information is written
100 425 bojilova
    * @param action - "INSERT" or "UPDATE"
101
    * @param docid to be inserted or updated into JDBC connection
102 680 bojilova
    * @param user the user connected to MetaCat servlet and owns the document
103 802 bojilova
    * @param groups the groups to which user belongs
104 680 bojilova
    * @param pub flag for public "read" access on document
105
    * @param serverCode the serverid from xml_replication on which this document
106
    *        resides.
107
    *
108 203 jones
    */
109 955 tao
   public DBSAXHandler(Connection conn, String action, String docid,
110
                      String user, String[] groups, String pub, int serverCode)
111 425 bojilova
   {
112 203 jones
     this(conn);
113
     this.action = action;
114
     this.docid = docid;
115 425 bojilova
     this.user = user;
116 802 bojilova
     this.groups = groups;
117 680 bojilova
     this.pub = pub;
118
     this.serverCode = serverCode;
119 471 bojilova
     this.xmlIndex = new Thread(this);
120 955 tao
   }
121
122
  /** Construct an instance of the handler class
123
    * In this constructor, user can specify the version need to upadate
124
    *
125
    * @param conn the JDBC connection to which information is written
126
    * @param action - "INSERT" or "UPDATE"
127
    * @param docid to be inserted or updated into JDBC connection
128
    * @param revision, the user specified the revision need to be update
129
    * @param user the user connected to MetaCat servlet and owns the document
130
    * @param groups the groups to which user belongs
131
    * @param pub flag for public "read" access on document
132
    * @param serverCode the serverid from xml_replication on which this document
133
    *        resides.
134
    *
135
    */
136
   public DBSAXHandler(Connection conn, String action, String docid,
137
     String revision, String user, String[] groups, String pub, int serverCode)
138
   {
139
     this(conn);
140
     this.action = action;
141
     this.docid = docid;
142
     this.revision = revision;
143
     this.user = user;
144
     this.groups = groups;
145
     this.pub = pub;
146
     this.serverCode = serverCode;
147
     this.xmlIndex = new Thread(this);
148 203 jones
   }
149 680 bojilova
150 72 bojilova
   /** SAX Handler that receives notification of beginning of the document */
151 122 jones
   public void startDocument() throws SAXException {
152 203 jones
     MetaCatUtil.debugMessage("start Document");
153
154 185 jones
     // Create the document node representation as root
155 457 bojilova
     rootNode = new DBSAXNode(conn, this.docid);
156 185 jones
     // Add the node to the stack, so that any text data can be
157
     // added as it is encountered
158
     nodeStack.push(rootNode);
159 72 bojilova
   }
160
161
   /** SAX Handler that receives notification of end of the document */
162 122 jones
   public void endDocument() throws SAXException {
163 203 jones
     MetaCatUtil.debugMessage("end Document");
164 471 bojilova
     // Starting new thread for writing XML Index.
165
     // It calls the run method of the thread.
166
     try {
167
       xmlIndex.start();
168
     } catch (NullPointerException e) {
169
       xmlIndex = null;
170
       throw new
171
       SAXException("Problem with starting thread for writing XML Index. " +
172
                    e.getMessage());
173
     }
174 72 bojilova
   }
175
176 821 bojilova
   /** SAX Handler that is called at the start of Namespace */
177
   public void startPrefixMapping(String prefix, String uri)
178
                                          throws SAXException
179
   {
180
    MetaCatUtil.debugMessage("NAMESPACE");
181
182
    namespaces.put(prefix, uri);
183
   }
184
185 185 jones
   /** SAX Handler that is called at the start of each XML element */
186
   public void startElement(String uri, String localName,
187
                            String qName, Attributes atts)
188
               throws SAXException {
189 821 bojilova
     MetaCatUtil.debugMessage("Start ELEMENT " + qName);
190
191 203 jones
     DBSAXNode parentNode = null;
192
     DBSAXNode currentNode = null;
193 17 jones
194 203 jones
     // Get a reference to the parent node for the id
195
     try {
196
       parentNode = (DBSAXNode)nodeStack.peek();
197
     } catch (EmptyStackException e) {
198 408 jones
       parentNode = null;
199 203 jones
     }
200 18 jones
201 203 jones
     // Document representation that points to the root document node
202 204 jones
     if (atFirstElement) {
203
       atFirstElement = false;
204 203 jones
       // If no DOCTYPE declaration: docname = root element name
205
       if (docname == null) {
206
         docname = localName;
207 204 jones
         doctype = docname;
208
         MetaCatUtil.debugMessage("DOCNAME-a: " + docname);
209
         MetaCatUtil.debugMessage("DOCTYPE-a: " + doctype);
210 203 jones
       } else if (doctype == null) {
211 204 jones
         doctype = docname;
212
         MetaCatUtil.debugMessage("DOCTYPE-b: " + doctype);
213 203 jones
       }
214
       rootNode.writeNodename(docname);
215
       try {
216 697 bojilova
         // for validated XML Documents store a reference to XML DB Catalog
217
         String catalogid = null;
218
         if ( systemid != null ) {
219
           Statement stmt = conn.createStatement();
220
           ResultSet rs = stmt.executeQuery(
221
                          "SELECT catalog_id FROM xml_catalog " +
222
                          "WHERE entry_type = 'DTD' " +
223
                          "AND public_id = '" + doctype + "'");
224
           boolean hasRow = rs.next();
225
           if ( hasRow ) {
226
            catalogid = rs.getString(1);
227
           }
228
           stmt.close();
229
         }
230 955 tao
231
         //create documentImpl object by the constructor which can specify
232
         //the revision
233 396 jones
         currentDocument = new DocumentImpl(conn, rootNode.getNodeID(),
234 955 tao
                               docname, doctype, docid, revision, action, user,
235 697 bojilova
                               this.pub, catalogid, this.serverCode);
236 955 tao
237
238 457 bojilova
       } catch (Exception ane) {
239 675 berkley
         throw (new SAXException("Error in DBSaxHandler.startElement " +
240
                                 action, ane));
241 408 jones
       }
242 203 jones
     }
243 135 jones
244 203 jones
     // Create the current node representation
245 826 bojilova
     currentNode = new DBSAXNode(conn, qName, localName, parentNode,
246 457 bojilova
                                 currentDocument.getRootNodeID(),docid,
247
                                 currentDocument.getDoctype());
248 471 bojilova
249 821 bojilova
     // Add all of the namespaces
250
     String prefix;
251
     String nsuri;
252
     Enumeration prefixes = namespaces.keys();
253
     while ( prefixes.hasMoreElements() ) {
254
       prefix = (String)prefixes.nextElement();
255
       nsuri = (String)namespaces.get(prefix);
256
       currentNode.setNamespace(prefix, nsuri, docid);
257
     }
258
     namespaces = null;
259
     namespaces = new Hashtable();
260
261 203 jones
     // Add all of the attributes
262
     for (int i=0; i<atts.getLength(); i++) {
263 821 bojilova
       currentNode.setAttribute(atts.getQName(i), atts.getValue(i), docid);
264 203 jones
     }
265 17 jones
266 203 jones
     // Add the node to the stack, so that any text data can be
267
     // added as it is encountered
268
     nodeStack.push(currentNode);
269 471 bojilova
     // Add the node to the vector used by thread for writing XML Index
270
     nodeIndex.addElement(currentNode);
271
272 203 jones
  }
273 471 bojilova
274 819 bojilova
  /* The run method of xmlIndex thread. It writes XML Index for the document. */
275 471 bojilova
  public void run () {
276
    DBSAXNode currNode = null;
277
    DBSAXNode prevNode = null;
278 513 bojilova
    Connection dbconn = null;
279 638 bojilova
    String doctype = currentDocument.getDoctype();
280 471 bojilova
    int step = 0;
281
    int counter = 0;
282 17 jones
283 471 bojilova
    try {
284
      // Opening separate db connection for writing XML Index
285
      MetaCatUtil util = new MetaCatUtil();
286 513 bojilova
      dbconn = util.openDBConnection();
287
      dbconn.setAutoCommit(false);
288 899 berkley
289
      //the following while loop construct checks to make sure that the docid
290
      //of the document that we are trying to index is already
291
      //in the xml_documents table.  if this is not the case, the foreign
292
      //key relationship between xml_documents and xml_index is temporarily
293
      //broken causing multiple problems.
294
      boolean inxmldoc = false;
295
      while(!inxmldoc)
296
      {
297
        String xmlDocumentsCheck = "select distinct docid from xml_documents";
298 955 tao
        PreparedStatement xmlDocCheck =
299
                                  dbconn.prepareStatement(xmlDocumentsCheck);
300 899 berkley
        xmlDocCheck.execute();
301
        ResultSet doccheckRS = xmlDocCheck.getResultSet();
302
        boolean tableHasRows = doccheckRS.next();
303
        Vector docids = new Vector();
304
        while(tableHasRows)
305
        {
306
          docids.add(doccheckRS.getString(1).trim());
307
          tableHasRows = doccheckRS.next();
308
        }
309
310
        for(int i=0; i<docids.size(); i++)
311
        {
312
          String d = ((String)docids.elementAt(i)).trim();
313
          if(docid.trim().equals(d))
314
          {
315
            inxmldoc = true;
316
          }
317
        }
318
        xmlDocCheck.close();
319
      }
320
321 471 bojilova
      // Going through the elements of the document and writing its Index
322
      Enumeration nodes = nodeIndex.elements();
323
      while ( nodes.hasMoreElements() ) {
324
        currNode = (DBSAXNode)nodes.nextElement();
325 638 bojilova
        currNode.updateNodeIndex(dbconn, docid, doctype);
326 471 bojilova
      }
327
328 513 bojilova
      dbconn.commit();
329 638 bojilova
330 819 bojilova
      //if this is a package file
331 887 berkley
      String packagedoctype = util.getOption("packagedoctype");
332
      Vector packagedoctypes = new Vector();
333
334
      packagedoctypes = MetaCatUtil.getOptionList(packagedoctype);
335
336
      if ( packagedoctypes.contains(doctype) )
337 638 bojilova
      {
338 819 bojilova
        // write the package info to xml_relation table
339 797 bojilova
        RelationHandler rth = new RelationHandler(docid, dbconn);
340 819 bojilova
        // from the relations get the access file id for that package
341
        String aclid = rth.getAccessFileID(docid);
342
        // if there are access file, write ACL for that package
343
        if ( aclid != null ) {
344
          runAccessControlList(dbconn, aclid);
345 645 bojilova
        }
346 638 bojilova
      }
347 819 bojilova
      // if it is an access file
348 887 berkley
      else if ( MetaCatUtil.getOptionList(
349
                            util.getOption("accessdoctype")).contains(doctype) )
350 819 bojilova
      {
351
        // write ACL for the package
352
        runAccessControlList(dbconn, docid);
353
      }
354 483 berkley
355 513 bojilova
      dbconn.close();
356 483 berkley
357 471 bojilova
    } catch (Exception e) {
358
      try {
359 513 bojilova
        dbconn.rollback();
360
        dbconn.close();
361 471 bojilova
      } catch (SQLException sqle) {}
362 819 bojilova
      System.out.println("Error in DBSAXHandler.run " + e.getMessage());
363
      e.printStackTrace();
364 471 bojilova
    }
365
  }
366 819 bojilova
367
  // It runs in xmlIndex thread. It writes ACL for a package.
368
  private void runAccessControlList (Connection conn, String aclid)
369
                                                throws Exception
370
  {
371
    // read the access file from xml_nodes
372
    // parse the access file and store the access info into xml_access
373
    AccessControlList aclobj =
374
    new AccessControlList(conn, aclid, //new StringReader(xml),
375
                          user, groups, serverCode);
376
    conn.commit();
377
  }
378 471 bojilova
379 819 bojilova
380 460 bojilova
  /** SAX Handler that is called for each XML text node */
381
  public void characters(char[] cbuf, int start, int len) throws SAXException {
382 203 jones
     MetaCatUtil.debugMessage("CHARACTERS");
383 186 jones
     DBSAXNode currentNode = (DBSAXNode)nodeStack.peek();
384 220 jones
     String data = null;
385
     int leftover = len;
386
     int offset = start;
387
     boolean moredata = true;
388
389
     // This loop deals with the case where there are more characters
390
     // than can fit in a single database text field (limit is
391
     // MAXDATACHARS).  If the text to be inserted exceeds MAXDATACHARS,
392
     // write a series of nodes that are MAXDATACHARS long, and then the
393
     // final node contains the remainder
394
     while (moredata) {
395
       if (leftover > MAXDATACHARS) {
396
         data = new String(cbuf, offset, MAXDATACHARS);
397
         leftover -= MAXDATACHARS;
398
         offset += MAXDATACHARS;
399
       } else {
400
         data = new String(cbuf, offset, leftover);
401
         moredata = false;
402
       }
403 122 jones
404 220 jones
       // Write the content of the node to the database
405 457 bojilova
       currentNode.writeChildNodeToDB("TEXT", null, data, docid);
406 220 jones
     }
407 17 jones
   }
408
409 31 jones
   /**
410 660 bojilova
    * SAX Handler that is called for each XML text node that is
411
    * Ignorable white space
412 31 jones
    */
413 660 bojilova
   public void ignorableWhitespace(char[] cbuf, int start, int len)
414
               throws SAXException {
415
     // When validation is turned "on", white spaces are reported here
416
     // When validation is turned "off" white spaces are not reported here,
417
     // but through characters() callback
418 203 jones
     MetaCatUtil.debugMessage("IGNORABLEWHITESPACE");
419 955 tao
420 660 bojilova
421
     DBSAXNode currentNode = (DBSAXNode)nodeStack.peek();
422
     String data = null;
423
     int leftover = len;
424
     int offset = start;
425
     boolean moredata = true;
426
427
     // This loop deals with the case where there are more characters
428
     // than can fit in a single database text field (limit is
429
     // MAXDATACHARS).  If the text to be inserted exceeds MAXDATACHARS,
430
     // write a series of nodes that are MAXDATACHARS long, and then the
431
     // final node contains the remainder
432
     while (moredata) {
433
       if (leftover > MAXDATACHARS) {
434
         data = new String(cbuf, offset, MAXDATACHARS);
435
         leftover -= MAXDATACHARS;
436
         offset += MAXDATACHARS;
437
       } else {
438
         data = new String(cbuf, offset, leftover);
439
         moredata = false;
440
       }
441
442
       // Write the content of the node to the database
443
       currentNode.writeChildNodeToDB("TEXT", null, data, docid);
444
     }
445 17 jones
   }
446
447 122 jones
   /**
448
    * SAX Handler called once for each processing instruction found:
449
    * node that PI may occur before or after the root element.
450
    */
451
   public void processingInstruction(String target, String data)
452
          throws SAXException {
453 203 jones
     MetaCatUtil.debugMessage("PI");
454 186 jones
     DBSAXNode currentNode = (DBSAXNode)nodeStack.peek();
455 457 bojilova
     currentNode.writeChildNodeToDB("PI", target, data, docid);
456 92 bojilova
   }
457 72 bojilova
458 31 jones
   /** SAX Handler that is called at the end of each XML element */
459 185 jones
   public void endElement(String uri, String localName,
460
                          String qName) throws SAXException {
461 821 bojilova
     MetaCatUtil.debugMessage("End ELEMENT " + qName);
462 17 jones
463 185 jones
     // Get the node from the stack
464
     DBSAXNode currentNode = (DBSAXNode)nodeStack.pop();
465 17 jones
   }
466
467 185 jones
   //
468
   // the next section implements the LexicalHandler interface
469
   //
470
471
   /** SAX Handler that receives notification of DOCTYPE. Sets the DTD */
472
   public void startDTD(String name, String publicId, String systemId)
473
               throws SAXException {
474
     docname = name;
475
     doctype = publicId;
476
     systemid = systemId;
477
478 204 jones
     MetaCatUtil.debugMessage("Start DTD");
479 203 jones
     MetaCatUtil.debugMessage("DOCNAME: " + docname);
480
     MetaCatUtil.debugMessage("DOCTYPE: " + doctype);
481
     MetaCatUtil.debugMessage("  SYSID: " + systemid);
482 185 jones
   }
483
484
   /**
485
    * SAX Handler that receives notification of end of DTD
486
    */
487
   public void endDTD() throws SAXException {
488 697 bojilova
489 204 jones
     MetaCatUtil.debugMessage("end DTD");
490 185 jones
   }
491
492
   /**
493
    * SAX Handler that receives notification of comments in the DTD
494
    */
495
   public void comment(char[] ch, int start, int length) throws SAXException {
496 203 jones
     MetaCatUtil.debugMessage("COMMENT");
497 660 bojilova
     if ( !processingDTD ) {
498
       DBSAXNode currentNode = (DBSAXNode)nodeStack.peek();
499
       currentNode.writeChildNodeToDB("COMMENT", null, new String(ch), docid);
500
     }
501 185 jones
   }
502
503
   /**
504
    * SAX Handler that receives notification of the start of CDATA sections
505
    */
506
   public void startCDATA() throws SAXException {
507 203 jones
     MetaCatUtil.debugMessage("start CDATA");
508 185 jones
   }
509
510
   /**
511
    * SAX Handler that receives notification of the end of CDATA sections
512
    */
513
   public void endCDATA() throws SAXException {
514 203 jones
     MetaCatUtil.debugMessage("end CDATA");
515 185 jones
   }
516
517
   /**
518
    * SAX Handler that receives notification of the start of entities
519
    */
520
   public void startEntity(String name) throws SAXException {
521 243 jones
     MetaCatUtil.debugMessage("start ENTITY: " + name);
522 697 bojilova
//System.out.println("start ENTITY: " + name);
523 243 jones
     if (name.equals("[dtd]")) {
524
       processingDTD = true;
525
     }
526 185 jones
   }
527
528
   /**
529
    * SAX Handler that receives notification of the end of entities
530
    */
531
   public void endEntity(String name) throws SAXException {
532 243 jones
     MetaCatUtil.debugMessage("end ENTITY: " + name);
533 697 bojilova
//System.out.println("end ENTITY: " + name);
534 243 jones
     if (name.equals("[dtd]")) {
535
       processingDTD = false;
536
     }
537 185 jones
   }
538 186 jones
539
   /**
540
    * SAX Handler that receives notification of element declarations
541
    */
542
   public void elementDecl(String name, String model)
543
                        throws org.xml.sax.SAXException {
544 697 bojilova
//System.out.println("ELEMENTDECL: " + name + " " + model);
545 243 jones
     MetaCatUtil.debugMessage("ELEMENTDECL: " + name + " " + model);
546 186 jones
   }
547
548
   /**
549
    * SAX Handler that receives notification of attribute declarations
550
    */
551
   public void attributeDecl(String eName, String aName,
552
                        String type, String valueDefault, String value)
553
                        throws org.xml.sax.SAXException {
554 821 bojilova
555 697 bojilova
//System.out.println("ATTRIBUTEDECL: " + eName + " "
556
//                        + aName + " " + type + " " + valueDefault + " "
557
//                        + value);
558 243 jones
     MetaCatUtil.debugMessage("ATTRIBUTEDECL: " + eName + " "
559
                        + aName + " " + type + " " + valueDefault + " "
560
                        + value);
561 186 jones
   }
562
563
   /**
564
    * SAX Handler that receives notification of internal entity declarations
565
    */
566
   public void internalEntityDecl(String name, String value)
567
                        throws org.xml.sax.SAXException {
568 697 bojilova
//System.out.println("INTERNENTITYDECL: " + name + " " + value);
569 243 jones
     MetaCatUtil.debugMessage("INTERNENTITYDECL: " + name + " " + value);
570 186 jones
   }
571
572
   /**
573
    * SAX Handler that receives notification of external entity declarations
574
    */
575
   public void externalEntityDecl(String name, String publicId,
576
                        String systemId)
577
                        throws org.xml.sax.SAXException {
578 697 bojilova
//System.out.println("EXTERNENTITYDECL: " + name + " " + publicId
579
//                              + " " + systemId);
580 243 jones
     MetaCatUtil.debugMessage("EXTERNENTITYDECL: " + name + " " + publicId
581
                              + " " + systemId);
582 831 bojilova
     // it processes other external entity, not the DTD;
583
     // it doesn't signal for the DTD here
584
     processingDTD = false;
585 186 jones
   }
586
587 204 jones
   //
588
   // the next section implements the ErrorHandler interface
589
   //
590 186 jones
591 204 jones
   /**
592
    * SAX Handler that receives notification of fatal parsing errors
593
    */
594
   public void fatalError(SAXParseException exception) throws SAXException {
595
     MetaCatUtil.debugMessage("FATALERROR");
596
     throw (new SAXException("Fatal processing error.", exception));
597
   }
598
599
   /**
600
    * SAX Handler that receives notification of recoverable parsing errors
601
    */
602
   public void error(SAXParseException exception) throws SAXException {
603
     MetaCatUtil.debugMessage("ERROR");
604 660 bojilova
     throw (new SAXException("Processing error.", exception));
605 204 jones
   }
606
607
   /**
608
    * SAX Handler that receives notification of warnings
609
    */
610
   public void warning(SAXParseException exception) throws SAXException {
611 530 jones
     MetaCatUtil.debugMessage("WARNING");
612 660 bojilova
     throw (new SAXException("Warning.", exception));
613 204 jones
   }
614
615
   //
616
   // Helper, getter and setter methods
617
   //
618
619
   /**
620
    * get the document name
621
    */
622
   public String getDocname() {
623
     return docname;
624
   }
625
626
   /**
627
    * get the document processing state
628
    */
629 243 jones
   public boolean processingDTD() {
630
     return processingDTD;
631 204 jones
   }
632 17 jones
}