netty与springboot的整合

netty框架

在网络编程领域,Netty是Java的一个优秀的框架,他将java的复杂和难以使用的关于OIO和NIO的一些框架
进行了封装,使其隐藏在易用的api后面。总之,如果你想编写高性能的网络服务,那么使用Netty就没错了。
目前各个大公司比如google,facebook等公司都在使用Netty框架,很多项目比如dubbo和Elasticsearch等就使用了Netty.

netty和springboot的整合

之前一直使用的都是springboot框架,习惯了spring的容器,于是就想着把netty也放到容器中以便于方便使用。
这次先用个demo先实现下,以后有更好的方式的时候再来更新。
首先是 pom.xml 文件


<project xmlns="http://maven.apache.org/POM/4.0.0"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0modelVersion>

    <groupId>liqiangzgroupId>
    <artifactId>netty-testartifactId>
    <version>0.0.1-SNAPSHOTversion>
    <packaging>jarpackaging>
    <parent>
        <groupId>org.springframework.bootgroupId>
        <artifactId>spring-boot-starter-parentartifactId>
        <version>2.0.3.RELEASEversion>
    parent>
    <dependencies>
        <dependency>
            <groupId>org.springframework.bootgroupId>
            <artifactId>spring-boot-configuration-processorartifactId>
            <optional>trueoptional>
        dependency>
        <dependency>
            <groupId>io.nettygroupId>
            <artifactId>netty-allartifactId> 
            <version>4.1.32.Finalversion>
            <scope>compilescope>
        dependency>
        <dependency>
            <groupId>org.springframework.bootgroupId>
            <artifactId>spring-boot-autoconfigureartifactId>
        dependency>
        <dependency>
            <groupId>org.springframework.bootgroupId>
            <artifactId>spring-boot-starter-loggingartifactId>
        dependency>
        <dependency>
            <groupId>org.springframework.bootgroupId>
            <artifactId>spring-boot-starter-log4jartifactId>
            <version>1.3.8.RELEASEversion>
        dependency>
    dependencies>
    <repositories>
        <repository>
            <id>aliyunmavenid>
            <url>http://maven.aliyun.com/nexus/content/groups/public/url>
        repository>
    repositories>
    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.bootgroupId>
                <artifactId>spring-boot-maven-pluginartifactId>
            plugin>
        plugins>
    build>

project>

然后是 启动main方法
在这里实现了CommandLineRunner接口,并重写了run方法,以便在springboot启动后就立即启动netty服务。

package io.liqiangz.server;

import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

/**
 * The type Netty application.
 * @author liqiangz
 */
@SpringBootApplication
public class NettyApplication implements CommandLineRunner {

    public static void main(String[] args) {
        SpringApplication.run(NettyApplication.class, args);
    }

    @Override
    public void run(String... strings) throws Exception {
        EchoServer echoServer = new EchoServer(8080);
        echoServer.start();
    }
}

接下来就是netty服务启动引导类,很简单的一个echo服务

package io.liqiangz.server;

import io.netty.bootstrap.ServerBootstrap;
import io.netty.channel.ChannelFuture;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.EventLoopGroup;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.SocketChannel;
import io.netty.channel.socket.nio.NioServerSocketChannel;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.net.InetSocketAddress;

/**
 * @author     :liqiangz.
 * @date       :Created in 21:03 2018/12/15
 */
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 {
        final EchoServerHandler serverHandler = new EchoServerHandler();
        log.info("启动服务");
        EventLoopGroup group = new NioEventLoopGroup();
        try {
            ServerBootstrap b = new ServerBootstrap();
            b.group(group)
                    .channel(NioServerSocketChannel.class)
                    .localAddress(new InetSocketAddress(port))
                    .childHandler(new ChannelInitializer<SocketChannel>() {

                        @Override
                        protected void initChannel(SocketChannel ch) throws Exception {
                            ch.pipeline().addLast(serverHandler);
                        }
                    });
            ChannelFuture f = b.bind().sync();
            f.channel().closeFuture().sync();
        }finally {
            group.shutdownGracefully().sync();
        }
    }
}

serverHandler类

package io.liqiangz.server;

import io.netty.buffer.ByteBuf;
import io.netty.channel.ChannelFutureListener;
import io.netty.channel.ChannelHandler.*;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelInboundHandlerAdapter;
import io.netty.util.CharsetUtil;

/**
 * @author     :liqiang.
 * @date       :Created in 21:04 2018/12/15
 */
@Sharable
public class EchoServerHandler extends ChannelInboundHandlerAdapter {
    @Override
    public void channelRead(ChannelHandlerContext ctx, Object msg){
        ByteBuf in = (ByteBuf) msg;
        System.out.println("Server received: " + in.toString(CharsetUtil.UTF_8));
        ctx.write(in);
    }

    @Override
    public void channelReadComplete(ChannelHandlerContext ctx){
        ctx.writeAndFlush(ChannelFutureListener.CLOSE);
    }

    @Override
    public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause){
        cause.printStackTrace();
        ctx.close();
    }

}

你可能感兴趣的:(java)