好得很程序员自学网

<tfoot draggable='sEl'></tfoot>

关于Netty--Http请求处理方式

Netty--Http请求处理

1.这几天在看Netty权威指南,代码敲了一下,就当做个笔记吧。

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

/**

  * Http服务端

  * @author Tang

  * 2018年5月13日

  */

public class HttpServer {

     public void run(String url,Integer port) {

         EventLoopGroup bossGroup = new NioEventLoopGroup();

         EventLoopGroup workerGroup = new NioEventLoopGroup();

         ServerBootstrap bootstrap = new ServerBootstrap();

         bootstrap.group(bossGroup, workerGroup);

         bootstrap.channel(NioServerSocketChannel. class );

         bootstrap.childHandler( new ChannelInitializer<Channel>() {

             @Override

             protected void initChannel(Channel ch) throws Exception {

                 ch.pipeline().addLast( "http-decoder" , new HttpRequestDecoder());

                 ch.pipeline().addLast( "http-aggregator" ,

                         new HttpObjectAggregator( 65536 ));

                 ch.pipeline()

                         .addLast( "http-encoder" , new HttpResponseEncoder());

                 ch.pipeline()

                         .addLast( "http-chunked" , new ChunkedWriteHandler());

                 ch.pipeline().addLast( "http-handler" , new HttpServerHandler());

             }

         });

         try {

             ChannelFuture channelFuture = bootstrap.bind(url, port).sync();

             channelFuture.channel().closeFuture().sync();

         } catch (InterruptedException e) {

             e.printStackTrace();

         } finally {

             bossGroup.shutdownGracefully();

             workerGroup.shutdownGracefully();

         }

     }

     public static void main(String[] args) {

         new HttpServer().run( "127.0.0.1" , 8001 );

     }

}

业务处理逻辑

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75

76

77

78

79

80

81

82

83

public class HttpServerHandler extends

         SimpleChannelInboundHandler<FullHttpRequest> {

     @Override

     protected void messageReceived(ChannelHandlerContext ctx,

             FullHttpRequest fullHttpRequest) throws Exception {

         // 构造返回数据

         JSONObject jsonRootObj = new JSONObject();

         JSONObject jsonUserInfo = new JSONObject();

         jsonUserInfo.put( "id" , 1 );

         jsonUserInfo.put( "name" , "张三" );

         jsonUserInfo.put( "password" , "123" );

         jsonRootObj.put( "userInfo" , jsonUserInfo);

         // 获取传递的数据

         Map<String, Object> params = getParamsFromChannel(ctx, fullHttpRequest);

         jsonRootObj.put( "params" , params);

         FullHttpResponse response = new DefaultFullHttpResponse(HTTP_1_1, OK);

         response.headers().set(CONTENT_TYPE, "application/json; charset=UTF-8" );

         StringBuilder bufRespose = new StringBuilder();

         bufRespose.append(jsonRootObj.toJSONString());

         ByteBuf buffer = Unpooled.copiedBuffer(bufRespose, CharsetUtil.UTF_8);

         response.content().writeBytes(buffer);

         buffer.release();

         ctx.writeAndFlush(response).addListener(ChannelFutureListener.CLOSE);

     }

     /**

      * 获取传递的参数

      *

      * @param ctx

      * @param fullHttpRequest

      * @return

      * @throws UnsupportedEncodingException

      */

     private static Map<String, Object> getParamsFromChannel(

             ChannelHandlerContext ctx, FullHttpRequest fullHttpRequest)

             throws UnsupportedEncodingException {

         HttpHeaders headers = fullHttpRequest.headers();

         String strContentType = headers.get( "Content-Type" ).trim();

         System.out.println( "ContentType:" + strContentType);

         Map<String, Object> mapReturnData = new HashMap<String, Object>();

         if (fullHttpRequest.getMethod() == HttpMethod.GET) {

             // 处理get请求

             QueryStringDecoder decoder = new QueryStringDecoder(

                     fullHttpRequest.getUri());

             Map<String, List<String>> parame = decoder.parameters();

             for (Entry<String, List<String>> entry : parame.entrySet()) {

                 mapReturnData.put(entry.getKey(), entry.getValue().get( 0 ));

             }

             System.out.println( "GET方式:" + parame.toString());

         } else if (fullHttpRequest.getMethod() == HttpMethod.POST) {

             // 处理POST请求

             if (strContentType.contains( "x-www-form-urlencoded" )) {

                 HttpPostRequestDecoder decoder = new HttpPostRequestDecoder(

                         new DefaultHttpDataFactory( false ), fullHttpRequest);

                 List<InterfaceHttpData> postData = decoder.getBodyHttpDatas();

                 for (InterfaceHttpData data : postData) {

                     if (data.getHttpDataType() == HttpDataType.Attribute) {

                         MemoryAttribute attribute = (MemoryAttribute) data;

                         mapReturnData.put(attribute.getName(),

                                 attribute.getValue());

                     }

                 }

             } else if (strContentType.contains( "application/json" )) {

                 // 解析json数据

                 ByteBuf content = fullHttpRequest.content();

                 byte [] reqContent = new byte [content.readableBytes()];

                 content.readBytes(reqContent);

                 String strContent = new String(reqContent, "UTF-8" );

                 System.out.println( "接收到的消息" + strContent);

                 JSONObject jsonParamRoot = JSONObject.parseObject(strContent);

                 for (String key : jsonParamRoot.keySet()) {

                     mapReturnData.put(key, jsonParamRoot.get(key));

                 }

             } else {

                 FullHttpResponse response = new DefaultFullHttpResponse(

                         HTTP_1_1, HttpResponseStatus.INTERNAL_SERVER_ERROR);

                 ctx.writeAndFlush(response).addListener(

                         ChannelFutureListener.CLOSE);

             }

             System.out.println( "POST方式:" + mapReturnData.toString());

         }

         return mapReturnData;

     }

}

支持Get和PostContentType为application/json、x-www-form-urlencoded的处理。

用Postman亲测无问题。

Netty处理简单Http请求的例子

废话不多说 上代码

HttpHelloWorldServerInitializer.java

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

import io.netty.channel.ChannelInitializer;

   import io.netty.channel.ChannelPipeline;

   import io.netty.channel.socket.SocketChannel;

   import io.netty.handler.codec.http.HttpServerCodec;

   import io.netty.handler.ssl.SslContext;

   public class HttpHelloWorldServerInitializer extends ChannelInitializer<SocketChannel> {

       private final SslContext sslCtx;

       public HttpHelloWorldServerInitializer(SslContext sslCtx) {

          this .sslCtx = sslCtx;

       }

       @Override

       public void initChannel(SocketChannel ch) {

           ChannelPipeline p = ch.pipeline();

           if (sslCtx != null ) {

               p.addLast(sslCtx.newHandler(ch.alloc()));

           }

           p.addLast( new HttpServerCodec());

           p.addLast( new HttpHelloWorldServerHandler());

       }

   }

HttpHelloWorldServerHandler.java

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

import io.netty.buffer.Unpooled;

import io.netty.channel.ChannelFutureListener;

import io.netty.channel.ChannelHandlerAdapter;

import io.netty.channel.ChannelHandlerContext;

import io.netty.handler.codec.http.DefaultFullHttpResponse;

import io.netty.handler.codec.http.FullHttpResponse;

import io.netty.handler.codec.http.HttpHeaderUtil;

import io.netty.handler.codec.http.HttpHeaderValues;

import io.netty.handler.codec.http.HttpRequest;

import static io.netty.handler.codec.http.HttpHeaderNames.*;

import static io.netty.handler.codec.http.HttpResponseStatus.*;

import static io.netty.handler.codec.http.HttpVersion.*;

   public class HttpHelloWorldServerHandler extends ChannelHandlerAdapter {

       private static final byte [] CONTENT = { 'H' , 'e' , 'l' , 'l' , 'o' , ' ' , 'W' , 'o' , 'r' , 'l' , 'd' };

       @Override

       public void channelReadComplete(ChannelHandlerContext ctx) {

           ctx.flush();

       }

       @Override

       public void channelRead(ChannelHandlerContext ctx, Object msg) {

           if (msg instanceof HttpRequest) {

               HttpRequest req = (HttpRequest) msg;

               if (HttpHeaderUtil.is100ContinueExpected(req)) {

                   ctx.write( new DefaultFullHttpResponse(HTTP_1_1, CONTINUE));

               }

               boolean keepAlive = HttpHeaderUtil.isKeepAlive(req);

               FullHttpResponse response = new DefaultFullHttpResponse(HTTP_1_1, OK, Unpooled.wrappedBuffer(CONTENT));

               response.headers().set(CONTENT_TYPE, "text/plain" );

               response.headers().setInt(CONTENT_LENGTH, response.content().readableBytes());

               if (!keepAlive) {

                   ctx.write(response).addListener(ChannelFutureListener.CLOSE);

               } else {

                   response.headers().set(CONNECTION, HttpHeaderValues.KEEP_ALIVE);

                   ctx.write(response);

               }

           }

       }

       @Override

       public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) {

           cause.printStackTrace();

           ctx.close();

       }

   }

HttpHelloWorldServer.java

?

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

import io.netty.bootstrap.ServerBootstrap;

import io.netty.channel.Channel;

import io.netty.channel.ChannelOption;

import io.netty.channel.EventLoopGroup;

import io.netty.channel.nio.NioEventLoopGroup;

import io.netty.channel.socket.nio.NioServerSocketChannel;

import io.netty.handler.logging.LogLevel;

import io.netty.handler.logging.LoggingHandler;

import io.netty.handler.ssl.SslContext;

import io.netty.handler.ssl.util.SelfSignedCertificate;

/**

  * An HTTP server that sends back the content of the received HTTP request

  * in a pretty plaintext form.

  */

public final class HttpHelloWorldServer {

       static final boolean SSL = System.getProperty( "ssl" ) != null ;

       static final int PORT = Integer.parseInt(System.getProperty( "port" , SSL? "8443" : "8080" ));

       public static void main(String[] args) throws Exception {

           // Configure SSL.

           final SslContext sslCtx;

           if (SSL) {

               SelfSignedCertificate ssc = new SelfSignedCertificate();

               sslCtx = SslContext.newServerContext(ssc.certificate(), ssc.privateKey());

           } else {

               sslCtx = null ;

           }

           // Configure the server.

           EventLoopGroup bossGroup = new NioEventLoopGroup( 1 );

           EventLoopGroup workerGroup = new NioEventLoopGroup();

           try {

               ServerBootstrap b = new ServerBootstrap();

               b.option(ChannelOption.SO_BACKLOG, 1024 );

               b.group(bossGroup, workerGroup)

                .channel(NioServerSocketChannel. class )

                .handler( new LoggingHandler(LogLevel.INFO))

                .childHandler( new HttpHelloWorldServerInitializer(sslCtx));

               Channel ch = b.bind(PORT).sync().channel();

               System.err.println( "Open your web browser and navigate to " +

                       (SSL? "https" : "http" ) + "://127.0.0.1:" + PORT + '/' );

               ch.closeFuture().sync();

           } finally {

               bossGroup.shutdownGracefully();

               workerGroup.shutdownGracefully();

           }

       }

}

以上为个人经验,希望能给大家一个参考,也希望大家多多支持。

原文链接:https://blog.csdn.net/BtWangZhi/article/details/80303577

查看更多关于关于Netty--Http请求处理方式的详细内容...

  阅读:14次