有人活了大半辈子还不知道servlet是啥?它在tomcat中又是怎么生活的呢?来,安排上~~
让我们把回忆拉回到很久很久以前,呃,就是 springboot 启动的时间点,找到 ServletWebServerApplicationContext#refresh() 这个方法,走下去,是 onRefresh() 方法里的createWebServer() 方法,点开它:
这里以 dispatcherServlet 的加载为例,待会就盯着她。点开getSelfInitializer()方法,在关键地方打个断点:
可以看到,这里通过getServletContextInitializerBeans()方法,获取到所有的 ServletContextInitializer进行遍历,调用各自的 onStartup()。在遍历到 DispatcherServletRegistrationBean的时候,进入 onStartup()方法看看:
已经看到dispatcherServlet了,感觉离成功不远啰~
点 register(description, servletContext)进去:
再点 addRegistration()进入,拼上最后一口气,追到这里,看关键代码:
private ServletRegistration.Dynamic addServlet(String servletName, String servletClass,
Servlet servlet, Map<String,String> initParams) throws IllegalStateException {
……
// 查找context里是否有该servlet(这里的context是TomcatEmbeddedContext,
// servletName是 dispatcherServlet)
Wrapper wrapper = (Wrapper) context.findChild(servletName);
// 查找不到,则创建一个添加到context中。Wrappe 封装了servlet
if (wrapper == null) {
wrapper = context.createWrapper();
wrapper.setName(servletName);
context.addChild(wrapper);
}
………
// 继续设置wrapper的servlet属性
wrapper.setServletClass(servlet.getClass().getName());
wrapper.setServlet(servlet);
……
// 构建 ApplicationServletRegistration返回
ServletRegistration.Dynamic registration =
new ApplicationServletRegistration(wrapper, context);
return registration;
}
啰啰嗦嗦了半天,一句话概括就是:把servlet注册到context里
到这里,已是柳暗花明。我们再讲讲这里的 dispatcherServlet 是什么时候创建的。
再回想公元前某个夜晚,我们讲的springboot自动装配原理,打开:
打开DispatcherServletAutoConfiguration这个类,上图,此时无声胜有声:
简简单单,关机落班~