|
马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。
您需要 登录 才可以下载或查看,没有帐号?立即注册
x
有了这样一个呼声:让java代替C语言成为基本语言。这些足以说明java简单易学的这个优点。其次,java的功能强大,前面我也提到了,EJB3.0的推出使java成为了大型项目的首选。技能接待浏览本期的EnterpriseJavaTechnologiesTechTips。上面你将取得利用企业Java手艺和API的技能,如Java2Platform和EnterpriseEdition(J2EE)中的Java手艺和技能。
本文会商:
自界说标志文件
和JSPPages一同利用EnterpriseBeans
这些技能是利用Java2,EnterpriseEdition,v1.4SDK开辟的。您能够下载SDK,网址为http://java.sun.com/j2ee/1.4/download-dr.html。
TechTips中的成绩由MarkJohnson编写,他是elucifytechnicalcommunications的总裁,也是DesigningEnterpriseApplicationswiththeJ2EEPlatform,2ndEdition的作者之一。MarkJohnson主管一个开放论坛会商这些技能。
您能够下载这些技能的示例存档。使用程序的高低文根是ttfeb2004,index.html接待文件指出怎样利用该示例代码。利用上面的代码和/或信息的应恪守允许条目。
自界说标志文件
JSP页中的自界说标志看上往像HTML标志。而自界说标志在运转时会交换为文本,这些文本是由一个与该标志相干联的处置程序类输入的。上一个EnterpriseTechTipUsingCustomTag申明了怎样创立一个如许的类。本月的第一技能将先容一个新的更简单的办法来完成自界说标志。
在JSP2.0之前,创立自界说标志的唯一办法是将其作为Java标志处置程序类来完成。处置程序类开辟职员还必要创立一个TLD文件,该文件卖力为web容器形貌标志。只管自界说标志很壮大,它也必要编程技能和深切懂得JSP页是怎样翻译成HTML的。
JSP2.0标志文件的新特性可以让非编程职员编写可重用的标志。同时也使编程职员的编程生存变得轻松自若。JSP2.0语法与JavaServerPagesStandardTagLibrary(JSTL)及其表达式言语(EL)一同利用,不必誊写任何Java代码就可以创立自界说标志。
标志文件是JSP页的可反复利用组件。它有诸多长处:
可用来埋没或删除scriptlet。
经由过程援用而不是经由过程剪切和粘贴来进步代码的重用性。
可以使JSP页更容易誊写、视觉加倍分歧且更容易于保护。
可由非编程职员誊写。
其语法比Java更靠近于HTML,以是JSP页看上往更像是用一种言语誊写而成的。
可构成初级组件以进步事情效力和开辟速率。
自界说标志所利用的TLD文件一般可主动天生。
可用来重构现有页。代码的大众部分能够兼并到一个标志文件,该文件可在使用程序视图之间共享。
标志文件其实不完整替换自界说标志句柄类。当对有相干结构和暗示的可复用内容举行封装时,标志文件更加可取。而在JSP页中反复利用使用程序逻辑(applicationlogic)时,自界说标志要更胜一筹。比方,页眉和页脚是标志文件的特长好戏。比拟之下,JSTL中的自界说标志是作为Java言语处置程序类完成的。
标志文件细节
实践上,标志文件会被翻译和编译成标志句柄类。标志处置程序和标志处置程序类之间的唯一区分是:标志处置程序是用JSP语法写的,而标志处置程序类是用Java言语写的。
JSP2.0兼容的容器在Web存档路径WEB-INF/tags中查找标志文件。标志文件也可在WEB-INF/lib下打包成JAR文件。当Web容器为JSP页供应服务时,每当该容器碰到与标志文件相干的标志时,该标志文件中JSP内容的输入都将被剖析并包括在呼应流中。标志文件可界说属性,并可完整会见JSP2.0的表达式言语(EL)。标志文件也可创立在其实行终了后仍能持续存在的EL变量。
标志文件用属性指令声明其属性。上面是选自本技能所附带的示例代码中的一个例子。标志文件以一个属性指令入手下手:
<%@attributename="format"required="false"%>
本标志(用于格局化日期)用这行代码告知容器估计呈现一个大概的“format”属性。指令中的“required”属性为强迫属性设置为“true”。这些指令同意web容器在部署时天生本人的TLD文件。
标志经由过程其属性承受输出。除标志文件天生的输入文本外,标志也能够经由过程创立EL变量“输入”数据。标志文件能够将一个值前往到挪用它的页面,以下所示:
<%@variablename-given="filesincluded"scope="AT_END"%>
“name-given”可为标志完成后将要在页面中设置的变量供应称号。“AT_END”指定该变量是在标志文件停止设置的。
标志文件示例
本技能中的示例代码包含一个标志文件,该文件从头完成了为2002年9月的TechTip“UsingCustomTags”而开辟的自界说标志。原始标志可用三种办法对服务器的日期举行格局化:
假如格局未设置或为空,则标志用默许格局显现日期。
假如格局参数以美圆标记开首,则标志利用该字符串的其他部分作为一个情况项的称号。然后标志查找这个已定名的情况项并将它的值作为格局。
假如“format”参数包括一个格局字符串(与java.text.SimpleDateFormat兼容),那末该字符串就用来格局化日期。
标志文件指定的标志功效略有分歧。假如格局参数以一个美圆标记开首,则标志查找一个servlet高低文初始化参数,而不是查找一个情况项。(表达式言语JSTL1.0其实不为会见情况项供应内涵的撑持。)
本示例标志文件date.tag以用于界说该文件中预期属性的指令入手下手。它也为该标志利用到的其他标志库指定了定名空间。
<%@attributename="format"required="false"%>
<%@tagliburi=
"http://java.sun.com/jsp/jstl/core"prefix="c"%>
<%@tagliburi=
"http://java.sun.com/jsp/jstl/fmt"prefix="fmt"%>
<%@tagliburi=
"http://java.sun.com/jsp/jstl/functions"
prefix="fn"%>
日期标志文件的下一代码块利用<c:choose>标志断定该格局字符串。<c:choose>是JSP页中完成if/then/else功效所选用的标志。假如格局未设置或为空,则第一个“when”语句会将EL变量“format”设置为默许值。代码以下:
<c:choose>
<%--Ifformatisblank,setdefault--%>
<c:whentest="${format==nullorformat==}">
<c:setvar="format"
value="EEEE,dMMMMyyyyatkk:mm:ssz"/>
</c:when>
...
假如“format”非空,那末它将以一个“$”或不以一个“$”开首。在前一种情形下,<choose>标志的<otherwise>语句将往失落打头的“$”,并用有给命名称的高低文参数的内容替换“format”变量。
<c:otherwise>
<%--Elseifformatstartswith"$",
lookupincontextparam,
andset"format"toitsvalue.--%>
<c:iftest="${fn:substring(format,0,1)==$}">
<c:setvar="format_name"
value="${fn:substringAfter(format,$)}"/>
<c:setvar="format"
value="${initParam[format_name]}"/>
</c:if>
<%--Otherwiseleaveitasitis--%>
</c:otherwise>
</c:choose>
正文中指出,假如“format”不以一个“$”开首,它的值坚持稳定。
至此,EL变量“format”的值被赋给一个字符串,该字符串将用来格局化日期。useBean代码行创立了一个唆使以后工夫的Date对象。fmt:formatDate办法用给定的“format”格局化该日期:
<%--Nowactuallycreateandformatthedate--%>
<jsp:useBeanid="now"class="java.util.Date"/>
<fmt:formatDatevalue="${now}"pattern="${format}"/>
至此就完成了标志文件。
利用标志文件更简单。示例页DatePage.jsp(可链接到本月示例存档中index.jsp以外)顶部的一个指令申明存档目次(/WEB-INF/tags)下的一切标志都可使用“mytags”前缀来会见。该指令以下:
<%@taglibtagdir="/WEB-INF/tags"prefix="mytags"%>
如今,就能够很复杂的利用JSP标志文件了,就仿佛是在利用任何的自界说标志一样。上面代码节选自示例页DatePage.jsp:
默许格局下的服务器工夫和日期
are<b><mytags:date/></b>.<br>
服务器的时区是
<b><mytags:dateformat="zzzz"/></b>.<br>
服务器日期是
<b><mytags:dateformat="M/d/yyyy"/></b>.<br>
服务器工夫是
<b><mytags:dateformat="hh:mm:ssa"/></b>.<br>
<mytags:date>的每次呈现时城市挪用该标志文件,而且在输入中该标志会被服务器对应的工夫和日期所替换。
这个例子只是举一反三。JSP标志文件另有很多这里没有提到的选项。要懂得更多有关JSP标志文件的信息,请浏览J2EE1.4Tutorial中“CustomTaginJSPPages”一章节。
backtotop
和JspPages一同利用EnterpriseBean
2004年1月26日版的TechTips中形貌了JSP2.0ExpressionLanguage(EL)。该技能中的示例之一先容了怎样利用EL变量经由过程称号对JavaBean举行会见。JavaBean的属性也能够用复杂的EL表达式会见。这一特性使得EJB组件在JSP页中十分易于利用。只需将使用程序视图所需的EnterpriseJavaBeans组件(enterprisebeans)放进已定名的属性中,并让JSP页经由过程EL表达式中的称号会见该属性便可。分析此手艺的最好办法就是举例了。
示例代码
本技能中的示例代码是一个信誉卡考证使用程序。信誉卡公司有一系列划定可用来考证一个信誉卡号的无效性。一个信誉卡号大概无效并被透支、已过时或已作废。无效性反省的目标是在数据受权传送之前捕获数据输出毛病。
信誉卡号鄙人面几种情形下无效:
有信誉卡范例的准确前缀。
信誉卡号有准确的数字位数。
信誉卡号经由过程了checksum测试。
信誉卡没有过时。
本示例程序利用了三个组件:
一个有形态的会话beanCreditCardLocal,它代表信誉卡数据,并实行考证。
一个servletFeb2004Servlet,它在会话局限中创立该bean的一个实例,如许每一个用户都有一个实例。
一个JSP页ValidateCard.jsp,它搜集数据并显现考证了局。
该代码是如许事情的:index.jsp窗体上的一个链接指向servlet,该servlet创立会话bean句柄并将其置于会话高低文中。然后servlet将哀求转发给URLjsp/ValidateCard.jsp,由它处置卡号输出和考证。用户完成数据输出后该窗体就回递到它本人。在一个实在的使用程序中,当信誉卡准确考证后,窗体味主动转发到推销流程中的下一步。
servlet中的代码很复杂了然。它只是创立了一个CreditCardLocal范例的有形态会话bean,并以“creditCard”之名把它置于一个HttpSession属性当中。当该servlet被挪用时,假如如许一个变量已存在,那末该servlet就会删除前一个实例。
CreditCardLocalcreditCard=(CreditCardLocal)
req.getSession().getAttribute("creditCard");
//Removeitifitexists--werestartingover.
if(creditCard!=null){
try{
creditCard.remove();
}catch(Exceptione){
System.err.println(
"Exceptionremovingcreditcard:"+e);
}
System.err.println("INFO:Removedpreviouscard.");
}
//Createnewenterprisebeanreferenceinsessionscope
try{
InitialContextctx=newInitialContext();
CreditCardLocalHomecclh=
(CreditCardLocalHome)ctx.lookup(
"java:comp/env/ejb/CreditCard");
StringcardName=req.getParameter("cardName");
StringcardType=req.getParameter("cardType");
StringcardNumber=req.getParameter("cardNumber");
StringcardDate=req.getParameter("cardDate");
creditCard=cclh.create(
cardName,cardNumber,cardType,cardDate);
req.getSession().setAttribute(
"creditCard",creditCard);
}catch(Exceptione){
thrownewServletException(e);
}
RequestDispatcherrd=req.getRequestDispatcher(
"/jsp/ValidateCard.jsp");
rd.forward(req,res);
注重下面代码的最初两行。在创立完enterprisebean援用以后,servlet就将哀求转发给ValidateCard.jsp页,该页处置输出和考证。
该页的第一部分会将大概已被送达到该页的任何参数拷贝到该enterprisebean的对应属性中。注重<c:set>标志是怎样利用“target”和“property”来会见给命名称的enterprisebean的属性的。
<!--CopyparameterstocreditCardproperties-->
<c:settarget="${creditCard}"property="name"
value="${param[cardName]}"/>
<c:settarget="${creditCard}"property="type"
value="${param[cardType]}"/>
<c:iftest="${param.cardNumber!=nulland
param.cardNumber!=}">
<c:settarget="${creditCard}"property="number"
value="${param.cardNumber}"/>
</c:if>
<c:settarget="${creditCard}"
property="expirationDateStr"
value="${param[cardDate]}"/>
假如哀求参数未设置(页面第一次显现时,没有设置哀求参数),表达式如${param[cardName]}失掉的值为空,那末对应的bean属性也被设置为空。
ValidateCard.jsp页的下一部分从用户那边搜集数据。当用户单击提交按钮时,这些数据被回递统一个页面。这部分的代码有一些风趣的特性。窗体老是回递到它本人,因而上面界说的每一个输出都包含一个属性,该属性将输出值设置为信誉卡确当前值。
窗体的第一部分利用了一个表格来把持结构和当地背景色彩,而且为窗体属性“cardName”界说了一个输出元素。
<inputtype="text"name="cardName"size="32"
value="${creditCard.name}"><br>
cardName的值被赋给EL表达式${creditCard.name},该表达式同等于以下代码:
<%=((CreditCardLocal)request.getSession().
getAttribute("creditCard")).getName()%>
假如窗体之前已被提交过,那末该域输出过的任何称号都将显现在cardName输出框中。
下一个输出是一组单选按钮,一个按钮对应一种信誉卡范例。信誉卡对象有一个范例为CCInfo的“info”属性。该对象是一个含有一切无效信誉卡范例信息的java.util.HashMap。该map的中心是每一个信誉卡的标记称号,比方,“mc”代表万事达信誉卡(MasterCard)。值为CCDesc范例,是用于形貌卡的对象。(要懂得概况,请参阅代码示例中的格局化源代码)。<c:forEach>轮回会在吸收到的信誉卡范例中往返轮回,并为每一个范例创立一个单选按钮。
<p>
<b>Typeofcard:</b><br>
<c:forEachvar="item"items="${creditCard.info}">
<inputtype="radio"name="cardType"
value="${item.key}"
${(item.keyeqcreditCard.type)?checked:}>
${item.value.description}<br>
</c:forEach>
假如在creditCard对象中正在创立的单选按钮是以后选中按钮,那末表达式${(item.keyeqcreditCard.type)?checked:}就失掉字符串“checked”。该轮回以可扩大的体例供应了一个埋没的优点。如需增加一个新的信誉卡范例,只需向CreditCard的CCInfo中增加一个该范例的CCdesc形貌便可。鄙人次ValidatePage.jsp实行时,该轮回就会吸收这个新的信誉卡范例并将其到场到列表中。
上面两个输出包含信誉卡号和过时日期:
<b>Cardnumber:</b>
<inputtype="text"name="cardNumber"size="24"
value="${creditCard.number}"><p>
<b>Expirationdate(mm/yyyy):</b>
<inputtype="text"name="cardDate"size="10"
value="${creditCard.expirationDateStr}">
再次注重:该值被赋给了响应的enterprisebean属性值。
假如符合的话,窗体的第三部分会显现一个毛病信息,大概一个申明该卡无效的信息。这部分含有两个<c:when>标志和一个<c:otherwise>标志。当信誉卡号为空时,第一个标志用来避免显现毛病信息。
<c:choose>
<c:when
test=
"${creditCard.number==null||creditCard.number==}">
<!--Nonumber,sononeedtocomplain
thatitsnotvalid-->
</c:when>
当信誉卡号无效时,第二个<c:when>标志显现一个乐成信息。
<c:whentest="${creditCard.valid}">
Thefollowingcardisvalid:<br>
<tableborder="0">
<tr><thalign="left">Name:</th>
<td>${creditCard.name}</td>
</tr>
<!--andsoon...-->
</c:when>
此时,一个真实的使用程序便可能将用户的扫瞄器转递到一个窗体,该窗体搜集记账地点信息(billingaddressinfomation)。这里要注重:对<c:if>的测试是一个布尔值。以是表达式${creditCard.valid}必需是布尔型的。本属性的存取器(accessor)是CreditCardLocal.isValid(),这是由于布尔值的get属性存取器的定名习气是利用“is”而不是“get”。
最初一个标志<c:otherwise>是针对的是信誉卡号有效的情形。
<c:otherwise>
<hr>
<fontcolor="red">Thisnumberisnotvalid.</font>
<br>
<i>Problem</i>:${creditCard.validityMessage}<br>
Pleasecorrecttheproblemandtryagain.
</c:otherwise>
</c:choose>
CreditCardLocal.getValidityMessage前往一条用户友爱的毛病信息注释信誉卡有效的缘故原由。
本示例中风趣和有效的中央是enterprisebean界面可存储在使用程序的会话(或其他)高低文中,且能够经由过程JSPEL表达式中的称号援用。由于在scriptlet中并没有正在完成使用程序逻辑,以是利用此手艺能够改善封装。它也使得JSP页更容易创立、了解和保护。
运转示例代码
下载这些技能的示例存档。使用程序的高低文根(contextroot)是ttfeb2004。下载的ear文件也含有示例的全体源代码。
可使用部署工具程序(deploytoolprogram)或办理把持台(adminconsole)在J2EE1.4ApplicationServer上部署此使用程序存档(ttfeb2004.ear)。也能够经由过程运转asadmin命令举行部署:
asadmindeployinstall_dir/ttfeb2004.ear
用安装war文件的路径替换install_dir。
要会见该使用程序,请链接:http://localhost:8000/ttfeb2004。
关于J2EE1.4ApplicationServer以外的一个J2EE1.4相容的完成,可以使用本人J2EE产物的部署工具在本人的平台上部署该使用程序。
当启动该使用程序时,将会看到以下一个页面(只显现了该页面的一部分):
手机用到的是用j2me所编出来的小程序。 |
|