Java Notes-14(DateAtHost Client, TinyHttpd Server, Socket Options)

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/yu444/article/details/50710735

Summary: DateAtHost Client, TinyHttpd Server, Socket Options

The DateAtHost Client

-DateAtHost , includes a subclass of java.util.Date that fetches the time from a remote host instead of initializing itself from the local clock. 

-DateAtHost connects to the time service (port 37) and reads four bytes representing the time on the remote host. These four bytes have a peculiar specification that we decode to get the time. Here’s the code

//file: DateAtHost.java
import java.net.Socket;
import java.io.*;
public class DateAtHost extends java.util.Date {
static int timePort = 37;
// seconds from start of 20th century to Jan 1, 1970 00:00 GMT
static final long offset = 2208988800L;
public DateAtHost( String host ) throws IOException {
this( host, timePort );
}
public DateAtHost( String host, int port ) throws IOException {
Socket server = new Socket( host, port );
DataInputStream din =
new DataInputStream( server.getInputStream() );
int time = din.readInt();
server.close();
setTime( (((1L << 32) + time) - offset) * 1000 );
}
}
The TinyHttpd Server

-we’re going to build  TinyHttpd , a minimal but functional web server.TinyHttpd listens on a specified port and services simple HTTP  GET requests.

-TinyHttpd services each request in its own thread. Therefore, TinyHttpd can service several requests concurrently.

-here’s  TinyHttpd:

//file: TinyHttpd.java
import java.net.*;
import java.io.*;
import java.util.regex.*;
import java.util.concurrent.*;
public class TinyHttpd {
public static void main( String argv[] ) throws IOException {
Executor executor = Executors.newFixedThreadPool(3);
ServerSocket ss = new ServerSocket( Integer.parseInt(argv[0]) );
while ( true )
executor.execute( new TinyHttpdConnection( ss.accept() ) );
}
}
class TinyHttpdConnection implements Runnable {
Socket client;
TinyHttpdConnection ( Socket client ) throws SocketException {
this.client = client;
}
public void run() {
try {
BufferedReader in = new BufferedReader(
new InputStreamReader(client.getInputStream(), "8859_1" ) );
OutputStream out = client.getOutputStream();
PrintWriter pout = new PrintWriter(
new OutputStreamWriter(out, "8859_1"), true );
String request = in.readLine();
System.out.println( "Request: "+request);
Matcher get = Pattern.compile("GET /?(\\S*).*").matcher( request );
if ( get.matches() ) {
request = get.group(1);
if ( request.endsWith("/") || request.equals("") )
Sockets  |  479
www.it-ebooks.info
request = request + "index.html";
try {
FileInputStream fis = new FileInputStream ( request );
byte [] data = new byte [ 64*1024 ];
for(int read; (read = fis.read( data )) > -1; )
out.write( data, 0, read );
out.flush();
} catch ( FileNotFoundException e ) {
pout.println( "404 Object Not Found" ); }
} else
pout.println( "400 Bad Request" );
client.close();
} catch ( IOException e ) {
System.out.println( "I/O error " + e ); }
}
}
-Once we have the filename, we try to open the specified file and send its contents using a large byte array. Here we loop, reading one buffer at a time and writing to the client via the  OutputStream . If we can’t parse the request or the file doesn’t exist, we use the PrintStream to send a textual message. Then we return a standard HTTP error message.Finally, we close the socket and return from  run() , completing our task.

Socket Options

-The  SO_TIMEOUT option sets a timer on all I/O methods of a socket that block so that you don’t have to wait forever if they don’t return. This works for operations such as accept() on server sockets and  read() or  write() on all sockets. If the timer expires before the operation would complete, an  InterruptedIOException is thrown. 

serverSocket.setSoTimeout( 2000 ); // 2 seconds
while ( !shutdown ) {
try {
Socket client = serverSocket.accept();
handleClient( client );
} catch ( InterruptedIOException e ) {
// ignore the exception
}
// exit
}
- TCP_NODELAY tries to prevent certain interactive applications from flooding the network with very tiny packets.

-SO_LINGER This option controls what happens to any unsent data when you perform a  close() on an active socket connection, send or dicard

-TCP_KEEPALIVE  This option can be enabled with the  setKeepAlive() method. It triggers a feature of TCP that polls the other side every two hours if there is no other activity.

-Half-close you can shut down sending but not receiving, or vice versa. 



猜你喜欢

转载自blog.csdn.net/yu444/article/details/50710735