最近接到一个关于写UDP服务器的任务,然后去netty官网下载了netty的jar包(netty-4.0.49.Final.tar.bz2),解压后,可以看到上面有不少example,找到其中的关于UDP的例子。

在此学习。

直接上栗子:

服务端:QuoteOfTheMomentServer.java(其中的代码稍微有点修改,测试了下redis,需要的同学可以直接把jar包中的栗子拷贝下来即可)

 package com.wj.test;

 import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import io.netty.bootstrap.Bootstrap;
import io.netty.channel.ChannelOption;
import io.netty.channel.EventLoopGroup;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.nio.NioDatagramChannel; /**
* A UDP server that responds to the QOTM (quote of the moment) request to a {@link QuoteOfTheMomentClient}.
*
* Inspired by <a href="http://docs.oracle.com/javase/tutorial/networking/datagrams/clientServer.html">the official
* Java tutorial</a>.
*/
public final class QuoteOfTheMomentServer { private static final int PORT = Integer.parseInt(System.getProperty("port", "8889")); private static final Logger log=LoggerFactory.getLogger(QuoteOfTheMomentServer.class); public static void main(String[] args) throws Exception {
EventLoopGroup group = new NioEventLoopGroup();
log.info("QuoteOfTheMomentServer" + " + start");
try {
Bootstrap b = new Bootstrap();
b.group(group)
.channel(NioDatagramChannel.class)
.option(ChannelOption.SO_BROADCAST, true)
.handler(new QuoteOfTheMomentServerHandler()); b.bind(PORT).sync().channel().closeFuture().await();
} finally {
group.shutdownGracefully();
}
}
}
 
 /*
* Copyright 2012 The Netty Project
*
* The Netty Project licenses this file to you under the Apache License,
* version 2.0 (the "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at:
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*/
package com.wj.test; 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 redis.clients.jedis.Jedis; import java.util.Random;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory; import com.wj.test.redis.RedisUtil; public class QuoteOfTheMomentServerHandler extends SimpleChannelInboundHandler<DatagramPacket> { private static final Logger log=LoggerFactory.getLogger(QuoteOfTheMomentServerHandler.class); private static final Random random = new Random(); // Quotes from Mohandas K. Gandhi:
private static final String[] quotes = {
"Where there is love there is life.",
"First they ignore you, then they laugh at you, then they fight you, then you win.",
"Be the change you want to see in the world.",
"The weak can never forgive. Forgiveness is the attribute of the strong.",
}; private static String nextQuote() {
int quoteId;
synchronized (random) {
quoteId = random.nextInt(quotes.length);
}
return quotes[quoteId];
} @Override
public void channelRead0(ChannelHandlerContext ctx, DatagramPacket packet) throws Exception {
System.err.println(packet); if (packet.content().toString(CharsetUtil.UTF_8) != null ) { System.out.println(packet.content().toString(CharsetUtil.UTF_8));
System.out.println(packet.sender()); Jedis jedisK = RedisUtil.getJedis();
jedisK.select(1);
jedisK.lpush("test:udp:msg", packet.content().toString(CharsetUtil.UTF_8)); ctx.write(new DatagramPacket(
// Unpooled.copiedBuffer("QOTM: " + nextQuote(), CharsetUtil.UTF_8), packet.sender()));
Unpooled.copiedBuffer("QOTM: " + "sometest", CharsetUtil.UTF_8), packet.sender()));
}else {
log.info("Exception");
}
} @Override
public void channelReadComplete(ChannelHandlerContext ctx) {
ctx.flush();
} @Override
public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) {
cause.printStackTrace();
// We don't close the channel because we can keep serving requests.
}
}

客户端:QuoteOfTheMomentClient.java

 /*
* Copyright 2012 The Netty Project
*
* The Netty Project licenses this file to you under the Apache License,
* version 2.0 (the "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at:
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*/
package com.wj.test; import io.netty.bootstrap.Bootstrap;
import io.netty.buffer.Unpooled;
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.DatagramPacket;
import io.netty.channel.socket.nio.NioDatagramChannel;
import io.netty.util.CharsetUtil;
import io.netty.util.internal.SocketUtils; /**
* A UDP broadcast client that asks for a quote of the moment (QOTM) to {@link QuoteOfTheMomentServer}.
*
* Inspired by <a href="http://docs.oracle.com/javase/tutorial/networking/datagrams/clientServer.html">the official
* Java tutorial</a>.
*/
public final class QuoteOfTheMomentClient { static final int PORT = Integer.parseInt(System.getProperty("port", "8889")); public static void main(String[] args) throws Exception { EventLoopGroup group = new NioEventLoopGroup();
try {
Bootstrap b = new Bootstrap();
b.group(group)
.channel(NioDatagramChannel.class)
.option(ChannelOption.SO_BROADCAST, true)
.handler(new QuoteOfTheMomentClientHandler()); Channel ch = b.bind(0).sync().channel(); // Broadcast the QOTM request to port 8080.
String str = "38567071 13801783144 18917565379 20170621183115 20170621183118 05";
ch.writeAndFlush(new DatagramPacket(
Unpooled.copiedBuffer(str, CharsetUtil.UTF_8),
SocketUtils.socketAddress("localhost", PORT))).sync(); // QuoteOfTheMomentClientHandler will close the DatagramChannel when a
// response is received. If the channel is not closed within 5 seconds,
// print an error message and quit.
if (!ch.closeFuture().await(5000)) {
System.err.println("QOTM request timed out.");
}
} finally {
group.shutdownGracefully();
}
}
}
 package com.wj.test;

 /*
* Copyright 2012 The Netty Project
*
* The Netty Project licenses this file to you under the Apache License,
* version 2.0 (the "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at:
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*/ import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.SimpleChannelInboundHandler;
import io.netty.channel.socket.DatagramPacket;
import io.netty.util.CharsetUtil; public class QuoteOfTheMomentClientHandler extends SimpleChannelInboundHandler<DatagramPacket> { @Override
public void channelRead0(ChannelHandlerContext ctx, DatagramPacket msg) throws Exception {
String response = msg.content().toString(CharsetUtil.UTF_8);
if (response.startsWith("QOTM: ")) {
System.out.println("++++Quote of the Moment: " + response.substring(6));
ctx.close();
}
} @Override
public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) {
cause.printStackTrace();
ctx.close();
}
}

该官方的栗子确实可以很好的实现UDP服务器的功能,甚至你可以写个jedis,与redis链接起来,但是往往项目开发中简单的结合是远远不够的。比如我们要将次UDP服务器与spring框架或者是spring boot框架结合起来,并使用RedisTemplate的操作类访问Redis或者使用JPA链接MySQL的时候,那么该server就要更改了,下一篇文章将会讲解此UDP服务器如何与spring boot框架整合起来,并使用RedisTemplate的操作类访问Redis。

netty学习:UDP服务器与Spring整合的更多相关文章

  1. netty学习:UDP服务器与Spring整合(2)

    上一篇文章中,介绍了netty实现UDP服务器的栗子. 本文将会对UDP服务器与spring boot整合起来,并使用RedisTemplate的操作类访问Redis和使用Spring DATA JP ...

  2. Struts2学习笔记——Struts2与Spring整合

      Struts2与Spring整合后,可以使用Spring的配置文件applicationContext.xml来描述依赖关系,在Struts2的配置文件struts.xml来使用Spring创建的 ...

  3. MyBatis学习(三)---MyBatis和Spring整合

    想要了解MyBatis基础的朋友可以通过传送门: MyBatis学习(一)---配置文件,Mapper接口和动态SQL http://www.cnblogs.com/ghq120/p/8322302. ...

  4. Spring框架学习(4)spring整合hibernate

    内容源自:spring整合hibernate    spring整合注解形式的hibernate 这里和上一部分学习一样用了模板模式, 将hibernate开发流程封装在ORM层提供的模板类Hiber ...

  5. Mybatis学习(六)————— Spring整合mybatis

    一.Spring整合mybatis思路 非常简单,这里先回顾一下mybatis最基础的根基, mybatis,有两个配置文件 全局配置文件SqlMapConfig.xml(配置数据源,全局变量,加载映 ...

  6. Spring学习笔记六:Spring整合Hibernate

    转载请注明原文地址:http://www.cnblogs.com/ygj0930/p/6785323.html  前言:整合概述 Spring整合Hibernate主要是把Hibernate中常用的S ...

  7. Spring框架学习(5)spring整合struts2

    内容源自:spring整合struts2 一.spring框架对struts等表现层框架的整合原理 : 使用spring的ioc容器管理struts中用于处理请求的Action 将Action配置成i ...

  8. Netty学习第四章 spring boot整合netty的使用

    现在大多数项目都是基于spring boot进行开发,所以我们以spring boot作为开发框架来使用netty.使用spring boot的一个好处就是能给将netty的业务拆分出来,并通过spr ...

  9. MyBatis学习(二):与Spring整合(非注解方式配置MyBatis)

    搭建SpringMVC的-->传送门<-- 一.环境搭建: 目录结构: 引用的JAR包: 如果是Maven搭建的话,pom.xml的配置如下: <?xml version=" ...

随机推荐

  1. 【Codeforces 464A】No to Palindromes!

    [链接] 我是链接,点我呀:) [题意] 题意 [题解] 因为原序列没有任何长度超过2的回文串. 所以,我们在改变的时候,只要时刻保证改变位置s[i]和s[i-1]以及s[i-2]都不相同就好. 因为 ...

  2. Win32编程API 基础篇 -- 4.消息循环

    消息循环 理解消息循环 为了编写任何即使是最简单的程序,了解windows程序的消息循环和整个消息发送结构是非常有必要的.既然我们已经尝试了一点消息处理的东西,我们应该对整个程序有更深入的理解,如果你 ...

  3. [bzoj 1059][ZJOI 2007]矩阵游戏(二分图最大匹配)

    题目:http://www.lydsy.com/JudgeOnline/problem.php?id=1059 分析:不论如何交换,同一行或同一列的点还是同一行或同一列,如果我们称最后可以排成题目要求 ...

  4. vim 安装插件的网站

    我在想, 怎么让vim可以 显示目录结构呢?一个目录里面的文件? vim插件的网站:http://www.vim.org/scripts/script.php?script_id=1658 原文:ht ...

  5. git bash here真牛!

    git bash here真牛! 在Windows上面安装了git,在文件夹里面空白处右键点击,选择git bash here: 随手敲了几个命令:ls,ls -a,which ls,who, fin ...

  6. [React Native] Prevent the On-screen Keyboard from Covering up Text Inputs

    When you bring up the on screen keyboard in a mobile app, it will cover any text input or buttons on ...

  7. Android MTP 文件浏览Demo

    本apk实现了MTP文件浏览的简单功能. 通过Demo apk能够浏览连接到当前设备上的MTP设备上的文件. Demo路径:http://download.csdn.net/detail/sailin ...

  8. Redis源代码分析(三十)--- pubsub公布订阅模式

    今天学习了Redis中比較高大上的名词,"公布订阅模式".公布订阅模式这个词在我最開始接触听说的时候是在JMS(Java Message Service)java消息服务中听说的. ...

  9. raywenderlich.com的Swift编程风格指南

    翻译自:https://github.com/raywenderlich/swift-style-guide 这个风格指南可能和你从其它地方看到的不同,我们的焦点主要集中在互联网和文章上的可读性.创建 ...

  10. Android studio一些设置项

    ------Appearance选项------------------------------------------------------------- Cylic scrolling in l ...