SpringBoot+RXTXcomm实现Java串口通信 读取串口数据以及发送数据

2023-05-16

记录一下使用SpringBoot+RXTXcomm实现Java串口通信,使用Java语言开发串口,对串口进行读写操作。
RXTXcomm.jar这个包支持的系统较多,但是更新太慢,在win系统下使用没有问题,但是在centos的工控机系统里使用读取和发送有问题,至今没能解决,报错的日志也记录一下


serial port com start success
#
# A fatal error has been detected by the Java Runtime Environment:
#
#  SIGSEGV (0xb) at pc=0x00007f5e636f75da, pid=18871, tid=0x00007f5e635ee700
#
# JRE version: Java(TM) SE Runtime Environment (8.0_144-b01) (build 1.8.0_144-b01)
# Java VM: Java HotSpot(TM) 64-Bit Server VM (25.144-b01 mixed mode linux-amd64 compressed oops)
# Problematic frame:
# C  [librxtxSerial.so+0x75da]  Java_gnu_io_RXTXPort_nativeDrain+0xea
#
# Failed to write core dump. Core dumps have been disabled. To enable core dumping, try "ulimit -c unlimited" before starting Java again
#
# An error report file with more information is saved as:
# /home/hs_err_pid18871.log
#
# If you would like to submit a bug report, please visit:
#   http://bugreport.java.com/bugreport/crash.jsp
# The crash happened outside the Java Virtual Machine in native code.
# See problematic frame for where to report the bug.
#
已放弃
[root@localhost home]# 
Java HotSpot(TM) Server VM warning: You have loaded library /home/jdk18/jre/lib/i386/librxtxSerial.so which might have disabled stack guard. The VM will try to fix the stack guard now.
It's highly recommended that you fix the library with 'execstack -c <libfile>', or link it with '-z noexecstack'.
java.lang.UnsatisfiedLinkError: /home/jdk18/jre/lib/i386/librxtxSerial.so: /home/jdk18/jre/lib/i386/librxtxSerial.so: 错误 ELF 类: ELFCLASS64 (Possible cause: architecture word width mismatch) thrown while loading gnu.io.RXTXCommDriver
15:33:11.580 spring-boot-logging [main] INFO  o.s.b.a.l.ConditionEvaluationReportLoggingListener - 

19:26:03.323 spring-boot-logging [main] INFO  c.z.d.serialport.SerialPortManager - open serial port success:/dev/ttyS1
serial port com start success
19:26:15.326 spring-boot-logging [Thread-5] INFO  c.z.data.serialport.SerialPortThread - stepCount--200
#
# A fatal error has been detected by the Java Runtime Environment:
#
#  SIGSEGV (0xb) at pc=0x00007ffa604a7733, pid=17020, tid=0x00007ffa6019e700
#
# JRE version: Java(TM) SE Runtime Environment (8.0_144-b01) (build 1.8.0_144-b01)
# Java VM: Java HotSpot(TM) 64-Bit Server VM (25.144-b01 mixed mode linux-amd64 compressed oops)
# Problematic frame:
# C  [librxtxSerial.so+0x7733]  Java_gnu_io_RXTXPort_nativeDrain+0xc3
#
# Core dump written. Default location: /usr/local/core or core.17020
#
# An error report file with more information is saved as:
# /usr/local/hs_err_pid17020.log
#
# If you would like to submit a bug report, please visit:
#   http://bugreport.java.com/bugreport/crash.jsp
# The crash happened outside the Java Virtual Machine in native code.
# See problematic frame for where to report the bug.
#
已放弃(吐核)


因此如果要使用RXTXcomm.jar这个串口包,建议在win系统下使用更好一些,其他系统使用可能出现莫名其妙的问题,如果非要在linux(centos)系统使用,推荐使用jSerialComm.jar

<dependency>
    <groupId>com.fazecast</groupId>
    <artifactId>jSerialComm</artifactId>
    <version>2.9.2</version>
</dependency>

这里记录使用SpringBoot加RXTXcomm在win10系统下的使用
mfz-rxtx-2.2-20081207-win-x64的下载地址

http://fizzed.com/oss/rxtx-for-java

myw
根据自己的系统选择对应的下载包
myw
myw
从readme.txt得知编译的环境特别旧了,将来的使用定然是越来越少

win-x86, win-x64, ia64
-----------------------------------------------
Built using Microsoft Visual C++ 2008 - not MinGW. The
x86 and x64 versions are native and do not rely on
any other non-standard windows libraries.  Just drop
in the compiled .dlls that are specific to the version
of Java you run. If you installed the 64-bit version
of the JDK, then install the x64 build.

I've tested the x86 and x64 version with Windows 2008,
2003, and Vista SP1.


linux-i386 & linux-x86_64
-----------------------------------------------
Built using CentOS 5.2 and gcc 4.1.2.

Just drop in the compiled .dlls that are specific to
the version of Java you run. If you installed the 64-bit
version of the JDK, then install the x64 build.

I've tested the x86 and x64 versions with x86 and x64
versions of CentOS 5.0 and 5.2.

myw
根据文档,先将rxtxSerial.dll和rxtxParallel.dll放在指定的目录内
我自己电脑的JAVA_HOME
myw
那么文件存放位置
myw
至于 RXTXcomm.jar包不放在文档里的位置,放在具体的项目内引用(根据个人喜好来,我直接按照文档的方式去放,发现不起作用)

pom.xml

<?xml version="1.0" encoding="UTF-8"?>
<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.0</modelVersion>
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.0.5.RELEASE</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>

    <groupId>boot.example.mfz.rxtx</groupId>
    <artifactId>boot-example-serial-port-mfz-rxtx-2.0.5</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>boot-example-serial-port-mfz-rxtx-2.0.5</name>
    <description>Demo project for Spring Boot</description>

    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
        <java.version>1.8</java.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <dependency>
            <groupId>gnu.io</groupId>
            <artifactId>RXTXcomm</artifactId>
            <version>2.2</version>
            <scope>system</scope>
            <systemPath>${project.basedir}/libs/jar/RXTXcomm.jar</systemPath>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <configuration>
                    <mainClass>com.example.BootRXTXApplication</mainClass>
                    <includeSystemScope>true</includeSystemScope><!--外部进行打包-->
                </configuration>
                <executions>
                    <execution>
                        <goals>
                            <goal>repackage</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>
        </plugins>
    </build>

</project>

这里有个点儿

<systemPath>${project.basedir}/libs/jar/RXTXcomm.jar</systemPath>

myw
BootRXTXApplication.java

package com.example;


import com.example.serialport.SerialPortManager;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.scheduling.annotation.EnableAsync;
import org.springframework.scheduling.annotation.EnableScheduling;
import javax.annotation.PreDestroy;
import java.io.IOException;
import java.util.List;


@SpringBootApplication
@EnableScheduling
@EnableAsync
public class BootRXTXApplication implements CommandLineRunner {

    private final Logger log =  LoggerFactory.getLogger(this.getClass());

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

    @Override
    public void run(String... args) throws Exception {
        try{
            List<String> portList = SerialPortManager.getSerialPortList();
            if(!portList.isEmpty()){
                log.info(portList.toString());
                SerialPortManager.connectSerialPort();
            }
        } catch (Exception e){
            log.error("获取串口信息失败");
        }

    }

    @PreDestroy
    public void destroy() {
        SerialPortManager.closeSerialPort();
        System.exit(0);
    }



}

测试往串口发数据
SerialPortSendController.java

package com.example.controller;

import com.example.serialport.ConvertHexStrAndStrUtils;
import com.example.serialport.SerialPortManager;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;


@Controller
public class SerialPortSendController {

    //  http://localhost:8781/sendTest?message=mywmyyhtw

    @GetMapping(value = "/sendTest")
    @ResponseBody
    public String sendStringTopic(@RequestParam(name="message",required = true) String message) throws Exception {
        SerialPortManager.sendSerialPortData(ConvertHexStrAndStrUtils.strToHexStr(message));
        return "success";
    }

}

字符串以及16进制以及字节之间的转换工具类ConvertHexStrAndStrUtils.java

package com.example.serialport;

import java.nio.charset.StandardCharsets;

public class ConvertHexStrAndStrUtils {

    private static final char[] HEXES = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'};

    public static String bytesToHexStr(byte[] bytes) {
        if (bytes == null || bytes.length == 0) {
            return null;
        }
        StringBuilder hex = new StringBuilder(bytes.length * 2);
        for (byte b : bytes) {
            hex.append(HEXES[(b >> 4) & 0x0F]);
            hex.append(HEXES[b & 0x0F]);
        }
        return hex.toString().toUpperCase();
    }

    public static byte[] hexStrToBytes(String hex) {
        if (hex == null || hex.length() == 0) {
            return null;
        }
        char[] hexChars = hex.toCharArray();
        byte[] bytes = new byte[hexChars.length / 2];   // 如果 hex 中的字符不是偶数个, 则忽略最后一个
        for (int i = 0; i < bytes.length; i++) {
            bytes[i] = (byte) Integer.parseInt("" + hexChars[i * 2] + hexChars[i * 2 + 1], 16);
        }
        return bytes;
    }

    public static String strToHexStr(String str) {
        StringBuilder sb = new StringBuilder();
        byte[] bs = str.getBytes();
        int bit;
        for (int i = 0; i < bs.length; i++) {
            bit = (bs[i] & 0x0f0) >> 4;
            sb.append(HEXES[bit]);
            bit = bs[i] & 0x0f;
            sb.append(HEXES[bit]);
        }
        return sb.toString().trim();
    }

    public static String hexStrToStr(String hexStr) {
        //能被16整除,肯定可以被2整除
        byte[] array = new byte[hexStr.length() / 2];
        try {
            for (int i = 0; i < array.length; i++) {
                array[i] = (byte) (0xff & Integer.parseInt(hexStr.substring(i * 2, i * 2 + 2), 16));
            }
            hexStr = new String(array, StandardCharsets.UTF_8);
        } catch (Exception e) {
            e.printStackTrace();
            return "";
        }
        return hexStr;
    }

}

串口工具类 我这里默认写死COM1 波特率9600
SerialPortManager.java

package com.example.serialport;

import gnu.io.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.List;
import java.util.TooManyListenersException;
import java.util.concurrent.TimeUnit;

public class SerialPortManager {

    private static final Logger log =  LoggerFactory.getLogger(SerialPortManager.class);

    public static String SERIAL_PORT_NUMBER = "COM1";

    public static final int SERIAL_BAUD_RATE = 9600;

    public static volatile long SERIAL_CALLBACK_TIME = System.currentTimeMillis()/1000;

    public static volatile boolean SERIAL_PORT_STATE = false;

    public static volatile SerialPort SERIAL_PORT_OBJECT = null;

    //  获得系统可用的端口名称列表
    @SuppressWarnings("unchecked")
    public static List<String> getSerialPortList() {
        List<String> systemPorts = new ArrayList<>();
        //获得系统可用的端口
        Enumeration<CommPortIdentifier> portList = CommPortIdentifier.getPortIdentifiers();
        while (portList.hasMoreElements()) {
            String portName = portList.nextElement().getName();//获得端口的名字
            systemPorts.add(portName);
        }
        return systemPorts;
    }

    public static void connectSerialPort(){
        try {
            closeSerialPort();
            TimeUnit.MILLISECONDS.sleep(4000);
            if(openSerialPort()){
                System.out.println("serial port com start success");
            }
        } catch (InterruptedException ex) {
            ex.printStackTrace();
        }
    }

    //  打开串口  设置中断和监听事件
    public static boolean openSerialPort() {
        try {
            CommPortIdentifier portIdentifier = CommPortIdentifier.getPortIdentifier(SERIAL_PORT_NUMBER);
            CommPort commPort = portIdentifier.open(SERIAL_PORT_NUMBER, 3000);
            if(commPort == null){return false;}
            //判断是不是串口
            if (commPort instanceof SerialPort) {
                SerialPort serialPort = (SerialPort) commPort;
                //设置串口参数(波特率,数据位8,停止位1,校验位无)
                serialPort.setSerialPortParams(SERIAL_BAUD_RATE, SerialPort.DATABITS_8, SerialPort.STOPBITS_1, SerialPort.PARITY_NONE);
                // 当有数据到达时唤醒数据接收线程
                serialPort.notifyOnDataAvailable(true);
                // 当串口连接中断时唤醒中断线程
                serialPort.notifyOnBreakInterrupt(true);
                serialPort.notifyOnCarrierDetect(true);
                serialPort.notifyOnDSR(true);
                // 添加串口监听事件
                serialPort.addEventListener(new SerialPortListener(new SerialPortCallback()));
                SerialPortManager.SERIAL_PORT_OBJECT = serialPort;
                SerialPortManager.SERIAL_PORT_STATE = true;
                log.info("open serial port success:" + SERIAL_PORT_NUMBER);
                return true;
            } else {
                //是其他类型的端口
                throw new NoSuchPortException();
            }
        } catch (NoSuchPortException e) {
            log.error("not find serial port:" + e.getMessage());
        } catch (PortInUseException e) {
            log.error("the serial port used:" + e.getMessage());
        } catch (UnsupportedCommOperationException e) {
            log.error("open others serial port:" + e.getMessage());
        } catch (TooManyListenersException e) {
            log.error("the more listener this serial port:"+ e.getMessage());
        }

        return false;
    }

    //  关闭串口
    public static void closeSerialPort() {
        SERIAL_PORT_STATE = false;
        if (SERIAL_PORT_OBJECT != null) {
            SERIAL_PORT_OBJECT.close();
            SERIAL_PORT_OBJECT = null;
            log.info("serial port close");
        }
    }

    //  向串口发送数据
    public static void sendSerialPortData(String data) {
        OutputStream outputStream = null;
        try {
            outputStream = SERIAL_PORT_OBJECT.getOutputStream();
            outputStream.write(ConvertHexStrAndStrUtils.hexStrToBytes(data));
            outputStream.flush();
            log.info("send data success:"+data);
        } catch (IOException e) {
            log.error("read data exception:"+e.getMessage());
        } finally {
            try {
                outputStream.close();
            } catch (IOException e) {
                log.error("read data inputStream close error:"+ e.getMessage());
            }
        }
    }

    //  从串口读取数据
    public static byte[] readSerialPortData() {
        InputStream in = null;
        byte[] bytes = {};
        try {
            TimeUnit.MILLISECONDS.sleep(200);
            in = SERIAL_PORT_OBJECT.getInputStream();
            byte[] readBuffer = new byte[1];
            int bytesNum = in.read(readBuffer);
            while (bytesNum > 0) {
                bytes = concat(bytes, readBuffer);
                bytesNum = in.read(readBuffer);
            }
        } catch (IOException | InterruptedException e) {
            e.printStackTrace();
        } finally {
            try {
                if (in != null) {
                    in.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return bytes;
    }


    public static byte[] concat(byte[] firstArray, byte[] secondArray) {
        if (firstArray == null || secondArray == null) {
            return null;
        }
        byte[] bytes = new byte[firstArray.length + secondArray.length];
        System.arraycopy(firstArray, 0, bytes, 0, firstArray.length);
        System.arraycopy(secondArray, 0, bytes, firstArray.length, secondArray.length);
        return bytes;
    }

}

SerialPortListener.java

package com.example.serialport;

import gnu.io.SerialPortEvent;
import gnu.io.SerialPortEventListener;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class SerialPortListener implements SerialPortEventListener {

    private final Logger log =  LoggerFactory.getLogger(this.getClass());

    private final SerialPortCallback serialPortCallback;

    public SerialPortListener(SerialPortCallback serialPortCallback) {
        this.serialPortCallback = serialPortCallback;
    }

    public void serialEvent(SerialPortEvent serialPortEvent) {
        log.warn("SerialPortTestListener:"+serialPortEvent.getEventType());
        SerialPortManager.SERIAL_CALLBACK_TIME = System.currentTimeMillis()/1000;
        if (serialPortEvent.getEventType() == SerialPortEvent.DATA_AVAILABLE) {
            if (serialPortCallback != null) {
                serialPortCallback.dataAvailable();
            }
        }

    }




}

从串口接收数据的SerialPortCallback.java

package com.example.serialport;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class SerialPortCallback {

    private final Logger log =  LoggerFactory.getLogger(this.getClass());

    public void dataAvailable() {
        try {
            //throw new Exception();
            byte[] data = SerialPortManager.readSerialPortData();
            String s = ConvertHexStrAndStrUtils.bytesToHexStr(data);
            log.info("rev--data:"+s);
        } catch (Exception e) {
            log.error(e.toString());
        }
    }



}

定时器SerialPortTimer.java

package com.example.serialport;

import org.springframework.scheduling.annotation.Async;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Service;

import java.io.IOException;
import java.text.DateFormat;
import java.text.SimpleDateFormat;


@Service
public class SerialPortTimer {


    @Async
    @Scheduled(cron = "0 0/5 * * * ?")
    public void timeSerialPortScheduled() throws IOException, InterruptedException {
        long now = System.currentTimeMillis();
        DateFormat format = new SimpleDateFormat("yyyy-MM-dd:HH:mm:ss");
        System.out.println("timeSerialPortScheduled--"+format.format(now));
        long interval = 2 * 60 * 60;
        long rebootInterval = 24 * 60 * 60;
        long difference =  now/1000 - SerialPortManager.SERIAL_CALLBACK_TIME;

        // 当2个小时内收不到串口数据重启串口
        if(difference > interval){
            SerialPortManager.connectSerialPort();
        }

        //  当24小时内都还是收不到串口数据重启系统
        if(difference > rebootInterval){
            try {
                String osName = System.getProperty("os.name");
                if(osName.startsWith("Windows")) {
                    Runtime.getRuntime().exec("shutdown -r -t 0 -f");
                } else if(osName.startsWith("Linux")){
                    Runtime.getRuntime().exec("reboot");
                }
            } catch (IOException e) {
                throw new RuntimeException(e);
            }
        }

    }

}

代码结构

│  pom.xml
│  
├─doc
│  │  mfz-rxtx-2.2-20081207-win-x64.zip
│  │  mfz-rxtx-2.2-20081207-win-x86.zip
│  │  
│  └─mfz-rxtx-2.2-20081207-win-x64
│          BuildProperties.txt
│          Install.txt
│          Readme.txt
│          ReleaseNotes.txt
│          RXTXcomm.jar
│          rxtxParallel.dll
│          rxtxSerial.dll
│          
├─libs
│  └─jar
│          jna.jar
│          RXTXcomm.jar
│          
├─src
│  ├─main
│  │  ├─java
│  │  │  └─com
│  │  │      └─example
│  │  │          │  BootRXTXApplication.java
│  │  │          │  
│  │  │          ├─controller
│  │  │          │      SerialPortSendController.java
│  │  │          │      
│  │  │          └─serialport
│  │  │                  ConvertHexStrAndStrUtils.java
│  │  │                  SerialPortCallback.java
│  │  │                  SerialPortListener.java
│  │  │                  SerialPortManager.java
│  │  │                  SerialPortTimer.java
│  │  │                  
│  │  └─resources
│  │          application.properties
│  │          logback-spring.xml
│  │          
│  └─test
│      └─java
│          └─com
│              └─example
│                      BootRXTXApplicationTest.java
│            

接收数据测试 通过com2 向 com1发送数据 那么就算SpringBoot串口接收数据
myw
可以看到控制台有打印数据
myw
发送数据测试

http://localhost:8781/sendTest?message=mywmyyhtw

可以看到控制台
myw
对应的接收端
myw

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

SpringBoot+RXTXcomm实现Java串口通信 读取串口数据以及发送数据 的相关文章

随机推荐

  • 联合索引的最左匹配原则的成因

    联合索引的最左匹配原则的成因 上面我们只看的是单一的索引 xff0c 接下来咱们来看看联合索引 xff0c 也就是回答第二个问题 联合索引的最左匹配原则的成因 什么是联合索引呢 xff0c 就是由多列组成的索引了 那亦要了解其成因 xff0
  • 腾讯云轻量服务器的Ubuntu如何使用root(根)用户登陆ssh/Shell/terminal/终端/WindTerm/FinalShell

    Ubuntu 系统的默认用户名是 ubuntu xff0c 并在安装过程中默认不设置 root 帐户和密码 您如有需要 xff0c 可在设置中开启允许 root 用户登录 具体操作步骤如下 xff1a 使用 ubuntu 帐户登录轻量应用服
  • Ubuntu安装sshd服务

    ubuntu安装ssh服务 一 安装shhd SSH分客户端openssh client和openssh server 如果你只是想登陆别的机器的SSH只需要安装openssh client xff08 ubuntu有默认安装 xff0c
  • Linux环境(六)--资源与限制

    资源与限制 运行在Linux系统上的程序是有资源限制的 这些也许是硬件引起的限制 例如内存 xff0c 也许由系统策略引起的限制 例如 xff0c 允许 的CPU时间 xff0c 或者是实现的限制 例如 xff0c 整数的尺寸或是文件名允许
  • 遇到了C/C++控制台程序无法输入中文的情况

    其实C C 43 43 控制台程序无法cin中文的情况并不是你使用了string xff0c string是能输入并保存中文的 xff1b 经过一番探究 xff0c 我发现主要的问题是文件的编码和控制台所处的代码页 xff08 控制台的编码
  • Jpg2Dcm中文乱码问题

    Jpg2Dcm中文乱码问题 最近老板提出了一个新的功能要求 xff0c 希望可以把图片转成dcm 在实现功能的问题中遇见了很多问题和掉过许多坑 于是在此记录下来 问题 xff1a 第一次在进行Jpg2Dcm时 xff0c 可以进行图片转dc
  • 神经网络的数学表达式,神经网络的数学理论

    什么是神经网络 神经网络可以指向两种 xff0c 一个是生物神经网络 xff0c 一个是人工神经网络 生物神经网络 xff1a 一般指生物的大脑神经元 xff0c 细胞 xff0c 触点等组成的网络 xff0c 用于产生生物的意识 xff0
  • python装饰器详解(四)---把参数传递给装饰器

    因为装饰器必须接收一个函数当做参数 所以 不可以直接把被装饰函数的参数传递给装饰器 装饰器就是一个普通的函数 xff0c 回顾 def my decorator func print 34 I am an ordinary function
  • Motion Deblurring图像运动去模糊代码

    http www di ens fr whyte Efficient Deblurring for Shaken and Partially Saturated Images http www di ens fr willow resear
  • maven执行install时报错 The packaging for this project did not assign a file to the build artifact

    问题描述 maven中执行plugins下面的install install时会报如下错误 span class token class name Failed span span class token keyword to span s
  • realsense相机两种获取相机内外参的方式

    https www it610 com article 1296417297711308800 htm 命令 xff1a rs sensor control 这个命令是一个exe文件 xff0c 可以去 C Program Files x8
  • wget设置代理

    1 在bash shell中设定代理 basrhc export http proxy 61 34 166 111 53A 167 3128 34 export ftp proxy 61 34 166 111 53A 167 3128 34
  • chown,chgrp,chmod,u+s,g+s,o+t

    chown user file directory change owner 将后面的目标文件或者目录的所有者替换成 user chgrp group file directory change group 将目标文件或者目录的所有组替换成
  • Segment Routing笔记(一)

    SR 理论 一 MPLS TE缺点 RSVP TE大部分都是为了FRR的目的不支持ECMP所有流量都需要在隧道里诞生了 战术型 TE xff0c 只在需要的时候使用 术语 TI LFA 与拓扑无关的无环路备份 xff0c 能保证备份路径的最
  • Springboot+Netty搭建UDP服务端

    UDP是一个无连接协议 xff0c 应用范围很大 xff0c 对于一些低功耗的设备可以使用UDP方式向云端推送消息信息 xff0c 也可以在推送消息时收到从云端原路返回的消息 xff0c 使用Netty 43 SpringBoot方式可以快
  • Springboot+Netty搭建UDP客户端

    使用Netty 43 SpringBoot方式可以快速地开发一套基于UDP协议的服务端程序 xff0c 同样的也可以开发客户端 xff0c 一般使用UDP都是使用原生的方式 xff0c 发送消息后就不管不问 xff0c 也就是不需要确定消息
  • Springboot+Netty搭建MQTT协议的服务端(基础Demo)

    Netty是业界最流行的nio框架之一 xff0c 结合springboot可以满足快速开发 MQTT xff08 Message Queuing Telemetry Transport xff0c 消息队列遥测传输协议 xff09 xff
  • SpringBoot+Shiro+Jwt+Vue+elementUI实现前后端分离单体系统Demo

    记录一下使用SpringBoot集成Shiro框架和Jwt框架实现前后端分离Web项目的过程 xff0c 后端使用SpringBoot整合Shiro 43 Jwt auth0 xff0c 前端使用vue 43 elementUI框架 xff
  • Centos系统安装RabbitMQ消息中间件

    记录一下在centos7 x下面安装RabbitMQ消息中间件 RabbitMQ是一个开源而且遵循 AMQP协议实现的基于 Erlang语言编写 xff0c 因此安装RabbitMQ之前是需要部署安装Erlang环境的 先安装Erlang
  • SpringBoot+RXTXcomm实现Java串口通信 读取串口数据以及发送数据

    记录一下使用SpringBoot 43 RXTXcomm实现Java串口通信 xff0c 使用Java语言开发串口 xff0c 对串口进行读写操作 RXTXcomm jar这个包支持的系统较多 xff0c 但是更新太慢 xff0c 在win