servlet入门2alibaba - 威尼斯人

servlet入门2alibaba

2019-02-08 10:07:55 | 作者: 白亦 | 标签: 办法,客户端,服务器 | 浏览: 5978

1.1 关于Servlets

Servlets是JAVA 2.0中新增的一个全新功用。JAVA Servlets 是运转在恳求/面向恳求服务器上的模块,比方一个Java-enabled web 服务器, 和相似这样的延伸场合. 例如, 一个servlet可以从一个HTML订单表中获取数据然后用一些商业上的算法来更新公司相应的订单数据库。

也就是说:servlet可以象CGI脚本相同扩展WEB服务器功用,可是servlet占用很少密布资源,有很多用CGI脚本编制的一些站点由 于访问量剧增,功用敏捷下降,这是CGI脚本一个缺陷。一起由于servlet 是用java编写的,因而是跨渠道的。实践servlet是电子商务真实的开端。

Servlet API, 是用来写servlet的, 编写servlet是已没有CGI脚本那样比如关怀一个servlet是这样被装载, servlet运转的服务器环境是什么, 或许用来传输数据的协议是什么等等,这样servlets就可以融合在不同的web服务器中.

Servlet可以适当有效地代替CGI脚本: 它可以便利地发生简略编写而且运转快的动态文本. 可以很便利的调试寻找出程序问题. Servlet程序是用Java Servlet API开发的, a standard Java extension. 但不是Java 中心结构的一部分,可以作为通用的附加产品包被商家购买运用.

1.2 举例

下面是一些servlet运用规模:

用于处理HTML表单经过HTTPS发生POSTed数据, 包括生意订单或信用卡数据. 因而servlet可以成为订单处理体系的一部分, 和产品存货数据库一道作业,或许可以用在在线付出体系上.

答应人们之间的协作. 一个servlet能并发处理多个恳求; 他们可以运用在比如在线会议这样的同步恳求支撑体系.

转送恳求. Servlet可以转送恳求给其他的服务器和servlets. 这就答应在镜象相同内容的几个服务器之间平衡负载. 依照使命类型或组织规模,可以答应被用来在几个服务器中区分逻辑上的服务器.

servlet 编写者们可以界说彼此之间一起作业的激活署理,每个署理者是一个servlet, 而且署理者可以在他们之间传送数据.

1.3 Servlet 结构总视

在详细把握servlet之前,须对java言语有所了解。下面是根据您了解java基础上的,在Servlet API中最重要的是Servlet interface. 一切的servlets implement(履行)这个interface, 办法多种:或许是直接的,或许经过extending 这个class履行它,如 HttpServlet. 这个Servlet interface 供给组织servlet与客户端联络的办法. Servlet 编写者可以在他们开发 servlet程序时供给更多一些或一切的这样办法.

当一个servlet接纳来自客户端的调用恳求, 它接纳两个目标: 一个是ServletRequest,别的一个是ServletResponse. 这个ServletRequest class 归纳从客户端到服务器之间的联络, 而 ServletResponse class 归纳从servlet 回来客户端的联络.

ServletRequest interface 可以获取到这样一些信息如由客户端传送的论述称号,客户端正在运用的协议, 发生恳求而且接纳恳求的服务器远端主机名. 它也供给获取数据流的servlet, ServletInputStream, 这些数据是客户端引证中运用HTTP POST 和 PUT 办法递送的. 一个ServletRequest的子类可以让 servlet获取更多的协议特性数据. 例如: HttpServletRequest 包括获取 HTTP-specific头部信息的办法.

ServletResponse interface 给出相应客户端的servlet办法. 它答应servlet 设置内容长度和回应的mime类型, 而且供给输出流, ServletOutputStream, 经过编写者可以发回相应数据. ServletResponse子类可以给出更多 protocol-specific容量的信息。 例如: HttpServletResponse 包括答应servlet 操作HTTP-specific头部信息的办法.

上面有关classes 和 interfaces描绘构成了一个根本的Servlet结构. HTTP servlets有一些附加的可以供给session-tracking capabilities的办法. servlet编写者可以用这些API在有别人操作时保护servlet与客户端之间的状况.

1.4 Servlet Lifecycle

服务器装载运转servlets:接纳来自客户端的多个恳求而且回来数据给客户端. 然后在删去移开servlets. 这就是servlets lifecycle进程. 下面详细描绘:

当一个服务器装载servlet时, 它运转servlet的 init 办法. 这个办法不能重复调用,一旦调用就是再装载servlet. 直到服务器调用 destroy 办法卸载 servlet后才干再调用.

在服务器装载初始化后servlet, servlet就可以处理客户端的恳求. 用 service 办法做到这一点. 每个客户端恳求有它自己service办法: 这些办法接纳客户端恳求, 而且发回相应的呼应.

Servlets能一起运转多个service. 这是很重要的, 这样, service办法可以按一个thread-safe 款式编写. 如:service办法更新servlet目标中的一个字段field, 这个字段可以一起存取的. 假设某个服务器不能一起并发运转 service办法,也可以用SingleThreadModel interface. 这个 interface 保证不会有两个以上的线程threads并发运转.

Servlets一向运转到他们被服务器卸载。

在servlet的lifecycle中, 编写一个thread-safe编码以卸载servlet是很重要的。



Servlets 履行 javax.servlet.Servlet interface. 当servlet编写者可以经过直接implement interface开发servlet, 但这样一般没有必要. 由于大多数servlet是针对用HTTP协议的web服务器, 这样最通用开发servlet办法是用 javax.servlet.http.HttpServlet 内.

HttpServlet 类经过extend GenericServlet基类履行 Servlet interface, 供给了处理HTTP协议的功用. 他的service办法支撑规范HTTP/1.1恳求.

一般地, 用HttpServlet指定的类编写的servlets可以多线程地并发运转 service办法.

2.1 与客户端的交互性

Servlet编写者留意HttpServlet类有几个短缺的办法,你可以自己界说办法中内容,可是有必要运用这些办法称号以使servlet知道你想做什么,

doGet, 用于处理 GET、有条件的GET 和头部 HEAD恳求

doPost, 用户处理 POST 恳求

doPut, 用于处理 PUT 恳求

doDelete, 用于处理 DELETE恳求

HttpServlet的service办法, 一般地, 当它接纳到一个OPTIONS恳求时,会调用doOptions 办法, 当接纳一个TRACE恳求是调用doTrace . doOptions缺省履行办法是主动决议什么样的HTTP被挑选而且回来哪个信息.

在你运用这些办法时,有必要带两个论述. 第一个包括来自客户端的数据 HttpServletRequest. 第二个参数包括客户端的呼应HttpServletResponse. 在下例中是这样的状况.

一个HttpServletRequest目标供给抵达HTTP 头部数据, 也答应你获取客户端的数据. 怎样获取这些数据取决于HTTP端恳求办法.

不论任何HTTP办法, 你可以用 getParameterValues 办法, 这个用来回来特定称号的参数值. 关于用 HTTP GET 恳求的办法, 这个 getQueryString 办法将会回来一个可以用来解剖剖析的.

关于用HTTP POST, PUT, 和 DELETE恳求的办法, 你有两种办法可以挑选. 假如是文本数据,你能经过getReader办法用BufferedReader获取 ; 假如是二进制数据, 能经过getReader 办法用 ServletInputStream获取.

为了呼应客户端, 一个HttpServletResponse目标供给回来数据给用户的两个办法. 你可以用getWriter 办法回来,或许 getOutputStream 办法以输出流回来. 你应该用getWriter回来文本数据,而用getOutputStream回来二进制数据.

在运用Writer 或 OutputStream之前, HTTP 头部应该先被设置. HttpServletResponse内供给这样一个办法,之后可以用writer 或 outputstream 将呼应主体部分发回用户. 完结后要封闭 writer 或 output stream以便让服务器知道呼应现已完毕.

2.2 一个HTTP Servlet处理GET和HEAD办法的比如



public class SimpleServlet extends HttpServlet {

public void doGet(HttpServletRequest req, HttpServletResponse res)
throws ServletException, IOException
{
// 首要设置头部
res.setContentType("text/html");

// 用 writer办法回来呼应数据
PrintWriter out = res.getWriter();
out.println("");
out.println("
SimpleServlet Output
");
out.println("

This is output is from SimpleServlet.");
out.println("
");
out.close();
}

public String getServletInfo() {
return "A simple servlet";
}

}

这个比如完整地实际了一个servlet.
2.3 一个HTTP Servlet处理POST办法的比如

这儿是个用HTML带POST表单的比如:





https://demo:8080/servlet/survey method=POST




How Many Employees in your Company?


1-100

100-200

200-300

300-400

500-more



General Comments?






What IDEs do you use?


JavaWorkShop

J++

Cafe








这儿的servlet将表单数据写入一个文件,而且用一个thank you信息响运用户. 这儿servlet的办法,如下例:


public void doPost(HttpServletRequest req, HttpServletResponse res)
throws ServletException, IOException
{
// 首要设置呼应的 "content type" 头部
res.setContentType("text/html");

//得到呼应的 PrintWriter以回来文本给客户端.
PrintWriter toClient = res.getWriter();

try {
//翻开一个文件写入Survey的成果.
String surveyName = req.getParameterValues("survey")[0];
FileWriter resultsFile = new FileWriter(resultsDir
+ System.getProperty("file.separator")
+ surveyName + ".txt", true);
PrintWriter toFile = new PrintWriter(resultsFile);

// 从客户端得到表单数据 存贮在这个文件中
toFile.println("");
Enumeration values = req.getParameterNames();
while(values.hasMoreElements()) {
String name = (String)values.nextElement();
String value = req.getParameterValues(name)[0];
if(name.compareTo("submit") != 0) {
toFile.println(name + ": " + value);
}
}
toFile.println("");

//封闭文件.
resultsFile.close();

// 用一个thank you回来客户端
toClient.println("");
toClient.println("");
toClient.println("Thank you for participating");
toClient.println("");

} catch(IOException e) {
e.printStackTrace();
toClient.println(
"A problem occured while recording your answers. "
+ "Please try again.");
}

// 封闭writer; 呼应完结.
toClient.close();
}

这个doPost办法是用getParameterNames和getParameterValues办法来从表单中获取数据的. 由于它回来文本给客户端, doPost 将调用 getWriter 办法. 在写入呼应主体部分之前,它设置了呼应头部字段的设置, 但呼应完结后,封闭.





3.1 重编Init 初始化办法

在初始化进程中, servlet应当准备好它要组织的一些资源, 以便这个servlet 可以接纳恳求,做到这些可以不必考虑多线程, 由于在servlet初始化是只能是单进程的。 一旦初始化办法完结, servlet就能接纳客户端的恳求。 当然假如初始化不能成功,这个办法会扔出throw UnavailableException解说的.

初始化办法运用ServletConfig 目标作为参数. 这个办法应该保存这个目标, 以便它能有办法getServletConfig回来. 最简略的办法是,搞出一个新类,他的初始化办法数调用super.init. 假如的确这样做, 你就应当自己保存ServletConfig 目标, 而且自己重编getServletConfig 办法以便它能重新的方位得到目标.

下面是个初始化办法的比如. 它是来自Survey Servlet的初始化办法, 从一个表单接纳输入然后存储到文件中,为了存储survey信息, 它需求一个目录. 它以初始化参数接纳这个目录.


public void init(ServletConfig config)
throws ServletException
{
super.init(config);

//获取目录
resultsDir = getInitParameter("resultsDir");

//假如没有目录, 不处理客户端
if (resultsDir null) {
throw new UnavailableException (this,
"Not given a directory to write survey results!");
}
}

这儿的初始化办法调用super.init 办法来办理组织ServletConfig目标. 这个初始化办法也设置了一个字段: resultsDir, 作为初始化参数供给的目录名. 假如没有目录名被供给, 这个 servlet扔出一个不适用的解说. 假如初始化 办法成功完结,servlet将能处理客户端恳求

初始化参数

初始化参数的规则是一个服务器方面的规则。假如初始化参数被规则, 都可以用相同的办法得到: 用 getInitParameter办法. 这个办法将参数名作为自己的参数项.

3.2 重编Destroy 办法

当服务器卸载一个servlet, 它将调用servlet的destroy办法. 这个 destroy办法是与初始化办法相反,一起从内存中开释servlet.

并不是一切的调用了初始化init办法是也有必要调用destroy办法.

关于大多数的servlets, 一些初始化的作业有必要反做的. 如, 假设有一个servlet,它在初始化时翻开一个数据库衔接,他的destroy 办法如下显现:需求封闭这个衔接的



public void destroy() {
try {
con.close();
} catch (SQLException e) {
while(e != null) {
log("SQLException: " + e.getSQLState() + \t +
e.getMessage() + \t +
e.getErrorCode() + \t);
e = e.getNextException();
}
} catch (Exception e) {
e.printStackTrace();
}
}

关于一个Servlet中止触及的多线程

但一个服务器卸载一个servlet, 它会在一切的service现已完结后调用 destroy. 假如你的操作运转需求很长时刻, 但destroy 被调用时还有线程在运转. 这个servlet编写者有职责保证一切的线程都现已完结;

长时刻运转呼应客户端恳求的那些servlet应当保存当时有多少办法在运转的记载. 他的 long-running 办法应当周期性地轮询以保证他们可以持续运转下去. 假如servlet被destroy办法调用, 那么这个long-running 办法假如必要有必要停止作业或铲除.

举例, 变量serviceCounter用来计算有多少service办法在运转, 变量 shuttingDown显现这个servlet是否被destory. 每个变量有它自己的获取办法:


public ShutdownExample extends HttpServlet {
private int serviceCounter = 0;
private Boolean shuttingDown;
...
// serviceCounter
protected synchronized void enteringServiceMethod() {
serviceCounter++;
}
protected synchronized void leavingServiceMethod() {
serviceCounter;
}
protected synchronized int numServices() {
return serviceCounter;
}
//shuttingDown
protected setShuttingDown(Boolean flag) {
shuttingDown = flag;
}
protected Boolean isShuttingDown() {
return shuttingDown;
}
}

这个service办法每次在它进入时要添加,而在它回来退出时要削减:

protected void service(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException
{
enteringServiceMethod();
try {
super.service(req, resp);
} finally {
leavingServiceMethod();
}
}

destroy办法应当查看serviceCounter, 假如存在长时刻办法运转的话, 设置变量shuttingDown . 这个变量将会让那个正在处理恳求的线程知道:该完毕了,封闭吧! destroy 办法应当等候这几个service 办法完结, 这样就是一个清楚的封闭进程了.


public void destroy() {

if (numServices() 0) {
setShuttingDown(true);
}


while(numService() 0) {
try {
thisThread.sleep(interval);
} catch (InterruptedException e) {
}
}
}

long-running 办法如必要应当查看这个变量,而且解说他们的作业:

public void doPost(...) {
...
for(i = 0; ((i lotsOfStuffToDo) !isShuttingDown()); i++) {
try {
partOfLongRunningOperation(i);
} catch (InterruptedException e) {
}
}
}

3.3 供给关于Servlet的信息

public class SimpleServlet extends HttpServlet {

...

public String getServletInfo() {
return "A simple servlet";
}
}
版权声明
本文来源于网络,版权归原作者所有,其内容与观点不代表威尼斯人立场。转载文章仅为传播更有价值的信息,如采编人员采编有误或者版权原因,请与我们联系,我们核实后立即修改或删除。

猜您喜欢的文章

阅读排行

  • 1
  • 2
  • 3
  • 4
  • 5

    hibernate缓存csdn

    数据,目标,运用
  • 6

    组合优于承继快报

    承继,目标,子类
  • 7

    跳出多层循环sina

    循环,符号,方法
  • 8

    servlet入门2alibaba

    办法,客户端,服务器
  • 9

    JAXB 的根本用法mingxing

    办法,特点,节点