在研读StandardHost的时候,我们再查看下它的继承关系:
我们会发现其实它跟StandardEngine的继承关系是很相似的,只是变了个Host接口和多个个Deployer接口而已,其他都是一样的。
同样的
1, 调用了ContainerBase中的Invoke方法
2,进而掉用了valve的invoke方法,而这里实现了valve接口的实现类是StandardHostValve
3,这个时候将会调用StandardHostValve的invoke方法了
public void invoke(Request request, Responseresponse,
ValveContextvalveContext)
throws IOException, ServletException {
// Validate the request and response object types
if (!(request.getRequest() instanceof HttpServletRequest) ||
!(response.getResponse() instanceof HttpServletResponse)) {
return; // NOTE - Not muchelse we can do generically
}
// Select the Context to be used for this Request
StandardHost host = (StandardHost) getContainer();
Context context = (Context) host.map(request, true);
if (context == null) {
((HttpServletResponse) response.getResponse()).sendError
(HttpServletResponse.SC_INTERNAL_SERVER_ERROR,
sm.getString("standardHost.noContext"));
return;
}
// Bind the context CL to the current thread
Thread.currentThread().setContextClassLoader
(context.getLoader().getClassLoader());
// Update the session last access time for our session (if any)
HttpServletRequest hreq = (HttpServletRequest) request.getRequest();
String sessionId = hreq.getRequestedSessionId();
if (sessionId != null) {
Manager manager = context.getManager();
if (manager != null) {
Session session =manager.findSession(sessionId);
if ((session != null)&& session.isValid())
session.access();
}
}
// Ask this Context to process this request
context.invoke(request, response);
}
1, 这个时候根据StandardHost的StandardHostMapper,查看map方法
publicContainer map(Request request, boolean update) {
// Has this request already beenmapped?
if (update &&(request.getContext() != null))
return (request.getContext());
// Perform mapping on our request URI
String uri = ((HttpRequest)request).getDecodedRequestURI();
Context context = host.map(uri);
// Update the request (if requested)and return the selected Context
if (update) {
request.setContext(context);
if (context != null)
((HttpRequest)request).setContextPath(context.getPath());
else
((HttpRequest)request).setContextPath(null);
}
return (context);
}
知道根据url返回了实现了context接口的standardContext
6、这时请求就转移到了standardContext的invoke方法上了
standardardHost的请求流程图:
StandardardHost的请求关系类图