使用Netty实现的一个简单HTTP服务器
1.HttpServer,Http服务启动类,用于初始化各种线程和通道
public class HttpServer {
public void bind(int port) throws Exception {
EventLoopGroup bossGroup = new NioEventLoopGroup();
EventLoopGroup workerGroup = new NioEventLoopGroup();
try {
ServerBootstrap b = new ServerBootstrap();
b.group(bossGroup, workerGroup)
.channel(NioServerSocketChannel.class)
.option(ChannelOption.SO_BACKLOG, 1024)
.childHandler(new HttpChannelInitService()).option(ChannelOption.SO_BACKLOG, 128)
.childOption(ChannelOption.SO_KEEPALIVE, true);
ChannelFuture f = b.bind(port).sync();
f.channel().closeFuture().sync();
} finally {
bossGroup.shutdownGracefully();
workerGroup.shutdownGracefully();
}
}
public static void main(String[] args) throws Exception {
int port = 8080;
if (args != null && args.length > 0) {
try {
port = Integer.valueOf(args[0]);
} catch (NumberFormatException e) {
}
}
new HttpServer().bind(port);
}
}
2.HttpChannelInitService,通道初始化类
public class HttpChannelInitService extends ChannelInitializer<SocketChannel>{
@Override
protected void initChannel(SocketChannel sc)
throws Exception {
sc.pipeline().addLast(new HttpResponseEncoder());
sc.pipeline().addLast(new HttpRequestDecoder());
sc.pipeline().addLast(new HttpChannelHandler());
}
}
3.HttpChannelHandler,处理请求的HTTP信息
public class HttpChannelHandler extends ChannelInboundHandlerAdapter {
private HttpRequest request = null;
private FullHttpResponse response = null;
@Override
public void channelRead(ChannelHandlerContext ctx, Object msg)
throws Exception {
if (msg instanceof HttpRequest) {
request = (HttpRequest) msg;
String uri = request.getUri();
String res = "";
try {
res = ReadUtils.readFile(uri.substring(1));
response = new DefaultFullHttpResponse(HttpVersion.HTTP_1_1,HttpResponseStatus.OK, Unpooled.wrappedBuffer(res.getBytes("UTF-8")));
setJsessionId(isHasJsessionId());
setHeaders(response);
} catch (Exception e) {//处理出错,返回错误信息
res = "<html><body>Server Error</body></html>";
response = new DefaultFullHttpResponse(HttpVersion.HTTP_1_1,HttpResponseStatus.OK, Unpooled.wrappedBuffer(res.getBytes("UTF-8")));
setHeaders(response);
}
if(response!=null)
ctx.write(response);
}
if (msg instanceof HttpContent) {
HttpContent content = (HttpContent) msg;
ByteBuf buf = content.content();
System.out.println(buf.toString(CharsetUtil.UTF_8));
buf.release();
}
}
/**
* 设置HTTP返回头信息
*/
private void setHeaders(FullHttpResponse response) {
response.headers().set(HttpHeaders.Names.CONTENT_TYPE, "text/html");
response.headers().set(HttpHeaders.Names.CONTENT_LANGUAGE, response.content().readableBytes());
if (HttpHeaders.isKeepAlive(request)) {
response.headers().set(HttpHeaders.Names.CONNECTION, Values.KEEP_ALIVE);
}
}
/**
* 设置JSESSIONID
*/
private void setJsessionId(boolean isHasJsessionId) {
if(!isHasJsessionId){
CookieEncoder encoder = new CookieEncoder(true);
encoder.addCookie(HttpSession.SESSIONID, HttpSessionManager.getSessionId());
String encodedCookie = encoder.encode();
response.headers().set(HttpHeaders.Names.SET_COOKIE, encodedCookie);
}
}
/**
* 从cookie中获取JSESSIONID信息
* 判断服务器是否有客户端的JSESSIONID
* @author yangsong
* @date 2015年3月26日 下午2:08:07
*/
private boolean isHasJsessionId() {
try {
String cookieStr = request.headers().get("Cookie");
Set<Cookie> cookies = CookieDecoder.decode(cookieStr);
Iterator<Cookie> it = cookies.iterator();
while(it.hasNext()){
Cookie cookie = it.next();
if(cookie.getName().equals(HttpSession.SESSIONID)){
if(HttpSessionManager.isHasJsessionId(cookie.getValue())){
return true;
}
System.out.println("JSESSIONID:"+cookie.getValue());
}
}
} catch (Exception e1) {
e1.printStackTrace();
}
return false;
}
@Override
public void channelReadComplete(ChannelHandlerContext ctx) throws Exception {
System.out.println("server channelReadComplete..");
ctx.flush();//刷新后才将数据发出到SocketChannel
}
@Override
public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause)
throws Exception {
System.out.println("server exceptionCaught..");
ctx.close();
}
}
5.HttpSessionManager,Session管理类
/**
* HttpSession管理器
*/
public class HttpSessionManager { private static final HashMap<String,HttpSession> sessionMap = new HashMap<String, HttpSession>(); /**
* 创建一个session并返回sessionId
*/
public static String getSessionId(){
synchronized (sessionMap) {
HttpSession httpSession = new HttpSession();
sessionMap.put(httpSession.getSessionID(), httpSession);
return httpSession.getSessionID();
}
}
/**
* 判断服务器是否包含该客户端的session信息
*/
public static boolean isHasJsessionId(String sessiondId){
synchronized (sessionMap) {
return sessionMap.containsKey(sessiondId);
}
} }
6.页面信息与cookie

使用Netty实现的一个简单HTTP服务器的更多相关文章
- 用nodejs搭建一个简单的服务器
使用nodejs搭建一个简单的服务器 nodejs优点:性能高(读写文件) 数据操作能力强 官网:www.nodejs.org 验证是否安装成功:cmd命令行中输入node -v 如果显示版本号表示安 ...
- 初学Node(六)搭建一个简单的服务器
搭建一个简单的服务器 通过下面的代码可以搭建一个简单的服务器: var http = require("http"); http.createServer(function(req ...
- 轻松创建nodejs服务器(1):一个简单nodejs服务器例子
这篇文章主要介绍了一个简单nodejs服务器例子,本文实现了一个简单的hello world例子,并展示如何运行这个服务器,需要的朋友可以参考下 我们先来实现一个简单的例子,hello world ...
- Node学习(二) --使用http和fs模块实现一个简单的服务器
1.创建一个www目录,存储静态文件1.html.1.jpg. * html文件内容如下: 12345678910111213 <html lang="en">< ...
- Express 的基本使用(创建一个简单的服务器)
Express 的基本使用(创建一个简单的服务器) const express = require('express') // 创建服务器应用程序 // 相当于 http.creatServer co ...
- Netty练手项目-简单Http服务器
简单的设计思路就是,启动一个可以截断并处理Http请求的服务器代码.使用netty提供的boss线程与worker线程的模型,并使用netty的http解码器.自行编写了http url处理的部分.在 ...
- 理解与模拟一个简单web服务器
先简单说下几个概念,根据自己的理解,不正确请见谅. web服务器 首先要知道什么是web服务器,简单说web服务器就是可以使用HTTP传输协议与客户端进行通信的服务器.最初的web服务器只能用来处理静 ...
- Linux:写一个简单的服务器
开始了新篇章:Linux网络编程. 基础知识: 套接字概念 Socket本身有"插座"的意思,在Linux环境下,用于表示进程间网络通信的特殊文件类型.本质为内核借助缓冲区形成的伪 ...
- Windows 上静态编译 Libevent 2.0.10 并实现一个简单 HTTP 服务器(无数截图)
[文章作者:张宴 本文版本:v1.0 最后修改:2011.03.30 转载请注明原文链接:http://blog.s135.com/libevent_windows/] 本文介绍了如何在 Window ...
随机推荐
- linux uart驱动——uart platfrom 注册(三)
一:注册platform device 注册一个platfrom device一般需要初始化两个内容,设备占用的资源resource和设备私有数据dev.platfrom_data.设备的resour ...
- C#抓取网面上的html内容(JS动态生成的无法抓取)
抓取内容的代码: /// </summary> /// <param name="url">路径URL</param> /// <para ...
- Java知识点梳理——读写分离
1.读写分离:可以通过Spring提供的AbstractRoutingDataSource类,重写determineCurrentLookupKey方法,实现动态切换数据源的功能:读写分离可以有效减轻 ...
- iOS开发 僵尸调试
本文转载至 http://blog.sina.com.cn/s/blog_a843a8850101dxin.html 引自:http://blog.csdn.net/likendsl/articl ...
- java中随机生成汉字
main方法中使用: //随机生成100个汉字 String ss=""; for(int i=0;i<100;i++){ ss+=getChinese(i); } Syst ...
- C#中的new和override(转)
在衍生类中的方法上使用new和override关键字有何意义,可以通过一系列问题来找到答案.先看一段代码: 1 class Program 2 { 3 static void Main(string[ ...
- React-Native开源项目学习
https://github.com/liuhongjun719/react-native-DaidaiHelperNew 借贷助手https://github.com/liuhongjun719/r ...
- Intellij Idea生成JavaDoc
JavaDoc是一种将注释生成HTML文档的技术,生成的HTML文档类似于Java的API,易读且清晰明了.在简略介绍JavaDoc写法之后,再看一下在Intellij Idea 中如何将代码中的注释 ...
- ABAP 给动态变量赋值
[转自 http://blog.csdn.net/forever_crazy/article/details/6544830] 需求: 有时写程序的时候,需要给某个动态变量 赋值操作,当字段比较多时, ...
- shell执行lua脚本传参数
#lua test.lua 2 5arg[0]= test.lua arg[1]= 2arg[2]= 5 if arg[1] and arg[1] == "2" then prin ...