[v0.0.0] 原始哈勃服务器代码
commit
f016e02e75
@ -0,0 +1,2 @@
|
|||||||
|
/target/
|
||||||
|
/.idea/
|
@ -0,0 +1,132 @@
|
|||||||
|
<?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 https://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.1.5.RELEASE</version>
|
||||||
|
<relativePath/> <!-- lookup parent from repository -->
|
||||||
|
</parent>
|
||||||
|
<groupId>com.platform</groupId>
|
||||||
|
<artifactId>pass-through</artifactId>
|
||||||
|
<version>1.0.0</version>
|
||||||
|
<name>pass-through</name>
|
||||||
|
<description>Demo project for Spring Boot</description>
|
||||||
|
|
||||||
|
<properties>
|
||||||
|
<java.version>1.8</java.version>
|
||||||
|
</properties>
|
||||||
|
|
||||||
|
<dependencies>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-web</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.projectlombok</groupId>
|
||||||
|
<artifactId>lombok</artifactId>
|
||||||
|
<optional>true</optional>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-test</artifactId>
|
||||||
|
<scope>test</scope>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>io.netty</groupId>
|
||||||
|
<artifactId>netty-all</artifactId>
|
||||||
|
<version>4.1.32.Final</version>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.alibaba</groupId>
|
||||||
|
<artifactId>fastjson</artifactId>
|
||||||
|
<version>1.2.76</version>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter</artifactId>
|
||||||
|
<exclusions>
|
||||||
|
<exclusion>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-logging</artifactId>
|
||||||
|
</exclusion>
|
||||||
|
</exclusions>
|
||||||
|
</dependency>
|
||||||
|
<!-- log4j2 日志记录-->
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-log4j2</artifactId>
|
||||||
|
</dependency>
|
||||||
|
<!-- 加上这个才能辨认到log4j2.yml文件 -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.fasterxml.jackson.dataformat</groupId>
|
||||||
|
<artifactId>jackson-dataformat-yaml</artifactId>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-actuator</artifactId>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>io.springfox</groupId>
|
||||||
|
<artifactId>springfox-swagger2</artifactId>
|
||||||
|
<version>2.7.0</version>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>io.springfox</groupId>
|
||||||
|
<artifactId>springfox-swagger-ui</artifactId>
|
||||||
|
<version>2.7.0</version>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-data-redis</artifactId>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.apache.commons</groupId>
|
||||||
|
<artifactId>commons-pool2</artifactId>
|
||||||
|
</dependency>
|
||||||
|
</dependencies>
|
||||||
|
|
||||||
|
<build>
|
||||||
|
<plugins>
|
||||||
|
<plugin>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-maven-plugin</artifactId>
|
||||||
|
</plugin>
|
||||||
|
<!--<plugin>
|
||||||
|
<groupId>org.mybatis.generator</groupId>
|
||||||
|
<artifactId>mybatis-generator-maven-plugin</artifactId>
|
||||||
|
<version>1.3.2</version>
|
||||||
|
<executions>
|
||||||
|
<execution>
|
||||||
|
<id>Generate MyBatis Artifacts</id>
|
||||||
|
<goals>
|
||||||
|
<goal>generate</goal>
|
||||||
|
</goals>
|
||||||
|
</execution>
|
||||||
|
</executions>
|
||||||
|
<configuration>
|
||||||
|
<!– generator 工具配置文件的位置 –>
|
||||||
|
<configurationFile>src/main/resources/mybatis-generator/generatorConfig.xml</configurationFile>
|
||||||
|
<verbose>true</verbose>
|
||||||
|
<overwrite>true</overwrite>
|
||||||
|
</configuration>
|
||||||
|
<dependencies>
|
||||||
|
<dependency>
|
||||||
|
<groupId>mysql</groupId>
|
||||||
|
<artifactId>mysql-connector-java</artifactId>
|
||||||
|
<version>5.1.34</version>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.mybatis.generator</groupId>
|
||||||
|
<artifactId>mybatis-generator-core</artifactId>
|
||||||
|
<version>1.3.2</version>
|
||||||
|
</dependency>
|
||||||
|
</dependencies>
|
||||||
|
</plugin>-->
|
||||||
|
</plugins>
|
||||||
|
</build>
|
||||||
|
|
||||||
|
|
||||||
|
</project>
|
@ -0,0 +1,14 @@
|
|||||||
|
package com.platform;
|
||||||
|
|
||||||
|
|
||||||
|
import org.springframework.boot.SpringApplication;
|
||||||
|
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||||
|
|
||||||
|
@SpringBootApplication
|
||||||
|
public class BootApplication {
|
||||||
|
|
||||||
|
public static void main(String[] args) {
|
||||||
|
SpringApplication.run(BootApplication.class, args);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,29 @@
|
|||||||
|
package com.platform.config;
|
||||||
|
|
||||||
|
import org.springframework.stereotype.Component;
|
||||||
|
|
||||||
|
import javax.servlet.*;
|
||||||
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
@Component
|
||||||
|
public class ClientHttpFilter implements Filter {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain) throws IOException, ServletException {
|
||||||
|
HttpServletResponse response = (HttpServletResponse) res;
|
||||||
|
response.setHeader("Access-Control-Allow-Origin", "*");
|
||||||
|
response.setHeader("Access-Control-Allow-Methods", "POST, GET, OPTIONS, DELETE");
|
||||||
|
response.setHeader("Access-Control-Max-Age", "3600");
|
||||||
|
response.setHeader("Access-Control-Allow-Headers", "x-requested-with");
|
||||||
|
chain.doFilter(req, res);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void init(FilterConfig filterConfig) {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void destroy() {
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,14 @@
|
|||||||
|
package com.platform.config;
|
||||||
|
|
||||||
|
import lombok.Data;
|
||||||
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
|
import org.springframework.context.annotation.Configuration;
|
||||||
|
|
||||||
|
@Configuration
|
||||||
|
@Data
|
||||||
|
public class ServiceConfig {
|
||||||
|
@Value("${log.debug}")
|
||||||
|
private boolean debug;
|
||||||
|
@Value("${service.port}")
|
||||||
|
private Integer port;
|
||||||
|
}
|
@ -0,0 +1,219 @@
|
|||||||
|
package com.platform.controller;
|
||||||
|
|
||||||
|
import com.platform.model.ManyToMany;
|
||||||
|
import com.platform.model.OneToMany;
|
||||||
|
import com.platform.util.SessionCache;
|
||||||
|
import io.swagger.annotations.ApiImplicitParam;
|
||||||
|
import io.swagger.annotations.ApiImplicitParams;
|
||||||
|
import io.swagger.annotations.ApiModelProperty;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
import org.springframework.util.ObjectUtils;
|
||||||
|
import org.springframework.util.StringUtils;
|
||||||
|
import org.springframework.web.bind.annotation.*;
|
||||||
|
|
||||||
|
import java.util.*;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
|
||||||
|
@RestController
|
||||||
|
@Slf4j
|
||||||
|
public class ClientController {
|
||||||
|
@Autowired
|
||||||
|
private SessionCache sessionCache;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取已经连接上的session ip
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@GetMapping("/session/ips")
|
||||||
|
public List<String> getSessions() {
|
||||||
|
List<String> ips = new ArrayList<>();
|
||||||
|
Set set= sessionCache.tcpSession.keySet();
|
||||||
|
Iterator iterator = set.iterator();
|
||||||
|
while (iterator.hasNext()){
|
||||||
|
ips.add(iterator.next().toString());
|
||||||
|
}
|
||||||
|
return ips;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 添加一对一连接
|
||||||
|
*
|
||||||
|
* @param source
|
||||||
|
* @param target
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@PostMapping("/mapping/oneToOne")
|
||||||
|
public Boolean addSnMap(@RequestParam("source") String source, @RequestParam("target") String target) {
|
||||||
|
sessionCache.snToSnMap.put(source, target);
|
||||||
|
sessionCache.snToSnMap.put(target, source);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 添加一对多连接
|
||||||
|
* @param param
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@PostMapping("/mapping/oneToMany")
|
||||||
|
public Boolean addSnsMap(@RequestBody OneToMany param) {
|
||||||
|
List<String> list = param.getTarget();
|
||||||
|
List<String> target = list.stream().map(String::toUpperCase).collect(Collectors.toList());
|
||||||
|
String source = param.getSource().toUpperCase();
|
||||||
|
target.forEach(sn -> sessionCache.snToSnMap.put(sn, source));
|
||||||
|
if(!sessionCache.snList.contains(source)) {
|
||||||
|
sessionCache.snList.add(source);
|
||||||
|
}
|
||||||
|
List<String> oldTarget = sessionCache.snToListMap.get(source);
|
||||||
|
if (!ObjectUtils.isEmpty(oldTarget)) {
|
||||||
|
oldTarget.forEach(sn ->{
|
||||||
|
if (!target.contains(sn)) {
|
||||||
|
target.add(sn);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
sessionCache.snToListMap.put(source, target);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 添加一对一、一对多、多对多映射
|
||||||
|
* @param param
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@PostMapping("/mapping/all")
|
||||||
|
public Boolean addSourcesAndTargetsMap(@RequestBody ManyToMany param) {
|
||||||
|
List<String> targetList = param.getTarget().stream().map(String::toUpperCase).collect(Collectors.toList());
|
||||||
|
List<String> sourceList = param.getSource().stream().map(String::toUpperCase).collect(Collectors.toList());
|
||||||
|
List<String> sourceTmp = new ArrayList<>();
|
||||||
|
targetList.forEach(target->{
|
||||||
|
List<String> oldSource = sessionCache.mappingListMap.get(target);
|
||||||
|
if (!ObjectUtils.isEmpty(oldSource)) {
|
||||||
|
oldSource.forEach(sn ->{
|
||||||
|
if (!sourceList.contains(sn)) {
|
||||||
|
sourceList.add(sn);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
List<String> newSource= new ArrayList<>();
|
||||||
|
newSource.addAll(sourceList);
|
||||||
|
if (!sourceTmp.isEmpty()){
|
||||||
|
newSource.addAll(sourceTmp);
|
||||||
|
sourceTmp.clear();
|
||||||
|
}
|
||||||
|
sessionCache.mappingListMap.put(target, newSource);
|
||||||
|
});
|
||||||
|
List<String> targetTmp = new ArrayList<>();
|
||||||
|
sourceList.forEach(source ->{
|
||||||
|
List<String> oldTarget = sessionCache.mappingListMap.get(source);
|
||||||
|
if (!ObjectUtils.isEmpty(oldTarget)) {
|
||||||
|
oldTarget.forEach(sn ->{
|
||||||
|
if (!targetList.contains(sn)) {
|
||||||
|
targetTmp.add(sn);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
List<String> newTarget = new ArrayList<>();
|
||||||
|
newTarget.addAll(targetList);
|
||||||
|
if (!targetTmp.isEmpty()){
|
||||||
|
newTarget.addAll(targetTmp);
|
||||||
|
targetTmp.clear();
|
||||||
|
}
|
||||||
|
sessionCache.mappingListMap.put(source, newTarget);
|
||||||
|
});
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 删除映射关系
|
||||||
|
* @param param
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@PostMapping("/mapping/delete")
|
||||||
|
public Boolean deleteSourcesAndTargetsMap(@RequestBody ManyToMany param) {
|
||||||
|
List<String> sourceList = param.getSource().stream().map(String::toUpperCase).collect(Collectors.toList());
|
||||||
|
List<String> targetList = param.getTarget().stream().map(String::toUpperCase).collect(Collectors.toList());
|
||||||
|
List<String> all = new ArrayList<>();
|
||||||
|
all.addAll(sourceList);
|
||||||
|
all.addAll(targetList);
|
||||||
|
all.forEach(code ->{
|
||||||
|
List<String> valueList = sessionCache.mappingListMap.get(code);
|
||||||
|
List<String> deletedList = new ArrayList<>();
|
||||||
|
if (!ObjectUtils.isEmpty(valueList)) {
|
||||||
|
valueList.forEach(value ->{
|
||||||
|
if (all.contains(value)){
|
||||||
|
deletedList.add(value);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
deletedList.forEach(deleted -> valueList.remove(deleted));
|
||||||
|
if (valueList.size() > 0) {
|
||||||
|
sessionCache.mappingListMap.put(code, valueList);
|
||||||
|
} else{
|
||||||
|
sessionCache.mappingListMap.remove(code);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取一对一映射关系
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@GetMapping("/mapping/oneToOne")
|
||||||
|
public Map<String, String> getSnMap() {
|
||||||
|
return sessionCache.snToSnMap;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取一对多映射关系
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@GetMapping("/mapping/oneToMany")
|
||||||
|
public Map<String, List<String>> getSnListMap() {
|
||||||
|
return sessionCache.snToListMap;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取所有映射关系
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@GetMapping("/mapping/get")
|
||||||
|
public Map<String, List<String>> getTargetListMap() {
|
||||||
|
return sessionCache.mappingListMap;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 配置监控接口
|
||||||
|
*
|
||||||
|
* @param supervisor
|
||||||
|
* @param monitored
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@ApiImplicitParams({
|
||||||
|
@ApiImplicitParam(name = "supervisor", value = "监控者", required = true),
|
||||||
|
@ApiImplicitParam(name = "monitored", value = "被监控者", required = true),
|
||||||
|
})
|
||||||
|
@GetMapping("/sn/mapping/monitor/add")
|
||||||
|
@ApiModelProperty(value = "配置监控接口")
|
||||||
|
public Boolean addMonitorMap(String supervisor, String monitored) {
|
||||||
|
if(StringUtils.isEmpty(supervisor) || StringUtils.isEmpty(monitored)){
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
sessionCache.snToMonitorMap.clear();
|
||||||
|
sessionCache.snToMonitorMap.put(monitored,supervisor);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询监控关系
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@GetMapping("/sn/mapping/monitor/get")
|
||||||
|
@ApiModelProperty(value = "查询监控关系接口")
|
||||||
|
public Map<String,String> getMonitorMap() {
|
||||||
|
return sessionCache.snToMonitorMap;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,12 @@
|
|||||||
|
package com.platform.model;
|
||||||
|
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
import java.io.Serializable;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public class ManyToMany implements Serializable {
|
||||||
|
private List<String> source;
|
||||||
|
private List<String> target;
|
||||||
|
}
|
@ -0,0 +1,12 @@
|
|||||||
|
package com.platform.model;
|
||||||
|
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
import java.io.Serializable;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public class OneToMany implements Serializable {
|
||||||
|
private String source;
|
||||||
|
private List<String> target;
|
||||||
|
}
|
@ -0,0 +1,75 @@
|
|||||||
|
package com.platform.service;
|
||||||
|
|
||||||
|
import com.platform.config.ServiceConfig;
|
||||||
|
import com.platform.util.SessionCache;
|
||||||
|
import com.platform.util.StringUtil;
|
||||||
|
import io.netty.bootstrap.ServerBootstrap;
|
||||||
|
import io.netty.channel.*;
|
||||||
|
import io.netty.channel.nio.NioEventLoopGroup;
|
||||||
|
import io.netty.channel.socket.nio.NioServerSocketChannel;
|
||||||
|
import io.netty.handler.codec.bytes.ByteArrayDecoder;
|
||||||
|
import io.netty.handler.codec.bytes.ByteArrayEncoder;
|
||||||
|
import io.netty.handler.timeout.IdleStateHandler;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
import org.springframework.stereotype.Component;
|
||||||
|
|
||||||
|
import javax.annotation.PostConstruct;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
|
@Component
|
||||||
|
@Slf4j
|
||||||
|
public class ServerService {
|
||||||
|
|
||||||
|
public ChannelFuture mChannelFuture;
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private ServiceConfig config;
|
||||||
|
@Autowired
|
||||||
|
private StringUtil stringUtil;
|
||||||
|
@Autowired
|
||||||
|
private SessionCache sessionCache;
|
||||||
|
|
||||||
|
private void startServer() {
|
||||||
|
//服务端需要2个线程组 boss处理客户端连接 work进行客服端连接之后的处理
|
||||||
|
log.warn("【读取配置端口】 端口 = " + config.getPort());
|
||||||
|
EventLoopGroup boss = new NioEventLoopGroup();
|
||||||
|
EventLoopGroup work = new NioEventLoopGroup(10);
|
||||||
|
try {
|
||||||
|
ServerBootstrap bootstrap = new ServerBootstrap();
|
||||||
|
//服务器 配置
|
||||||
|
bootstrap.group(boss, work);
|
||||||
|
bootstrap.channel(NioServerSocketChannel.class);
|
||||||
|
bootstrap.childHandler(new ChannelInitializer<Channel>() {
|
||||||
|
@Override
|
||||||
|
protected void initChannel(Channel channel) throws Exception {
|
||||||
|
channel.pipeline().addLast(new ByteArrayDecoder());
|
||||||
|
channel.pipeline().addLast(new ByteArrayEncoder());
|
||||||
|
channel.pipeline().addLast(new IdleStateHandler(0, 0,
|
||||||
|
60 * 24, TimeUnit.MINUTES));
|
||||||
|
channel.pipeline().addLast(new InMessageHandler(sessionCache, stringUtil, config));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
bootstrap.option(ChannelOption.SO_BACKLOG, 2048);
|
||||||
|
bootstrap.childOption(ChannelOption.SO_KEEPALIVE, true);
|
||||||
|
bootstrap.childOption(ChannelOption.TCP_NODELAY, true);
|
||||||
|
mChannelFuture = bootstrap.bind(config.getPort()).sync();
|
||||||
|
mChannelFuture.channel().closeFuture().sync();
|
||||||
|
log.warn("【服务器启动成功========端口:" + config.getPort() + "】");
|
||||||
|
} catch (Exception e) {
|
||||||
|
log.error("【服务器启动失败】", e);
|
||||||
|
} finally {
|
||||||
|
//关闭资源
|
||||||
|
boss.shutdownGracefully();
|
||||||
|
work.shutdownGracefully();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@PostConstruct()
|
||||||
|
public void init() {
|
||||||
|
log.warn("【初始化......】");
|
||||||
|
//需要开启一个新的线程来执行netty server 服务器
|
||||||
|
new Thread(() -> startServer()).start();
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,69 @@
|
|||||||
|
package com.platform.util;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.concurrent.ConcurrentHashMap;
|
||||||
|
|
||||||
|
public class ControlDevice {
|
||||||
|
|
||||||
|
private static final HashMap<Byte, String> deviceSnToFkID = new HashMap<Byte, String>(){{
|
||||||
|
put((byte) 0x11,"D80A72");
|
||||||
|
put((byte) 0x13,"D80B00");
|
||||||
|
put((byte) 0x23,"D80AD8");
|
||||||
|
put((byte) 0x24,"D80A83");
|
||||||
|
put((byte) 0x25,"D80A87");
|
||||||
|
put((byte) 0x30,"D80A88");
|
||||||
|
put((byte) 0x31,"D80B0A");
|
||||||
|
put((byte) 0x32,"D80AB6");
|
||||||
|
|
||||||
|
put((byte) 0x01,"F492C1");
|
||||||
|
put((byte) 0x02,"F492C2");
|
||||||
|
put((byte) 0x03,"F492C3");
|
||||||
|
put((byte) 0xff,"all");
|
||||||
|
|
||||||
|
}};
|
||||||
|
|
||||||
|
public static String getSn(Byte fkID){return deviceSnToFkID.get(fkID);}
|
||||||
|
|
||||||
|
public static boolean isTure(Byte fkID){return deviceSnToFkID.containsKey(fkID);}
|
||||||
|
|
||||||
|
|
||||||
|
public static int getFk(String uavId){
|
||||||
|
int fk = 0;
|
||||||
|
for(Byte key: deviceSnToFkID.keySet()){
|
||||||
|
if(deviceSnToFkID.get(key).equals(uavId)){
|
||||||
|
fk = key;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return fk;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public static Map<String, String> currenCtrDevice = new ConcurrentHashMap<>(16); // 设备编号对应的mac地址
|
||||||
|
|
||||||
|
|
||||||
|
public static void clearCurrenCtrDeviceByMac(String mac){
|
||||||
|
|
||||||
|
for(String key: currenCtrDevice.keySet()){
|
||||||
|
if(currenCtrDevice.get(key).equals(mac)){
|
||||||
|
currenCtrDevice.remove(key);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static List<String> getCurrenCtrDevicesByMac(String mac){
|
||||||
|
|
||||||
|
List<String> ctrDevices = new ArrayList<>();
|
||||||
|
for(String key: currenCtrDevice.keySet()){
|
||||||
|
if(currenCtrDevice.get(key).equals(mac)){
|
||||||
|
ctrDevices.add(key);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return ctrDevices;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,143 @@
|
|||||||
|
package com.platform.util;
|
||||||
|
|
||||||
|
import com.alibaba.fastjson.JSON;
|
||||||
|
import io.netty.channel.Channel;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.springframework.stereotype.Component;
|
||||||
|
import org.springframework.util.ObjectUtils;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Optional;
|
||||||
|
import java.util.concurrent.ConcurrentHashMap;
|
||||||
|
|
||||||
|
@Component
|
||||||
|
@Slf4j
|
||||||
|
public class SessionCache {
|
||||||
|
|
||||||
|
public Map<String, Channel> tcpSession = new ConcurrentHashMap<>(16);
|
||||||
|
|
||||||
|
public Map<String, String> addToSnMap = new ConcurrentHashMap<>(16); // ip地址对应的设备编号
|
||||||
|
public Map<String, String> snToAddMap = new ConcurrentHashMap<>(16); // 设备编号对应的ip地址
|
||||||
|
public Map<String, String> snToSnMap = new ConcurrentHashMap<>(16); //一对一映射关系
|
||||||
|
public Map<String, String> snToMonitorMap = new ConcurrentHashMap<>(16); //监控映射
|
||||||
|
public Map<String, List<String>> mappingListMap = new ConcurrentHashMap<>(16); //所有映射关系
|
||||||
|
public Map<String, List<String>> snToListMap = new ConcurrentHashMap<>(16); //一对多映射关系
|
||||||
|
public List<String> snList = new ArrayList<>();
|
||||||
|
|
||||||
|
public Optional<Channel> findTargetChannel(String sourceAddr) {
|
||||||
|
String sSn = addToSnMap.get(sourceAddr);
|
||||||
|
String tSn = snToSnMap.get(sSn);
|
||||||
|
if (tSn == null) {
|
||||||
|
log.warn("找不到" + sourceAddr + "的目标映射;" +
|
||||||
|
"addToSnMap = " + JSON.toJSONString(addToSnMap) + "; " +
|
||||||
|
"snToSnMap = " + JSON.toJSONString(snToSnMap));
|
||||||
|
return Optional.empty();
|
||||||
|
}
|
||||||
|
|
||||||
|
String targetAddr = snToAddMap.get(tSn);
|
||||||
|
if (targetAddr == null) {
|
||||||
|
log.warn("目标映射" + tSn + "的地址找不到; " +
|
||||||
|
"snToAddMap = " + JSON.toJSONString(snToAddMap));
|
||||||
|
return Optional.empty();
|
||||||
|
}
|
||||||
|
|
||||||
|
Channel c = tcpSession.get(targetAddr);
|
||||||
|
if (c == null) {
|
||||||
|
log.warn("目标地址" + targetAddr + "的session channel找不到; " +
|
||||||
|
"tcpSession = " + JSON.toJSONString(tcpSession));
|
||||||
|
return Optional.empty();
|
||||||
|
}
|
||||||
|
|
||||||
|
return Optional.of(c);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Optional<Channel> findMonitorChannel(String sourceAddr) {
|
||||||
|
String sSn = addToSnMap.get(sourceAddr);
|
||||||
|
String tSn = snToMonitorMap.get(sSn);
|
||||||
|
if (tSn == null) {
|
||||||
|
log.warn("找不到" + sourceAddr + "的目标映射;" +
|
||||||
|
"addToSnMap = " + JSON.toJSONString(addToSnMap) + "; " +
|
||||||
|
"snToMonitorMap = " + JSON.toJSONString(snToMonitorMap));
|
||||||
|
return Optional.empty();
|
||||||
|
}
|
||||||
|
|
||||||
|
String targetAddr = snToAddMap.get(tSn);
|
||||||
|
if (targetAddr == null) {
|
||||||
|
log.warn("目标映射" + tSn + "的地址找不到; " +
|
||||||
|
"snToAddMap = " + JSON.toJSONString(snToAddMap));
|
||||||
|
return Optional.empty();
|
||||||
|
}
|
||||||
|
|
||||||
|
Channel c = tcpSession.get(targetAddr);
|
||||||
|
if (c == null) {
|
||||||
|
log.warn("目标地址" + targetAddr + "的session channel找不到; " +
|
||||||
|
"tcpSession = " + JSON.toJSONString(tcpSession));
|
||||||
|
return Optional.empty();
|
||||||
|
}
|
||||||
|
|
||||||
|
return Optional.of(c);
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<Channel> findManyTargetChannel(String sSn) {
|
||||||
|
List<Channel> channel = new ArrayList<>();
|
||||||
|
List<String> tSn = snToListMap.get(sSn);
|
||||||
|
|
||||||
|
if (!ObjectUtils.isEmpty(tSn)) {
|
||||||
|
tSn.forEach(s -> {
|
||||||
|
String targetAddr = snToAddMap.get(s);
|
||||||
|
if (targetAddr != null) {
|
||||||
|
Channel c = tcpSession.get(targetAddr);
|
||||||
|
if (c == null) {
|
||||||
|
log.warn("targetAddr " + targetAddr + " channel is null" + ", tcpSession = " + JSON.toJSONString(tcpSession));
|
||||||
|
} else {
|
||||||
|
channel.add(c);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
return channel;
|
||||||
|
}
|
||||||
|
|
||||||
|
public List<Channel> findMappingTargetChannel(String sSn) {
|
||||||
|
List<Channel> channel = new ArrayList<>();
|
||||||
|
List<String> tSn = mappingListMap.get(sSn); // 设备的映射关系
|
||||||
|
|
||||||
|
if (!ObjectUtils.isEmpty(tSn)) {
|
||||||
|
tSn.forEach(s -> { //
|
||||||
|
String targetAddr = snToAddMap.get(s); // 根据设备编号找到ip地址
|
||||||
|
if (targetAddr != null) {
|
||||||
|
Channel c = tcpSession.get(targetAddr); // 根据ip找到通道
|
||||||
|
if (c == null) {
|
||||||
|
log.warn("targetAddr " + targetAddr + " channel is null" + ", tcpSession = " + JSON.toJSONString(tcpSession));
|
||||||
|
} else {
|
||||||
|
channel.add(c);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
return channel;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* channel找ip地址
|
||||||
|
*/
|
||||||
|
|
||||||
|
public String findSnByChannel(Channel channel){
|
||||||
|
String fk = null;
|
||||||
|
for(String key: tcpSession.keySet()){
|
||||||
|
if(tcpSession.get(key).equals(channel)){
|
||||||
|
fk = key;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return fk;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
}
|
@ -0,0 +1,390 @@
|
|||||||
|
package com.platform.util;
|
||||||
|
|
||||||
|
import org.springframework.stereotype.Component;
|
||||||
|
|
||||||
|
import java.nio.ByteBuffer;
|
||||||
|
import java.nio.CharBuffer;
|
||||||
|
import java.nio.charset.Charset;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.regex.Pattern;
|
||||||
|
|
||||||
|
@Component
|
||||||
|
public class StringUtil {
|
||||||
|
|
||||||
|
private static Pattern pattern = Pattern.compile("\\b\\w+:\\w+:\\w+:\\w+:\\w+:\\w+\\b");
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert the hex string to byte array;
|
||||||
|
*
|
||||||
|
* @param strHexValue the hex string value.
|
||||||
|
* @return byte[] the resolved value.
|
||||||
|
*/
|
||||||
|
public byte[] stringToByteArray(String strHexValue) {
|
||||||
|
String[] strAryHex = strHexValue.split(" ");
|
||||||
|
byte[] btAryHex = new byte[strAryHex.length];
|
||||||
|
|
||||||
|
try {
|
||||||
|
int nIndex = 0;
|
||||||
|
for (String strTemp : strAryHex) {
|
||||||
|
btAryHex[nIndex] = (byte) Integer.parseInt(strTemp, 16);
|
||||||
|
nIndex++;
|
||||||
|
}
|
||||||
|
} catch (NumberFormatException e) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
return btAryHex;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert the Hex string array to byte array
|
||||||
|
*
|
||||||
|
* @param strAryHex the hex string value.
|
||||||
|
* @param nLen the needed parse length.
|
||||||
|
* @return byte[] the resolved value.
|
||||||
|
*/
|
||||||
|
public byte[] stringArrayToByteArray(String[] strAryHex, int nLen) {
|
||||||
|
if (strAryHex == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (strAryHex.length < nLen) {
|
||||||
|
nLen = strAryHex.length;
|
||||||
|
}
|
||||||
|
|
||||||
|
byte[] btAryHex = new byte[nLen];
|
||||||
|
|
||||||
|
try {
|
||||||
|
for (int i = 0; i < nLen; i++) {
|
||||||
|
btAryHex[i] = (byte) Integer.parseInt(strAryHex[i], 16);
|
||||||
|
}
|
||||||
|
} catch (NumberFormatException e) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
return btAryHex;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert the Hex string array to byte array
|
||||||
|
*
|
||||||
|
* @param btAryHex the hex string value.
|
||||||
|
* @param nIndex the starting parse position.
|
||||||
|
* @param nLen the needed parse length.
|
||||||
|
* @return byte[] the resolved value.
|
||||||
|
*/
|
||||||
|
public String byteArrayToString(byte[] btAryHex, int nIndex, int nLen) {
|
||||||
|
if (nIndex + nLen > btAryHex.length) {
|
||||||
|
nLen = btAryHex.length - nIndex;
|
||||||
|
}
|
||||||
|
|
||||||
|
String strResult = String.format("%02X", btAryHex[nIndex]);
|
||||||
|
for (int nloop = nIndex + 1; nloop < nIndex + nLen; nloop++) {
|
||||||
|
String strTemp = String.format(" %02X", btAryHex[nloop]);
|
||||||
|
|
||||||
|
strResult += strTemp;
|
||||||
|
}
|
||||||
|
|
||||||
|
return strResult;
|
||||||
|
}
|
||||||
|
|
||||||
|
public String bytesToHexString(byte[] bArray) {
|
||||||
|
StringBuffer sb = new StringBuffer(bArray.length);
|
||||||
|
String sTemp;
|
||||||
|
for (int i = 0; i < bArray.length; i++) {
|
||||||
|
sTemp = Integer.toHexString(0xFF & bArray[i]);
|
||||||
|
if (sTemp.length() < 2) {
|
||||||
|
sb.append(0);
|
||||||
|
}
|
||||||
|
sb.append(sTemp.toUpperCase());
|
||||||
|
}
|
||||||
|
return sb.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert the String to StringArray
|
||||||
|
*
|
||||||
|
* @param strValue the src string
|
||||||
|
* @param nLen needed convert length
|
||||||
|
* @return String[] the parsed value.
|
||||||
|
*/
|
||||||
|
public String[] stringToStringArray(String strValue, int nLen) {
|
||||||
|
String[] strAryResult = null;
|
||||||
|
|
||||||
|
if (strValue != null && !"".equals(strValue)) {
|
||||||
|
ArrayList<String> strListResult = new ArrayList<String>();
|
||||||
|
String strTemp = "";
|
||||||
|
int nTemp = 0;
|
||||||
|
|
||||||
|
for (int nloop = 0; nloop < strValue.length(); nloop++) {
|
||||||
|
if (strValue.charAt(nloop) == ' ') {
|
||||||
|
continue;
|
||||||
|
} else {
|
||||||
|
nTemp++;
|
||||||
|
|
||||||
|
if (!pattern.matcher(strValue.substring(nloop, nloop + 1)).matches()) {
|
||||||
|
return strAryResult;
|
||||||
|
}
|
||||||
|
|
||||||
|
strTemp += strValue.substring(nloop, nloop + 1);
|
||||||
|
|
||||||
|
if ((nTemp == nLen) || (nloop == strValue.length() - 1
|
||||||
|
&& (strTemp != null && !"".equals(strTemp)))) {
|
||||||
|
strListResult.add(strTemp);
|
||||||
|
nTemp = 0;
|
||||||
|
strTemp = "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (strListResult.size() > 0) {
|
||||||
|
strAryResult = new String[strListResult.size()];
|
||||||
|
for (int i = 0; i < strAryResult.length; i++) {
|
||||||
|
strAryResult[i] = strListResult.get(i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return strAryResult;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert the byte array to special encode char array.
|
||||||
|
*
|
||||||
|
* @param bytes the needed byte array.
|
||||||
|
* @param encoding the encoding format.
|
||||||
|
* @return char[] the converted char array.
|
||||||
|
*/
|
||||||
|
@Deprecated
|
||||||
|
public char[] getChars(byte[] bytes, String encoding) {
|
||||||
|
Charset cs = Charset.forName(encoding);
|
||||||
|
ByteBuffer bb = ByteBuffer.allocate(bytes.length);
|
||||||
|
bb.put(bytes);
|
||||||
|
bb.flip();
|
||||||
|
CharBuffer cb = cs.decode(bb);
|
||||||
|
return cb.array();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* resolve the bytes String data to ASCII.String like this "2f3Eab"
|
||||||
|
*
|
||||||
|
* @param hexString the needed parse data.
|
||||||
|
* @return String the return value.
|
||||||
|
*/
|
||||||
|
@Deprecated
|
||||||
|
public String toASCIIString(String hexString) {
|
||||||
|
StringBuilder stringBuilder = new StringBuilder();
|
||||||
|
int i = 0;
|
||||||
|
while (i < hexString.length()) {
|
||||||
|
stringBuilder.append((char) Integer.parseInt(hexString.substring(i, i + 2), 16));
|
||||||
|
i = i + 2;
|
||||||
|
}
|
||||||
|
return stringBuilder.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Resolve the bytes String data to ASCII.String like this "2f3Eab"
|
||||||
|
*
|
||||||
|
* @param hexString the needed parse data.
|
||||||
|
* @return String the return value.
|
||||||
|
*/
|
||||||
|
public String hexStringToASCIIString(String hexString) {
|
||||||
|
StringBuilder stringBuilder = new StringBuilder();
|
||||||
|
if (hexString == null || "".equals(hexString)) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
for (int i = 0; i < hexString.length(); i = i + 2) {
|
||||||
|
char high = hexString.charAt(i);
|
||||||
|
char low = hexString.charAt(i + 1);
|
||||||
|
|
||||||
|
char no = (char) (charToInt(high) * 16 + charToInt(low));
|
||||||
|
stringBuilder.append(no);
|
||||||
|
}
|
||||||
|
return stringBuilder.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert the char 1-f to int value;
|
||||||
|
*
|
||||||
|
* @param c the needed converter character.
|
||||||
|
* @return int the converted value.
|
||||||
|
*/
|
||||||
|
|
||||||
|
private int charToInt(char c) {
|
||||||
|
int num = -1;
|
||||||
|
num = "0123456789ABCDEF".indexOf(String.valueOf(c));
|
||||||
|
if (num < 0) {
|
||||||
|
num = "0123456789abcdef".indexOf(String.valueOf(c));
|
||||||
|
}
|
||||||
|
return num;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the sub bytes of the parent bytes;
|
||||||
|
*
|
||||||
|
* @param bytes parent bytes;
|
||||||
|
* @param start start position;
|
||||||
|
* @param end end position;
|
||||||
|
* @return the child bytes;
|
||||||
|
*/
|
||||||
|
public byte[] subBytes(byte[] bytes, int start, int end) {
|
||||||
|
byte[] subBytes = new byte[end - start];
|
||||||
|
System.arraycopy(bytes, start, subBytes, 0, end - start);
|
||||||
|
return subBytes;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the child position in their parents string
|
||||||
|
*
|
||||||
|
* @param parentBytes parent bytes;
|
||||||
|
* @param childBytes child bytes;
|
||||||
|
* @param startPosition start scan position;
|
||||||
|
* @return if -1 child not in parent string,or the child first position found in parent;
|
||||||
|
*/
|
||||||
|
public int subBytesContains(byte[] parentBytes, byte[] childBytes, int startPosition) {
|
||||||
|
if (parentBytes.length < childBytes.length) {
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
for (int i = startPosition; i < parentBytes.length; i++) {
|
||||||
|
for (int j = 0; j < childBytes.length; j++) {
|
||||||
|
if (parentBytes[i + j] == childBytes[j]) {
|
||||||
|
if (j == childBytes.length - 1) {
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
continue;
|
||||||
|
} else {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert hexString to byte array.
|
||||||
|
*
|
||||||
|
* @param hexString to bytes
|
||||||
|
* @return The converted byte array.
|
||||||
|
*/
|
||||||
|
public byte[] hexStringToBytes(String hexString) {
|
||||||
|
byte[] bytes = new byte[hexString.length() / 2];
|
||||||
|
if (hexString == null || "".equals(hexString)) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
for (int i = 0; i < hexString.length(); i = i + 2) {
|
||||||
|
char high = hexString.charAt(i);
|
||||||
|
char low = hexString.charAt(i + 1);
|
||||||
|
|
||||||
|
bytes[i / 2] = (byte) (charToInt(high) * 16 + charToInt(low));
|
||||||
|
}
|
||||||
|
return bytes;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* 将十六进制的字符串转换成字节数组
|
||||||
|
*
|
||||||
|
* @param hexString
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public byte[] hexStrToBinaryStr(String hexString) {
|
||||||
|
if (hexString=="") {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
hexString = hexString.replaceAll(" ", "");
|
||||||
|
int len = hexString.length();
|
||||||
|
int index = 0;
|
||||||
|
byte[] bytes = new byte[len / 2];
|
||||||
|
while (index < len) {
|
||||||
|
String sub = hexString.substring(index, index + 2);
|
||||||
|
bytes[index/2] = (byte)Integer.parseInt(sub,16);
|
||||||
|
index += 2;
|
||||||
|
}
|
||||||
|
return bytes;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Compare the both byte array
|
||||||
|
*
|
||||||
|
* @param first the first byte array
|
||||||
|
* @param second the second byte array
|
||||||
|
* @return if true first equals second ,otherwise unequal
|
||||||
|
*/
|
||||||
|
public boolean compareBytes(byte[] first, byte[] second) {
|
||||||
|
if (first.length != second.length) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
for (int i = 0; i < first.length; i++) {
|
||||||
|
if (first[i] != second[i]) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert Ascii string to byte array.
|
||||||
|
*
|
||||||
|
* @param string the needed converter data.
|
||||||
|
* @return byte[] the converted value.
|
||||||
|
*/
|
||||||
|
public byte[] asciiStringToBytes(String string) {
|
||||||
|
byte[] result = new byte[string.length()];
|
||||||
|
for (int i = 0; i < string.length(); i++) {
|
||||||
|
result[i] = (byte) string.charAt(i);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
public String computeCRC(String data) {
|
||||||
|
data = data.replace(" ", "");
|
||||||
|
int len = data.length();
|
||||||
|
if (!(len % 2 == 0)) {
|
||||||
|
return "0000";
|
||||||
|
}
|
||||||
|
int num = len / 2;
|
||||||
|
byte[] para = new byte[num];
|
||||||
|
for (int i = 0; i < num; i++) {
|
||||||
|
int value = Integer.valueOf(data.substring(i * 2, 2 * (i + 1)), 16);
|
||||||
|
para[i] = (byte) value;
|
||||||
|
}
|
||||||
|
return getCRC(para);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 计算CRC16校验码
|
||||||
|
*
|
||||||
|
* @param bytes
|
||||||
|
* 字节数组
|
||||||
|
* @return {@link String} 校验码
|
||||||
|
* @since 1.0
|
||||||
|
*/
|
||||||
|
public String getCRC(byte[] bytes) {
|
||||||
|
// CRC寄存器全为1
|
||||||
|
int CRC = 0x0000ffff;
|
||||||
|
// 多项式校验值
|
||||||
|
int POLYNOMIAL = 0x0000a001;
|
||||||
|
int i, j;
|
||||||
|
for (i = 0; i < bytes.length; i++) {
|
||||||
|
CRC ^= ((int) bytes[i] & 0x000000ff);
|
||||||
|
for (j = 0; j < 8; j++) {
|
||||||
|
if ((CRC & 0x00000001) != 0) {
|
||||||
|
CRC >>= 1;
|
||||||
|
CRC ^= POLYNOMIAL;
|
||||||
|
} else {
|
||||||
|
CRC >>= 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// 结果转换为16进制
|
||||||
|
String result = Integer.toHexString(CRC).toUpperCase();
|
||||||
|
if (result.length() != 4) {
|
||||||
|
StringBuffer sb = new StringBuffer("0000");
|
||||||
|
result = sb.replace(4 - result.length(), 4, result).toString();
|
||||||
|
}
|
||||||
|
//高位在前地位在后
|
||||||
|
//return result.substring(2, 4) + " " + result.substring(0, 2);
|
||||||
|
// 交换高低位,低位在前高位在后
|
||||||
|
return result.substring(2, 4) + " " + result.substring(0, 2);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int byteToInt(byte b) {
|
||||||
|
return (b) & 0xff;
|
||||||
|
}
|
||||||
|
}
|
@ -0,0 +1,6 @@
|
|||||||
|
server:
|
||||||
|
port: 11727
|
||||||
|
service:
|
||||||
|
port: 11728
|
||||||
|
log:
|
||||||
|
debug: false
|
@ -0,0 +1,3 @@
|
|||||||
|
spring:
|
||||||
|
profiles:
|
||||||
|
active: dev
|
Loading…
Reference in New Issue