原文地址:http://tutorials.jenkov.com,本文为原文翻译,一切权益归原作者。
该部分教程主要是对web应用的架构和技术进行介绍。这不意味着会介绍的比较详细,而是对各种不同的选择进行一个概览。各部分较为详细的介绍会在他们各自对应的教程中进行。
Applets
Applets是第一代java web技术。一个Applet是一段小的JAVA程序:从服务端下载下来,并在客户端执行。就像是一个Flash Movie或者Active X组件,Applets在最开始的时候就很专注于媒体业务,但是却从来没有真正发展成为 web应用的GUI平台。今天,Applets已经成为了一项古老的技术,在将来,会被更为现代化的RIA技术JAVAFX所替代。
Applets可以完全在客户端运行,或者也可以与其对应的服务端进行通信。
Servlets
Servlets是第一代服务端web技术。他可以作为早期web技术“CGI 脚本”的代替品。CGI脚本是运行在服务端的一个程序,当请求到达的时候,可以由CGI脚本处理该请求。因此,当一个请求到达的时候,对应的CGI脚本进程就会相应的启动和结束。启动一个进程是很慢的,而且会收到内存的制约。因此Sun公司开发了Servlets。一个CGI脚本可以使用很多种语言开发,例如perl和C。
一个Servlet是一个实现了特殊的Servlet接口的普通的JAVA类,这个类部署在Servlet容器中。通常Servlet容器会与一个web服务器相联系起来,当一个应该被servlet处理的HTTP请求到达web服务器时,web服务器会把该请求转发到servlet容器,而servlet容器会把请求转发到相应的servlet以进行处理。
由于servlet容器一直在运行,所以servlet也是如此。换句话说,当请求到达给定的servlet时,该servlet已经被加载到内存中,并准备好处理请求。 不会再启动CGI脚本或Java进程。
今天,大多数servlet容器都内建在web服务器中,所以一般不需要对这二者进行明确的区分。带有servlet容器的web服务器有如下几种:Tomcat和Jetty。就个人而言,我更喜欢Jetty,因为它体积小,易于使用,启动和停止耗费时间短, 在开发过程中快速重启可能非常方便。
JSP
JSP是 Java Server Pages的简写。将HTML嵌入到Java代码中是一种不好的理念,作为对这种idea的应对,JSP被提出来。如果需要更改站点的布局,则必须在Java代码中进行布局。 这并不总是那么容易,因为HTML生成代码与本地逻辑代码交错。 JSP也是对当时来自微软的新的Web技术ASP(Active Server Pages)和PHP的应对,它们都是和JSP相似的技术。
在JSP中,角色是相反的。 在JSP中,您可以像在标准HTML页面中那样编写HTML。 然后你可以在HTML中插入“scriplets”(小段Java代码)。 例如,您可以重复一段HTML,或者在两段HTML之间进行选择。
下面是一个小的servlet和JSP示例,以更好地说明差异:
public void service(ServletRequest request, ServletResponse response){
PrintWriter writer = ((HttpServletResponse) response)).getWriter();
writer.write("");
writer.write("");
writer.write("");
for(int i=0; i<10; i++){
writer.write("");
writer.write("" + i);
writer.write(" ");
}
writer.write("
");
writer.write("");
writer.write("");
}
<%
for(int i=0; i<10; i++){
%><%=i%> <%
}
%>
如您所见,JSP示例比Servlet示例短得多,并且可以更容易地从宏观上把握HTML代码。 然而,这并非总是如此。 如果您正在使用具有较多本地逻辑而只有少量HTML的应用程序,那么使用servlet可能会更容易。 如果你有很多的HTML并且只有一点逻辑,那么JSP可能会更适合这个任务。
Model 2 架构
JSP使编织一些代码到你的HTML代码里变的更容易。 但是,它不会干净地将视图(HTML)从控件(本地逻辑)中分离出来。 如果JSP页面内部所需的Java代码数量增加,那么JSP将很快看起来像一盘意大利面,就像一个带有大量HTML代码的Servlet一样。 Servlets和JSP都不是完美的解决方案。
作为对这种情况的应对,一些人(我不记得是谁)提出了一个新的Web应用程序架构,称为“Model 2”。 在模型2体系结构中,Servlet首先处理请求并执行所有必要的本地逻辑。 当servlet处理完成时,它将所有必要的数据附加到请求属性,并将请求转发给JSP(或其他视图技术)。 JSP然后呈现要发送回浏览器的HTML。 这为本地逻辑和生成的HTML之间提供了更为清晰的分离。
Struts是最早和最受欢迎的Model 2架构Web框架之一。
Model 2架构的最大问题是本地逻辑(控制)和HTML(视图)的硬分离。有时你需要几个较小的组件来处理它们各自对应的请求,并生成它们返回给浏览器的最终HTML页面。在严格意义上的Model 2模型架构中,这是有点难以做到的。一旦本地逻辑(控制)执行完毕,请求就会被转向视图(JSP),这个视图可以在内部再次包含一个小的控制逻辑,每个控制逻辑都可能将请求转向视图。
这个模型的问题是控制逻辑和视图逻辑过于混合。 执行过程变得像这样:
control --> view
--> control --> view
--> control --> view
--> control --> view
假设上面例子中的最后一个控件遇到一个错误,并且想要中止整个请求处理。 这样做的一个正常的方法是发送一个500 HTTP错误的浏览器。 但是,由于视图生成已经在进行中,最后一个组件可能无法更改响应头文件! 它也不能发送HTTP重定向头。 如果在最后一个控件中引发异常,浏览器将返回半页,并且没有错误消息。
基于组件的架构
基于组件的体系结构受Swing,AWT和其他窗口工具包中的桌面组件库的启发。他们也可以被认为是模型2架构的一个改进。
在基于组件的Web应用程序中,您将拥有与页面上的各个组件相匹配的组件。例如,具有表单的页面将具有与表单字段相对应的表单组件。基于组件的Web框架将尝试将表单域中的值填充到表单组件中,因此它会自动完成。有点像Swing应用中的表单字段。这是Apache Wicket的工作原理。
就个人而言,我不太在乎在服务器端有太多的组件。从表单字段组件中复制值并不总是比从HTTP请求对象中复制要容易得多。我更喜欢访问原始的HTTP请求。事实上,在使用像Flex,JavaFX或Silverlight这样的通过HTTP / XML或HTTP / SOAP与服务器端通信的RIA前端时,与请求参数相匹配的服务器端组件实际上可能更多,而不是对您有利。
一些基于组件的web框架体系结构也通过将模型2体系结构的1遍请求处理拆分为2遍请求处理过程来避免模型2控制视图控制交织问题。如下所示:
component.control
--> component.control
--> component.control
--> component.control
--> component.control
component.view
--> component.view
--> component.view
--> component.view
--> component.view
首先,层次结构中的所有组件都执行其控制逻辑(域逻辑)。如果任何组件在这个时候抛出一个异常,那么整个请求可以被中止,并且一个50X的HTTP响应被发送回浏览器,或者显示一个错误页面等等。层次结构中的任何组件也可以发出HTTP重定向响应,如果需要。
其次,层次结构中的所有组件都执行其视图逻辑。视图逻辑通常生成HTML或XML。在生成HTML时,视图逻辑通常通过将请求转发给一个JSP来实现,该JSP生成的是整个HTML的组成部分。父组件(例如,JSP)的查看逻辑通常具有标记,其指定了在所生成的HTML / XML中的哪个位置应该包括每个子控件的HTML / XML。
基于组件的体系结构与严格的Model 2体系结构的另一个优点是,基于组件的体系结构中的每个组件都知道其子组件(如果有)。这意味着,如果请求不应该由那个子控件处理,父组件可以禁用(避免调用)它的一个或多个子组件。此外,如有必要,组件可能会在请求处理时添加新的子项。例如,一个组件可以根据请求来决定添加一个ChildA或ChildB,然后将请求处理传递给添加的组件。
在模型2架构中,控件不知道它的子控件。只有视图知道在哪里包括子控件。要禁用子控件+视图将会更困难。这将需要发送禁用信号到子控制+视图,可能通过请求属性。添加新组件也非常困难。您将不得不在运行时修改视图。但是,视图通常是JSP的,在运行时不太容易修改。
基于组件的web框架有:
JSF (Java Server Faces)
Butterfly Web UI
Wicket
Tapestry
JSF
JSF是Java Server Faces的缩写。 JSF是由Sun开发的基于组件的Web框架。 JSF是JSP的替代品。
JavaFX
JavaFX是Sun开发的RIA(富Internet应用程序)技术,受Adobe Flex的启发。 RIA应用程序就像一个Applet。 这是一个小程序,在用户浏览器中下载并执行。 RIA技术通常比传统的Applet更适合与服务器端进行通信。 他们通常也更容易布局。
Adobe Flex
Adobe Flex是最早出现的RIA技术之一。 Flex是一个用于在Flash中创建RIA应用程序的GUI框架。 一个Flex应用程序被编译成一个Flash文件,然后可以包含在你的HTML页面中。 Flex使用MXML进行布局非常简单 - 一种类似于HTML的XML格式。
虽然Flex不是Java,但是我已经包含了它,因为将Flex RIA应用程序与Java服务器端集成非常容易。 Flex可以通过RMI,SOAP或简单的HTTP / XML来调用Java服务器端。 我更喜欢HTTP / XML机制,因为开发和调试非常简单。 另外,Flex比JavaFX推出更早,因此(写作时)更加成熟。