简单的 http 服务器
简单的基于socket和NIO的 http server示例:
项目路径:https://github.com/windwant/windwant-demo/tree/master/httpserver-demo
1. Request:
package org.windwant.httpserver; import java.io.IOException;
import java.io.InputStream; /**
* Created by windwant on 2016/6/12.
*/
public class Request { private InputStream in; public String getUri() {
return uri;
} private String uri; public Request(){} public Request(InputStream in){
this.in = in;
} public void read(){
StringBuffer sb = new StringBuffer();
int i = 0;
byte[] b = new byte[2048];
try {
i = in.read(b);
for (int j = 0; j < i; j++) {
sb.append((char)b[j]);
}
takeUri(sb);
} catch (IOException e) {
e.printStackTrace();
}
} public void takeUri(StringBuffer sb){
int i = sb.indexOf(" ");
if(i > 0){
int j = sb.indexOf(" ", i + 1);
if(j > 0){
uri = sb.substring(i + 1, j).toString();
System.out.println("http request uri: " + uri);
if(!(uri.endsWith("/index.html") || uri.endsWith("/test.jpg"))){
uri = "/404.html";
System.out.println("http request uri rewrite: " + uri);
}
}
}
} }
2. Response:
package org.windwant.httpserver; import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.OutputStream;
import java.nio.ByteBuffer;
import java.nio.channels.SocketChannel; /**
* Created by windwant on 2016/6/12.
*/
public class Response {
private static final int BUFFER_SIZE = 1024; public void setRequest(Request request) {
this.request = request;
} Request request; OutputStream out; SocketChannel osc; public Response(OutputStream out){
this.out = out;
} public Response(SocketChannel osc){
this.osc = osc;
} public void response(){
byte[] b = new byte[BUFFER_SIZE];
File file = new File(HttpServer.WEB_ROOT, request.getUri());
try {
StringBuilder sb = new StringBuilder();
if(file.exists()){
FileInputStream fi = new FileInputStream(file);
int ch = 0;
while ((ch = fi.read(b, 0, BUFFER_SIZE)) > 0){
out.write(b, 0, ch);
}
out.flush();
}else{
sb.append("HTTP/1.1 404 File Not Found \r\n");
sb.append("Content-Type: text/html\r\n");
sb.append("Content-Length: 24\r\n" );
sb.append("\r\n" );
sb.append("<h1>File Not Found!</h1>");
out.write(sb.toString().getBytes());
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
} public void responseNIO(){
byte[] b = new byte[BUFFER_SIZE];
File file = new File(HttpServer.WEB_ROOT, request.getUri());
try {
StringBuilder sb = new StringBuilder();
if(file != null && file.exists()){
FileInputStream fi = new FileInputStream(file);
while (fi.read(b) > 0){
osc.write(ByteBuffer.wrap(b));
b = new byte[BUFFER_SIZE];
}
}else{
sb.append("HTTP/1.1 404 File Not Found \r\n");
sb.append("Content-Type: text/html\r\n");
sb.append("Content-Length: 24\r\n" );
sb.append("\r\n" );
sb.append("<h1>File Not Found!</h1>");
osc.write(ByteBuffer.wrap(sb.toString().getBytes()));
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
} }
3. HttpServer:
package org.windwant.httpserver; import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.InetAddress;
import java.net.ServerSocket;
import java.net.Socket; /**
* Created by windwant on 2016/6/12.
*/
public class HttpServer {
public static final String WEB_ROOT = System.getProperty("user.dir") + "\\src\\test\\resources\\webroot";
public static final int SERVER_PORT = 8888;
public static final String SERVER_IP = "127.0.0.1"; public static void main(String[] args) {
HttpServer httpServer = new HttpServer();
httpServer.await();
} public void await(){
ServerSocket serverSocket = null;
try {
serverSocket = new ServerSocket(SERVER_PORT, 1, InetAddress.getByName(SERVER_IP));
while (true){
Socket socket = serverSocket.accept();
InputStream in = socket.getInputStream();
OutputStream out = socket.getOutputStream();
Request request = new Request(in);
request.read(); Response response = new Response(out);
response.setRequest(request);
response.response();
socket.close();
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
4. HttpNIOServer:
package org.windwant.httpserver; import java.io.IOException;
import java.net.InetSocketAddress;
import java.net.ServerSocket;
import java.nio.ByteBuffer;
import java.nio.channels.SelectionKey;
import java.nio.channels.Selector;
import java.nio.channels.ServerSocketChannel;
import java.nio.channels.SocketChannel;
import java.util.Iterator;
import java.util.Set;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors; /**
* Created by windwant on 2016/6/13.
*/
public class HttpNIOServer { private ServerSocketChannel serverSocketChannel; private ServerSocket serverSocket; private Selector selector; Request request; private ExecutorService es; private static final Integer SERVER_PORT = 8888; public void setShutdown(boolean shutdown) {
this.shutdown = shutdown;
} private boolean shutdown = false; public static void main(String[] args) {
HttpNIOServer server = new HttpNIOServer();
server.start();
System.exit(0);
} HttpNIOServer(){
try {
es = Executors.newFixedThreadPool(5);
serverSocketChannel = ServerSocketChannel.open();
serverSocketChannel.configureBlocking(false);
serverSocket = serverSocketChannel.socket();
serverSocket.bind(new InetSocketAddress(SERVER_PORT)); selector = Selector.open();
serverSocketChannel.register(selector, SelectionKey.OP_ACCEPT);
System.out.println("server init...");
} catch (IOException e) {
e.printStackTrace();
}
} public void start(){
try {
while (!shutdown){
selector.select();
Set<SelectionKey> selectionKeySet = selector.selectedKeys();
Iterator<SelectionKey> it = selectionKeySet.iterator();
while (it.hasNext()){
SelectionKey selectionKey = it.next();
it.remove();
handleRequest(selectionKey);
}
}
} catch (IOException e) {
e.printStackTrace();
}
} public void handleRequest(SelectionKey selectionKey){
ServerSocketChannel ssc = null;
SocketChannel ss = null;
try {
if(selectionKey.isAcceptable()){
ssc = (ServerSocketChannel) selectionKey.channel();
ss = ssc.accept(); ss.configureBlocking(false);
ss.register(selector, SelectionKey.OP_READ);
}else if(selectionKey.isReadable()){
ss = (SocketChannel) selectionKey.channel();
ByteBuffer byteBuffer = ByteBuffer.allocate(2048);
StringBuffer sb = new StringBuffer();
while (ss.read(byteBuffer) > 0){
byteBuffer.flip();
int lgn = byteBuffer.limit();
for (int i = 0; i < lgn; i++) {
sb.append((char)byteBuffer.get(i));
}
byteBuffer.clear();
}
if(sb.length() > 0) {
request = new Request();
request.takeUri(sb);
ss.register(selector, SelectionKey.OP_WRITE);
}
}else if(selectionKey.isWritable()){
ss = (SocketChannel) selectionKey.channel();
ByteBuffer rb = ByteBuffer.allocate(2048);
Response response = new Response(ss);
response.setRequest(request);
response.responseNIO();
ss.register(selector, SelectionKey.OP_READ);
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
简单的 http 服务器的更多相关文章
- 使用 Nodejs 搭建简单的Web服务器
使用Nodejs搭建Web服务器是学习Node.js比较全面的入门教程,因为要完成一个简单的Web服务器,你需要学习Nodejs中几个比较重要的模块,比如:http协议模块.文件系统.url解析模块. ...
- 一个简单的 Web 服务器 [未完成]
最近学习C++,linux和网络编程,想做个小(mini)项目. 就去搜索引擎, 开源中国, Sourceforge上找http server的项目. 好吧,也去了知乎. 知乎上程序员氛围好, ...
- 20145216 20145330 《信息安全系统设计基础》 实验五 简单嵌入式WEB 服务器实验
20145216 20145330 <信息安全系统设计基础> 实验五 简单嵌入式WEB 服务器实验 实验报告封面 实验步骤 1.阅读理解源码 进入/arm2410cl/exp/basic/ ...
- 自己动手模拟开发一个简单的Web服务器
开篇:每当我们将开发好的ASP.NET网站部署到IIS服务器中,在浏览器正常浏览页面时,可曾想过Web服务器是怎么工作的,其原理是什么?“纸上得来终觉浅,绝知此事要躬行”,于是我们自己模拟一个简单的W ...
- 深入剖析tomcat之一个简单的web服务器
这个简单的web服务器包含三个类 HttpServer Request Response 在应用程序的入口点,也就是静态main函数中,创建一个HttpServer实例,然后调用其await()方法. ...
- 20145208《信息安全系统设计基础》实验五 简单嵌入式WEB 服务器实验
20145208<信息安全系统设计基础>实验五 简单嵌入式WEB 服务器实验 20145208<信息安全系统设计基础>实验五 简单嵌入式WEB 服务器实验
- 用Python建立最简单的web服务器
利用Python自带的包可以建立简单的web服务器.在DOS里cd到准备做服务器根目录的路径下,输入命令: python -m Web服务器模块 [端口号,默认8000] 例如: python -m ...
- 计算机网络(13)-----java nio手动实现简单的http服务器
java nio手动实现简单的http服务器 需求分析 最近在学习HTTP协议,还是希望动手去做一做,所以就自己实现了一个http服务器,主要功能是将http请求封装httpRequest,通过解析 ...
- 20145210 20145226 《信息安全系统设计基础》实验五 简单嵌入式WEB服务器实验
20145210 20145226 <信息安全系统设计基础>实验五 简单嵌入式WEB服务器实验 结对伙伴:20145226 夏艺华 实验报告封面 实验目的与要求 · 掌握在ARM开发板实现 ...
- 20145221 《信息安全系统设计基础》实验五 简单嵌入式WEB服务器实验
20145221 <信息安全系统设计基础>实验五 简单嵌入式WEB服务器实验 实验报告 队友博客:20145326蔡馨熠 实验博客:<信息安全系统设计基础>实验五 简单嵌入式W ...
随机推荐
- Tigase XMPP Server的安装
Tigase和OpenFire都是基于XMPP(Extensible Messaging and Presence Protocol, 可扩展通讯和表示协议)的,主要功能是实现消息的即时通信.Goog ...
- Android使用SQLite数据库(1)
Android中使用SQLite数据库要通过SQLiteOpenHelper类. 首先,定义相关变量: // 数据库变量 DatabaseHelper mDBH; SQLiteDatabase db; ...
- @RequestMapping映射请求
1.SpringMVC使用@RequestMapping注解为控制器指定可以处理哪些URL请求. 2.在控制器的类定义和方法定义处都可标注@RequestMapping 2.1 类定义处:提 ...
- Hibernate总结(二)
在上一篇Hibernate总结(一)简单总结了一级缓存,快照,增删改查的简单使用,这一篇总结两张表的级联操作. 级联涉及到三种情况,many-many,1-many,many-1. 首先是1-many ...
- mysql安装中出现的问题,
花了一天的时间明天mysql的安装方法: 自己的错误: 主要原因: (1):bin文件坏境配置出现了问题,没有重新在系统中配置文件 解决方法:右击电脑——属性——高级系统设置——变量配置——在path ...
- python 学习笔记9(面向对象)
面向过程.函数式.面向对象 面向过程:根据业务逻辑从上到下写垒代码 函数式:将某功能代码封装到函数中,日后便无需重复编写,仅调用函数即可 面向对象(Object Oriented Programmin ...
- PHP内核探索之变量(4)- 数组操作
上一节(PHP内核探索之变量(3)- hash table),我们已经知道,数组在PHP的底层实际上是HashTable(链接法解决冲突),本文将对最常用的函数系列-数组操作的相关函数做进一步的跟踪. ...
- linux系统新建用户ssh远程登陆显示-bash-4.1$解决方法
linux系统新建的用户用ssh远程登陆显示-bash-4.1$,不显示用户名路径 网络上好多解决办法,大多是新建.bash_profile文件然后输入XXXXX....然而并没有什么用没有用.... ...
- 解决asp.net动态压缩
本来想写一个网站优化的系列(前端到后端的数据库,垂直优化到分布式,后面会补上),但没有时间(借口),今天就总结一下前几天优化网站的过程. 网站优化重点在于找出出现性能问题的地方,往往是解决方案很简单, ...
- [deviceone开发]-doSpace应用源码开源
一.简介 这个是我们的一个门户App,能够动态加载示例,查看文档,视频,朋友圈聊天等功能.目前开源供大家参考学习,另外"讨论"里对应的BBS上有详细的文档说明,非常值得大家参考和学 ...