1、基于 Applet 和 Servlet 的 Web 应用系统的实现引言应用技术刘冬(华东师范大学 GIS 重点实验室,上海 200062)摘要:简要介绍了 Applet 和 Servlet 技术,分析了 Applet 直接访问数据库的局限性,并由此讨论引入AppletServlet 一数据库三层结构加以解决.最后给出了三层结构实现过程中的关键技术,并用代码进行说明.关键词:Java;Applet;Servlet; 数据库近年来.随着 Intemet/Intranet 技术的迅猛发展和Web 技术的广泛应用,基于浏览器 /服务器(B,S) 模式的 Web 应用.因其具有开发容易 ,操作简单,维护
2、升级方便,良好的可重用性和可扩展性等优点,逐渐成为企业信息系统市场的主流.在现有的基于 Web 应用系统的开发方案中 ,由于 Java 语言先天就是 lnternet 互联网蓬勃发展的产物,它的可移植性,安全性,平台无关性,多进程等特点使它具有其他任何开发平台所无法比拟的优势.随着 Java 标准的确立和技术的不断成熟 ,如今的 Java已不仅仅是一门语言,而是一个包含 Applet,Servlet,JSP,JavaBean,JDBC,RMI 等一系列技术的企业软件应用平台,其中 JDBCAPI 为开发者开发数据库应用提供了标准的应用程序编程接口.客户端的 Applet技术为用户提供了友好的界
3、面,动态交互的效果.服务器端的 Servlet 技术继承了 Java 语言面向对象,简单易用,跨平台,多线程等特点,(比起以前的 CGI 技术)极大地提高了系统的效率.扩展了服务器的功能.由于 Applet 技术其本身设计之初对安令性的考虑所做的限制,使它直接访问数据库的能力受到了一定的阻碍.而使用 Servlet 作为 Applet 和数据库之间的中间控制器.这种 AppletServlet 一数据苹.层构架模式可以较好地解决这个问题.本文将讨沧采用这种 j 层架构模式创建 Web 应用系统的原因 ,以及具体实现此模式中的关键技术并用代码进行说明.lLavaApp1et 与 LaVa5erV
4、1et 技术(1JavaApplet 技术JavaApplet 又称 Java 小应用程序,是 Java 语言编写的一段代码,可以在浏览器环境中运行.它通过标签嵌入到 HTML 文件中,在网页文件被调用期间随同 HTML 文件一起下载到客户端,由支持 Java 的浏览器(目前大多数浏览器都支持)解释执行,实现与用户的交互.它与 Java 应用程序的主要区别是执行方式的不同,Java 应用程序从其中的 main()方法开始执行,Applet 程序则是由浏览器自动执行几个固定的方法.如 init(),paint()等.在 Java 问世的前几年里,Applet 技术因其具有让“让 Internet
5、 动起来“的能力而引起了巨大的轰动.如今.使用动态 HTML(DHTML)语言以及脚本编制语言也能达到许多动态和互动的效果,但是由于 Applet小应用程序是 Java 这个全功能语言的一个类 ,有丰富的 JavaAPI 类库的支持 ,困此在很多场合,如网上多媒体技术(声音,图像) 和网络编程等方面仍然有很大的应用前景.f2)JavaServlet 技术.IavaSenlet 是 Java 语青编写的运行在服务器端的小应 H1 程序.与运行在客户端的 JavaApplet 小应用程序相对.功能类似于 CGI(公共网关接|1)程序但是夫 l 为它是 Java 语言的一个类,冈而具有 Java语言
6、的所有特点,如良好的可移植性等更要的是,1|vlet 运行在 Java 虚拟机中,多次渊用同一个 Servlet程序时只用加载一次且 p 可.而一般的 CGI 程序是一个独立的操作系统进程,一次调用只能处理一个用户请MODERNCOMPUTER2oo5.6馕计算三=现代计算机总第二-_:一期应用技术求.所以,每次收到一个客户端请求,都必须启动一个CGI 进程.当用户很多时,会挤占大量的系统资源,使系统变得不稳定,执行效率降低.另外.由于 Servlet 是以 Java 为基础的,比 CGI 进入门槛低.只要是熟悉 Java 的程序员就可以轻易地撰写出各式各样的 Servlet 程序.由于这些优
7、点,JavaServlet 有着十分广泛的应用.不仅能简单地处理客户端的请求,借助 Java 强大的功能 ,使用 Servlet 还可以实现大量的服务器端的管理维护功能.以及并发处理多个请求,转送请求,代理等任务.2 基于 Web 应用的系统结构传统的 Web 应用系统的模式是两层结构 .即用户层和数据服务层(如图 1).用户层由运行在客户端的 Applet 程序构成.业务逻辑和 GUI(图形用户界面)表示逻辑都封装在 Applet 中.Applet 通过 JDBC 接口直接连接数据库服务器.本文将从以下几个方面来讨论两层结构的局限性,或者说 Applet 直接访问数据库的局限性客户端浏览器-
8、.数据服务器端南图 12.1Applet 直接访问数据库的局限性(1)Applet 的“沙箱“ 机制Applet 小程序由于可以通过浏览器从 Web 服务器下载到客户机本地执行,为了避免植入计算机病毒或者含有恶意代码的 Applet 破坏客户机本地文件系统,在设计之初就认为所有的 Applet 都是不可信任的,所以对所有 Applet 都做了安全性的限制.这种安全性的限制被形象地称之为“沙箱“, 在沙箱中能够很好地运行,而试图离开沙箱的行为将会被禁止.这些安全性的限制包括不能在运行时调用其他程序,不能进行文件读写操作,不能装载动态链接库和调用任何本地方法,不能与 Applet 宿主机之外的机器
9、进行socket 连接等等.由于 Applet 只能与其所在的宿主机建立网络连接,因此也只能对宿主机上的数据库进行访问,对除宿主机以外的数据库则无法进行访问.而我们在实际应用中或者由于安全考虑或者因为其他原因很难保证 Web 服务器和数据库服务器位于同一机器 .这就给 Applet 访问数据库造成了困难.MODERNCOMPUTER2005.6(2)Java2 的数字签名技术Java2 提供了数字签名技术和修改客户安全策略文件的方法来解决 Applet 的安全限制问题,通过在客户端验证 Applet 的身份来得到用户的信任.但是这种方法开发较为复杂,要把数据库驱动包加到Applet 所在目录,
10、将类文件和资源文件一起进行打包,然后进行创建公钥和密钥,生成签名证书,数字签名等一系列步骤.每次改动 Applet 都要重新进行打包和签名,比较繁琐.同时由于打包了很多东西.用户每次浏览网页时下载 Applet 都要等待较长时间(3)Applet 代码的安全问题除了上面论及的两点,业务逻辑放在 Applet 中还有安全方面的弊端,这里的安全性不是指上面谈到的 Applet 可能破坏本地文件的问题.而是指 Applet程序被用户下载后关键代码可能泄漏的问题.在二层结构里显示逻辑和业务逻辑都包含在 Applet 中由于 Applet 程序是通过浏览器下载到客户机本机执行,用户可以通过反编译工具破解
11、下载到客户端的Applet 字节码文件.Applet 原代码中包括数据库连接字串和用户名密码等重要信息,这些信息如果泄漏出去,后果比较严重2.2Applet-ServletDatabase 三层结构基于以上谈到的几点 Applet 直接访问数据库的局限性,本文使用 JavaServet 作为 Applet 与数据库之间的中间控制器,形成 AppletServlet 一数据库三层结构(如图 2).客户墙谢览嚣 IHTTPI.蝴务嚣墙图 2其中,第一层是客户端表现层,为客户机浏览器上运行的 Applet 应用程序.与两层结构不同.客户层仅仅承担整个应用系统与用户交互的功能.即用户界面部分,不包含任
12、何业务逻辑.处于第二层的是应用服务层,由服务器端的 Servlet 构件构成,用于处理复杂的业务逻辑,如访问数据库,数值计算等工作.这一层具有良好的扩展性,可根据应用的需要增加处理业务逻辑的扩展模块.处于第三层的是数据服务层.提供数据服务3AppetServetDatabaSe 三层结构的实现(1)基于三层结构的应用系统的工作流程Applet 从 Web 服务器下载后在客户端运行.请求与 Servlet 进行连接.()Servlet 响应客户端的请求,建立与客户机的连接.通过连接实现客户机与服务器的通信.Applet 将访问数据库的请求发送给 Servlet,Servlet 根据请求通过 JD
13、BC 调用数据库,数据库将结果返回给 Servlet.Servlet 将结果送回 Applet,Applet 负责按要求显示结果(2)Applet 与 Servlet 程序包含的具体内容根据以上的系统工作流程.Applet 程序应该包含的内容有:用户图形界面;接收用户的请求,建立与服务器的连接,然后将请求发送到服务器:接收从服务器发回来的响应信息并进行显示Servlet 程序应该包含的内容有:接收 Applet 的请求,并解析这些请求:根据请求通过 JDBC 访问数据库;将结果返回给客户端从中可以看到,系统实现关键的问题是 Applet 与Servlet 之间的通信和 Servlet 通过 J
14、DBC 对数据库的访问.(3)三层结构实现的关键技术Applet 与 Servlet 之间的通信技术三层体系结构中最关键的部分就是 Applet 和Servlet 之间的通信 .二者之间的通信方式一般有四种,分别为通过 Http 协议,使用 Socket 技术,使用RMI 技术,使用 COBRA 技术.四种方法各有自己的特点,中通过 Http 协议通信是最简单的一种方式,程序员不必关心复杂的网络通信问题.Applet 利用 Java 提供的 URL 和 URLConnection 两个类即可连接远端的 Servlet.由于大部分防火墙都允许 Http 协议通过,所以该方法可以穿越防火墙.但是该
15、方法只能南 Applet 先发出请求,Servlet 在其应答 Applet 之前只能消极等待.服务器端的变化也不能由 Servlet 主动通知 Applet,实时性有所降低.通过 Socket 技术建立的是双向,持续的通信.用线程来处理用户请求,减少了资源消耗,提高了效率.但其缺点是不能穿越防火墙,同时比前一种方法编写代码复杂一些,服务器需要一直在特定端口上监听客户请求.RMI(RemoteMethodInvocation)技术是使在一台计算机上的 Java 程序可以远程执行另外一台计算机上的对象方法的技术.这种技术给程序员带来了极大的方便,只需按照 RMI 规程设计程序.不必关心其下的细节
16、,该方法能够穿越防火墙.当大量的数据是由服务器端的对象动态提供时,使用 RMI 是非常应用技术合适的.虽然 RM1 支持面向对象的分布式编程 ,但它要求客户端和服务器端都是 Java 程序.因此,对于使用混合语言开发的应用来说,CORBA 比 RMI 更为适用.CORBA 即公用对象请求代理体系(CommonOb.jectRequestBrokerArchitecture),它的使用方法类似于 RMI.两者主要的不同之处在于,CORBA 使用一种语言中立的接口定义语言(IDL)来定义接口,从而不同语言编写的分布式对象之间也能够进行通信.由于基于 Http 协议的通信方式简单易行,普及率较高,同
17、时功能也比较完善,能够满足一般的 Web应用需求,本文将采用这种方式.下面给出关于两者通信的部分实现代码.OApplet 方:tryStringchatURL=“http:/localhost:8080/shanghai/test“:URLurl=newURL(ehatURL+queryString);,/创建 URL 对象BufferedReaderin:newBufferedReader(newInputStreamReader(ur1.openStream();/生成输入流line:in.readLine(1:,读取服务器发来的信息text1.setText(1ine);i显示息in.c
18、lose();catch(Exceptione)e.printStackTrace();其中,chatURI 是服务器上的 Servlet 类名.queryString 是已经编码的要传递给 Servlet 的参数,Servlet 可以利用它获得 Applet 的信息.此方法是Applet 把本身信息传递给 Servet 最常用的方法.这里Servlet 向 Applet 传送的是普通的文本.如果传送对象,需要利用 ObjectInputstream 对象的 readObject()方法,在此就不详细列出了.Servlet 方:publicvoiddoGet(HttpServletReques
19、treq,HttpServlet-Responseres)throwsServletException,IOException|鼷祆请求Strings=req.getParameter(“query“1:StringSl=s.substring(1.21;PrintWriterout:res.getWriter();/生成输出流MODERNCOMPUTER2oo5.6【现重应用技术out.println(indexl+“%“1;,/输出发送给 Applet 的信息out.close();Servlet 通过 JDBC 对数据库的访问在 Java 中.通过 JDBC 访问数据库包含以下步骤装载并
20、注册数据库的 JDBC 驱动程序:建立与数据库的连接;创建 Statement 对象;调用 SQL 语句:访问 ResuhSet 中的记录集:依次关闭 Resuhset,Statement,Connection 对象.下面以 Access 数据库为例 ,给出 Servlet 访问数据库的代码.由于 Access 数据库的 JDBC-ODBC 驱动是在 JavaJDK 自带的.默认已经注册,所以不需要再注册驱动程序.如果使用其他数据库只需在下列代码中加上一行注册驱动程序的代码即可.tryClass.forName(“sun.jdbc.odbc.JdbcOdbcDfiver“);Connectioncn=DfiverManager.getConnection(“jdbc:odbc:shanghai“);Statementstmtcn.createStatement();ResuhSetRS=stmt.executeQuery(SELECTFROMshanghaiWHEREindex=“+temp+“);RS.next();