|
马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。
您需要 登录 才可以下载或查看,没有帐号?立即注册
x
比如模式、敏捷方法什么的,这些思想好,但是实施的人没有理解而且没有正确运用这些知识导致了开发周期的延长。比如说对象,通过getName()方法不能获取对象的名字。web|web服务|web服务器|编程|收集超文本传输协定(HTTP)是位于TCP/IP协定的使用层,是最广为人知的协定,也是互连网中最中心的协定之一,一样,HTTP也是基于C/S或B/S模子完成的。现实上,我们利用的扫瞄器如Netscape或IE是完成HTTP协定中的客户端,而一些经常使用的Web服务器软件如Apache、IIS和iPlanetWebServer等是完成HTTP协定中的服务器端。Web页由服务端资本定位,传输到扫瞄器,经由扫瞄器的注释后,被客户所看到。
Web的事情基于客户机/服务器盘算模子,由Web扫瞄器(客户机)和Web服务器(服务器)组成,二者之间接纳超文本传送协定(HTTP)举行通讯。HTTP协定是Web扫瞄器和Web服务器之间的使用层协定,是通用的、无形态的、面向对象的协定。
一个完全的HTTP协定会话历程包含四个步骤:
◆毗连,Web扫瞄器与Web服务器创建毗连,翻开一个称为Socket(套接字)的假造文件,此文件的创建标记着毗连创建乐成;
◆哀求,Web扫瞄器经由过程Socket向Web服务器提交哀求。HTTP的哀求通常为GET或POST命令(POST用于FORM参数的传送);
◆应对,Web扫瞄器提交哀求后,经由过程HTTP协定传送给Web服务器。Web服务器接到后,举行事件处置,处置了局又经由过程HTTP传回给Web扫瞄器,从而在Web扫瞄器上显现出所哀求的页面;
◆封闭毗连,应对停止后Web扫瞄器与Web服务器必需断开,以包管别的Web扫瞄器可以与Web服务器创建毗连。
Java完成Web服务器功效的程序计划
编程思绪
依据上述HTTP协定的会话历程,本实例中完成了GET哀求的Web服务器程序的办法,办法以下:
经由过程创立ServerSocket类对象,侦听用户指定的端口(为8080),守候并承受客户机哀求到端口。创立与Socket相干联的输出流和输入流,然后读取客户机的哀求信息。若哀求范例是GET,则从哀求信息中猎取所会见的HTML文件名;假如HTML文件存在,则翻开HTML文件,把HTTP头信息和HTML文件内容经由过程Socket传回给Web扫瞄器,然后封闭文件,不然发送毛病信息给Web扫瞄器。最初封闭与响应Web扫瞄器毗连的Socket。
用Java编写Web服务器httpServer.java文件的源代码以下:
//httpServer.java
importjava.net.*;
importjava.io.*;
importjava.util.*;
importjava.lang.*;
publicclasshttpServer{
publicstaticvoidmain(Stringargs[]){
intport;
ServerSocketserver_socket;
//读取服务器端标语
try{
port=Integer.parseInt(args[0]);
}
catch(Exceptione){
port=8080;
}
try{
//监听服务器端口,守候毗连哀求
server_socket=newServerSocket(port);
System.out.println("httpServerrunningonport"+
server_socket.getLocalPort());
//显现启动信息
while(true){
Socketsocket=server_socket.accept();
System.out.println("Newconnectionaccepted"+
socket.getInetAddress()+
":"+socket.getPort());
//创立分线程
try{
httpRequestHandlerrequest=
newhttpRequestHandler(socket);
Threadthread=newThread(request);
//启动线程
thread.start();
}
catch(Exceptione){
System.out.println(e);
}
}
}
catch(IOExceptione){
System.out.println(e);
}
}
}
classhttpRequestHandlerimplementsRunnable
{
finalstaticStringCRLF="
";
Socketsocket;
InputStreaminput;
OutputStreamoutput;
BufferedReaderbr;
//机关办法
publichttpRequestHandler(Socketsocket)throwsException
{
this.socket=socket;
this.input=socket.getInputStream();
this.output=socket.getOutputStream();
this.br=
newBufferedReader(newInputStreamReader(socket.getInputStream()));
}
//完成Runnable接口的run()办法
publicvoidrun()
{
try{
processRequest();
}
catch(Exceptione){
System.out.println(e);
}
}
privatevoidprocessRequest()throwsException
{
while(true){
//读取并显现Web扫瞄器提交的哀求信息
StringheaderLine=br.readLine();
System.out.println("Theclientrequestis"+headerLine);
if(headerLine.equals(CRLF)||headerLine.equals(""))break;
StringTokenizers=newStringTokenizer(headerLine);
Stringtemp=s.nextToken();
if(temp.equals("GET")){
StringfileName=s.nextToken();
fileName="."+fileName;
//翻开所哀求的文件
FileInputStreamfis=null;
booleanfileExists=true;
try
{
fis=newFileInputStream(fileName);
}
catch(FileNotFoundExceptione)
{
fileExists=false;
}
//完成回应动静
StringserverLine="Server:asimplejavahttpServer";
StringstatusLine=null;
StringcontentTypeLine=null;
StringentityBody=null;
StringcontentLengthLine="error";
if(fileExists)
{
statusLine="HTTP/1.0200OK"+CRLF;
contentTypeLine="Content-type:"+
contentType(fileName)+CRLF;
contentLengthLine="Content-Length:"
+(newInteger(fis.available())).toString()
+CRLF;
}
else
{
statusLine="HTTP/1.0404NotFound"+CRLF;
contentTypeLine="text/html";
entityBody="<HTML>"+
"<HEAD><TITLE>404NotFound</TITLE></HEAD>"+
"<BODY>404NotFound"
+"<br>usage:http://yourHostName:port/"
+"fileName.html</BODY></HTML>";
}
//发送到服务器信息
output.write(statusLine.getBytes());
output.write(serverLine.getBytes());
output.write(contentTypeLine.getBytes());
output.write(contentLengthLine.getBytes());
output.write(CRLF.getBytes());
//发送信息内容
if(fileExists)
{
sendBytes(fis,output);
fis.close();
}
else
{
output.write(entityBody.getBytes());
}
}
}
//封闭套接字和流
try{
output.close();
br.close();
socket.close();
}
catch(Exceptione){}
}
privatestaticvoidsendBytes(FileInputStreamfis,OutputStreamos)
throwsException
{
//创立一个1Kbuffer
byte[]buffer=newbyte[1024];
intbytes=0;
//将文件输入到套接字输入流中
while((bytes=fis.read(buffer))!=-1)
{
os.write(buffer,0,bytes);
}
}
privatestaticStringcontentType(StringfileName)
{
if(fileName.endsWith(".htm")||fileName.endsWith(".html"))
{
return"text/html";
}
return"fileName";
}
}
编程技能申明
◆主线程计划
主线程的计划就是在主线程httpServer类中完成了服务器端口的侦听,服务器承受一个客户端哀求以后创立一个线程实例处置哀求,代码以下:
importjava.net.*;
importjava.io.*;
importjava.util.*;
importjava.lang.*;
publicclasshttpServer{
publicstaticvoidmain(Stringargs[]){
port;
ServerSocketserver_socket;
//读取服务器端标语
try{
port=Integer.parseInt(args[0]);
}
catch(Exceptione){
port=8080;
}
try{
//监听服务器端口,守候毗连哀求
server_socket=newServerSocket(port);
System.out.println("httpServerrunningonport"
+server_socket.getLocalPort());
..........
..........
◆毗连处置分线程计划
在分线程httpRequestHandler类中完成了HTTP协定的处置,这个类完成了Runnable接口,代码以下:
classhttpRequestHandlerimplementsRunnable
{
finalstaticStringCRLF="
";
Socketsocket;
InputStreaminput;
OutputStreamoutput;
BufferedReaderbr;
//机关办法
publichttpRequestHandler(Socketsocket)throwsException
{
this.socket=socket;
//失掉输出输入流
this.input=socket.getInputStream();
this.output=socket.getOutputStream();
this.br=
newBufferedReader(newInputStreamReader(socket.getInputStream()));
}
//完成Runnable接口的run()办法
publicvoidrun()
{
try{
processRequest();
}
catch(Exceptione){
System.out.println(e);
}
}
◆构建processRequest()办法来处置信息的吸收和发送
作为完成Runnable接口的次要内容,在run()办法中挪用processRequest()办法来处置客户哀求内容的吸收和服务器前往信息的发送,代码以下:
privatevoidprocessRequest()throwsException
{
while(true){
//读取并显现Web扫瞄器提交的哀求信息
StringheaderLine=br.readLine();
System.out.println("Theclientrequestis"+headerLine);
if(headerLine.equals(CRLF)||headerLine.equals(""))break;
//依据哀求字符串中的空格拆分客户哀求
StringTokenizers=newStringTokenizer(headerLine);
Stringtemp=s.nextToken();
if(temp.equals("GET")){
StringfileName=s.nextToken();
fileName="."+fileName;
.............
.............
在processRequest()办法中失掉客户端哀求后,使用一个StringTokenizer类完成了字符串的拆分,这个类能够完成依据字符串中指定的分开符(缺省为空格)将字符串拆分红为字串的功效。使用nextToken()办法顺次失掉这些字串;sendBytes()办法完成信息内容的发送,contentType()办法用于判别文件的范例。
显现Web页面
显现Web页面的index.html文件代码以下:
<html>
<head>
<metahttp-equiv="Content-Language"content="zh-cn">
<metaname="GENERATOR"content="MicrosoftFrontPage5.0">
<metahttp-equiv="Content-Type"content="text/html;charset=gb2312">
<title>JavaWeb服务器</title>
</head>
<body>
<p>*********<fontcolor="#FF0000">接待你的到来!</font>*********</p>
<p>这是一个用Java言语完成的Web服务器</p>
<hr>
</body>
</html>
运转实例
为了测试上述程序的准确性,将编译后的httpServer.class、httpRequestHandler.class和下面的index.html文件置于收集的某台主机的统一目次中。
起首运转服务器程序javahttpServer8080,服务器程序运转后显现端口信息“httpServerruningonport8080”,然后在扫瞄器的地点栏中输出http://localhost:8080/index.html,就能够准确显现网页,同时在显现“httpServerruningonport8080”窗口中服务器会呈现一些信息。
学习JAVA的目的更多的是培养自身的工作能力,我觉得工作能力的一个核心就是:独立思考能力,因为只有独立思考后,才会有自己的见解 |
|