fix:线程阻塞问题处理2
This commit is contained in:
@@ -210,7 +210,6 @@ public class BeltConveyorDeviceDriver extends AbstractOpcDeviceDriver implements
|
|||||||
JSONObject led_message = null;
|
JSONObject led_message = null;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Device getDevice() {
|
public Device getDevice() {
|
||||||
return this.device;
|
return this.device;
|
||||||
@@ -245,7 +244,7 @@ public class BeltConveyorDeviceDriver extends AbstractOpcDeviceDriver implements
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (move != 0 && task > 0) {
|
if (move != 0 && task > 0) {
|
||||||
if (null!=inst) {
|
if (null != inst) {
|
||||||
inst_message = "指令号:" + inst.getInstruction_code() + " " + inst.getStart_point_code() + "->" + inst.getNext_point_code();
|
inst_message = "指令号:" + inst.getInstruction_code() + " " + inst.getStart_point_code() + "->" + inst.getNext_point_code();
|
||||||
}
|
}
|
||||||
CompletableFuture.runAsync(() -> {
|
CompletableFuture.runAsync(() -> {
|
||||||
@@ -261,7 +260,7 @@ public class BeltConveyorDeviceDriver extends AbstractOpcDeviceDriver implements
|
|||||||
if (mode == 8 && !requireSucess) {
|
if (mode == 8 && !requireSucess) {
|
||||||
if (container_type == 0) {
|
if (container_type == 0) {
|
||||||
message = "托盘类型为空";
|
message = "托盘类型为空";
|
||||||
}else {
|
} else {
|
||||||
applyEmptyTask(StorageTypeEnum.DISKS_OUT.getType(), mode);
|
applyEmptyTask(StorageTypeEnum.DISKS_OUT.getType(), mode);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -332,7 +331,7 @@ public class BeltConveyorDeviceDriver extends AbstractOpcDeviceDriver implements
|
|||||||
this.iserror = true;
|
this.iserror = true;
|
||||||
LuceneLogDto logDto = LuceneLogDto.builder()
|
LuceneLogDto logDto = LuceneLogDto.builder()
|
||||||
.device_code(device_code)
|
.device_code(device_code)
|
||||||
.content(this.device_code+ "读取信号值时出现异常:" + var17.getMessage() + ",this.itemProtocol is null")
|
.content(this.device_code + "读取信号值时出现异常:" + var17.getMessage() + ",this.itemProtocol is null")
|
||||||
.build();
|
.build();
|
||||||
logDto.setLog_level(4);
|
logDto.setLog_level(4);
|
||||||
luceneExecuteLogService.deviceExecuteLog(logDto);
|
luceneExecuteLogService.deviceExecuteLog(logDto);
|
||||||
@@ -493,7 +492,7 @@ public class BeltConveyorDeviceDriver extends AbstractOpcDeviceDriver implements
|
|||||||
} else {
|
} else {
|
||||||
//查看是否存在输送线到对接为的指令
|
//查看是否存在输送线到对接为的指令
|
||||||
Instruction byNextDeviceCodeFromCache = instructionService.findByNextDeviceCodeFromCache(this.device_code);
|
Instruction byNextDeviceCodeFromCache = instructionService.findByNextDeviceCodeFromCache(this.device_code);
|
||||||
if (ObjectUtil.isNotEmpty(byNextDeviceCodeFromCache)){
|
if (ObjectUtil.isNotEmpty(byNextDeviceCodeFromCache)) {
|
||||||
LuceneLogDto logDto = LuceneLogDto.builder()
|
LuceneLogDto logDto = LuceneLogDto.builder()
|
||||||
.device_code(device_code)
|
.device_code(device_code)
|
||||||
.content("存在堆垛机对接为的指令")
|
.content("存在堆垛机对接为的指令")
|
||||||
@@ -561,7 +560,7 @@ public class BeltConveyorDeviceDriver extends AbstractOpcDeviceDriver implements
|
|||||||
TaskDto taskdto = taskserver.findByStartCodeAndReady(device_code);
|
TaskDto taskdto = taskserver.findByStartCodeAndReady(device_code);
|
||||||
if (ObjectUtil.isNotNull(taskdto)) {
|
if (ObjectUtil.isNotNull(taskdto)) {
|
||||||
//移除行架任务
|
//移除行架任务
|
||||||
if (taskdto.getTask_type().equals(TaskTypeEnum.Truss_Task.getIndex())){
|
if (taskdto.getTask_type().equals(TaskTypeEnum.Truss_Task.getIndex())) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
//判断指令的起点和当前的设备号相同
|
//判断指令的起点和当前的设备号相同
|
||||||
|
|||||||
@@ -1,8 +1,12 @@
|
|||||||
package org.nl.acs.opc;
|
package org.nl.acs.opc;
|
||||||
|
|
||||||
|
import javax.annotation.Resource;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
import java.util.concurrent.ExecutorService;
|
||||||
|
import java.util.concurrent.Executors;
|
||||||
|
import java.util.concurrent.ThreadPoolExecutor;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author LENOVO
|
* @author LENOVO
|
||||||
@@ -11,6 +15,7 @@ public abstract class BlockedRunable implements Runnable {
|
|||||||
private String threadName;
|
private String threadName;
|
||||||
private Date startTime;
|
private Date startTime;
|
||||||
private Map<String, BlockedRunable> index = new HashMap();
|
private Map<String, BlockedRunable> index = new HashMap();
|
||||||
|
// ExecutorService executor = Executors.newSingleThreadExecutor();
|
||||||
|
|
||||||
public BlockedRunable() {
|
public BlockedRunable() {
|
||||||
}
|
}
|
||||||
@@ -25,6 +30,9 @@ public abstract class BlockedRunable implements Runnable {
|
|||||||
*/
|
*/
|
||||||
public abstract String getCode();
|
public abstract String getCode();
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* subRun
|
* subRun
|
||||||
* @throws Exception
|
* @throws Exception
|
||||||
|
|||||||
@@ -1,11 +1,14 @@
|
|||||||
package org.nl.acs.opc;
|
package org.nl.acs.opc;
|
||||||
|
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.dromara.dynamictp.core.DtpRegistry;
|
||||||
import org.nl.acs.auto.run.AbstractAutoRunnable;
|
import org.nl.acs.auto.run.AbstractAutoRunnable;
|
||||||
import org.nl.acs.auto.run.AutoRunService;
|
import org.nl.acs.auto.run.AutoRunService;
|
||||||
import org.nl.acs.device_driver.driver.ExecutableDeviceDriver;
|
import org.nl.acs.device_driver.driver.ExecutableDeviceDriver;
|
||||||
|
import org.nl.acs.instruction.service.InstructionService;
|
||||||
import org.nl.acs.udw.UnifiedDataAccessor;
|
import org.nl.acs.udw.UnifiedDataAccessor;
|
||||||
import org.nl.acs.udw.UnifiedDataAccessorFactory;
|
import org.nl.acs.udw.UnifiedDataAccessorFactory;
|
||||||
|
import org.nl.config.SpringContextHolder;
|
||||||
import org.nl.config.thread.TheadFactoryName;
|
import org.nl.config.thread.TheadFactoryName;
|
||||||
import org.nl.config.thread.ThreadPoolExecutorUtil;
|
import org.nl.config.thread.ThreadPoolExecutorUtil;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
@@ -38,6 +41,8 @@ public class DeviceExecuteAutoRun extends AbstractAutoRunnable {
|
|||||||
@Resource
|
@Resource
|
||||||
private ThreadPoolExecutor executorService;
|
private ThreadPoolExecutor executorService;
|
||||||
|
|
||||||
|
ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(30);
|
||||||
|
|
||||||
Map<String, BlockedRunable> runs;
|
Map<String, BlockedRunable> runs;
|
||||||
|
|
||||||
public DeviceExecuteAutoRun() {
|
public DeviceExecuteAutoRun() {
|
||||||
@@ -114,10 +119,35 @@ public class DeviceExecuteAutoRun extends AbstractAutoRunnable {
|
|||||||
//不包含正在执行的线程,则进行执行
|
//不包含正在执行的线程,则进行执行
|
||||||
if (!this.runs.keySet().contains(deviceDriver.getDeviceCode())) {
|
if (!this.runs.keySet().contains(deviceDriver.getDeviceCode())) {
|
||||||
BlockedRunable runnable = new BlockedRunable() {
|
BlockedRunable runnable = new BlockedRunable() {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void subRun() throws Exception {
|
public void subRun() throws Exception {
|
||||||
deviceDriver.executeAuto();
|
deviceDriver.executeAuto();
|
||||||
|
/* ThreadPoolExecutor executor= DtpRegistry.getDtpExecutor("dtpExecutor1");
|
||||||
|
|
||||||
|
Future<?> submit = executor.submit(() -> {
|
||||||
|
try {
|
||||||
|
deviceDriver.executeAuto();
|
||||||
|
} catch (Exception e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
try {
|
||||||
|
// 设置超时时间为 15 秒,如果任务超时,抛出 TimeoutException
|
||||||
|
submit.get(10, TimeUnit.SECONDS);
|
||||||
|
System.out.println();
|
||||||
|
} catch (TimeoutException e) {
|
||||||
|
System.out.println("任务超时,取消任务!");
|
||||||
|
// 使用反射获取 FutureTask 中的线程,并使用 Thread.stop() 强制终止
|
||||||
|
Field runnerField = submit.getClass().getDeclaredField("runner");
|
||||||
|
runnerField.setAccessible(true);
|
||||||
|
Thread runnerThread = (Thread) runnerField.get(submit);
|
||||||
|
if (runnerThread != null) {
|
||||||
|
runnerThread.stop(); // 强制终止线程(不推荐)
|
||||||
|
}
|
||||||
|
|
||||||
|
} catch (InterruptedException | ExecutionException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}*/
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -144,7 +174,7 @@ public class DeviceExecuteAutoRun extends AbstractAutoRunnable {
|
|||||||
|
|
||||||
|
|
||||||
//plc断连后强制终止线程
|
//plc断连后强制终止线程
|
||||||
try {
|
/* try {
|
||||||
// 设置超时时间为 15 秒,如果任务超时,抛出 TimeoutException
|
// 设置超时时间为 15 秒,如果任务超时,抛出 TimeoutException
|
||||||
future.get(15, TimeUnit.SECONDS);
|
future.get(15, TimeUnit.SECONDS);
|
||||||
} catch (TimeoutException e) {
|
} catch (TimeoutException e) {
|
||||||
@@ -159,7 +189,42 @@ public class DeviceExecuteAutoRun extends AbstractAutoRunnable {
|
|||||||
|
|
||||||
} catch (InterruptedException | ExecutionException e) {
|
} catch (InterruptedException | ExecutionException e) {
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}*/
|
||||||
|
|
||||||
|
// 使用调度器在超时后取消任务
|
||||||
|
scheduler.schedule(() -> {
|
||||||
|
if (!future.isDone()) {
|
||||||
|
|
||||||
|
// future.cancel(true); // 尝试中断任务
|
||||||
|
// Field runnerField = null;
|
||||||
|
// try {
|
||||||
|
// runnerField = future.getClass().getDeclaredField("runner");
|
||||||
|
// runnerField.setAccessible(true);
|
||||||
|
// Thread runnerThread = (Thread) runnerField.get(future);
|
||||||
|
// if (runnerThread != null) {
|
||||||
|
// runnerThread.stop(); // 强制终止线程(不推荐)
|
||||||
|
// }
|
||||||
|
// } catch (Exception e) {
|
||||||
|
// throw new RuntimeException(e);
|
||||||
|
// }
|
||||||
|
|
||||||
|
try {
|
||||||
|
// 设置超时时间为 30 秒,如果任务超时,抛出 TimeoutException
|
||||||
|
future.get(5, TimeUnit.SECONDS);
|
||||||
|
} catch (TimeoutException e) {
|
||||||
|
System.out.println("任务超时,取消任务!");
|
||||||
|
// 超时后取消任务,并设置为 true 以中断执行中的线程
|
||||||
|
future.cancel(true);
|
||||||
|
} catch (InterruptedException | ExecutionException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
}, 5, TimeUnit.SECONDS); // 设置超时时间为10秒
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import cn.hutool.core.date.DateUtil;
|
|||||||
import cn.hutool.core.date.TimeInterval;
|
import cn.hutool.core.date.TimeInterval;
|
||||||
import cn.hutool.core.util.NumberUtil;
|
import cn.hutool.core.util.NumberUtil;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.dromara.dynamictp.core.DtpRegistry;
|
||||||
import org.jinterop.dcom.common.JIException;
|
import org.jinterop.dcom.common.JIException;
|
||||||
import org.jinterop.dcom.core.*;
|
import org.jinterop.dcom.core.*;
|
||||||
import org.nl.acs.device_driver.driver.ItemValue;
|
import org.nl.acs.device_driver.driver.ItemValue;
|
||||||
@@ -13,11 +14,12 @@ import org.nl.config.language.LangProcess;
|
|||||||
import org.openscada.opc.lib.common.ConnectionInformation;
|
import org.openscada.opc.lib.common.ConnectionInformation;
|
||||||
import org.openscada.opc.lib.da.*;
|
import org.openscada.opc.lib.da.*;
|
||||||
|
|
||||||
|
import java.lang.reflect.Field;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Iterator;
|
import java.util.Iterator;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.concurrent.Executors;
|
import java.util.concurrent.*;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author 20220102CG\noblelift
|
* @author 20220102CG\noblelift
|
||||||
@@ -42,6 +44,7 @@ public class OpcUtl {
|
|||||||
public static void writeValue(Group group, WriteRequest... requests) throws BadRequestException {
|
public static void writeValue(Group group, WriteRequest... requests) throws BadRequestException {
|
||||||
try {
|
try {
|
||||||
Map<Item, Integer> e = null;
|
Map<Item, Integer> e = null;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
e = group.write(requests);
|
e = group.write(requests);
|
||||||
// group.write(requests);
|
// group.write(requests);
|
||||||
@@ -230,7 +233,8 @@ public class OpcUtl {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static Server getAutoServer(String host, String clsid, String user, String password, String domain) throws BadRequestException {
|
public static Server getAutoServer(String host, String clsid, String user, String password, String domain) throws
|
||||||
|
BadRequestException {
|
||||||
checkTimeout();
|
checkTimeout();
|
||||||
Server server = null;
|
Server server = null;
|
||||||
server = new Server(getConnection(host, clsid, user, password, domain), Executors.newSingleThreadScheduledExecutor());
|
server = new Server(getConnection(host, clsid, user, password, domain), Executors.newSingleThreadScheduledExecutor());
|
||||||
|
|||||||
Reference in New Issue
Block a user