SpringBoot+Netty 实现Http Server简单实例;跨域,请求参数解析(GET, POST)

参考文章 https://blog.csdn.net/yzh_1346983557/article/details/84769914

接下来贴上我的学习过程,加了一些补充,如果这套看不懂的同学推荐先看我的这篇博文:https://blog.csdn.net/qq_41850449/article/details/88864219

但是后来我发现这样写太冗余了,大家也可以看我这篇
https://blog.csdn.net/qq_41850449/article/details/88992460

  1. 添加依赖并且消除Tomcat依赖

     <dependency>
         <groupId>io.netty</groupId>
         <artifactId>netty-all</artifactId>
         <version>4.1.31.Final</version>
     </dependency>
     
     <dependency>
         <groupId>org.springframework.boot</groupId>
         <artifactId>spring-boot-starter-web</artifactId>
         <exclusions>
             <exclusion>
                 <groupId>org.springframework.boot</groupId>
                 <artifactId>spring-boot-starter-tomcat</artifactId>          //该布为消除tomcat依赖
             </exclusion>
         </exclusions>
     </dependency>
    
  2. 建一个EchoServer类

     	public class EchoServer {
     		private final int port;
     		private Logger log = LoggerFactory.getLogger(this.getClass());
    
     		public EchoServer(int port)
     		{
     			this.port=port;
     		}
    
     		public void start() throws Exception{
     			EventLoopGroup group = new NioEventLoopGroup();
      			try
     			 {
          			ServerBootstrap serverBootstrap=new ServerBootstrap();
          			serverBootstrap.group(group)
                  		.localAddress(new InetSocketAddress(port))
                  		.channel(NioServerSocketChannel.class)
                  		.childHandler(new ChannelInitializer<SocketChannel>() {
                      		@Override
                      		protected void initChannel(SocketChannel channel) throws Exception {
                          			channel.pipeline().addLast(new HttpRequestDecoder());
                          			channel.pipeline().addLast(new HttpObjectAggregator(65535));
                          			channel.pipeline().addLast(new HttpResponseEncoder());
                          			channel.pipeline().addLast(new HttpHandler());     
                      				}              //顺序别乱写
                  				});
          			ChannelFuture f=serverBootstrap.bind().sync();
          			f.channel().closeFuture().sync();
      				}
     				 finally {
          				group.shutdownGracefully().sync();
     				 }
     		}
     	}
    
  3. 建一个HttpHandler类

     @ChannelHandler.Sharable
     public class HttpHandler extends SimpleChannelInboundHandler<Object> {
    
     @Override
     protected void channelRead0(ChannelHandlerContext ctx, Object obj) throws Exception {
     		FullHttpResponse response = new DefaultFullHttpResponse(
            HTTP_1_1, OK, Unpooled.wrappedBuffer("OK OK OK OK".getBytes()));
     		response.headers().set(CONTENT_TYPE, "text/plain"); //返回是字符串
    
    
     		//允许跨域访问
     		response.headers().set(ACCESS_CONTROL_ALLOW_ORIGIN,"*");
     		response.headers().set(ACCESS_CONTROL_ALLOW_HEADERS,"Origin, X-Requested-With, Content-Type, Accept");
     		response.headers().set(ACCESS_CONTROL_ALLOW_METHODS,"GET, POST, PUT,DELETE");
    
     		response.headers().set(CONTENT_LENGTH,
            response.content().readableBytes());
     		response.headers().set(CONNECTION, HttpHeaderValues.KEEP_ALIVE);
     		ctx.write(response);
    		ctx.flush();
    
     		FullHttpRequest fullHttpRequest=(FullHttpRequest) obj;
     		 // 将GET, POST所有请求参数转换成Map对象
     		Map<String, String> parmMap = new RequestParser(fullHttpRequest).parse();
     		System.out.println(parmMap);
     }
    
     	@Override
     	public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
    		//cause.printStackTrace();
     		ctx.close();
     		System.out.println("error");
     	}
    
  4. 参数解析类:

     public class RequestParser {
     	private FullHttpRequest fullReq;
    
     	/**
     		* 构造一个解析器
     		* @param req
     	*/
     	public RequestParser(FullHttpRequest req) {
     	this.fullReq = req;
     	}
    
     /**
     	* 解析请求参数
     	* @return 包含所有请求参数的键值对, 如果没有参数, 则返回空Map
     	 *
     	* @throws
     	* @throws IOException
     */
     	public Map<String, String> parse() throws Exception, IOException {
     		HttpMethod method = fullReq.method();
     		Map<String, String> parmMap = new HashMap<>();
    
     			if (HttpMethod.GET == method) {
         			// 是GET请求
         			QueryStringDecoder decoder = new QueryStringDecoder(fullReq.uri());
         			decoder.parameters().entrySet().forEach( entry -> {
             		// entry.getValue()是一个List, 只取第一个元素
             		parmMap.put(entry.getKey(), entry.getValue().get(0));
         			});
    			 } else if (HttpMethod.POST == method) {
         			// 是POST请求
         			HttpPostRequestDecoder decoder = new HttpPostRequestDecoder(fullReq);
         			decoder.offer(fullReq);
    
         			List<InterfaceHttpData> parmList = decoder.getBodyHttpDatas();
     	            for (InterfaceHttpData parm : parmList) {
    
             			Attribute data = (Attribute) parm;
             			parmMap.put(data.getName(), data.getValue());
         				}
     			} else {
        				 // 不支持其它方法
        				// throw new MethodNotSupportedException(""); // 这是个自定义的异常, 可删掉这一行
     				}
    
     			return parmMap;
     		}
     }
    
  5. 最后的一步。

     @SpringBootApplication
     	public class HttpWebsocketApplication implements CommandLineRunner {
    
     		 public static void main(String[] args) {
     			SpringApplication.run(HttpWebsocketApplication.class, args);
     		 }
    
     	 @Override
     		public void run(String... strings) throws Exception {
     		EchoServer echoServer = new EchoServer(7000);
     		echoServer.start();
     		}
     	}
    
  6. 这样就完成啦
    在这里插入图片描述

  • 0
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
实现心跳保活机制是为了确保网络连接的稳定性和可靠性,防止连接因长时间不活动而被关闭。在Spring Boot和Netty中,可以通过以下步骤实现心跳保活机制: 1. 创建一个Netty服务器并设置相关参数,如端口号和TCP参数。可以使用Spring Boot提供的`@Configuration`注解和Netty的`ServerBootstrap`类来完成这一步骤。 2. 使用Netty的`ChannelInitializer`类创建一个处理器来处理客户端的请求,并实现`ChannelInboundHandlerAdapter`类的`channelRead`方法。 3. 在处理器的`channelRead`方法中,判断收到的消息是否为心跳消息。可以根据消息内容或自定义的标识来判断是否为心跳消息。 4. 如果接收到的消息是心跳消息,可以通过向客户端发送一个固定的心跳响应消息来维持连接。可以使用Netty的`ctx.writeAndFlush()`方法来发送心跳响应消息。 5. 如果接收到的消息不是心跳消息,可以继续处理其他业务逻辑。 6. 在处理器的`channelInactive`方法中,可以处理连接断开时的逻辑。可以在此方法中关闭连接、释放资源等操作。 7. 在Netty服务器的配置中,设置心跳超时时间。可以使用Netty的`IdleStateHandler`类来实现心跳超时的检测和处理。 8. 在上述步骤完成后,运行Spring Boot应用程序,并使用客户端发送心跳消息来保持连接。可以通过不断发送心跳消息,来确保连接保持活动状态。 通过以上步骤,就可以在Spring Boot和Netty实现心跳保活机制,确保网络连接的稳定性和可靠性。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值