专栏首页xyjincanTCP 长连接小尝试

TCP 长连接小尝试

版权声明:本文为博主原创文章,转载请保留出处 https://blog.csdn.net/xyjincan/article/details/69357504

TCP 长连接小尝试,demo

本文学习了这两天看了不少tcp的使用细节,也看了不少有用的前辈经验,这里只是简单总结一下,有些奇怪的地方,BufferedReader,sendUrgentData。

  • 面临的问题是:写一个第三方程序信息接收服务器,协议上完全被动,等待连接接收消息。

服务端主要逻辑更新

堵塞的(BufferedReader)读取每条信息
        InputStream inputStream = null;
        InputStreamReader inputStreamReader = null;
        BufferedReader bufferedReader = null;

        try {
            // 获取一个输入流,接收服务端的信息
            inputStream = (InputStream) socket.getInputStream();
            // 包装成字符流,提高效率,如果有乱码问题
            inputStreamReader = new InputStreamReader(inputStream, "xxx");
            bufferedReader = new BufferedReader(inputStreamReader);

            char[] rcchar = new char[REVEIVEBUFFERSIZE];
            while (run) {//长连接读取远程信息,当连接断开会抛出异常
                int len = bufferedReader.read(rcchar);
                if(len==-1){//连接中断,,,           
                    throw new Exception("read socket err");
                }
                String crtstr = String.valueOf(rcchar, 0, len);
                System.out.println(new Date() + " : " + crtstr);
            }

        } catch (Exception e) {
            //与客户端连接中断
            try {
                bufferedReader.close();
                inputStreamReader.close();
                inputStream.close();
                socket.close();
            } catch (IOException e1) {
            }
        }

服务端主要逻辑

当serversocket接收到连接时,开启一个线程服务,非堵塞读取

class XXXConnect extends Thread {
    // 定义系统信息接收延迟:一秒
    private static final int receiveDelayMS = 1000;
    // 接收缓存8k,可能含多条数据,粘包等等。
    private static final int REVEIVEBUFFERSIZE = 1024 * 8;


    private Socket socket;
    private InputStream in;
    private boolean run = true;
    private byte[] receiveData = new byte[REVEIVEBUFFERSIZE];

    public XXXConnect(Socket socket) {

        this.socket = socket;
        try {
            in = socket.getInputStream();
        } catch (IOException e) {
            run = false;
            try {
                socket.close();
            } catch (IOException e1) {
            }
        }
    }

    @Override
    public void run() {
        try {
            while (run) {
                // 从远程读取数据时,远程连接断开将抛出异常
                //(Software caused connection abort: recv failed)
                int len = in.read(receiveData, 0, REVEIVEBUFFERSIZE);
                if (len != -1) {
                    System.out.println(new Date() 
                        + "receive:" + new String(receiveData, 0, len));
                }
                Thread.sleep(receiveDelayMS);
                // 测试:异常表明远程连接断开:Connection reset by peer: send
                // 发送任意数据:测试连接是否正常(心跳)
                socket.sendUrgentData(0xFF);
            }
            socket.close();
        } catch (Exception e) {

        }
    }

}

客户端发送测试

多次发送数据,然后服务端接收

            // 创建Socket对象
            Socket socket = new Socket("127.0.0.1", 11101);
            // 根据输入输出流和服务端连接
            OutputStream outputStream = (OutputStream) socket.getOutputStream();// 获取一个输出流,向服务端发送信息
            PrintWriter printWriter = new PrintWriter(outputStream);// 将输出流包装成打印流
            int ccc = 40;
            while (ccc > 0) {
                //Thread.sleep(1200);
                printWriter.print("服务端你ashfgehjsfbehjdsfbsjffj219278 27 3 好,我是Balla_兔子");
                printWriter.flush();
                ccc--;
            }

            Thread.sleep(10000);//等待那边服务器接收玩消息退出,
            System.out.println("bye server");
            printWriter.close();
            outputStream.close();
            socket.close();

这些写完后,发现了一个问题发送sendUrgentData 影响对方的报文接收。

            int ccc = 30;
            while (ccc > 0) {
                socket.sendUrgentData(0xFF);
                printWriter.print(ccc +  "服务端你ashfgehjsfbehjdsfbsjffj219278 27 3 好,我是Balla_兔子");
                printWriter.flush();
                //Thread.sleep(3000);
                ccc--;
            }
  1. windows下,如果A给B,发送一段报文,同时也发送多次socket.sendUrgentData(0xFF) ,B接收到的报文会缺失部分。
  2. 我又试了试linux下,如果A给B,发送一段报文,同时也发送多次socket.sendUrgentData(0xFF) ,A接收到的报文会混入未知字符。 Microsoft Windows [版本 10.0.14393] java version “1.8.0_91” Java(TM) SE Runtime Environment (build 1.8.0_91-b14) Java HotSpot(TM) 64-Bit Server VM (build 25.91-b14, mixed mode) Linux 4.10.6-200.fc25.x86_64 #1 SMP Mon Mar 27 14:06:23 UTC 2017 x86_64 x86_64 x86_64 GNU/Linux java version “1.8.0_111” Java(TM) SE Runtime Environment (build 1.8.0_111-b14) Java HotSpot(TM) 64-Bit Server VM (build 25.111-b14, mixed mode)

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • SpringMVC 中文乱码

    版权声明:本文为博主原创文章,转载请保留出处 ...

    xyjincan
  • java程序打包后JAR后运行特别慢原因

    版权声明:本文为博主原创文章,转载请保留出处 ...

    xyjincan
  • 自动批量删除全部微博(自动翻页加载)

    版权声明:本文为博主原创文章,转载请保留出处 ...

    xyjincan
  • 工位上的Python——简单SSH服务器

    最近在看python网络方面的知识,发现使用socket编写一些小的服务器真是太方便了,简单几行代码就能实现一个服务器,真是高大上呀,废话少说,直接上代码:

    用户2398817
  • Errno 9: Bad file de

       写了一个循环检测端口的程序,循环的次数多了,会报Errno 9: Bad file descriptor in python socket错误。程序如下...

    用户2398817
  • Socket.IO + Express实现的跨浏览器、子域的聊天室

    实例中用到了(实例在Windows XP下运行):Node.js、Socket.IO、Express.js、jade、stylus

    meteoric
  • socket读写返回值的处理

    在调用socket读写函数read(),write()时,都会有返回值。如果没有正确处理返回值,就可能引入一些问题 总结了以下几点 1当read()或者writ...

    用户1117071
  • CSS中的选择器

    版权声明:本文为博主原创文章,转载请注明出处。 ...

    魏晓蕾
  • PHP网络技术(四)——Socket简介

    PHP网络技术(四)——Socket简介 (原创内容,转载请注明来源,谢谢) Socket又称为套接字,是操作系统提供的通信层的API,通过套接字,应用程序可以...

    用户1327360
  • 工具| 诸神之眼nmap定制化之NSE进阶

    上一期斗哥跟大家介绍了Nmap中NSE脚本和常见的NSE的API,本期将为大家介绍Nmap的库文件以及如何利用Nmap的自身库将nmap的扫描结果保存在数据中。...

    漏斗社区

扫码关注云+社区

领取腾讯云代金券