中文字幕av专区_日韩电影在线播放_精品国产精品久久一区免费式_av在线免费观看网站

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

Springboot中怎么用Netty開啟UDP服務方式

發布時間:2021-11-16 13:28:05 來源:億速云 閱讀:299 作者:小新 欄目:開發技術

這篇文章主要介紹了Springboot中怎么用Netty開啟UDP服務方式,具有一定借鑒價值,感興趣的朋友可以參考下,希望大家閱讀完這篇文章之后大有收獲,下面讓小編帶著大家一起了解一下。

Netty

Netty是一種提供網絡編程的工具,是對socket編程的一例優秀的包裝,支持TCP、UDP、FTP等協議。我們可以用Netty開發自己的http服務器、udp服務器、FTP服務器,RPC服務器等

Netty大受歡迎的原因:

  • 并發高

Netty支持NIO編程,NIO的持支,可以大大提升并發性能。

  • 傳輸快

Netty NIO的一個特性是零拷貝,直接在內存中開辟一塊,剩去了socket緩沖區,

  • 封裝好

接下來寫一個簡單的udp demo。大體思路:

  • 寫一個netty的 基于UDP的Server 用來接受數據

  • 寫個一處理類,用于對接受的數據進行處理,然后返回信息

新建一個springboot項目。在pom中引入jar

pom.xml

       <!--springboot version 我用的是2.1.3.RELEASE-->
		 <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter</artifactId>
            <version>2.1.3.RELEASE</version>
        </dependency>
       
       <!--web模塊的啟動器 -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <!-- netty依賴 springboot2.x自動導入版本 -->
        <dependency>
            <groupId>io.netty</groupId>
            <artifactId>netty-all</artifactId>
        </dependency>
        
		<!-- 這里我用到了@slf4j 所以引入這個jar -->
      <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <optional>true</optional>
        </dependency>

創建NettyUDPServer

Channel 通道的類型

  • NioSocketChannel, 代表異步的客戶端 TCP Socket 連接.

  • NioServerSocketChannel, 異步的服務器端 TCP Socket 連接.

  • NioDatagramChannel, 異步的 UDP 連接

  • NioSctpChannel, 異步的客戶端 Sctp 連接.

  • NioSctpServerChannel, 異步的 Sctp 服務器端連接.

  • OioSocketChannel, 同步的客戶端 TCP Socket 連接.

  • OioServerSocketChannel, 同步的服務器端 TCP Socket 連接.

  • OioDatagramChannel, 同步的 UDP 連接

  • OioSctpChannel, 同步的 Sctp 服務器端連接.

  • OioSctpServerChannel, 同步的客戶端 TCP Socket 連接.

Bootstrap 是 Netty 提供的一個便利的工廠類,可以通過它來完成 Netty 的客戶端或服務器端的 Netty 初始化。

package com.demo.udpdemo.UDPServer;
import com.demo.udpdemo.handler.BootNettyUdpSimpleChannelInboundHandler;
import io.netty.bootstrap.Bootstrap;
import io.netty.channel.ChannelFuture;
import io.netty.channel.ChannelOption;
import io.netty.channel.EventLoopGroup;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.nio.NioDatagramChannel;
import lombok.extern.slf4j.Slf4j;
/**
 * @author 
 */
@Slf4j
public class BootNettyUdpServer {
    /**
     * 啟動服務
     */
    public void bind(int port) {
        log.info("-------------------------------udpServer-------------------------");
        //表示服務器連接監聽線程組,專門接受 accept 新的客戶端client 連接
        EventLoopGroup bossLoopGroup  = new NioEventLoopGroup();
        try {
            //1,創建netty bootstrap 啟動類
            Bootstrap serverBootstrap = new Bootstrap();
            //2、設置boostrap 的eventLoopGroup線程組
            serverBootstrap = serverBootstrap.group(bossLoopGroup);
            //3、設置NIO UDP連接通道
            serverBootstrap = serverBootstrap.channel(NioDatagramChannel.class);
            //4、設置通道參數 SO_BROADCAST廣播形式
            serverBootstrap = serverBootstrap.option(ChannelOption.SO_BROADCAST, true);
            //5、設置處理類 裝配流水線
            serverBootstrap = serverBootstrap.handler(new BootNettyUdpSimpleChannelInboundHandler());
            //6、綁定server,通過調用sync()方法異步阻塞,直到綁定成功
            ChannelFuture f = serverBootstrap.bind(port).sync();
            log.info(BootNettyUdpServer.class.getName()+" started and listend on "+f.channel().localAddress());
            //7、監聽通道關閉事件,應用程序會一直等待,直到channel關閉
            f.channel().closeFuture().sync();
        } catch (Exception e) {
            // TODO: handle exception
        } finally {
            System.out.println("netty udp close!");
            //8 關閉EventLoopGroup,
            bossLoopGroup.shutdownGracefully();
        }
    }
}

NettyUdpSimpleChannelInboundHandler

package com.demo.udpdemo.handler;
import io.netty.buffer.Unpooled;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.SimpleChannelInboundHandler;
import io.netty.channel.socket.DatagramPacket;
import io.netty.util.CharsetUtil;
import lombok.extern.slf4j.Slf4j;
/**
 * @author 
 */
@Slf4j
public class BootNettyUdpSimpleChannelInboundHandler extends SimpleChannelInboundHandler<DatagramPacket> {
    @Override
    protected void channelRead0(ChannelHandlerContext ctx, DatagramPacket msg) throws Exception {
        try {
            String strdata = msg.content().toString(CharsetUtil.UTF_8);
            //打印收到的消息
            log.info("---------------------receive data--------------------------");
            log.info(strdata);
            log.info("---------------------receive data--------------------------");
            //收到udp消息后,可通過此方式原路返回的方式返回消息,例如返回時間戳
            ctx.writeAndFlush(new DatagramPacket(Unpooled.copiedBuffer("ok", CharsetUtil.UTF_8), msg.sender()));
        } catch (Exception e) {
        }
    }
}

修改啟動類,啟動執行UDPServer.bind方法,啟動udpServer

@SpringBootApplication
@EnableAsync
public class UdpDemoApplication implements CommandLineRunner {
    public static void main(String[] args) {
        SpringApplication app = new SpringApplication(UdpDemoApplication.class);
        app.run(args);
    }
    @Async
    @Override
    public void run(String... args){
       new BootNettyUdpServer().bind(51000);
    }
}

test

在test類下面,新建一個test方法

sendUdpRequestTest

  //定義客戶端ip
  private static final String SERVER_HOSTNAME = "127.0.0.1";
    // 服務器端口
    private static final int SERVER_PORT = 51000;
    // 本地發送端口
    private static final int LOCAL_PORT = 8888;
 @Test
    public void sendUdpRequestTest() {
        try {
            // 1,創建udp服務。通過DatagramSocket對象。
            DatagramSocket socket = new DatagramSocket(LOCAL_PORT);
            // 2,確定數據,并封裝成數據包。DatagramPacket(byte[] buf, int length, InetAddress
            // address, int port)
            byte[] buf = "hello".getBytes();
            DatagramPacket dp = new DatagramPacket(buf, buf.length, InetAddress.getByName(SERVER_HOSTNAME),
                    SERVER_PORT);
            // 3,通過socket服務,將已有的數據包發送出去。通過send方法。
            socket.send(dp);
            // 4,關閉資源。
            socket.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

結果

2021-09-03 13:14:47.912 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : ---------------------receive data--------------------------
2021-09-03 13:14:47.912 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : 你好,世界
2021-09-03 13:14:47.912 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : ---------------------receive data--------------------------
2021-09-03 13:16:11.748 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : ---------------------receive data--------------------------
2021-09-03 13:16:11.748 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : 你好,世界
2021-09-03 13:16:11.748 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : ---------------------receive data--------------------------
2021-09-03 13:17:11.664 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : ---------------------receive data--------------------------
2021-09-03 13:17:11.664 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : hello
2021-09-03 13:17:11.664 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : ---------------------receive data--------------------------
2021-09-03 13:17:32.714 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : ---------------------receive data--------------------------
2021-09-03 13:17:32.714 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : hello
2021-09-03 13:17:32.714 INFO 11608 --- [ntLoopGroup-2-1] .BootNettyUdpSimpleChannelInboundHandler : ---------------------receive data--------------------------

感謝你能夠認真閱讀完這篇文章,希望小編分享的“Springboot中怎么用Netty開啟UDP服務方式”這篇文章對大家有幫助,同時也希望大家多多支持億速云,關注億速云行業資訊頻道,更多相關知識等著你來學習!

向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

谷城县| 陕西省| 静乐县| 读书| 万州区| 阿坝县| 湟源县| 凉山| 大方县| 如东县| 庄河市| 安平县| 扶沟县| 嘉义市| 余姚市| 霍城县| 分宜县| 夏津县| 临颍县| 蒲江县| 武汉市| 息烽县| 象州县| 庆阳市| 涿州市| 米林县| 上林县| 宝清县| 西乌| 九龙坡区| 济宁市| 万载县| 华亭县| 尤溪县| 北京市| 宁南县| 左权县| 叙永县| 长白| 瑞安市| 浦县|