1. // $Id: TransformerException.java,v 1.2 2003/09/10 01:45:55 jsuttor Exp $
  2. /*
  3. * @(#)TransformerException.java 1.17 04/07/26
  4. *
  5. * Copyright 2004 Sun Microsystems, Inc. All rights reserved.
  6. * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
  7. */
  8. package javax.xml.transform;
  9. import java.lang.reflect.Method;
  10. import java.lang.reflect.InvocationTargetException;
  11. /**
  12. * This class specifies an exceptional condition that occured
  13. * during the transformation process.
  14. */
  15. public class TransformerException extends Exception {
  16. /** Field locator specifies where the error occured */
  17. SourceLocator locator;
  18. /**
  19. * Method getLocator retrieves an instance of a SourceLocator
  20. * object that specifies where an error occured.
  21. *
  22. * @return A SourceLocator object, or null if none was specified.
  23. */
  24. public SourceLocator getLocator() {
  25. return locator;
  26. }
  27. /**
  28. * Method setLocator sets an instance of a SourceLocator
  29. * object that specifies where an error occured.
  30. *
  31. * @param location A SourceLocator object, or null to clear the location.
  32. */
  33. public void setLocator(SourceLocator location) {
  34. locator = location;
  35. }
  36. /** Field containedException specifies a wrapped exception. May be null. */
  37. Throwable containedException;
  38. /**
  39. * This method retrieves an exception that this exception wraps.
  40. *
  41. * @return An Throwable object, or null.
  42. * @see #getCause
  43. */
  44. public Throwable getException() {
  45. return containedException;
  46. }
  47. /**
  48. * Returns the cause of this throwable or <code>null</code> if the
  49. * cause is nonexistent or unknown. (The cause is the throwable that
  50. * caused this throwable to get thrown.)
  51. */
  52. public Throwable getCause() {
  53. return ((containedException == this)
  54. ? null
  55. : containedException);
  56. }
  57. /**
  58. * Initializes the <i>cause</i> of this throwable to the specified value.
  59. * (The cause is the throwable that caused this throwable to get thrown.)
  60. *
  61. * <p>This method can be called at most once. It is generally called from
  62. * within the constructor, or immediately after creating the
  63. * throwable. If this throwable was created
  64. * with {@link #TransformerException(Throwable)} or
  65. * {@link #TransformerException(String,Throwable)}, this method cannot be called
  66. * even once.
  67. *
  68. * @param cause the cause (which is saved for later retrieval by the
  69. * {@link #getCause()} method). (A <tt>null</tt> value is
  70. * permitted, and indicates that the cause is nonexistent or
  71. * unknown.)
  72. * @return a reference to this <code>Throwable</code> instance.
  73. * @throws IllegalArgumentException if <code>cause</code> is this
  74. * throwable. (A throwable cannot
  75. * be its own cause.)
  76. * @throws IllegalStateException if this throwable was
  77. * created with {@link #TransformerException(Throwable)} or
  78. * {@link #TransformerException(String,Throwable)}, or this method has already
  79. * been called on this throwable.
  80. */
  81. public synchronized Throwable initCause(Throwable cause) {
  82. if (this.containedException != null) {
  83. throw new IllegalStateException("Can't overwrite cause");
  84. }
  85. if (cause == this) {
  86. throw new IllegalArgumentException(
  87. "Self-causation not permitted");
  88. }
  89. this.containedException = cause;
  90. return this;
  91. }
  92. /**
  93. * Create a new TransformerException.
  94. *
  95. * @param message The error or warning message.
  96. */
  97. public TransformerException(String message) {
  98. super(message);
  99. this.containedException = null;
  100. this.locator = null;
  101. }
  102. /**
  103. * Create a new TransformerException wrapping an existing exception.
  104. *
  105. * @param e The exception to be wrapped.
  106. */
  107. public TransformerException(Throwable e) {
  108. super(e.toString());
  109. this.containedException = e;
  110. this.locator = null;
  111. }
  112. /**
  113. * Wrap an existing exception in a TransformerException.
  114. *
  115. * <p>This is used for throwing processor exceptions before
  116. * the processing has started.</p>
  117. *
  118. * @param message The error or warning message, or null to
  119. * use the message from the embedded exception.
  120. * @param e Any exception
  121. */
  122. public TransformerException(String message, Throwable e) {
  123. super(((message == null) || (message.length() == 0))
  124. ? e.toString()
  125. : message);
  126. this.containedException = e;
  127. this.locator = null;
  128. }
  129. /**
  130. * Create a new TransformerException from a message and a Locator.
  131. *
  132. * <p>This constructor is especially useful when an application is
  133. * creating its own exception from within a DocumentHandler
  134. * callback.</p>
  135. *
  136. * @param message The error or warning message.
  137. * @param locator The locator object for the error or warning.
  138. */
  139. public TransformerException(String message, SourceLocator locator) {
  140. super(message);
  141. this.containedException = null;
  142. this.locator = locator;
  143. }
  144. /**
  145. * Wrap an existing exception in a TransformerException.
  146. *
  147. * @param message The error or warning message, or null to
  148. * use the message from the embedded exception.
  149. * @param locator The locator object for the error or warning.
  150. * @param e Any exception
  151. */
  152. public TransformerException(String message, SourceLocator locator,
  153. Throwable e) {
  154. super(message);
  155. this.containedException = e;
  156. this.locator = locator;
  157. }
  158. /**
  159. * Get the error message with location information
  160. * appended.
  161. *
  162. * @return A <code>String</code> representing the error message with
  163. * location information appended.
  164. */
  165. public String getMessageAndLocation() {
  166. StringBuffer sbuffer = new StringBuffer();
  167. String message = super.getMessage();
  168. if (null != message) {
  169. sbuffer.append(message);
  170. }
  171. if (null != locator) {
  172. String systemID = locator.getSystemId();
  173. int line = locator.getLineNumber();
  174. int column = locator.getColumnNumber();
  175. if (null != systemID) {
  176. sbuffer.append("; SystemID: ");
  177. sbuffer.append(systemID);
  178. }
  179. if (0 != line) {
  180. sbuffer.append("; Line#: ");
  181. sbuffer.append(line);
  182. }
  183. if (0 != column) {
  184. sbuffer.append("; Column#: ");
  185. sbuffer.append(column);
  186. }
  187. }
  188. return sbuffer.toString();
  189. }
  190. /**
  191. * Get the location information as a string.
  192. *
  193. * @return A string with location info, or null
  194. * if there is no location information.
  195. */
  196. public String getLocationAsString() {
  197. if (null != locator) {
  198. StringBuffer sbuffer = new StringBuffer();
  199. String systemID = locator.getSystemId();
  200. int line = locator.getLineNumber();
  201. int column = locator.getColumnNumber();
  202. if (null != systemID) {
  203. sbuffer.append("; SystemID: ");
  204. sbuffer.append(systemID);
  205. }
  206. if (0 != line) {
  207. sbuffer.append("; Line#: ");
  208. sbuffer.append(line);
  209. }
  210. if (0 != column) {
  211. sbuffer.append("; Column#: ");
  212. sbuffer.append(column);
  213. }
  214. return sbuffer.toString();
  215. } else {
  216. return null;
  217. }
  218. }
  219. /**
  220. * Print the the trace of methods from where the error
  221. * originated. This will trace all nested exception
  222. * objects, as well as this object.
  223. */
  224. public void printStackTrace() {
  225. printStackTrace(new java.io.PrintWriter(System.err, true));
  226. }
  227. /**
  228. * Print the the trace of methods from where the error
  229. * originated. This will trace all nested exception
  230. * objects, as well as this object.
  231. * @param s The stream where the dump will be sent to.
  232. */
  233. public void printStackTrace(java.io.PrintStream s) {
  234. printStackTrace(new java.io.PrintWriter(s));
  235. }
  236. /**
  237. * Print the the trace of methods from where the error
  238. * originated. This will trace all nested exception
  239. * objects, as well as this object.
  240. * @param s The writer where the dump will be sent to.
  241. */
  242. public void printStackTrace(java.io.PrintWriter s) {
  243. if (s == null) {
  244. s = new java.io.PrintWriter(System.err, true);
  245. }
  246. try {
  247. String locInfo = getLocationAsString();
  248. if (null != locInfo) {
  249. s.println(locInfo);
  250. }
  251. super.printStackTrace(s);
  252. } catch (Throwable e) {}
  253. Throwable exception = getException();
  254. for (int i = 0; (i < 10) && (null != exception); i++) {
  255. s.println("---------");
  256. try {
  257. if (exception instanceof TransformerException) {
  258. String locInfo =
  259. ((TransformerException) exception)
  260. .getLocationAsString();
  261. if (null != locInfo) {
  262. s.println(locInfo);
  263. }
  264. }
  265. exception.printStackTrace(s);
  266. } catch (Throwable e) {
  267. s.println("Could not print stack trace...");
  268. }
  269. try {
  270. Method meth =
  271. ((Object) exception).getClass().getMethod("getException",
  272. null);
  273. if (null != meth) {
  274. Throwable prev = exception;
  275. exception = (Throwable) meth.invoke(exception, null);
  276. if (prev == exception) {
  277. break;
  278. }
  279. } else {
  280. exception = null;
  281. }
  282. } catch (InvocationTargetException ite) {
  283. exception = null;
  284. } catch (IllegalAccessException iae) {
  285. exception = null;
  286. } catch (NoSuchMethodException nsme) {
  287. exception = null;
  288. }
  289. }
  290. // insure output is written
  291. s.flush();
  292. }
  293. }