通威测试视觉相关逻辑

湖北-大华摄像头
LAPTOP-S9HJSOEB\昊天 1 year ago
parent 818bf0a376
commit 413669db08

@ -19,6 +19,6 @@ public class LicenseAspect {
*/ */
@Before("execution(public * com.zhehekeji..*.controller.*.*(..))") @Before("execution(public * com.zhehekeji..*.controller.*.*(..))")
public void handler(){ public void handler(){
Assert.isTrue(LPLicense.checkLic(),"未获取授权请将C:\\hzleaper_auto_install\\logistics_package\\lp.key发送给授权人员"); //Assert.isTrue(LPLicense.checkLic(),"未获取授权请将C:\\hzleaper_auto_install\\logistics_package\\lp.key发送给授权人员");
} }
} }

@ -1,5 +1,6 @@
package com.zhehekeji.web.controller; package com.zhehekeji.web.controller;
import com.sun.jna.ptr.IntByReference;
import com.zhehekeji.common.util.PathUtil; import com.zhehekeji.common.util.PathUtil;
import com.zhehekeji.core.pojo.Result; import com.zhehekeji.core.pojo.Result;
import com.zhehekeji.core.util.Assert; import com.zhehekeji.core.util.Assert;
@ -22,6 +23,8 @@ import javax.annotation.Resource;
import java.time.LocalDateTime; import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter; import java.time.format.DateTimeFormatter;
import static com.zhehekeji.web.lib.hik.HCNetSDK.*;
@Api(value = "CameraControl",tags = "球机控制管理") @Api(value = "CameraControl",tags = "球机控制管理")
@RestController @RestController
@RequestMapping("/camera/control") @RequestMapping("/camera/control")
@ -60,6 +63,40 @@ public class CameraControlController {
return Result.success(); return Result.success();
} }
@PostMapping("/ptzControl/{id}")
@ApiOperation(value = "球机控制指定")
public Result ptzControl(@PathVariable Integer id) {
log.debug("球机控制");
checkLogin(id);
HCNetSDK.NET_DVR_PTZPOS struPtTZPos = new HCNetSDK.NET_DVR_PTZPOS();
IntByReference intByReference = new IntByReference(1);
boolean b_GetPTZ =HikLoginModuleImpl.hcNetsdk.NET_DVR_GetDVRConfig( CameraConnMap.getConnId(id).intValue(), NET_DVR_GET_PTZPOS, 1,struPtTZPos.getPointer(), struPtTZPos.size(),intByReference);
if (b_GetPTZ==false){
System.out.println("获取PTZ坐标信息失败错误码" + HikLoginModuleImpl.hcNetsdk.NET_DVR_GetLastError());
}else {
struPtTZPos.read();
String p=Integer.toHexString(struPtTZPos.wPanPos);
String t=Integer.toHexString(struPtTZPos.wTiltPos);
String z=Integer.toHexString(struPtTZPos.wZoomPos);
System.out.println("P参数"+p+"\n");
System.out.println("T参数"+t+"\n");
System.out.println("Z参数"+z+"\n");
}
struPtTZPos.wAction = 1;
struPtTZPos.wPanPos = (short) (struPtTZPos.wPanPos+0x10);
struPtTZPos.wTiltPos = (short) (struPtTZPos.wTiltPos+0x10);
//struPtTZPos.wZoomPos = (short) (struPtTZPos.wZoomPos+60);
struPtTZPos.write();
HikLoginModuleImpl.hcNetsdk.NET_DVR_SetDVRConfig( CameraConnMap.getConnId(id).intValue(), NET_DVR_SET_PTZPOS, 1,struPtTZPos.getPointer(), struPtTZPos.size());
return Result.success();
}
@PostMapping("/up/stop/{id}") @PostMapping("/up/stop/{id}")
@ApiOperation(value = "球机控制向上 停止") @ApiOperation(value = "球机控制向上 停止")
public Result upStop(@PathVariable Integer id) { public Result upStop(@PathVariable Integer id) {
@ -333,7 +370,7 @@ public class CameraControlController {
@Resource @Resource
private CameraService cameraService; private CameraService cameraService;
private void checkLogin(Integer cameraId) { public void checkLogin(Integer cameraId) {
if (CameraConnMap.getConnId(cameraId) != null) { if (CameraConnMap.getConnId(cameraId) != null) {
Boolean ok = false; Boolean ok = false;
if (configProperties.getCameraConfig().getCameraType() == ConfigProperties.HIK_CAMERA) { if (configProperties.getCameraConfig().getCameraType() == ConfigProperties.HIK_CAMERA) {

@ -1,25 +1,42 @@
package com.zhehekeji.web.controller; package com.zhehekeji.web.controller;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.github.pagehelper.PageInfo; import com.github.pagehelper.PageInfo;
import com.sun.jna.ptr.IntByReference;
import com.zhehekeji.common.util.PathUtil;
import com.zhehekeji.common.util.ValidatorUtil; import com.zhehekeji.common.util.ValidatorUtil;
import com.zhehekeji.core.pojo.Result; import com.zhehekeji.core.pojo.Result;
import com.zhehekeji.web.config.ConfigProperties;
import com.zhehekeji.web.entity.LightSource;
import com.zhehekeji.web.entity.Street;
import com.zhehekeji.web.lib.CameraConnMap;
import com.zhehekeji.web.lib.hik.HCNetSDK;
import com.zhehekeji.web.lib.hik.HikLoginModuleImpl;
import com.zhehekeji.web.mapper.StreetMapper;
import com.zhehekeji.web.pojo.OrderSaveReq; import com.zhehekeji.web.pojo.OrderSaveReq;
import com.zhehekeji.web.pojo.OrderSearch; import com.zhehekeji.web.pojo.OrderSearch;
import com.zhehekeji.web.pojo.OrderVO; import com.zhehekeji.web.pojo.OrderVO;
import com.zhehekeji.web.service.OrderService; import com.zhehekeji.web.service.*;
import com.zhehekeji.web.service.PlcCmdInfo;
import com.zhehekeji.web.service.PlcService;
import io.swagger.annotations.Api; import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation; import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam; import io.swagger.annotations.ApiParam;
import io.swagger.models.auth.In;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value; import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource; import javax.annotation.Resource;
import java.io.File;
import java.util.HashMap;
import java.util.List;
import static com.zhehekeji.web.lib.hik.HCNetSDK.NET_DVR_GET_PTZPOS;
import static com.zhehekeji.web.lib.hik.HCNetSDK.NET_DVR_SET_PTZPOS;
@Api(value = "OrderController",tags = "订单管理") @Api(value = "OrderController",tags = "订单管理")
@RestController(value = "OrderController") @RestController(value = "OrderController")
@RequestMapping("/order") @RequestMapping("/order")
@Slf4j
public class OrderController { public class OrderController {
@Resource @Resource
@ -29,6 +46,9 @@ public class OrderController {
@Resource @Resource
private ValidatorUtil validatorUtil; private ValidatorUtil validatorUtil;
@Resource
private CameraControlController cameracheckLogin;
@Value("${zhehe.filter.postToken}") @Value("${zhehe.filter.postToken}")
private String postToken; private String postToken;
@ -84,4 +104,157 @@ public class OrderController {
return Result.success(orderService.orders(orderSearch)); return Result.success(orderService.orders(orderSearch));
} }
@Resource
ConfigProperties configProperties;
@Resource
CodeService codeService;
@Resource
StreetMapper streetMapper;
@Resource
LightSourceService lightSourceService;
@PostMapping("/test1/{id}")
@ApiOperation(value = "test1")
//@SessionHandler
public Result<String> test1(@PathVariable Integer id) {
//validatorUtil.validate(orderSearch);
Street street = streetMapper.selectOne(new QueryWrapper<Street>().eq("camera1_Id", id).or().eq("camera2_Id", id));
List<LightSource> lightSources = lightSourceService.getLightSourceByStreetId(street.getId());
lightSources.forEach(lightSource -> {
lightSourceService.controllerLightSource(lightSource,1);
});
//球机调用指定预置点位
plcService.gyrateCameraByCode(id,"E1");
//球机拍照
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
String path = "work\\1.jpg";
plcService.cameraCapture(id,false,null,path);
//交予灵闪识别
HashMap<String,String> stringMap = new HashMap<>();
stringMap.put("code","");
stringMap.put("location","");
CodeService.readOCR("127.0.0.1",9040,stringMap);
System.out.println("stringMap: "+stringMap);
//25601440
if(!"".equals(stringMap.get("location"))){
//调整位置
ge( id, stringMap.get("location"));
}
//球机拍照
try {
Thread.sleep(8000);
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
plcService.cameraCapture(id,false,null,path);
//交予灵闪识别
String code = CodeService.readOCR("127.0.0.1",9040,stringMap);
lightSources.forEach(lightSource -> {
lightSourceService.controllerLightSource(lightSource,0);
});
return Result.success(code);
}
@PostMapping("/test/{id}")
@ApiOperation(value = "test")
//@SessionHandler
public Result<String> test(@PathVariable Integer id) {
//validatorUtil.validate(orderSearch);
Street street = streetMapper.selectOne(new QueryWrapper<Street>().eq("camera1_Id", id).or().eq("camera2_Id", id));
List<LightSource> lightSources = lightSourceService.getLightSourceByStreetId(street.getId());
lightSources.forEach(lightSource -> {
lightSourceService.controllerLightSource(lightSource,1);
});
//球机调用指定预置点位
plcService.gyrateCameraByCode(id,"E1");
//球机拍照
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
String path = "work\\1.jpg";
plcService.cameraCapture(id,false,null,path);
//交予灵闪识别
HashMap<String,String> stringMap = new HashMap<>();
stringMap.put("code","");
stringMap.put("location","");
String code = CodeService.readOCR("127.0.0.1",9040,stringMap);
//25601440
return Result.success(code);
}
////25601440
void ge(int id,String location){
String[] locations = location.split(",");
cameracheckLogin.checkLogin(id);
HCNetSDK.NET_DVR_PTZPOS struPtTZPos = new HCNetSDK.NET_DVR_PTZPOS();
IntByReference intByReference = new IntByReference(1);
boolean b_GetPTZ = HikLoginModuleImpl.hcNetsdk.NET_DVR_GetDVRConfig( CameraConnMap.getConnId(id).intValue(), NET_DVR_GET_PTZPOS, 1,struPtTZPos.getPointer(), struPtTZPos.size(),intByReference);
if (b_GetPTZ==false){
System.out.println("获取PTZ坐标信息失败错误码" + HikLoginModuleImpl.hcNetsdk.NET_DVR_GetLastError());
return;
}else {
System.out.println("获取PTZ坐标信息成功");
struPtTZPos.read();
}
//水平
int p = ((int) Math.round( Double.parseDouble(locations[0]))-(2560/2))/30;
//垂直
int t = ((int) Math.round( Double.parseDouble(locations[1]))-(1440/2))/30;
struPtTZPos.wAction = 1;
//水平
System.out.println(struPtTZPos.wPanPos);
struPtTZPos.wPanPos = (short) (struPtTZPos.wPanPos+0x10*p);
System.out.println(struPtTZPos.wPanPos);
//垂直
System.out.println();
System.out.println(struPtTZPos.wTiltPos);
struPtTZPos.wTiltPos = (short) (struPtTZPos.wTiltPos+0x10*t);
System.out.println(struPtTZPos.wTiltPos);
struPtTZPos.wZoomPos = 0x0150;
struPtTZPos.write();
boolean flag = HikLoginModuleImpl.hcNetsdk.NET_DVR_SetDVRConfig( CameraConnMap.getConnId(id).intValue(), NET_DVR_SET_PTZPOS, 1,struPtTZPos.getPointer(), struPtTZPos.size());
if(!flag){
System.out.println("设置PTZ坐标信息失败错误码" + HikLoginModuleImpl.hcNetsdk.NET_DVR_GetLastError());
}else {
System.out.println("设置PTZ坐标信息成功 p:"+p+" t:"+t);
}
}
public static void main(String[] args) {
String location = "963.465209960937500,1373.154296875000000";
String[] locations = location.split(",");
int p = ((int) Math.round( Double.parseDouble(locations[0]))-(2560/2))/30;
int t = ((int) Math.round( Double.parseDouble(locations[1]))-(1440/2))/32;
System.out.println(p+" "+t);
}
} }

@ -92,20 +92,7 @@ public class StreetController {
List<LightSource> lightSources = lightSourceService.getLightSource(); List<LightSource> lightSources = lightSourceService.getLightSource();
lightSources.forEach(lightSource -> { lightSources.forEach(lightSource -> {
JSONObject obj = JSONObject.parseObject(configProperties.getLightSource().getInfo()); lightSourceService.controllerLightSource(lightSource,1);
if(configProperties.getLightSource().getType() == 1){
JYDAMEquip equip = JYDamHelper.Connect(lightSource.getIp(),lightSource.getPort());
JYDamHelper.openDO(equip,configProperties.getLightSource().getIndex());
Integer status = JYDamHelper.ReadStatus(equip,configProperties.getLightSource().getNum(),configProperties.getLightSource().getIndex());
log.info("ip:{},status:{}",lightSource.getIp(),status);
equip.DisConnect();
}else if(configProperties.getLightSource().getType() == 2){
HikControlSocket.openLight(lightSource.getIp(),lightSource.getPort(),configProperties.getLightSource().getIndex(),1);
}else if (configProperties.getLightSource().getType() == 3){
LightSourceService.lightController(lightSource.getIp(),lightSource.getPort(),1);
}
}); });
@ -118,19 +105,9 @@ public class StreetController {
List<LightSource> lightSources = lightSourceService.getLightSource(); List<LightSource> lightSources = lightSourceService.getLightSource();
lightSources.forEach(lightSource -> { lightSources.forEach(lightSource -> {
JSONObject obj = JSONObject.parseObject(configProperties.getLightSource().getInfo()); lightSourceService.controllerLightSource(lightSource,0);
if(configProperties.getLightSource().getType() == 1){
JYDAMEquip equip = JYDamHelper.Connect(lightSource.getIp(),lightSource.getPort());
JYDamHelper.closeDO(equip,obj.getInteger("index"));
Integer status = JYDamHelper.ReadStatus(equip,obj.getInteger("num"),obj.getInteger("index"));
log.info("ip:{},status:{}",lightSource.getIp(),status);
}else if(configProperties.getLightSource().getType() == 2){
HikControlSocket.openLight(lightSource.getIp(),lightSource.getPort(),configProperties.getLightSource().getIndex(),0);
}else if (configProperties.getLightSource().getType() == 3){
LightSourceService.lightController(lightSource.getIp(),lightSource.getPort(),0);
}
}); });
@ -142,17 +119,7 @@ public class StreetController {
public Result openStreetLightSource(@PathVariable Integer streetId){ public Result openStreetLightSource(@PathVariable Integer streetId){
List<LightSource> lightSources = lightSourceService.getLightSourceByStreetId(streetId); List<LightSource> lightSources = lightSourceService.getLightSourceByStreetId(streetId);
lightSources.forEach(lightSource -> { lightSources.forEach(lightSource -> {
if(configProperties.getLightSource().getType() == 1){ lightSourceService.controllerLightSource(lightSource,1);
JYDAMEquip equip = JYDamHelper.Connect(lightSource.getIp(),lightSource.getPort());
JYDamHelper.openDO(equip,configProperties.getLightSource().getIndex());
Integer status = JYDamHelper.ReadStatus(equip,configProperties.getLightSource().getNum(),configProperties.getLightSource().getIndex());
log.info("ip:{},status:{}",lightSource.getIp(),status);
equip.DisConnect();
}else if(configProperties.getLightSource().getType() == 2){
HikControlSocket.openLight(lightSource.getIp(),lightSource.getPort(),configProperties.getLightSource().getIndex(),1);
}else if (configProperties.getLightSource().getType() == 3){
LightSourceService.lightController(lightSource.getIp(),lightSource.getPort(),1);
}
}); });
@ -164,20 +131,11 @@ public class StreetController {
public Result closeStreetLightSource(@PathVariable Integer streetId){ public Result closeStreetLightSource(@PathVariable Integer streetId){
List<LightSource> lightSources = lightSourceService.getLightSourceByStreetId(streetId); List<LightSource> lightSources = lightSourceService.getLightSourceByStreetId(streetId);
lightSources.forEach(lightSource -> { lightSources.forEach(lightSource -> {
if(configProperties.getLightSource().getType() == 1){ lightSourceService.controllerLightSource(lightSource,0);
JYDAMEquip equip = JYDamHelper.Connect(lightSource.getIp(),lightSource.getPort());
JYDamHelper.closeDO(equip,configProperties.getLightSource().getIndex());
Integer status = JYDamHelper.ReadStatus(equip,configProperties.getLightSource().getNum(),configProperties.getLightSource().getIndex());
log.info("ip:{},status:{}",lightSource.getIp(),status);
equip.DisConnect();
}else if(configProperties.getLightSource().getType() == 2){
HikControlSocket.openLight(lightSource.getIp(),lightSource.getPort(),configProperties.getLightSource().getIndex(),0);
}else if (configProperties.getLightSource().getType() == 3){
LightSourceService.lightController(lightSource.getIp(),lightSource.getPort(),0);
}
}); });
return Result.success(); return Result.success();
} }

@ -12,6 +12,7 @@ import lombok.Data;
import lombok.NoArgsConstructor; import lombok.NoArgsConstructor;
import java.time.LocalDateTime; import java.time.LocalDateTime;
import java.util.concurrent.*;
@Data @Data
@TableName("`stock`") @TableName("`stock`")
@ -93,5 +94,43 @@ public class Stock {
@TableField(exist = false) @TableField(exist = false)
private String streetName; private String streetName;
public static void main(String[] args) {
ExecutorService executor = Executors.newSingleThreadExecutor();
// 提交一个可调用任务
Future<String> future = executor.submit(new Callable<String>() {
@Override
public String call() throws Exception {
System.out.println("开始");
int i = 5/0;
// 模拟一个长时间运行的方法
Thread.sleep(5000); // 5秒
System.out.println("完成");
return "任务完成";
}
});
try {
// 尝试在3秒内获取结果
String result = future.get(3, TimeUnit.SECONDS);
System.out.println("任务完成: " + result);
} catch (TimeoutException e) {
System.out.println("任务超时,触发新方法");
// 触发新的方法
newMethod();
// 取消原任务,但允许其继续运行
//future.cancel(false);
} catch (InterruptedException | ExecutionException e) {
e.printStackTrace();
} finally {
System.out.println("最后");
// 关闭线程池
executor.shutdown();
}
}
private static void newMethod() {
System.out.println("新方法被触发");
// 新方法的逻辑
}
} }

@ -4,6 +4,7 @@ import com.zhehekeji.web.lib.joyware.NetSDKLib;
import java.util.HashMap; import java.util.HashMap;
import java.util.Map; import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
/** /**
* camera login handler * camera login handler
@ -14,13 +15,13 @@ public class CameraConnMap {
* key :cameraId * key :cameraId
* value: loginId * value: loginId
*/ */
public static Map<Integer, NetSDKLib.LLong> cameraMap = new HashMap<>(); public static Map<Integer, NetSDKLib.LLong> cameraMap = new ConcurrentHashMap<>();
/** /**
* key:loginId * key:loginId
* value: cameraId * value: cameraId
*/ */
public static Map<NetSDKLib.LLong,Integer> loginMap = new HashMap<>(); public static Map<NetSDKLib.LLong,Integer> loginMap = new ConcurrentHashMap<>();
public static void conn(Integer cameraId,NetSDKLib.LLong handlerId){ public static void conn(Integer cameraId,NetSDKLib.LLong handlerId){
synchronized (cameraId.toString().intern()){ synchronized (cameraId.toString().intern()){

@ -0,0 +1,175 @@
package com.zhehekeji.web.service;
import lombok.extern.slf4j.Slf4j;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;
import java.io.*;
import java.net.InetSocketAddress;
import java.net.Socket;
import java.nio.charset.StandardCharsets;
import java.util.HashMap;
import java.util.Map;
@Slf4j
@Service
public class CodeService {
private static final Logger tcpLogger = LoggerFactory.getLogger("sick");
public static void main(String[] args) {
Map<String,String> map = new HashMap<>();
map.put("Lotnum","");
map.put("2","");
String code = readOCR("127.0.0.1", 554,"",map);
System.out.println(map);
}
/*
* OCR
* @param ip
* @param port
* @param writeCmd
* @param stringMap :;
* @return
*/
public static String readOCR(String ip, int port, String writeCmd, Map<String,String> stringMap){
Socket socket = new Socket();
String code = "NoRead";
OutputStream os = null;
InputStream is = null;
try {
socket.connect(new InetSocketAddress(ip,port),3000);
socket.setSoTimeout(35000);
os = socket.getOutputStream();
is = socket.getInputStream();
int i = 0;
//扫描ocr
//拍照
writeCmd(os,"start:1");
String[] codes = read(is);
for (String c :codes) {
if (c.contains(":")) {
String[] split = code.split(":");
if (stringMap.get(split[0]) != null && split.length > 2) {
stringMap.put(split[0], split[1]);
}
}
}
//code = read(is);
} catch (IOException e) {
tcpLogger.error("sick time out,ip:{},info:{}",ip,e);
log.error("sick time out,ip:{},info:{}",ip,e);
}finally {
if(os != null){
try {
os.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if(is != null){
try {
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
try {
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
return code;
}
}
/*
* OCR
* @param ip
* @param port
* @param writeCmd
* @param stringMap :;
* @return
*/
public static String readOCR(String ip, int port,HashMap<String,String> stringMap){
Socket socket = new Socket();
String code = "NoRead";
OutputStream os = null;
InputStream is = null;
try {
socket.connect(new InetSocketAddress(ip,port),3000);
socket.setSoTimeout(355000);
os = socket.getOutputStream();
is = socket.getInputStream();
int i = 0;
//扫描ocr
//拍照
writeCmd(os,"start:1");
String[] codes = read(is);
System.out.println(codes);
for (String c :codes) {
if (c.contains(":")) {
String[] split = c.split(":");
if (stringMap.get(split[0]) != null && split.length == 2) {
stringMap.put(split[0], split[1]);
}
}
}
//code = read(is);
} catch (IOException e) {
tcpLogger.error("sick time out,ip:{},info:{}",ip,e);
log.error("sick time out,ip:{},info:{}",ip,e);
}finally {
if(os != null){
try {
os.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if(is != null){
try {
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
try {
socket.close();
} catch (IOException e) {
e.printStackTrace();
}
return stringMap.get("code");
}
}
private static void writeCmd(OutputStream os,String writeCmd) throws IOException {
byte[]bytes = writeCmd.getBytes(StandardCharsets.UTF_8);
os.write(bytes);
}
private static String[] read(InputStream inStream) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(inStream));
int c;
StringBuilder sb = new StringBuilder();
while ((c = br.read()) != -1) {
char ch = (char) c;
if (ch == '>') {
break; // 当读取到 "END" 时停止
}
sb.append(ch);
}
return sb.toString().split(";");
}
}

@ -1,11 +1,19 @@
package com.zhehekeji.web.service; package com.zhehekeji.web.service;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.zhehekeji.web.config.ConfigProperties;
import com.zhehekeji.web.entity.LightSource; import com.zhehekeji.web.entity.LightSource;
import com.zhehekeji.web.mapper.LightSourceMapper; import com.zhehekeji.web.mapper.LightSourceMapper;
import com.zhehekeji.web.service.damLightSource.JYDAMEquip;
import com.zhehekeji.web.service.damLightSource.JYDamHelper;
import com.zhehekeji.web.service.hikLightSource.HikControlSocket;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service; import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import java.io.DataOutputStream;
import java.io.IOException; import java.io.IOException;
import java.io.InputStream; import java.io.InputStream;
import java.io.OutputStream; import java.io.OutputStream;
@ -16,10 +24,13 @@ import java.util.HashMap;
import java.util.List; import java.util.List;
@Service @Service
@Slf4j
public class LightSourceService { public class LightSourceService {
@Autowired @Resource
private LightSourceMapper lightSourceMapper; private LightSourceMapper lightSourceMapper;
@Resource
ConfigProperties configProperties;
public List<LightSource> getLightSource(){ public List<LightSource> getLightSource(){
return lightSourceMapper.selectByMap(new HashMap<>()); return lightSourceMapper.selectByMap(new HashMap<>());
@ -29,6 +40,77 @@ public class LightSourceService {
return lightSourceMapper.selectList(new QueryWrapper<LightSource>().eq("street_id",streetId)); return lightSourceMapper.selectList(new QueryWrapper<LightSource>().eq("street_id",streetId));
} }
public boolean controllerLightSource(LightSource lightSource, int status) {
JSONObject obj = JSONObject.parseObject(configProperties.getLightSource().getInfo());
//1开灯 0关灯
if (status == 1) {
if (configProperties.getLightSource().getType() == 1) {
JYDAMEquip equip = JYDamHelper.Connect(lightSource.getIp(), lightSource.getPort());
JYDamHelper.openDO(equip, configProperties.getLightSource().getIndex());
Integer stat = JYDamHelper.ReadStatus(equip, configProperties.getLightSource().getNum(), configProperties.getLightSource().getIndex());
log.info("ip:{},status:{}", lightSource.getIp(), stat);
equip.DisConnect();
} else if (configProperties.getLightSource().getType() == 2) {
HikControlSocket.openLight(lightSource.getIp(), lightSource.getPort(), configProperties.getLightSource().getIndex(), 1);
} else if (configProperties.getLightSource().getType() == 3) {
relay(lightSource.getIp(), lightSource.getPort(),status);
}
} else {
if (configProperties.getLightSource().getType() == 1) {
JYDAMEquip equip = JYDamHelper.Connect(lightSource.getIp(), lightSource.getPort());
JYDamHelper.closeDO(equip, configProperties.getLightSource().getIndex());
Integer stat = JYDamHelper.ReadStatus(equip, configProperties.getLightSource().getNum(), configProperties.getLightSource().getIndex());
log.info("ip:{},status:{}", lightSource.getIp(), stat);
equip.DisConnect();
} else if (configProperties.getLightSource().getType() == 2) {
HikControlSocket.openLight(lightSource.getIp(), lightSource.getPort(), configProperties.getLightSource().getIndex(), 0);
} else if (configProperties.getLightSource().getType() == 3) {
relay(lightSource.getIp(), lightSource.getPort(),status);
}
}
return true;
}
/*
*/
public static void relay(String host, int port, int status) {
byte[][] data = new byte[2][];
if (status == 1) {
//01 05 00 00 ff 00 8c 3a
data[0] = new byte[]{0x01, 0x05, 0x00, 0x00, (byte) 0xFF, 0x00, (byte) 0x8c, (byte) 0x3A};
//网络继电器发送设置HEX 开01 05 00 01 FF 00 DD FA
//关01 05 00 01 00 00 9C 0A
data[1] = new byte[]{0x01, 0x05, 0x00, 0x01, (byte) 0xFF, 0x00, (byte) 0xdd, (byte) 0xfa};
} else {
//01 05 00 00 00 00 cd ca
data[0] = new byte[]{0x01, 0x05, 0x00, 0x00, (byte) 0x00, 0x00, (byte) 0xcd, (byte) 0xca};
data[1] = new byte[]{0x01, 0x05, 0x00, 0x01, (byte) 0x00, 0x00, (byte) 0x9c, (byte) 0x0A};
}
try (Socket socket = new Socket(host, port);
DataOutputStream outputStream = new DataOutputStream(socket.getOutputStream())) {
for (byte[] d :data){
socket.setSoTimeout(1000);
// 发送数据
outputStream.write(d);
outputStream.flush();
}
//System.out.println("Data sent successfully.");
} catch (IOException e) {
// System.err.println("Error sending data: " + e.getMessage());
e.printStackTrace();
}
}
/** /**
* *
* @param ip * @param ip

@ -2,11 +2,14 @@ package com.zhehekeji.web.service;
import codeDetector.BarcodeDetector; import codeDetector.BarcodeDetector;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.sun.jna.ptr.IntByReference;
import com.zhehekeji.common.util.PathUtil; import com.zhehekeji.common.util.PathUtil;
import com.zhehekeji.core.pojo.Result; import com.zhehekeji.core.pojo.Result;
import com.zhehekeji.web.config.ConfigProperties; import com.zhehekeji.web.config.ConfigProperties;
import com.zhehekeji.web.entity.*; import com.zhehekeji.web.entity.*;
import com.zhehekeji.web.lib.*; import com.zhehekeji.web.lib.*;
import com.zhehekeji.web.lib.hik.HCNetSDK;
import com.zhehekeji.web.lib.hik.HikLoginModuleImpl;
import com.zhehekeji.web.mapper.*; import com.zhehekeji.web.mapper.*;
import com.zhehekeji.web.pojo.CameraPtzPojo; import com.zhehekeji.web.pojo.CameraPtzPojo;
import com.zhehekeji.web.pojo.OrderVO; import com.zhehekeji.web.pojo.OrderVO;
@ -31,8 +34,14 @@ import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.PathVariable;
import javax.annotation.Resource; import javax.annotation.Resource;
import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.time.Duration; import java.time.Duration;
import java.time.LocalDateTime; import java.time.LocalDateTime;
import java.util.HashMap;
import java.util.HashSet; import java.util.HashSet;
import java.util.List; import java.util.List;
import java.util.Set; import java.util.Set;
@ -40,6 +49,11 @@ import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.BlockingDeque; import java.util.concurrent.BlockingDeque;
import java.util.concurrent.ThreadPoolExecutor; import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;
import static com.zhehekeji.web.lib.hik.HCNetSDK.NET_DVR_GET_PTZPOS;
import static com.zhehekeji.web.lib.hik.HCNetSDK.NET_DVR_SET_PTZPOS;
/** /**
* @Description plc * @Description plc
@ -628,6 +642,7 @@ public class PlcService {
@Resource @Resource
private LightSourceMapper lightSourceMapper; private LightSourceMapper lightSourceMapper;
Lock lock = new ReentrantLock();
public Boolean check(PlcCmdInfo plcCmdInfo,String cmdCode,String wmsCode,String wmsTrayCode,String wmsCatagary){ public Boolean check(PlcCmdInfo plcCmdInfo,String cmdCode,String wmsCode,String wmsTrayCode,String wmsCatagary){
@ -636,40 +651,37 @@ public class PlcService {
//CronTab.putTime(street.getId()); //CronTab.putTime(street.getId());
List<LightSource> lightSources = lightSourceMapper.selectList(new QueryWrapper<LightSource>().eq("street_id",street.getId())); List<LightSource> lightSources = lightSourceMapper.selectList(new QueryWrapper<LightSource>().eq("street_id",street.getId()));
lightSources.forEach(lightSource -> { lightSources.forEach(lightSource -> {
HikControlSocket.openLight(lightSource.getIp(),lightSource.getPort(),configProperties.getLightSource().getIndex(),1); lightSourceService.controllerLightSource(lightSource,1);
}); });
//南通通威拍摄货物顶部时按列号的单双来判断单数左侧 //南通通威拍摄货物顶部时按列号的单双来判断单数左侧
Integer cameraId = getCameraByPlcCmd(plcCmdInfo,plcCmdInfo.getColumn1()%2==1?1:2); //Integer cameraId = getCameraByPlcCmd(plcCmdInfo,plcCmdInfo.getColumn1()%2==1?1:2);
//对侧拍摄二维码 //对侧拍摄二维码
Integer cameraIdQt = getCameraByPlcCmd(plcCmdInfo, plcCmdInfo.getLeftRight1() == 1 ? 2 : 1); Integer cameraIdQt = getCameraByPlcCmd(plcCmdInfo, plcCmdInfo.getLeftRight1() == 1 ? 2 : 1);
gyrateCameraByCode(cameraId, "E1-Len"); gyrateCameraByCode(cameraIdQt, "E1");
//球机拍照
String path = PathUtil.createFileNameByRowColumn("jpg",cameraId,plcCmdInfo.getRow1(),plcCmdInfo.getColumn1());
//拍照暂停1s再拍,拍摄正面的二维码
try { try {
Thread.sleep(configProperties.getCameraConfig().getEDelayCaptureTime()); Thread.sleep(3000);
} catch (InterruptedException e) { } catch (InterruptedException e) {
e.printStackTrace(); throw new RuntimeException(e);
}
cameraCapture(cameraId,false,null,path);
//成都蜜雪冰城 只拍照人工核对
gyrateCameraByCode(cameraIdQt, "E1-QRCode");
try {
Thread.sleep(configProperties.getCameraConfig().getEDelayCaptureTime());
} catch (InterruptedException e) {
e.printStackTrace();
} }
cameraCapture(cameraIdQt,false,null,path+".jpg");
String path = PathUtil.createFileNameByRowColumn("jpg",cameraIdQt,plcCmdInfo.getRow1(),plcCmdInfo.getColumn1());
//拍照识别一维码后,保存图片
String code = blinkGetCode(cameraIdQt,path);
OrderInfo orderInfo = new OrderInfo(street,plcCmdInfo,1,cmdCode); OrderInfo orderInfo = new OrderInfo(street,plcCmdInfo,1,cmdCode);
Stock stock = stockMapper.getByStreetAndDirectionAndSideAndRowColumn(orderInfo.getStreetId(),orderInfo.getLeftRight(),orderInfo.getSeparation(),orderInfo.getRow(),orderInfo.getColumn()); Stock stock = stockMapper.getByStreetAndDirectionAndSideAndRowColumn(orderInfo.getStreetId(),orderInfo.getLeftRight(),orderInfo.getSeparation(),orderInfo.getRow(),orderInfo.getColumn());
//核对异常 //核对异常
int codeIsRight = !"".equals(code)?2:1;
if(stock == null){ if(stock == null){
stock = Stock.builder() stock = Stock.builder()
.checkNum(plcCmdInfo.getOrderNum()) .checkNum(plcCmdInfo.getOrderNum())
.lotnum(plcCmdInfo.getLotnum()) .lotnum(plcCmdInfo.getLotnum())
.code("") .code(code)
.wmsCode(wmsCode) .wmsCode(wmsCode)
.wmsCategory(wmsCatagary) .wmsCategory(wmsCatagary)
.wmsTrayCode(wmsTrayCode) .wmsTrayCode(wmsTrayCode)
@ -679,14 +691,14 @@ public class PlcService {
.side(orderInfo.getSeparation()) .side(orderInfo.getSeparation())
.row(orderInfo.getRow()) .row(orderInfo.getRow())
.column(orderInfo.getColumn()) .column(orderInfo.getColumn())
.status(0) .status(codeIsRight)
.checkPic(path) .checkPic(path)
.exportTime(LocalDateTime.now()) .exportTime(LocalDateTime.now())
.build(); .build();
stockMapper.insert(stock); stockMapper.insert(stock);
log.info("stockmapper insert new stock info."); log.info("stockmapper insert new stock info.");
}else { }else {
stock.setStatus(0); stock.setStatus(codeIsRight);
stock.setLotnum(plcCmdInfo.getLotnum()); stock.setLotnum(plcCmdInfo.getLotnum());
stock.setExportTime(LocalDateTime.now()); stock.setExportTime(LocalDateTime.now());
stock.setCheckPic(path); stock.setCheckPic(path);
@ -695,7 +707,7 @@ public class PlcService {
stock.setWmsTrayCode(wmsTrayCode); stock.setWmsTrayCode(wmsTrayCode);
stock.setWmsCategory(wmsCatagary); stock.setWmsCategory(wmsCatagary);
stock.setCategory(wmsCatagary); stock.setCategory(wmsCatagary);
stock.setCode(wmsTrayCode); stock.setCode(code);
//stock.setCode(scanCode); //stock.setCode(scanCode);
stock.setWmsCode(wmsCode); stock.setWmsCode(wmsCode);
stockMapper.updateById(stock); stockMapper.updateById(stock);
@ -708,15 +720,15 @@ public class PlcService {
long s = end - startTime; long s = end - startTime;
//发送图片触发拍照和id //发送图片触发拍照和id
//增加到队列中 // //增加到队列中
TransmissionPojo transmissionPojo = TransmissionPojo.builder() // TransmissionPojo transmissionPojo = TransmissionPojo.builder()
.ip(street.getPlcIp()) // .ip(street.getPlcIp())
.streetNumber(street.getPlcId()) // .streetNumber(street.getPlcId())
.direction(stock.getDirection()) // .direction(stock.getDirection())
.id(stock.getCheckNum()) // .id(stock.getCheckNum())
.localFilePath(configProperties.getSavePath().getMediaPath() + path) // .localFilePath(configProperties.getSavePath().getMediaPath() + path)
.build(); // .build();
GetPhotoDelayExecutor.addDelayTask(transmissionPojo,15000l); // GetPhotoDelayExecutor.addDelayTask(transmissionPojo,15000l);
@ -724,6 +736,69 @@ public class PlcService {
return true; return true;
} }
String blinkGetCode(Integer cameraIdQt ,String path){
String workPath = "work\\1.jpg";
IntByReference intByReference = new IntByReference(1);
HCNetSDK.NET_DVR_PTZPOS struPtTZPos = new HCNetSDK.NET_DVR_PTZPOS();
String code = "";
for (int i=0;i<=3;i++){
cameraCapture(cameraIdQt,false,null,workPath);
//交予灵闪识别
HashMap<String,String> stringMap = new HashMap<>();
stringMap.put("code","");
stringMap.put("location","");
code = CodeService.readOCR("127.0.0.1",9040,stringMap);
if (code!=null&& !"".equals(code)){
break;
}
//调整位置
boolean b_GetPTZ = HikLoginModuleImpl.hcNetsdk.NET_DVR_GetDVRConfig( CameraConnMap.getConnId(cameraIdQt).intValue(), NET_DVR_GET_PTZPOS, 1,struPtTZPos.getPointer(), struPtTZPos.size(),intByReference);
if (b_GetPTZ==false){
System.out.println("获取PTZ坐标信息失败错误码" + HikLoginModuleImpl.hcNetsdk.NET_DVR_GetLastError());
}else {
System.out.println("获取PTZ坐标信息成功");
struPtTZPos.read();
}
struPtTZPos.wAction = 1;
//水平
struPtTZPos.wPanPos = (short) (struPtTZPos.wPanPos+0x10);
//垂直
struPtTZPos.wTiltPos = (short) (struPtTZPos.wTiltPos+0x10);
//struPtTZPos.wZoomPos = 0x0150;不进行倍数调整
struPtTZPos.write();
boolean flag = HikLoginModuleImpl.hcNetsdk.NET_DVR_SetDVRConfig( CameraConnMap.getConnId(cameraIdQt).intValue(), NET_DVR_SET_PTZPOS, 1,struPtTZPos.getPointer(), struPtTZPos.size());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
}
//保存图片到指定为止
String sourceFile = configProperties.getSavePath().getMediaPath()+ workPath;
String destinationFile = configProperties.getSavePath().getMediaPath()+ path;
Path sourcePath = Paths.get(sourceFile);
Path destinationPath = Paths.get(destinationFile);
try {
// 创建父目录
Files.createDirectories(destinationPath.getParent());
Files.copy(sourcePath, destinationPath);
System.out.println("文件复制成功");
} catch (IOException e) {
e.printStackTrace();
}
return code;
}
//获取旧数据并发送给上位机 //获取旧数据并发送给上位机
public KsecInfo getKsecDataInfo(TransmissionPojo transmissionPojo, String type){ public KsecInfo getKsecDataInfo(TransmissionPojo transmissionPojo, String type){

@ -0,0 +1,125 @@
package com.zhehekeji.web.service.Queue;
import com.zhehekeji.common.util.SpringContextUtil;
import com.zhehekeji.web.lib.CameraControlModule;
import com.zhehekeji.web.lib.CameraDelayTask;
import com.zhehekeji.web.lib.TaskDelayExecutor;
import java.time.LocalDateTime;
import java.util.concurrent.*;
public class SingleThreadQueueWithTimeout {
private static ExecutorService exec = Executors.newFixedThreadPool(1);
class Task implements Delayed{
@Override
public long getDelay(TimeUnit unit) {
return 0;
}
@Override
public int compareTo(Delayed o) {
return 0;
}
}
private static DelayQueue<CameraDelayTask> queue = new DelayQueue<>();
public static void addMp4DelayTask(Integer cameraId, String path, LocalDateTime startTime, LocalDateTime endTime, Long delayTime) {
CameraDelayTask cameraDelayTask = new CameraDelayTask(cameraId, startTime, endTime,path, 0,delayTime);
queue.add(cameraDelayTask);
}
public static void addPicDelayTask(Integer cameraId, String path, Long delayTime) {
CameraDelayTask cameraDelayTask = new CameraDelayTask(cameraId, null, null,path, 1,delayTime);
queue.add(cameraDelayTask);
}
public static void addGyrateCameraTask(Integer cameraId, Long delayTime,Integer ptzId){
CameraDelayTask cameraDelayTask = new CameraDelayTask(cameraId, null, null,null, 2,delayTime);
cameraDelayTask.setPtzId(ptzId);
queue.add(cameraDelayTask);
}
public static void runMp4DownloadExecutor(){
exec.execute(new SingleThreadQueueWithTimeout.Consumer());
}
private static class Consumer implements Runnable {
@Override
public void run() {
while (true) {
try {
CameraControlModule cameraControlModule = SpringContextUtil.getBean(CameraControlModule.class);
CameraDelayTask cameraDelayTask = queue.take();
if(cameraDelayTask != null){
if(cameraDelayTask.getType() == 0){
cameraControlModule.downloadMp4(cameraDelayTask.getCameraId(), cameraDelayTask.getPath(), cameraDelayTask.getStartTime(), cameraDelayTask.getEndTime());
}else if(cameraDelayTask.getType() == 1){
cameraControlModule.pic(cameraDelayTask.getCameraId(),0, cameraDelayTask.getPath());
}else if(cameraDelayTask.getType() == 2){
cameraControlModule.toPtz(cameraDelayTask.getPtzId(),cameraDelayTask.getCameraId());
}
}
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
public static void main(String[] args) {
// 创建一个单线程的 ExecutorService
ExecutorService executorService = Executors.newSingleThreadExecutor();
// 创建一个 LinkedBlockingQueue 来存储任务
BlockingQueue<Runnable> queue = new LinkedBlockingQueue<>();
// 添加任务到队列
queue.add(() -> {
System.out.println("任务 1 开始执行");
try {
Thread.sleep(2000); // 模拟任务执行时间
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
System.out.println("任务 1 被中断");
}
System.out.println("任务 1 执行结束");
});
queue.add(() -> {
System.out.println("任务 2 开始执行");
try {
Thread.sleep(1000); // 模拟任务执行时间
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
System.out.println("任务 2 被中断");
}
System.out.println("任务 2 执行结束");
});
// 提交任务并设置超时处理
Future<?> future1 = executorService.submit(queue.poll());
Future<?> future2 = executorService.submit(queue.poll());
try {
// 设置超时时间
future1.get(3000, TimeUnit.MILLISECONDS);
future2.get(2000, TimeUnit.MILLISECONDS);
} catch (TimeoutException e) {
System.out.println("任务超时");
future1.cancel(true); // 取消任务
future2.cancel(true); // 取消任务
} catch (InterruptedException | ExecutionException e) {
e.printStackTrace();
} finally {
executorService.shutdown(); // 关闭 ExecutorService
}
}
}

@ -16,9 +16,7 @@ import org.springframework.util.StringUtils;
import java.nio.charset.Charset; import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
import java.util.concurrent.ArrayBlockingQueue; import java.util.concurrent.*;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
/** /**
* TCP JSON * TCP JSON
@ -119,7 +117,11 @@ public class KsecDecoder extends DelimiterBasedFrameDecoder {
} else if (Cmd.B2.name().equals(cmdName)) { } else if (Cmd.B2.name().equals(cmdName)) {
//B2 C4 一起发的需要停止等B2 //B2 C4 一起发的需要停止等B2
try {
plcService.action(plcCmdInfo, 4, "C4"+ "-" + plcCmdInfo.getLeftRightStr(4) + plcCmdInfo.getInOutStr(4));
} catch (InterruptedException e) {
e.printStackTrace();
}
//这里判断是不是双伸 //这里判断是不是双伸
if(plcCmdInfo.getSeparation2() == 2){ if(plcCmdInfo.getSeparation2() == 2){
//深测货架延迟 //深测货架延迟
@ -194,14 +196,41 @@ public class KsecDecoder extends DelimiterBasedFrameDecoder {
//转球机到盘点位 然后拍照 //转球机到盘点位 然后拍照
plcCmdInfo.setTimes(1); plcCmdInfo.setTimes(1);
//成都蜜雪冰城 将lotnum当成托盘条码描述 //成都蜜雪冰城 将lotnum当成托盘条码描述
Boolean ok = plcService.check(plcCmdInfo,ksecInfo.getData().getCmdName(), dataInfo.getCode(), dataInfo.getTrayCode(), dataInfo.getLotnum()); //Boolean ok = plcService.check(plcCmdInfo,ksecInfo.getData().getCmdName(), dataInfo.getCode(), dataInfo.getTrayCode(), dataInfo.getLotnum());
// Boolean ok = true; // Boolean ok = true;
if(ok){
ksecInfo.getData().setAckStatus(1); // 提交一个可调用任务
}else { PlcCmdInfo finalPlcCmdInfo = plcCmdInfo;
ksecInfo.getData().setAckStatus(0); Future<Boolean> future = threadPoolExecutor.submit(new Callable<Boolean>() {
@Override
public Boolean call() throws Exception {
Boolean ok = plcService.check(finalPlcCmdInfo,ksecInfo.getData().getCmdName(), dataInfo.getCode(), dataInfo.getTrayCode(), dataInfo.getLotnum());
return ok;
}
});
Boolean result=false;
try {
// 尝试在3秒内获取结果
result = future.get(5, TimeUnit.SECONDS);
System.out.println("任务完成: " + result);
} catch (TimeoutException e) {
System.out.println("任务超时,触发新方法");
// 触发新的方法
if (!result){
ksecInfo.getData().setAckStatus(0);
}else {
ksecInfo.getData().setAckStatus(1);
}
// 取消原任务,但允许其继续运行
future.cancel(false);
} catch (InterruptedException | ExecutionException e) {
e.printStackTrace();
}finally {
ctx.channel().writeAndFlush(ksecInfo);
} }
//ctx.channel().writeAndFlush(ksecInfo);
//log.info("盘点结束:"+ksecInfo.getData().toString()); //log.info("盘点结束:"+ksecInfo.getData().toString());
} }
//找到该货位的最后一张照片与现在的照片比照 //找到该货位的最后一张照片与现在的照片比照
@ -210,4 +239,5 @@ public class KsecDecoder extends DelimiterBasedFrameDecoder {
in.release(); in.release();
} }
} }
} }

Loading…
Cancel
Save