?? 0018.htm
字號(hào):
<html>
<head>
<title>新時(shí)代軟件教程:操作系統(tǒng) 主頁(yè)制作 服務(wù)器 設(shè)計(jì)軟件 網(wǎng)絡(luò)技術(shù) 編程語(yǔ)言 文字編輯</title>
<meta http-equiv="Content-Type" content="text/html; charset=gb2312">
<style>
<!--
body, table {font-size: 9pt; font-family: 宋體}
a {text-decoration:none}
a:hover {color: red;text-decoration:underline}
.1 {background-color: rgb(245,245,245)}
-->
</style>
</head>
<p align="center"><script src="../../1.js"></script></a>
<p align="center"><big><strong>JSP高級(jí)技術(shù)如何開(kāi)發(fā)動(dòng)態(tài)網(wǎng)站</strong></big></p>
<p><span class=smallFont>
近年來(lái),Jsp技術(shù)現(xiàn)在已經(jīng)成為一種卓越的動(dòng)態(tài)網(wǎng)站開(kāi)發(fā)技術(shù)。Java開(kāi)發(fā)者出于各種理由喜愛(ài)使用jsp。有人喜愛(ài)其“一次開(kāi)發(fā),處處使用”的性能,另外的人覺(jué)得jsp使java成為一種易學(xué)的服務(wù)器端scripting語(yǔ)言。但是,jsp最大的長(zhǎng)處在它將頁(yè)面的表現(xiàn)和頁(yè)面的商業(yè)邏輯分開(kāi)了。本章中,我們將深入地討論如何使用jsp模式2體系結(jié)構(gòu)來(lái)開(kāi)發(fā)網(wǎng)站。這一模式可以被看作是通用模式瀏覽控制模式(popular Model-View-Controller,MVC)模式的服務(wù)器端實(shí)現(xiàn)。<br>
<br>
<br>
<br>
Servlets有何缺陷?<br>
<br>
當(dāng)jsp成為開(kāi)發(fā)動(dòng)態(tài)網(wǎng)站的主要技術(shù)時(shí),可能有人會(huì)問(wèn)為何在jsp技術(shù)中我們不強(qiáng)調(diào)servlets。Servlets的應(yīng)用是沒(méi)有問(wèn)題的。它們非常適于服務(wù)器端的處理和編程,并且它們會(huì)長(zhǎng)期駐留在他們現(xiàn)在的位置。但是,從結(jié)構(gòu)上說(shuō),我們可以將jsp看作是servlet的一個(gè)高層的抽象實(shí)現(xiàn),特別是在servlet 2.2 API下。但是,你仍然不能無(wú)拘束地使用servlet;它們并不適合每一個(gè)人。例如,頁(yè)面設(shè)計(jì)者可以方便地使用html或者xml工具開(kāi)發(fā)jsp頁(yè)面,但servlet卻更適合于后端開(kāi)發(fā)者使用,他們的工具是ide——一個(gè)需要更多編程訓(xùn)練的開(kāi)發(fā)領(lǐng)域。當(dāng)發(fā)布servlet時(shí),每個(gè)開(kāi)發(fā)者必須小心地確定在頁(yè)面表現(xiàn)和頁(yè)面邏輯之間沒(méi)有緊密的關(guān)聯(lián)出現(xiàn)。你可以使用第三方html包裝工具,如htmlkona來(lái)混合html和servlet代碼。即使如此,這點(diǎn)靈活性還不足以讓你自由地改變風(fēng)格本身。例如,你希望從html改變到dhtml,則包裝本身需要被小心地測(cè)試,以確保新的格式可以正確使用。在最壞的情況下,包裝不可用,你就需要應(yīng)變馬來(lái)表現(xiàn)動(dòng)態(tài)內(nèi)容。所以,需要一種新的解決方案。你將會(huì)看到,一種方案就是混合jsp和servlet的使用。<br>
<br>
<br>
<br>
不同的方式<br>
<br>
早期的jsp標(biāo)準(zhǔn)給出了兩種使用jsp的方式。這些方式,都可以歸納為jsp模式1和jsp模式2,主要的差別在于處理大量請(qǐng)求的位置不同。在模式1中(圖1),jsp頁(yè)面獨(dú)自響應(yīng)請(qǐng)求并將處理結(jié)果返回客戶。這里仍然有表現(xiàn)和內(nèi)容的分離,因?yàn)樗械臄?shù)據(jù)依靠bean來(lái)處理。盡管模式1 可以很好的滿足小型應(yīng)用的需要,但卻不能滿足大型應(yīng)用的要求。大量使用模式1,常常會(huì)導(dǎo)致頁(yè)面被嵌入大量的script或者java代碼。特別是當(dāng)需要處理的商業(yè)邏輯很復(fù)雜時(shí),情況會(huì)變得嚴(yán)重。也許對(duì)于java程序員來(lái)說(shuō),這不算大的問(wèn)題。但如果開(kāi)發(fā)者是前端界面設(shè)計(jì)人員——在大型項(xiàng)目中,這非常常見(jiàn),——?jiǎng)t代碼的開(kāi)發(fā)和維護(hù)將出現(xiàn)困難。在任何項(xiàng)目中,這樣的模式多少總會(huì)導(dǎo)致定義不清的響應(yīng)和項(xiàng)目管理的困難。<br>
<br>
<br>
在圖2中顯示的模式2 結(jié)構(gòu),是一種面向動(dòng)態(tài)內(nèi)容的實(shí)現(xiàn),結(jié)合了servlet 和jsp技術(shù)。它利用了兩種技術(shù)原有的優(yōu)點(diǎn),采用jsp來(lái)表現(xiàn)頁(yè)面,采用servlets來(lái)完成大量的處理。這里,servlet扮演一個(gè)控制者的角色,并負(fù)責(zé)響應(yīng)客戶請(qǐng)求。接著,servlet創(chuàng)建jsp需要的bean和對(duì)象,再根據(jù)用戶的行為,決定將那個(gè)jsp頁(yè)面發(fā)送給用戶。特別要注意,jsp頁(yè)面中沒(méi)有任何商業(yè)處理邏輯;它只是簡(jiǎn)單地檢索servlet先前創(chuàng)建的bean 或者對(duì)象,再將動(dòng)態(tài)內(nèi)容插入預(yù)定義的模版。從開(kāi)發(fā)的觀點(diǎn)看,這一模式具有更清晰的頁(yè)面表現(xiàn),清楚的開(kāi)發(fā)者角色劃分,可以充分地利用開(kāi)發(fā)小組中的界面設(shè)計(jì)人員。事實(shí)上,越是復(fù)雜的項(xiàng)目,采用模式2 的好處就越突出。<br>
<br>
<br>
為了清楚地了解模式2 的開(kāi)發(fā)過(guò)程,我們舉一個(gè)網(wǎng)上音樂(lè)商店的例子。<br>
<br>
我們創(chuàng)建一個(gè)叫”音樂(lè)無(wú)國(guó)界”的銷售音樂(lè)制品的商店。“音樂(lè)無(wú)國(guó)界”在線商店的主界面,是一個(gè)叫“音樂(lè)無(wú)國(guó)界”的頁(yè)面(代碼1)。你會(huì)看到,這個(gè)頁(yè)面完全著眼于用戶界面,與處理邏輯無(wú)關(guān)。另外,注意另外一個(gè)jsp頁(yè)面,Cart.jsp(在代碼2中),用<jsp:include page="Cart.jsp" flush="true" />.嵌入Eshop.jsp中。<br>
<br>
<br>
<br>
Listing 1:<br>
EShop.jsp <br>
<br>
<%@ page session="true" %><br>
<html><br>
<head><br>
<title>Music Without Borders</title><br>
</head><br>
<body bgcolor="#33CCFF"><br>
<font face="Times New Roman,Times" size="+3"><br>
Music Without Borders<br>
</font><br>
<hr><p><br>
<center><br>
<form name="shoppingForm" <br>
action="/examples/servlet/ShoppingServlet" <br>
method="POST"><br>
<b>CD:</b> <br>
<select name=CD><br>
<option>Yuan | The Guo Brothers | China | $14.95</option><br>
<option>Drums of Passion | Babatunde Olatunji | Nigeria | $16.95</option><br>
<option>Kaira | Tounami Diabate| Mali | $16.95</option><br>
<option>The Lion is Loose | Eliades Ochoa | Cuba | $13.95</option><br>
<option>Dance the Devil Away | Outback | Australia | $14.95</option><br>
<option>Record of Changes | Samulnori | Korea | $12.95</option><br>
<option>Djelika | Tounami Diabate | Mali | $14.95</option><br>
<option>Rapture | Nusrat Fateh Ali Khan | Pakistan | $12.95</option><br>
<option>Cesaria Evora | Cesaria Evora | Cape Verde | $16.95</option><br>
<option>Ibuki | Kodo | Japan | $13.95</option><br>
</select><br>
<b>Quantity: </b><input type="text" name="qty" SIZE="3" value=1><br>
<input type="hidden" name="action" value="ADD"><br>
<input type="submit" name="Submit" value="Add to Cart"><br>
</form><br>
</center><br>
<p><br>
<jsp:include page="Cart.jsp" flush="true" /><br>
</body><br>
</html><br>
<br>
<br>
<br>
Listing 2:<br>
Cart.jsp <br>
<br>
<%@ page session="true" import="java.util.*, shopping.CD" %><br>
<%<br>
Vector buylist = (Vector) session.getValue("shopping.shoppingcart");<br>
if (buylist != null && (buylist.size() > 0)) {<br>
%><br>
<center><br>
<table border="0" cellpadding="0" width="100%" bgcolor="#FFFFFF"><br>
<tr><br>
<td><b>ALBUM</b></td><br>
<td><b>ARTIST</b></td><br>
<td><b>COUNTRY</b></td><br>
<td><b>PRICE</b></td><br>
<td><b>QUANTITY</b></td><br>
<td></td><br>
</tr><br>
<%<br>
for (int index=0; index < buylist.size();index++) {<br>
CD anOrder = (CD) buylist.elementAt(index);<br>
%><br>
<tr><br>
<td><b><%= anOrder.getAlbum() %></b></td><br>
<td><b><%= anOrder.getArtist() %></b></td><br>
<td><b><%= anOrder.getCountry() %></b></td><br>
<td><b><%= anOrder.getPrice() %></b></td><br>
<td><b><%= anOrder.getQuantity() %></b></td><br>
<td><br>
<form name="deleteForm"<br>
action="/examples/servlet/ShoppingServlet"<br>
method="POST"><br>
<input type="submit" value="Delete"><br>
<input type="hidden" name= "delindex" value='<%= index %>'><br>
<input type="hidden" name="action" value="DELETE"><br>
</form> <br>
</td><br>
</tr> <br>
<% } %><br>
</table><br>
<p><br>
<form name="checkoutForm"<br>
action="/examples/servlet/ShoppingServlet"<br>
method="POST"><br>
<input type="hidden" name="action" value="CHECKOUT"><br>
<input type="submit" name="Checkout" value="Checkout"><br>
</form><br>
</center><br>
<% } %><br>
<br>
<br>
<br>
這里,Cart.jsp按照MVC的模式1處理基于SESSION的購(gòu)物車的表現(xiàn)。請(qǐng)看Cart.jsp開(kāi)始處的代碼:<br>
<br>
<%<br>
Vector buylist = (Vector) session.getValue("shopping.shoppingcart");<br>
if (buylist != null && (buylist.size() > 0)) {<br>
%><br>
<br>
本質(zhì)上,這段代碼從SESSION中取出“購(gòu)物車”。如果“購(gòu)物車”為空或者沒(méi)有被創(chuàng)建,它就什么也不顯示。所以,在用戶第一次訪問(wèn)應(yīng)用時(shí),其界面如圖:<br>
<br>
<br>
如果“購(gòu)物車”不為空,用戶選擇的商品從車中取出,依次顯示在頁(yè)面上:<br>
<br>
<%<br>
for (int index=0; index < buylist.size(); index++) {<br>
CD anOrder = (CD) buylist.elementAt(index);<br>
%><br>
<br>
一旦生成一個(gè)物品的說(shuō)明,就使用JSP按照事先設(shè)定的模板將其插入靜態(tài)HTML頁(yè)面。下圖顯示了用戶選購(gòu)一些物品后的界面:<br>
<br>
<br>
<br>
<br>
需要注意的一個(gè)重要的地方是所有關(guān)于Eshop.jsp,Cart.jsp的處理有一個(gè)控制SERVLET,ShoppingServlet.java,代碼在源程序3中:<br>
<br>
Listing 3:<br>
ShoppingServlet.java <br>
<br>
import java.util.*;<br>
import java.io.*;<br>
import javax.servlet.*;<br>
import javax.servlet.http.*;<br>
import shopping.CD;<br>
public class ShoppingServlet extends HttpServlet {<br>
public void init(ServletConfig conf) throws ServletException {<br>
super.init(conf);<br>
}<br>
public void doPost (HttpServletRequest req, HttpServletResponse res)<br>
throws ServletException, IOException {<br>
HttpSession session = req.getSession(false);<br>
if (session == null) {<br>
res.sendRedirect("http://localhost:8080/error.html");<br>
}<br>
Vector buylist=<br>
(Vector)session.getValue("shopping.shoppingcart");<br>
String action = req.getParameter("action");<br>
if (!action.equals("CHECKOUT")) {<br>
if (action.equals("DELETE")) {<br>
String del = req.getParameter("delindex");<br>
int d = (new Integer(del)).intValue();<br>
buylist.removeElementAt(d);<br>
} else if (action.equals("ADD")) {<br>
//any previous buys of same cd?<br>
boolean match=false;<br>
CD aCD = getCD(req);<br>
if (buylist==null) {<br>
//add first cd to the cart<br>
buylist = new Vector(); //first order<br>
buylist.addElement(aCD);<br>
} else { // not first buy<br>
for (int i=0; i< buylist.size(); i++) {<br>
CD cd = (CD) buylist.elementAt(i);<br>
?? 快捷鍵說(shuō)明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號(hào)
Ctrl + =
減小字號(hào)
Ctrl + -