Как я могу напечатать трассировку стека ошибок на странице JSP?
Я установил свою страницу ошибки следующим образом в web.xml:
<error-page>
<exception-type>java.lang.Exception</exception-type>
<location>/errors/error.jsp</location>
</error-page>
Теперь я хотел бы напечатать трассировку стека ошибок на JSP (конечно, только в режиме разработки). Как я могу напечатать трассировку стека ошибок на моей странице JSP? Я не использую никаких фреймворков для этого приложения, поэтому для моей программы доступны только API-интерфейсы сервлетов по умолчанию.
8 ответов
Получить параметр из запроса, который установлен внутри, и использовать его для печати и обработки другой информации, такой как cause
, message
<c:set var="exception" value="${requestScope['javax.servlet.error.exception']}"/>
и распечатать трассировку стека
<!-- Stack trace -->
<jsp:scriptlet>
exception.printStackTrace(new java.io.PrintWriter(out));
</jsp:scriptlet>
Смотрите также
Следующие параметры будут установлены контейнером, когда запрос будет перенаправлен на страницу ошибки.
- javax.servlet.error.status_code
- javax.servlet.error.exception
- javax.servlet.error.message
- javax.servlet.error.request_uri
- javax.servlet.error.servlet_name
- javax.servlet.error.exception_type
В вашей ошибке JSP сделать это,
<%request.getAttribute("javax.servlet.error.exception").printStackTrace(new java.io.PrintWriter(out));
Или иначе, если ваша страница ошибки определена как Страница ошибки с Директивой страницы, как,
<%@ page isErrorPage="true" import="java.io.*"%>
Переменная сценария исключения будет объявлена в JSP. Вы можете распечатать переменную сценария, используя скриптлет, используя
exception.printStackTrace(new java.io.PrintWriter(out));
Или же,
<jsp:scriptlet>
exception.printStackTrace(response.getWriter())
</jsp:scriptlet>
Использование JSP скриптлетов не одобряется практикой с десятилетия. Тебе лучше всего избегать этого.
Если вы уже используете EL 2.2 или новее (Tomcat 7+, JBoss AS 6+, WildFly, GlassFish 3+ и т. Д.), С новой поддержкой выражений методов в форме ${instance.method()}
тогда вы можете просто использовать 100% EL для этого.
Сначала вам нужно явно очистить JSP-писатель через JspWriter#flush()
, так что все предыдущие выходные данные шаблона JSP действительно записываются в создатель ответа сервлета:
${pageContext.out.flush()}
Тогда вы можете просто пройти ServletResponse#getWriter()
в Throwable#printStackTrace()
,
${exception.printStackTrace(pageContext.response.writer)}
Полный пример:
<%@page pageEncoding="UTF-8" isErrorPage="true" %>
...
<pre>${pageContext.out.flush()}${exception.printStackTrace(pageContext.response.writer)}</pre>
Если вы уже используете EL 3.0 (Tomcat 8+, WildFly, GlassFish 4+ и т. Д.), Вы даже можете сделать его одним выражением с помощью нового оператора точки с запятой, который разделяет операторы EL:
<%@page pageEncoding="UTF-8" isErrorPage="true" %>
...
<pre>${pageContext.out.flush();exception.printStackTrace(pageContext.response.writer)}</pre>
Если вы не можете использовать isErrorPage="true"
по какой-то причине (и, таким образом, ${exception}
неявный объект недоступен), затем просто заменить на ${requestScope['javax.servlet.error.exception']}
:
<%@page pageEncoding="UTF-8" %>
...
<pre>${pageContext.out.flush()}${requestScope['javax.servlet.error.exception'].printStackTrace(pageContext.response.writer)}</pre>
Если вы все еще не пользуетесь EL 2.2, тогда вам лучше всего создать собственную функцию EL. Подробности можно найти в разделе Каков хороший способ пересылки исключения из сервлетов на страницу jsp?
Ниже приведен более полный пример страницы с ошибкой:
<%@page pageEncoding="UTF-8" isErrorPage="true" %>
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
...
<ul>
<li>Exception: <c:out value="${requestScope['javax.servlet.error.exception']}" /></li>
<li>Exception type: <c:out value="${requestScope['javax.servlet.error.exception_type']}" /></li>
<li>Exception message: <c:out value="${requestScope['javax.servlet.error.message']}" /></li>
<li>Request URI: <c:out value="${requestScope['javax.servlet.error.request_uri']}" /></li>
<li>Servlet name: <c:out value="${requestScope['javax.servlet.error.servlet_name']}" /></li>
<li>Status code: <c:out value="${requestScope['javax.servlet.error.status_code']}" /></li>
<li>Stack trace: <pre>${pageContext.out.flush()}${exception.printStackTrace(pageContext.response.writer)}</pre></li>
</ul>
Может быть, это поможет вам..
будет показано исключение StackTrace в браузер
exception.printStackTrace(response.getWriter());
Или же
<%
try{
int test = Integer.parseInt("hola");
}catch(Exception e){
**// HERE THE MAGIC BEGINS!!**
out.println("<div id=\"error\">");
e.printStackTrace(new java.io.PrintWriter(out));
out.println("</div>");
**// THE MAGIC ENDS!!**
}
%>
Если вы объявите <% page isErrorPage="true" %>
в верхней части error.jsp у вас есть доступ к выброшенному исключению (и, следовательно, ко всем его получателям) ${exception}
<p>Message: ${exception.message}
увидеть больше.. Отображение ошибок на экранах ошибок
На странице ошибки просто сделайте:
<jsp:scriptlet>
exception.printStackTrace(response.getWriter())
</jsp:scriptlet>
Хотя возникает вопрос: что пользователь собирается делать с исключением? Почему бы не записать исключение в журнал ошибок, чтобы оно сохранилось, и вы можете вернуться к нему после того, как пользователь пожаловался?
Или, чтобы избежать использования скриптлетов в вашем jsp, используйте jstl:
<%@taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
...
<c:set var="exception" value="${requestScope['javax.servlet.error.exception']}"/>
<c:if test="${exception != null}">
<h4>${exception}</h4>
<c:forEach var="stackTraceElem" items="${exception.stackTrace}">
<c:out value="${stackTraceElem}"/><br/>
</c:forEach>
</c:if>
В идеале, скриптлеты должны быть запрещены как лучшая практика. Явно запретите скрипты в ваших jsp-файлах через конфигурацию web.xml:
<jsp-config>
<jsp-property-group>
<url-pattern>*.jsp</url-pattern>
<scripting-invalid>true</scripting-invalid>
</jsp-property-group>
</jsp-config>
Объект сгенерированного исключения доступен в виде атрибута запроса с именем "javax.servlet.error.exception". Итак, в вашем JSP вы можете написать:
<% request.getAttribute("javax.servlet.error.exception").printStackTrace(new java.io.PrintWriter(out); %>
Вы можете использовать библиотеку ядра jstl
1) Импортировать tablib поверх файла JSP
<%@ taglib prefi x=”c” uri=”http://java.sun.com/jsp/jstl/core” %>
2) использовать тег
<c:catch var="myExceptionObject">
Code that might throw Exception
<c:catch/>
<c:if test="${myExceptionObject} != null">
There was an exception: ${myExceptionObject.message}
<c:if/>
В error.jsp добавьте следующие строки
<%Logger log = Logger.getLogger("error_jsp.class");
Exception e = (Exception)request.getAttribute("javax.servlet.error.exception");
log.debug(request.getAttribute("javax.servlet.error.message"));
e.printStackTrace();
log.debug(e.getStackTrace());%>