now开始第五章——【作为Web应用】之旅:
25、但是,师傅……本该用请求属性的,他却用了一个上下文属性,应该杀了他。
没有servlet能独立存在,在当前的现代化Web应用中,许多组建都是在一起协作共同完成一个目标。你会有M,C和V;会用到参数和属性;你还有一些辅助类。但是怎么把这些部分组织在一起呢?怎么让这些组件共享信息?如何隐藏信息?怎么让信息做到线程安全?能不能得出答案,这决定着你能不能活命。(P147);
26、servlet初始化之前不能使用servlet初始化参数。容器初始化一个servlet时,会为这个servlet建一个惟一的ServletConfig。(P151);
27、servlet初始化参数只能读一次——就是在容器初始化servlet的时候(P152);
一个重要的过程,非常重要:<1>容器读取一个servlet的部署描述文件(web.xml),包括初始化参数;
<2>容器为这个servlet创建一个新的ServletConfig实例;
<3>容器为每个servlet初始化参数创建一个(或多个)String键/值对;
<4>容器向ServletConfig提供键/值初始化参数的一个引用;
<5>容器创建servlet类的一个新实例;
<6>容器调用servlet的inin()方法,传入ServletConfig的应用。
(继续P152);
28、每个servlet一个ServletConfig
每个Web应用一个ServletContext
如果是分布的,那么每个JVM有一个ServletContext!(P159)
29、如果整个Web应用有一个main()方法就好了。能放一些在servlet或JSP之前运行的代码——她想要的是一个监听者(listener)(P165);
30、监听者对象向ServletContextEvent对象请求应用ServletContext对象的一个引用(P168);
31、容器怎么发现和使用监听者呢……通过web.xml部署描述文件;
你怎么告诉容器这个ServletContext事件的监听者?好像没有XML元素指出所监听的事件类型呀!……容器只会检查类,并注意监听者接口,以此明确监听什么类型的事件。
(P168 & 175);
32、一个重要的过程,非常重要(续):<1>~<4>同27;
<new5>容器创建MyServletContextListener.class的实例;
<new6>容器调用监听者contextInitialized()方法,传入新的ServletContextEvent。这个事件对象有一个ServletContext引用,所以事件处理代码可以从事件得到上下文,并从上下文得到上下文初始化参数;
<7>监听者向ServletContextEvent要ServletContext的一个引用;
<8>监听者向ServletContext要上下文初始化参数"breed”;
<9>监听者使用初始化参数干各种需要的活儿;
<10>容器建立一个新的servlet(也就是说,利用初始化参数建立一个新的Servletconfig,为这个ServletConfig提供ServletContext的一个引用,然后条用servlet的init()方法);
<11>servlet得到一个请求,向ServletContext请求属性;
<12>响应。
(P178-179);
33、属性就是一个对象。我们关心的只是属性所在的作用域(换句话说,我们关心谁能看到这个属性,以及属性能存活多久)(P185);
34、同步服务方法并不能保护上下文属性!
不是要对servlet加锁……而是需要对上下文加锁!(synchronized(getServletContext());)(synchronized(session))
(P196, 197, 200);
35、SingleThreadModel不会带来任何好处,如果应用有多个组件,只会让性能更糟。现在如果还有开发人员使用这个接口,肯定会被笑话的。(P201);
36、只有请求属性和局部变量是线程安全的!(P202);
丰盛的第六章之旅结束……