1 /* Copyright 2002-2005 Elliotte Rusty Harold
2 
3    This library is free software; you can redistribute it and/or modify
4    it under the terms of version 2.1 of the GNU Lesser General Public
5    License as published by the Free Software Foundation.
6 
7    This library is distributed in the hope that it will be useful,
8    but WITHOUT ANY WARRANTY; without even the implied warranty of
9    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10    GNU Lesser General Public License for more details.
11 
12    You should have received a copy of the GNU Lesser General Public
13    License along with this library; if not, write to the
14    Free Software Foundation, Inc., 59 Temple Place, Suite 330,
15    Boston, MA 02111-1307  USA
16 
17    You can contact Elliotte Rusty Harold by sending e-mail to
18    elharo@ibiblio.org. Please include the word "XOM" in the
19    subject line. The XOM home page is located at http://www.xom.nu/
20 */
21 
22 
23 package nu.xom;
24 
25 /**
26  * <p>
27  *  The generic superclass for most runtime exceptions thrown in
28  *  <code>nu.xom</code>. The general principle followed is that
29  *  anything that can normally be detected by testing such as
30  *  using spaces in an element name is a runtime exception.
31  *  Exceptions that depend on environmental conditions,
32  *  such as might occur when parsing an external file,
33  *  are checked exceptions, because these depend on variable input,
34  *  and thus all problems may not be detected during testing.
35  * </p>
36  *
37  * @author Elliotte Rusty Harold
38  * @version 1.1b3
39  *
40  */
41 public class XMLException extends RuntimeException {
42 
43 
44     private static final long serialVersionUID = -4497254051626978523L;
45 
46     private Throwable cause;
47 
48 
49     /**
50      * <p>
51      * Creates a new <code>XMLException</code>
52      * with the specified detail message
53      * and an underlying root cause.
54      * </p>
55      *
56      * @param message information about the cause of the exception
57      * @param cause the nested exception that caused this exception
58      */
XMLException(String message, Throwable cause)59     public XMLException(String message, Throwable cause) {
60         super(message);
61         this.initCause(cause);
62     }
63 
64 
65     /**
66      * <p>
67      *   Creates a new <code>XMLException</code> with
68      *   the specified detail message.
69      *  </p>
70      *
71      * @param message information about the cause of the exception
72      */
XMLException(String message)73     public XMLException(String message) {
74         super(message);
75     }
76 
77 
78     /**
79      * <p>
80      *  Return the original cause that led to this exception,
81      *  or null if there was no original exception.
82      * </p>
83      *
84      * @return the root cause of this exception
85      */
getCause()86     public Throwable getCause() {
87         return this.cause;
88     }
89 
90 
91     // null is insufficient for detecting an uninitialized cause.
92     // The cause may be set to null which may not then be reset.
93     private boolean causeSet = false;
94 
95 
96     /**
97      * <p>
98      * Sets the root cause of this exception. This may
99      * only be called once. Subsequent calls throw an
100      * <code>IllegalStateException</code>.
101      * </p>
102      *
103      * <p>
104      * This method is unnecessary in Java 1.4 where it could easily be
105      * inherited from the superclass. However, including it here
106      * allows this  method to be used in Java 1.3 and earlier.
107      * </p>
108      *
109      * @param cause the root cause of this exception
110      *
111      * @return this <code>XMLException</code>
112      *
113      * @throws IllegalArgumentException if the cause is this exception
114      *   (An exception cannot be its own cause.)
115      * @throws IllegalStateException if this method is called twice
116      */
initCause(Throwable cause)117     public final Throwable initCause(Throwable cause) {
118 
119         if (causeSet) {
120             throw new IllegalStateException("Can't overwrite cause");
121         }
122         else if (cause == this) {
123             throw new IllegalArgumentException("Self-causation not permitted");
124         }
125         else this.cause = cause;
126         causeSet = true;
127         return this;
128 
129     }
130 
131 
132 }
133