StandardHostValvepublic final class StandardHostValve extends org.apache.catalina.valves.ValveBase Valve that implements the default basic behavior for the
StandardHost container implementation.
USAGE CONSTRAINT: This implementation is likely to be useful only
when processing HTTP requests. |
Fields Summary |
---|
private static org.apache.juli.logging.Log | log | private static final String | infoThe descriptive information related to this implementation. | private static final org.apache.catalina.util.StringManager | smThe string manager for this package. |
Methods Summary |
---|
protected boolean | custom(org.apache.catalina.connector.Request request, org.apache.catalina.connector.Response response, org.apache.catalina.deploy.ErrorPage errorPage)Handle an HTTP status code or Java exception by forwarding control
to the location included in the specified errorPage object. It is
assumed that the caller has already recorded any request attributes
that are to be forwarded to this page. Return true if
we successfully utilized the specified error page location, or
false if the default error report should be rendered.
if (container.getLogger().isDebugEnabled())
container.getLogger().debug("Processing " + errorPage);
request.setPathInfo(errorPage.getLocation());
try {
// Reset the response if possible (else IllegalStateException)
//hres.reset();
// Reset the response (keeping the real error code and message)
Integer statusCodeObj =
(Integer) request.getAttribute(Globals.STATUS_CODE_ATTR);
int statusCode = statusCodeObj.intValue();
String message =
(String) request.getAttribute(Globals.ERROR_MESSAGE_ATTR);
response.reset(statusCode, message);
// Forward control to the specified location
ServletContext servletContext =
request.getContext().getServletContext();
RequestDispatcher rd =
servletContext.getRequestDispatcher(errorPage.getLocation());
rd.forward(request.getRequest(), response.getResponse());
// If we forward, the response is suspended again
response.setSuspended(false);
// Indicate that we have successfully processed this custom page
return (true);
} catch (Throwable t) {
// Report our failure to process this custom page
container.getLogger().error("Exception Processing " + errorPage, t);
return (false);
}
| public final void | event(org.apache.catalina.connector.Request request, org.apache.catalina.connector.Response response, org.apache.catalina.CometEvent event)Process Comet event.
// Select the Context to be used for this Request
Context context = request.getContext();
// Bind the context CL to the current thread
if( context.getLoader() != null ) {
// Not started - it should check for availability first
// This should eventually move to Engine, it's generic.
Thread.currentThread().setContextClassLoader
(context.getLoader().getClassLoader());
}
// Ask this Context to process this request
context.getPipeline().getFirst().event(request, response, event);
// Access a session (if present) to update last accessed time, based on a
// strict interpretation of the specification
if (Globals.STRICT_SERVLET_COMPLIANCE) {
request.getSession(false);
}
// Error page processing
response.setSuspended(false);
Throwable t = (Throwable) request.getAttribute(Globals.EXCEPTION_ATTR);
if (t != null) {
throwable(request, response, t);
} else {
status(request, response);
}
// Restore the context classloader
Thread.currentThread().setContextClassLoader
(StandardHostValve.class.getClassLoader());
| protected static org.apache.catalina.deploy.ErrorPage | findErrorPage(org.apache.catalina.Context context, java.lang.Throwable exception)Find and return the ErrorPage instance for the specified exception's
class, or an ErrorPage instance for the closest superclass for which
there is such a definition. If no associated ErrorPage instance is
found, return null .
if (exception == null)
return (null);
Class clazz = exception.getClass();
String name = clazz.getName();
while (!Object.class.equals(clazz)) {
ErrorPage errorPage = context.findErrorPage(name);
if (errorPage != null)
return (errorPage);
clazz = clazz.getSuperclass();
if (clazz == null)
break;
name = clazz.getName();
}
return (null);
| public java.lang.String | getInfo()Return descriptive information about this Valve implementation.
// ------------------------------------------------------------- Properties
return (info);
| public final void | invoke(org.apache.catalina.connector.Request request, org.apache.catalina.connector.Response response)Select the appropriate child Context to process this request,
based on the specified request URI. If no matching Context can
be found, return an appropriate HTTP error.
// Select the Context to be used for this Request
Context context = request.getContext();
if (context == null) {
response.sendError
(HttpServletResponse.SC_INTERNAL_SERVER_ERROR,
sm.getString("standardHost.noContext"));
return;
}
// Bind the context CL to the current thread
if( context.getLoader() != null ) {
// Not started - it should check for availability first
// This should eventually move to Engine, it's generic.
Thread.currentThread().setContextClassLoader
(context.getLoader().getClassLoader());
}
// Ask this Context to process this request
context.getPipeline().getFirst().invoke(request, response);
// Access a session (if present) to update last accessed time, based on a
// strict interpretation of the specification
if (Globals.STRICT_SERVLET_COMPLIANCE) {
request.getSession(false);
}
// Error page processing
response.setSuspended(false);
Throwable t = (Throwable) request.getAttribute(Globals.EXCEPTION_ATTR);
if (t != null) {
throwable(request, response, t);
} else {
status(request, response);
}
// Restore the context classloader
Thread.currentThread().setContextClassLoader
(StandardHostValve.class.getClassLoader());
| protected void | status(org.apache.catalina.connector.Request request, org.apache.catalina.connector.Response response)Handle the HTTP status code (and corresponding message) generated
while processing the specified Request to produce the specified
Response. Any exceptions that occur during generation of the error
report are logged and swallowed.
int statusCode = response.getStatus();
// Handle a custom error page for this status code
Context context = request.getContext();
if (context == null)
return;
/* Only look for error pages when isError() is set.
* isError() is set when response.sendError() is invoked. This
* allows custom error pages without relying on default from
* web.xml.
*/
if (!response.isError())
return;
ErrorPage errorPage = context.findErrorPage(statusCode);
if (errorPage != null) {
response.setAppCommitted(false);
request.setAttribute(Globals.STATUS_CODE_ATTR,
new Integer(statusCode));
String message = RequestUtil.filter(response.getMessage());
if (message == null)
message = "";
request.setAttribute(Globals.ERROR_MESSAGE_ATTR, message);
request.setAttribute
(ApplicationFilterFactory.DISPATCHER_REQUEST_PATH_ATTR,
errorPage.getLocation());
request.setAttribute(ApplicationFilterFactory.DISPATCHER_TYPE_ATTR,
new Integer(ApplicationFilterFactory.ERROR));
Wrapper wrapper = request.getWrapper();
if (wrapper != null)
request.setAttribute(Globals.SERVLET_NAME_ATTR,
wrapper.getName());
request.setAttribute(Globals.EXCEPTION_PAGE_ATTR,
request.getRequestURI());
if (custom(request, response, errorPage)) {
try {
response.flushBuffer();
} catch (ClientAbortException e) {
// Ignore
} catch (IOException e) {
container.getLogger().warn("Exception Processing " + errorPage, e);
}
}
}
| protected void | throwable(org.apache.catalina.connector.Request request, org.apache.catalina.connector.Response response, java.lang.Throwable throwable)Handle the specified Throwable encountered while processing
the specified Request to produce the specified Response. Any
exceptions that occur during generation of the exception report are
logged and swallowed.
Context context = request.getContext();
if (context == null)
return;
Throwable realError = throwable;
if (realError instanceof ServletException) {
realError = ((ServletException) realError).getRootCause();
if (realError == null) {
realError = throwable;
}
}
// If this is an aborted request from a client just log it and return
if (realError instanceof ClientAbortException ) {
if (log.isDebugEnabled()) {
log.debug
(sm.getString("standardHost.clientAbort",
realError.getCause().getMessage()));
}
return;
}
ErrorPage errorPage = findErrorPage(context, throwable);
if ((errorPage == null) && (realError != throwable)) {
errorPage = findErrorPage(context, realError);
}
if (errorPage != null) {
response.setAppCommitted(false);
request.setAttribute
(ApplicationFilterFactory.DISPATCHER_REQUEST_PATH_ATTR,
errorPage.getLocation());
request.setAttribute(ApplicationFilterFactory.DISPATCHER_TYPE_ATTR,
new Integer(ApplicationFilterFactory.ERROR));
request.setAttribute
(Globals.STATUS_CODE_ATTR,
new Integer(HttpServletResponse.SC_INTERNAL_SERVER_ERROR));
request.setAttribute(Globals.ERROR_MESSAGE_ATTR,
throwable.getMessage());
request.setAttribute(Globals.EXCEPTION_ATTR,
realError);
Wrapper wrapper = request.getWrapper();
if (wrapper != null)
request.setAttribute(Globals.SERVLET_NAME_ATTR,
wrapper.getName());
request.setAttribute(Globals.EXCEPTION_PAGE_ATTR,
request.getRequestURI());
request.setAttribute(Globals.EXCEPTION_TYPE_ATTR,
realError.getClass());
if (custom(request, response, errorPage)) {
try {
response.flushBuffer();
} catch (IOException e) {
container.getLogger().warn("Exception Processing " + errorPage, e);
}
}
} else {
// A custom error-page has not been defined for the exception
// that was thrown during request processing. Check if an
// error-page for error code 500 was specified and if so,
// send that page back as the response.
response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
// The response is an error
response.setError();
status(request, response);
}
|
|