package org.exist.xquery; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import org.exist.xquery.parser.XQueryAST; public class XPathException extends Exception { private int line = 0; private int column = 0; private String message = null; private List callStack = null; /** * @param message */ public XPathException(String message) { super(); this.message = message; } public XPathException(int line, int column, String message) { super(); this.message = message; this.line = line; this.column = column; } public XPathException(Expression expr, String message) { super(); this.message = message; this.line = expr.getLine(); this.column = expr.getColumn(); } public XPathException(XQueryAST ast, String message) { super(); this.message = message; if (ast != null) { this.line = ast.getLine(); this.column = ast.getColumn(); } } /** * @param cause */ public XPathException(Throwable cause) { super(cause); } /** * @param message * @param cause */ public XPathException(String message, Throwable cause) { super(cause); this.message = message; } public XPathException(Expression expr, String message, Throwable cause) { this(expr.getLine(), expr.getColumn(), message, cause); } public XPathException(int line, int column, String message, Throwable cause) { super(cause); this.message = message; this.line = line; this.column = column; } public XPathException(int line, int column, Throwable cause) { super(cause); this.line = line; this.column = column; } public void setLocation(int line, int column) { this.line = line; this.column = column; } public int getLine() { return line; } public int getColumn() { return column; } public void addFunctionCall(UserDefinedFunction def, Expression call) { if (callStack == null) callStack = new ArrayList(); callStack.add(new FunctionStackElement(def, call.getLine(), call.getColumn())); } public void prependMessage(String msg) { message = msg + message; } /* (non-Javadoc) * @see java.lang.Throwable#getMessage() */ public String getMessage() { StringBuilder buf = new StringBuilder(); if(message == null) message = ""; buf.append(message); if (getLine() > 0) { buf.append(" [at line "); buf.append(getLine()); buf.append(", column "); buf.append(getColumn()); buf.append("]"); } if (callStack != null) { buf.append("\nIn call to function:\n"); for (Iterator i = callStack.iterator(); i.hasNext(); ) { buf.append('\t').append(i.next()); if (i.hasNext()) buf.append('\n'); } } return buf.toString(); } /** * Returns just the error message, not including * line numbers or the call stack. * * @return error message */ public String getDetailMessage() { return message; } public String getMessageAsHTML() { StringBuilder buf = new StringBuilder(); if(message == null) message = ""; message = message.replaceAll("\r?\n", "<br/>"); buf.append("<h2>").append(message); if (getLine() > 0) { buf.append(" [at line "); buf.append(getLine()); buf.append(", column "); buf.append(getColumn()); buf.append("]"); } buf.append("</h2>"); if (callStack != null) { buf.append("<table id=\"xquerytrace\">"); buf.append("<caption>XQuery Stack Trace</caption>"); FunctionStackElement e; for (Iterator i = callStack.iterator(); i.hasNext(); ) { e = (FunctionStackElement) i.next(); buf.append("<tr><td class=\"func\">").append(e.function).append("</td>"); buf.append("<td class=\"lineinfo\">").append(e.line).append(':').append(e.column).append("</td>"); buf.append("</tr>"); } buf.append("</table>"); } return buf.toString(); } private static class FunctionStackElement { String function; int line; int column; FunctionStackElement(UserDefinedFunction func, int line, int column) { this.function = func.toString(); this.line = line; this.column = column; } public String toString() { StringBuilder buf = new StringBuilder(); buf.append(function).append(" ["); buf.append(line).append(":"); buf.append(column).append(']'); return buf.toString(); } } }