20251220:授权码(TCP校验)& GB28181
This commit is contained in:
parent
c26f430924
commit
2c44850c38
@ -18,11 +18,11 @@
|
|||||||
<dependencies>
|
<dependencies>
|
||||||
|
|
||||||
<!-- spring-boot-devtools -->
|
<!-- spring-boot-devtools -->
|
||||||
<dependency>
|
<!-- <dependency>
|
||||||
<groupId>org.springframework.boot</groupId>
|
<groupId>org.springframework.boot</groupId>
|
||||||
<artifactId>spring-boot-devtools</artifactId>
|
<artifactId>spring-boot-devtools</artifactId>
|
||||||
<optional>true</optional> <!-- 表示依赖不会传递 -->
|
<optional>true</optional> <!– 表示依赖不会传递 –>
|
||||||
</dependency>
|
</dependency>-->
|
||||||
|
|
||||||
<!-- swagger3-->
|
<!-- swagger3-->
|
||||||
<dependency>
|
<dependency>
|
||||||
|
|||||||
@ -127,10 +127,10 @@ emqx:
|
|||||||
ApiSecret: emqx.api.123
|
ApiSecret: emqx.api.123
|
||||||
# sip 配置
|
# sip 配置
|
||||||
sip:
|
sip:
|
||||||
enabled: false # 是否启用视频监控SIP,true为启用
|
enabled: true # 是否启用视频监控SIP,true为启用
|
||||||
## 本地调试时,绑定网卡局域网IP,设备在同一局域网,设备接入IP填写绑定IP
|
## 本地调试时,绑定网卡局域网IP,设备在同一局域网,设备接入IP填写绑定IP
|
||||||
## 部署服务端时,默认绑定容器IP,设备接入IP填写服务器公网IP
|
## 部署服务端时,默认绑定容器IP,设备接入IP填写服务器公网IP
|
||||||
ip: localhost
|
ip: 192.168.110.78 # 本服务启动的 IP
|
||||||
port: 5061 # SIP端口(保持默认)
|
port: 5061 # SIP端口(保持默认)
|
||||||
domain: 3402000000 # 由省级、市级、区级、基层编号组成
|
domain: 3402000000 # 由省级、市级、区级、基层编号组成
|
||||||
id: 34020000002000000001 # 同上,另外增加编号,(可保持默认)
|
id: 34020000002000000001 # 同上,另外增加编号,(可保持默认)
|
||||||
|
|||||||
@ -129,7 +129,7 @@ sip:
|
|||||||
enabled: true # 是否启用视频监控SIP,true为启用
|
enabled: true # 是否启用视频监控SIP,true为启用
|
||||||
## 本地调试时,绑定网卡局域网IP,设备在同一局域网,设备接入IP填写绑定IP
|
## 本地调试时,绑定网卡局域网IP,设备在同一局域网,设备接入IP填写绑定IP
|
||||||
## 部署服务端时,默认绑定容器IP,设备接入IP填写服务器公网IP
|
## 部署服务端时,默认绑定容器IP,设备接入IP填写服务器公网IP
|
||||||
ip: 177.7.0.13
|
ip: 177.7.0.13 # 容器部署容器IP:177.7.0.13;云服务器部署写公网IP;本地部署127.0.0.1;总原则:能被摄像机访问的地址
|
||||||
port: 5061 # SIP端口(保持默认)
|
port: 5061 # SIP端口(保持默认)
|
||||||
domain: 3402000000 # 由省级、市级、区级、基层编号组成
|
domain: 3402000000 # 由省级、市级、区级、基层编号组成
|
||||||
id: 34020000002000000001 # 同上,另外增加编号,(可保持默认)
|
id: 34020000002000000001 # 同上,另外增加编号,(可保持默认)
|
||||||
|
|||||||
@ -66,9 +66,9 @@ spring:
|
|||||||
max-file-size: 10MB # 单个文件大小
|
max-file-size: 10MB # 单个文件大小
|
||||||
max-request-size: 20MB # 设置总上传的文件大小
|
max-request-size: 20MB # 设置总上传的文件大小
|
||||||
# 服务模块
|
# 服务模块
|
||||||
devtools:
|
# devtools:
|
||||||
restart:
|
# restart:
|
||||||
enabled: true # 热部署开关
|
# enabled: true # 热部署开关
|
||||||
task:
|
task:
|
||||||
execution:
|
execution:
|
||||||
pool:
|
pool:
|
||||||
|
|||||||
@ -2,8 +2,8 @@
|
|||||||
<configuration>
|
<configuration>
|
||||||
<!-- 日志存放路径 -->
|
<!-- 日志存放路径 -->
|
||||||
<property name="log.path" scope="context" value="./logs"/>
|
<property name="log.path" scope="context" value="./logs"/>
|
||||||
<!-- 日志输出格式 -->
|
<!-- 日志输出格式,添加TraceId -->
|
||||||
<property name="log.pattern" value="%d{HH:mm:ss.SSS} [%thread] %-5level %class - [%method,%line] - %msg%n"/>
|
<property name="log.pattern" value="%d{HH:mm:ss.SSS} [%thread] [%X{traceId}] %-5level %class - [%method,%line] - %msg%n"/>
|
||||||
|
|
||||||
<!-- 控制台输出 -->
|
<!-- 控制台输出 -->
|
||||||
<appender name="console" class="ch.qos.logback.core.ConsoleAppender">
|
<appender name="console" class="ch.qos.logback.core.ConsoleAppender">
|
||||||
|
|||||||
@ -0,0 +1,108 @@
|
|||||||
|
package com.fastbee.common.utils;
|
||||||
|
|
||||||
|
import com.fastbee.common.utils.uuid.IdUtils;
|
||||||
|
import org.slf4j.MDC;
|
||||||
|
|
||||||
|
import java.util.concurrent.ThreadLocalRandom;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 日志追踪ID工具类
|
||||||
|
* 统一生成TraceId的逻辑,使用IdWorker和ThreadLocalRandom
|
||||||
|
*
|
||||||
|
* @author fastbee
|
||||||
|
*/
|
||||||
|
public class TraceIdUtils {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* TraceId在MDC中的key
|
||||||
|
*/
|
||||||
|
public static final String TRACE_ID_KEY = "traceId";
|
||||||
|
|
||||||
|
/**
|
||||||
|
* IdWorker实例(单例模式)
|
||||||
|
*/
|
||||||
|
private static volatile IdUtils idWorker;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取IdWorker实例(懒加载单例)
|
||||||
|
*
|
||||||
|
* @return IdWorker实例
|
||||||
|
*/
|
||||||
|
private static IdUtils getIdWorker() {
|
||||||
|
if (idWorker == null) {
|
||||||
|
synchronized (TraceIdUtils.class) {
|
||||||
|
if (idWorker == null) {
|
||||||
|
// 使用机器ID,可以根据实际情况配置
|
||||||
|
// 这里使用1作为默认workerId,可以通过配置文件读取
|
||||||
|
// IdUtils构造函数:workerId, datacenterId,-1表示随机生成
|
||||||
|
idWorker = new IdUtils(-1L, -1L);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return idWorker;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 生成TraceId
|
||||||
|
* 格式:IdWorker.nextId() * 1000 + ThreadLocalRandom.nextInt(1000)
|
||||||
|
* 参考:generateClueId() 的实现方式
|
||||||
|
* 使用Math.abs确保TraceId为正数
|
||||||
|
*
|
||||||
|
* @return TraceId
|
||||||
|
*/
|
||||||
|
public static long generateTraceId() {
|
||||||
|
long id = getIdWorker().nextId();
|
||||||
|
// 使用绝对值确保TraceId为正数,避免负数显示
|
||||||
|
long traceId = Math.abs(id) * 1000 + ThreadLocalRandom.current().nextInt(1000);
|
||||||
|
MDC.put(TRACE_ID_KEY, String.valueOf(traceId));
|
||||||
|
return traceId;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 生成TraceId并放入MDC
|
||||||
|
* 返回字符串格式的TraceId
|
||||||
|
*
|
||||||
|
* @return TraceId字符串
|
||||||
|
*/
|
||||||
|
public static String generateTraceIdString() {
|
||||||
|
long traceId = generateTraceId();
|
||||||
|
return String.valueOf(traceId);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 设置TraceId到MDC
|
||||||
|
*
|
||||||
|
* @param traceId TraceId
|
||||||
|
*/
|
||||||
|
public static void setTraceId(String traceId) {
|
||||||
|
if (traceId != null && !traceId.isEmpty()) {
|
||||||
|
MDC.put(TRACE_ID_KEY, traceId);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 设置TraceId到MDC(long类型)
|
||||||
|
*
|
||||||
|
* @param traceId TraceId
|
||||||
|
*/
|
||||||
|
public static void setTraceId(long traceId) {
|
||||||
|
MDC.put(TRACE_ID_KEY, String.valueOf(traceId));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 从MDC获取TraceId
|
||||||
|
*
|
||||||
|
* @return TraceId
|
||||||
|
*/
|
||||||
|
public static String getTraceId() {
|
||||||
|
return MDC.get(TRACE_ID_KEY);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 清除MDC中的TraceId
|
||||||
|
*/
|
||||||
|
public static void clearTraceId() {
|
||||||
|
MDC.remove(TRACE_ID_KEY);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@ -3,6 +3,7 @@ package com.fastbee.framework.config;
|
|||||||
import java.util.concurrent.TimeUnit;
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
import com.fastbee.framework.interceptor.LanguageInterceptor;
|
import com.fastbee.framework.interceptor.LanguageInterceptor;
|
||||||
|
import com.fastbee.framework.interceptor.TraceIdInterceptor;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
import org.springframework.context.annotation.Bean;
|
import org.springframework.context.annotation.Bean;
|
||||||
import org.springframework.context.annotation.Configuration;
|
import org.springframework.context.annotation.Configuration;
|
||||||
@ -31,6 +32,8 @@ public class ResourcesConfig implements WebMvcConfigurer
|
|||||||
private RepeatSubmitInterceptor repeatSubmitInterceptor;
|
private RepeatSubmitInterceptor repeatSubmitInterceptor;
|
||||||
@Resource
|
@Resource
|
||||||
private LanguageInterceptor languageInterceptor;
|
private LanguageInterceptor languageInterceptor;
|
||||||
|
@Autowired
|
||||||
|
private TraceIdInterceptor traceIdInterceptor;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void addResourceHandlers(ResourceHandlerRegistry registry)
|
public void addResourceHandlers(ResourceHandlerRegistry registry)
|
||||||
@ -51,6 +54,8 @@ public class ResourcesConfig implements WebMvcConfigurer
|
|||||||
@Override
|
@Override
|
||||||
public void addInterceptors(InterceptorRegistry registry)
|
public void addInterceptors(InterceptorRegistry registry)
|
||||||
{
|
{
|
||||||
|
// TraceId拦截器放在最前面,确保所有请求都有TraceId
|
||||||
|
registry.addInterceptor(traceIdInterceptor).addPathPatterns("/**").order(0);
|
||||||
registry.addInterceptor(repeatSubmitInterceptor).addPathPatterns("/**");
|
registry.addInterceptor(repeatSubmitInterceptor).addPathPatterns("/**");
|
||||||
//这里配置国际化拦截器的白名单
|
//这里配置国际化拦截器的白名单
|
||||||
registry.addInterceptor(languageInterceptor).addPathPatterns("/**").excludePathPatterns("/v2/api-docs",
|
registry.addInterceptor(languageInterceptor).addPathPatterns("/**").excludePathPatterns("/v2/api-docs",
|
||||||
|
|||||||
@ -0,0 +1,51 @@
|
|||||||
|
package com.fastbee.framework.interceptor;
|
||||||
|
|
||||||
|
import com.fastbee.common.utils.TraceIdUtils;
|
||||||
|
import org.springframework.stereotype.Component;
|
||||||
|
import org.springframework.web.servlet.HandlerInterceptor;
|
||||||
|
|
||||||
|
import javax.servlet.http.HttpServletRequest;
|
||||||
|
import javax.servlet.http.HttpServletResponse;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 日志追踪ID拦截器
|
||||||
|
* 用于生成和传递TraceId,方便同一个链路调用追查问题
|
||||||
|
*
|
||||||
|
* @author fastbee
|
||||||
|
*/
|
||||||
|
@Component
|
||||||
|
public class TraceIdInterceptor implements HandlerInterceptor {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
|
||||||
|
// 获取请求URI
|
||||||
|
String requestURI = request.getRequestURI();
|
||||||
|
|
||||||
|
// 尝试从请求头中获取TraceId(支持分布式追踪)
|
||||||
|
String traceId = request.getHeader("X-Trace-Id");
|
||||||
|
|
||||||
|
// 如果请求头中没有TraceId,则生成一个新的
|
||||||
|
if (traceId == null || traceId.isEmpty()) {
|
||||||
|
traceId = TraceIdUtils.generateTraceIdString();
|
||||||
|
} else {
|
||||||
|
// 如果请求头中有TraceId,设置到MDC
|
||||||
|
TraceIdUtils.setTraceId(traceId);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 将TraceId放入响应头,方便前端获取
|
||||||
|
response.setHeader("X-Trace-Id", traceId);
|
||||||
|
|
||||||
|
// 打印请求路径日志
|
||||||
|
org.slf4j.Logger log = org.slf4j.LoggerFactory.getLogger(TraceIdInterceptor.class);
|
||||||
|
log.info("拦截请求路径: {}", requestURI);
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
|
||||||
|
// 请求完成后清除MDC中的TraceId,避免内存泄漏
|
||||||
|
TraceIdUtils.clearTraceId();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@ -16,6 +16,9 @@ import com.fastbee.iot.domain.Device;
|
|||||||
import com.fastbee.iot.domain.DeviceLog;
|
import com.fastbee.iot.domain.DeviceLog;
|
||||||
import com.fastbee.iot.service.IDeviceService;
|
import com.fastbee.iot.service.IDeviceService;
|
||||||
import com.fastbee.iot.service.IProductService;
|
import com.fastbee.iot.service.IProductService;
|
||||||
|
import com.fastbee.iot.service.IProductAuthorizeService;
|
||||||
|
import com.fastbee.iot.domain.ProductAuthorize;
|
||||||
|
import com.fastbee.iot.domain.Product;
|
||||||
import com.fastbee.iot.tdengine.service.ILogService;
|
import com.fastbee.iot.tdengine.service.ILogService;
|
||||||
import com.fastbee.mqtt.manager.MqttRemoteManager;
|
import com.fastbee.mqtt.manager.MqttRemoteManager;
|
||||||
import com.fastbee.mqtt.model.PushMessageBo;
|
import com.fastbee.mqtt.model.PushMessageBo;
|
||||||
@ -33,6 +36,7 @@ import javax.annotation.Resource;
|
|||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Objects;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 设备调试错误日志AOP切面
|
* 设备调试错误日志AOP切面
|
||||||
@ -63,6 +67,9 @@ public class DeviceDebugLogAspect {
|
|||||||
@Resource
|
@Resource
|
||||||
private IProductService productService;
|
private IProductService productService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private IProductAuthorizeService productAuthorizeService;
|
||||||
|
|
||||||
@Resource
|
@Resource
|
||||||
private MqttRemoteManager mqttRemoteManager;
|
private MqttRemoteManager mqttRemoteManager;
|
||||||
|
|
||||||
@ -127,8 +134,7 @@ public class DeviceDebugLogAspect {
|
|||||||
String protocolCode = bo.getProtocolCode();
|
String protocolCode = bo.getProtocolCode();
|
||||||
Long productId = bo.getProductId();
|
Long productId = bo.getProductId();
|
||||||
|
|
||||||
saveErrorLog(serialNumber, sourceData, errorMsg, protocolCode, bo.getTopicName(),
|
saveErrorLog(serialNumber, sourceData, errorMsg, DeviceLogTypeEnum.DATA_PARSE_ERROR.getType(), "DEBUG_ERROR", productId);
|
||||||
DeviceLogTypeEnum.DATA_PARSE_ERROR.getType(), "DEBUG_ERROR", productId);
|
|
||||||
}
|
}
|
||||||
} catch (Exception ex) {
|
} catch (Exception ex) {
|
||||||
log.error("记录数据解析错误日志失败: {}", ex.getMessage(), ex);
|
log.error("记录数据解析错误日志失败: {}", ex.getMessage(), ex);
|
||||||
@ -186,7 +192,7 @@ public class DeviceDebugLogAspect {
|
|||||||
String protocolCode = getProtocolCodeBySerialNumber(serialNumber);
|
String protocolCode = getProtocolCodeBySerialNumber(serialNumber);
|
||||||
Long productId = getProductIdBySerialNumber(serialNumber);
|
Long productId = getProductIdBySerialNumber(serialNumber);
|
||||||
|
|
||||||
saveErrorLog(serialNumber, sourceData, errorMsg, protocolCode, deviceMessage.getTopicName(),
|
saveErrorLog(serialNumber, sourceData, errorMsg,
|
||||||
DeviceLogTypeEnum.COMMAND_SEND_ERROR.getType(), "SEND_ERROR", productId);
|
DeviceLogTypeEnum.COMMAND_SEND_ERROR.getType(), "SEND_ERROR", productId);
|
||||||
}
|
}
|
||||||
} catch (Exception ex) {
|
} catch (Exception ex) {
|
||||||
@ -242,7 +248,7 @@ public class DeviceDebugLogAspect {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// 协议解析错误也归类为数据解析错误
|
// 协议解析错误也归类为数据解析错误
|
||||||
saveErrorLog(serialNumber, sourceData, errorMsg, protocolCode, deviceData.getTopicName(),
|
saveErrorLog(serialNumber, sourceData, errorMsg,
|
||||||
DeviceLogTypeEnum.DATA_PARSE_ERROR.getType(), "PARSE_ERROR", productId);
|
DeviceLogTypeEnum.DATA_PARSE_ERROR.getType(), "PARSE_ERROR", productId);
|
||||||
}
|
}
|
||||||
} catch (Exception ex) {
|
} catch (Exception ex) {
|
||||||
@ -299,7 +305,7 @@ public class DeviceDebugLogAspect {
|
|||||||
* 保存错误日志到iot_device_log表,并推送到前端页面
|
* 保存错误日志到iot_device_log表,并推送到前端页面
|
||||||
*/
|
*/
|
||||||
private void saveErrorLog(String serialNumber, String sourceData, String errorMsg,
|
private void saveErrorLog(String serialNumber, String sourceData, String errorMsg,
|
||||||
String protocolCode, String topicName, Integer logType, String identity, Long productId) {
|
Integer logType, String identity, Long productId) {
|
||||||
try {
|
try {
|
||||||
if (StringUtils.isEmpty(serialNumber)) {
|
if (StringUtils.isEmpty(serialNumber)) {
|
||||||
log.warn("设备编号为空,无法保存错误日志");
|
log.warn("设备编号为空,无法保存错误日志");
|
||||||
@ -327,6 +333,27 @@ public class DeviceDebugLogAspect {
|
|||||||
productId = getProductIdBySerialNumber(serialNumber);
|
productId = getProductIdBySerialNumber(serialNumber);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 授权码校验:如果产品开启了授权码,但设备未绑定授权码,不记录日志也不推送消息
|
||||||
|
if (productId != null) {
|
||||||
|
try {
|
||||||
|
Product product = productService.selectProductByProductId(productId);
|
||||||
|
if (product != null && product.getIsAuthorize() != null && product.getIsAuthorize() == 1) {
|
||||||
|
// 产品开启了授权码,检查设备是否绑定了授权码
|
||||||
|
ProductAuthorize queryParam = new ProductAuthorize();
|
||||||
|
queryParam.setProductId(productId);
|
||||||
|
queryParam.setSerialNumber(serialNumber);
|
||||||
|
java.util.List<ProductAuthorize> authorizeList = productAuthorizeService.selectProductAuthorizeList(queryParam);
|
||||||
|
if (authorizeList == null || authorizeList.isEmpty()) {
|
||||||
|
log.debug("设备[{}]未绑定授权码,跳过错误日志记录和消息推送", serialNumber);
|
||||||
|
return; // 不记录日志,也不推送消息
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (Exception ex) {
|
||||||
|
log.warn("授权码校验失败: {}, 设备编号: {}, 继续记录日志", ex.getMessage(), serialNumber);
|
||||||
|
// 校验失败时继续记录日志,避免影响正常功能
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
DeviceLog deviceLog = new DeviceLog();
|
DeviceLog deviceLog = new DeviceLog();
|
||||||
deviceLog.setSerialNumber(serialNumber);
|
deviceLog.setSerialNumber(serialNumber);
|
||||||
deviceLog.setDeviceId(device.getDeviceId());
|
deviceLog.setDeviceId(device.getDeviceId());
|
||||||
@ -337,7 +364,7 @@ public class DeviceDebugLogAspect {
|
|||||||
// 存储错误信息(限制500字符)
|
// 存储错误信息(限制500字符)
|
||||||
deviceLog.setRemark(StringUtils.substring(errorMsg, 0, 500));
|
deviceLog.setRemark(StringUtils.substring(errorMsg, 0, 500));
|
||||||
deviceLog.setIdentity(identity);
|
deviceLog.setIdentity(identity);
|
||||||
deviceLog.setModelName(logType == DeviceLogTypeEnum.DATA_PARSE_ERROR.getType() ?
|
deviceLog.setModelName(Objects.equals(logType, DeviceLogTypeEnum.DATA_PARSE_ERROR.getType()) ?
|
||||||
"数据解析错误" : "指令发送错误");
|
"数据解析错误" : "指令发送错误");
|
||||||
deviceLog.setCreateTime(DateUtils.getNowDate());
|
deviceLog.setCreateTime(DateUtils.getNowDate());
|
||||||
deviceLog.setUserId(device.getTenantId());
|
deviceLog.setUserId(device.getTenantId());
|
||||||
@ -374,7 +401,7 @@ public class DeviceDebugLogAspect {
|
|||||||
List<ThingsModelSimpleItem> errorItems = new ArrayList<>();
|
List<ThingsModelSimpleItem> errorItems = new ArrayList<>();
|
||||||
ThingsModelSimpleItem errorItem = new ThingsModelSimpleItem();
|
ThingsModelSimpleItem errorItem = new ThingsModelSimpleItem();
|
||||||
errorItem.setId("ERROR_" + identity);
|
errorItem.setId("ERROR_" + identity);
|
||||||
errorItem.setName(logType == DeviceLogTypeEnum.DATA_PARSE_ERROR.getType() ? "数据解析错误" : "指令发送错误");
|
errorItem.setName(Objects.equals(logType, DeviceLogTypeEnum.DATA_PARSE_ERROR.getType()) ? "数据解析错误" : "指令发送错误");
|
||||||
errorItem.setValue(errorMsg);
|
errorItem.setValue(errorMsg);
|
||||||
errorItem.setRemark(errorMsg);
|
errorItem.setRemark(errorMsg);
|
||||||
errorItem.setTs(new Date());
|
errorItem.setTs(new Date());
|
||||||
|
|||||||
@ -9,6 +9,7 @@ import com.fastbee.common.utils.spring.SpringUtils;
|
|||||||
import com.fastbee.iot.domain.DeviceJob;
|
import com.fastbee.iot.domain.DeviceJob;
|
||||||
import com.fastbee.quartz.domain.SysJobLog;
|
import com.fastbee.quartz.domain.SysJobLog;
|
||||||
import com.fastbee.quartz.service.ISysJobLogService;
|
import com.fastbee.quartz.service.ISysJobLogService;
|
||||||
|
import com.fastbee.common.utils.TraceIdUtils;
|
||||||
import org.quartz.Job;
|
import org.quartz.Job;
|
||||||
import org.quartz.JobExecutionContext;
|
import org.quartz.JobExecutionContext;
|
||||||
import org.quartz.JobExecutionException;
|
import org.quartz.JobExecutionException;
|
||||||
@ -61,6 +62,11 @@ public abstract class DeviceAbstractQuartzJob implements Job
|
|||||||
protected void before(JobExecutionContext context, DeviceJob deviceJob)
|
protected void before(JobExecutionContext context, DeviceJob deviceJob)
|
||||||
{
|
{
|
||||||
threadLocal.set(new Date());
|
threadLocal.set(new Date());
|
||||||
|
|
||||||
|
// 为设备定时任务生成TraceId,使用统一的生成逻辑
|
||||||
|
TraceIdUtils.generateTraceId();
|
||||||
|
|
||||||
|
log.info("设备定时任务开始执行: {} - {}", deviceJob.getJobName(), deviceJob.getJobGroup());
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -110,6 +116,11 @@ public abstract class DeviceAbstractQuartzJob implements Job
|
|||||||
|
|
||||||
// 写入数据库当中
|
// 写入数据库当中
|
||||||
SpringUtils.getBean(ISysJobLogService.class).addJobLog(sysJobLog);
|
SpringUtils.getBean(ISysJobLogService.class).addJobLog(sysJobLog);
|
||||||
|
|
||||||
|
// 清除TraceId,避免内存泄漏
|
||||||
|
TraceIdUtils.clearTraceId();
|
||||||
|
|
||||||
|
log.info("设备定时任务执行完成: {} - {}, 耗时: {}ms", deviceJob.getJobName(), deviceJob.getJobGroup(), runMs);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@ -27,6 +27,9 @@ import com.fastbee.iot.model.DeviceStatusVO;
|
|||||||
import com.fastbee.iot.service.IDeviceService;
|
import com.fastbee.iot.service.IDeviceService;
|
||||||
import com.fastbee.iot.service.IFunctionLogService;
|
import com.fastbee.iot.service.IFunctionLogService;
|
||||||
import com.fastbee.iot.service.IProductService;
|
import com.fastbee.iot.service.IProductService;
|
||||||
|
import com.fastbee.iot.service.IProductAuthorizeService;
|
||||||
|
import com.fastbee.iot.domain.ProductAuthorize;
|
||||||
|
import com.fastbee.iot.domain.Product;
|
||||||
import com.fastbee.mq.producer.MessageProducer;
|
import com.fastbee.mq.producer.MessageProducer;
|
||||||
import com.fastbee.mqtt.manager.MqttRemoteManager;
|
import com.fastbee.mqtt.manager.MqttRemoteManager;
|
||||||
import com.fastbee.mqtt.model.PushMessageBo;
|
import com.fastbee.mqtt.model.PushMessageBo;
|
||||||
@ -41,10 +44,7 @@ import org.springframework.stereotype.Service;
|
|||||||
|
|
||||||
import javax.annotation.Resource;
|
import javax.annotation.Resource;
|
||||||
import java.nio.charset.StandardCharsets;
|
import java.nio.charset.StandardCharsets;
|
||||||
import java.util.HashMap;
|
import java.util.*;
|
||||||
import java.util.Map;
|
|
||||||
import java.util.Optional;
|
|
||||||
import java.util.Set;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 处理类 处理设备主动上报和设备回调信息
|
* 处理类 处理设备主动上报和设备回调信息
|
||||||
@ -60,6 +60,8 @@ public class DeviceReportMessageServiceImpl implements IDeviceReportMessageServi
|
|||||||
@Autowired
|
@Autowired
|
||||||
private IProductService productService;
|
private IProductService productService;
|
||||||
@Autowired
|
@Autowired
|
||||||
|
private IProductAuthorizeService productAuthorizeService;
|
||||||
|
@Autowired
|
||||||
private IProtocolManagerService protocolManagerService;
|
private IProtocolManagerService protocolManagerService;
|
||||||
@Autowired
|
@Autowired
|
||||||
private IFirmwareTaskDetailService firmwareTaskDetailService;
|
private IFirmwareTaskDetailService firmwareTaskDetailService;
|
||||||
@ -120,6 +122,23 @@ public class DeviceReportMessageServiceImpl implements IDeviceReportMessageServi
|
|||||||
log.debug("*MQ收到TCP推送消息[{}]", JSON.toJSON(bo.getThingsModelSimpleItem()));
|
log.debug("*MQ收到TCP推送消息[{}]", JSON.toJSON(bo.getThingsModelSimpleItem()));
|
||||||
DeviceStatusVO deviceStatusVO1 = deviceService.selectDeviceStatusAndTransportStatus(serialNumber);
|
DeviceStatusVO deviceStatusVO1 = deviceService.selectDeviceStatusAndTransportStatus(serialNumber);
|
||||||
Optional.ofNullable(deviceStatusVO1).orElseThrow(() -> new ServiceException("设备不存在"));
|
Optional.ofNullable(deviceStatusVO1).orElseThrow(() -> new ServiceException("设备不存在"));
|
||||||
|
|
||||||
|
// TCP协议授权码校验
|
||||||
|
productId = deviceStatusVO1.getProductId();
|
||||||
|
Product product = productService.selectProductByProductId(productId);
|
||||||
|
if (product != null && product.getIsAuthorize() != null && product.getIsAuthorize() == 1) {
|
||||||
|
// 产品开启了授权码,检查设备是否绑定了授权码
|
||||||
|
ProductAuthorize queryParam = new ProductAuthorize();
|
||||||
|
queryParam.setProductId(productId);
|
||||||
|
queryParam.setSerialNumber(serialNumber);
|
||||||
|
List<ProductAuthorize> authorizeList = productAuthorizeService.selectProductAuthorizeList(queryParam);
|
||||||
|
if (authorizeList == null || authorizeList.isEmpty()) {
|
||||||
|
log.warn("TCP数据上报-授权码校验失败: 设备[{}]未绑定授权码,拒绝数据上报", serialNumber);
|
||||||
|
return; // 拒绝数据上报
|
||||||
|
}
|
||||||
|
log.debug("TCP数据上报-授权码校验通过: 设备[{}]已绑定授权码", serialNumber);
|
||||||
|
}
|
||||||
|
|
||||||
//同步设备状态
|
//同步设备状态
|
||||||
this.synchDeviceStatus(serialNumber);
|
this.synchDeviceStatus(serialNumber);
|
||||||
DeviceReport deviceReport = new DeviceReport();
|
DeviceReport deviceReport = new DeviceReport();
|
||||||
|
|||||||
@ -4,6 +4,7 @@ import com.fastbee.common.constant.Constants;
|
|||||||
import com.fastbee.common.constant.ScheduleConstants;
|
import com.fastbee.common.constant.ScheduleConstants;
|
||||||
import com.fastbee.common.utils.ExceptionUtil;
|
import com.fastbee.common.utils.ExceptionUtil;
|
||||||
import com.fastbee.common.utils.StringUtils;
|
import com.fastbee.common.utils.StringUtils;
|
||||||
|
import com.fastbee.common.utils.TraceIdUtils;
|
||||||
import com.fastbee.common.utils.bean.BeanUtils;
|
import com.fastbee.common.utils.bean.BeanUtils;
|
||||||
import com.fastbee.common.utils.spring.SpringUtils;
|
import com.fastbee.common.utils.spring.SpringUtils;
|
||||||
import com.fastbee.quartz.domain.SysJob;
|
import com.fastbee.quartz.domain.SysJob;
|
||||||
@ -61,6 +62,11 @@ public abstract class AbstractQuartzJob implements Job
|
|||||||
protected void before(JobExecutionContext context, SysJob sysJob)
|
protected void before(JobExecutionContext context, SysJob sysJob)
|
||||||
{
|
{
|
||||||
threadLocal.set(new Date());
|
threadLocal.set(new Date());
|
||||||
|
|
||||||
|
// 为定时任务生成TraceId,使用统一的生成逻辑
|
||||||
|
TraceIdUtils.generateTraceId();
|
||||||
|
|
||||||
|
log.info("定时任务开始执行: {} - {}", sysJob.getJobName(), sysJob.getJobGroup());
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -95,6 +101,11 @@ public abstract class AbstractQuartzJob implements Job
|
|||||||
|
|
||||||
// 写入数据库当中
|
// 写入数据库当中
|
||||||
SpringUtils.getBean(ISysJobLogService.class).addJobLog(sysJobLog);
|
SpringUtils.getBean(ISysJobLogService.class).addJobLog(sysJobLog);
|
||||||
|
|
||||||
|
// 清除TraceId,避免内存泄漏
|
||||||
|
TraceIdUtils.clearTraceId();
|
||||||
|
|
||||||
|
log.info("定时任务执行完成: {} - {}, 耗时: {}ms", sysJob.getJobName(), sysJob.getJobGroup(), runMs);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@ -1,22 +1,29 @@
|
|||||||
spring:
|
spring:
|
||||||
# REDIS数据库配置
|
# REDIS数据库配置
|
||||||
redis:
|
redis:
|
||||||
|
# [可选] 超时时间
|
||||||
|
timeout: 10000
|
||||||
|
# 以下为单机配置
|
||||||
# [必须修改] Redis服务器IP, REDIS安装在本机的,使用127.0.0.1
|
# [必须修改] Redis服务器IP, REDIS安装在本机的,使用127.0.0.1
|
||||||
host: 127.0.0.1
|
host: redis
|
||||||
# [必须修改] 端口号
|
# [必须修改] 端口号
|
||||||
port: 6379
|
port: 6379
|
||||||
# [可选] 数据库 DB
|
# [可选] 数据库 DB
|
||||||
database: 8
|
database: 0
|
||||||
# [可选] 访问密码,若你的redis服务器没有设置密码,就不需要用密码去连接
|
# [可选] 访问密码,若你的redis服务器没有设置密码,就不需要用密码去连接
|
||||||
password:
|
password: fastbee
|
||||||
# [可选] 超时时间
|
# 以下为集群配置
|
||||||
timeout: 10000
|
# cluster:
|
||||||
|
# nodes: 192.168.1.242:7001
|
||||||
|
# password: 4767cb971b40a1300fa09b7f87b09d1c
|
||||||
|
|
||||||
# [可选] 监听的HTTP端口, 网页和接口调用都是这个端口
|
# [可选] 监听的HTTP端口, 网页和接口调用都是这个端口
|
||||||
# 您需要使用实际的证书名称替换domain_name.jks
|
# 您需要使用实际的证书名称替换domain_name.jks
|
||||||
# 证书获取参考文档:https://help.aliyun.com/zh/ssl-certificate/user-guide/enable-https-on-spring-boot
|
# 证书获取参考文档:https://help.aliyun.com/zh/ssl-certificate/user-guide/enable-https-on-spring-boot
|
||||||
server:
|
server:
|
||||||
port: 18081
|
port: 18081
|
||||||
|
servlet:
|
||||||
|
context-path: / # 应用的访问路径
|
||||||
# HTTPS配置, 默认不开启
|
# HTTPS配置, 默认不开启
|
||||||
ssl:
|
ssl:
|
||||||
# 是否开启HTTPS访问 默认关闭
|
# 是否开启HTTPS访问 默认关闭
|
||||||
@ -31,7 +38,9 @@ server:
|
|||||||
|
|
||||||
# [根据业务需求配置]
|
# [根据业务需求配置]
|
||||||
userSettings:
|
userSettings:
|
||||||
# [可选 ] zlm配置的录像路径,
|
# [必选 ] 服务ID
|
||||||
|
id: 334533
|
||||||
|
# [必选 ] zlm配置的录像路径
|
||||||
record: /opt/media/bin/www/record
|
record: /opt/media/bin/www/record
|
||||||
# [可选 ] 录像保存时长(单位: 天)每天晚12点自动对过期文件执行清理
|
# [可选 ] 录像保存时长(单位: 天)每天晚12点自动对过期文件执行清理
|
||||||
recordDay: 7
|
recordDay: 7
|
||||||
@ -44,6 +53,12 @@ userSettings:
|
|||||||
# [可选 ] 限制 ffmpeg 合并文件使用的线程数,间接限制cpu使用率, 默认2 限制到50%
|
# [可选 ] 限制 ffmpeg 合并文件使用的线程数,间接限制cpu使用率, 默认2 限制到50%
|
||||||
threads: 2
|
threads: 2
|
||||||
|
|
||||||
|
# MyBatis配置
|
||||||
|
mybatis:
|
||||||
|
typeAliasesPackage: com.fastbee.oss.domain # 搜索指定包别名
|
||||||
|
mapperLocations: classpath*:mapper/**/*Mapper.xml # 配置mapper的扫描,找到所有的mapper.xml映射文件
|
||||||
|
configLocation: classpath:mybatis/mybatis-config.xml # 加载全局的配置文件
|
||||||
|
|
||||||
swagger-ui:
|
swagger-ui:
|
||||||
|
|
||||||
# [可选] 日志配置, 一般不需要改
|
# [可选] 日志配置, 一般不需要改
|
||||||
|
|||||||
@ -41,15 +41,15 @@ userSettings:
|
|||||||
# [必选 ] 服务ID
|
# [必选 ] 服务ID
|
||||||
id: 334533
|
id: 334533
|
||||||
# [必选 ] zlm配置的录像路径
|
# [必选 ] zlm配置的录像路径
|
||||||
record: D:\soft\ZLMediaKit\www\record
|
record: D:\fastbee\ZLMediaKit\www\record
|
||||||
# [可选 ] 录像保存时长(单位: 天)每天晚12点自动对过期文件执行清理
|
# [可选 ] 录像保存时长(单位: 天)每天晚12点自动对过期文件执行清理
|
||||||
recordDay: 7
|
recordDay: 7
|
||||||
# [可选 ] 录像下载合成临时文件保存时长, 不配置默认取值recordDay(单位: 天)每天晚12点自动对过期文件执行清理
|
# [可选 ] 录像下载合成临时文件保存时长, 不配置默认取值recordDay(单位: 天)每天晚12点自动对过期文件执行清理
|
||||||
# recordTempDay: 7
|
# recordTempDay: 7
|
||||||
# [必选 ] ffmpeg路径
|
# [必选 ] ffmpeg路径
|
||||||
ffmpeg: D:\soft\ZLMediaKit\bin\ffmpeg
|
ffmpeg: D:\fastbee\ZLMediaKit\ffmpeg-8.0.1-essentials_build\bin\ffmpeg
|
||||||
# [必选 ] ffprobe路径, 一般安装ffmpeg就会自带, 一般跟ffmpeg在同一目录,用于查询文件的信息
|
# [必选 ] ffprobe路径, 一般安装ffmpeg就会自带, 一般跟ffmpeg在同一目录,用于查询文件的信息
|
||||||
ffprobe: D:\soft\ZLMediaKit\bin\ffprobe
|
ffprobe: D:\fastbee\ZLMediaKit\ffmpeg-8.0.1-essentials_build\bin\ffprobe
|
||||||
# [可选 ] 限制 ffmpeg 合并文件使用的线程数,间接限制cpu使用率, 默认2 限制到50%
|
# [可选 ] 限制 ffmpeg 合并文件使用的线程数,间接限制cpu使用率, 默认2 限制到50%
|
||||||
threads: 2
|
threads: 2
|
||||||
|
|
||||||
|
|||||||
@ -23,8 +23,7 @@ import java.util.List;
|
|||||||
* @author ruoyi
|
* @author ruoyi
|
||||||
*/
|
*/
|
||||||
@Service
|
@Service
|
||||||
public class SysConfigServiceImpl implements ISysConfigService
|
public class SysConfigServiceImpl implements ISysConfigService {
|
||||||
{
|
|
||||||
@Autowired
|
@Autowired
|
||||||
private SysConfigMapper configMapper;
|
private SysConfigMapper configMapper;
|
||||||
|
|
||||||
@ -35,8 +34,7 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* 项目启动时,初始化参数到缓存
|
* 项目启动时,初始化参数到缓存
|
||||||
*/
|
*/
|
||||||
@PostConstruct
|
@PostConstruct
|
||||||
public void init()
|
public void init() {
|
||||||
{
|
|
||||||
loadingConfigCache();
|
loadingConfigCache();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -48,8 +46,7 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
@DS("master")
|
@DS("master")
|
||||||
public SysConfig selectConfigById(Long configId)
|
public SysConfig selectConfigById(Long configId) {
|
||||||
{
|
|
||||||
SysConfig config = new SysConfig();
|
SysConfig config = new SysConfig();
|
||||||
config.setConfigId(configId);
|
config.setConfigId(configId);
|
||||||
return configMapper.selectConfig(config);
|
return configMapper.selectConfig(config);
|
||||||
@ -62,18 +59,15 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* @return 参数键值
|
* @return 参数键值
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public String selectConfigByKey(String configKey)
|
public String selectConfigByKey(String configKey) {
|
||||||
{
|
|
||||||
String configValue = Convert.toStr(redisCache.getCacheObject(getCacheKey(configKey)));
|
String configValue = Convert.toStr(redisCache.getCacheObject(getCacheKey(configKey)));
|
||||||
if (StringUtils.isNotEmpty(configValue))
|
if (StringUtils.isNotEmpty(configValue)) {
|
||||||
{
|
|
||||||
return configValue;
|
return configValue;
|
||||||
}
|
}
|
||||||
SysConfig config = new SysConfig();
|
SysConfig config = new SysConfig();
|
||||||
config.setConfigKey(configKey);
|
config.setConfigKey(configKey);
|
||||||
SysConfig retConfig = configMapper.selectConfig(config);
|
SysConfig retConfig = configMapper.selectConfig(config);
|
||||||
if (StringUtils.isNotNull(retConfig))
|
if (StringUtils.isNotNull(retConfig)) {
|
||||||
{
|
|
||||||
redisCache.setCacheObject(getCacheKey(configKey), retConfig.getConfigValue());
|
redisCache.setCacheObject(getCacheKey(configKey), retConfig.getConfigValue());
|
||||||
return retConfig.getConfigValue();
|
return retConfig.getConfigValue();
|
||||||
}
|
}
|
||||||
@ -86,11 +80,9 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* @return true开启,false关闭
|
* @return true开启,false关闭
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public boolean selectCaptchaEnabled()
|
public boolean selectCaptchaEnabled() {
|
||||||
{
|
|
||||||
String captchaEnabled = selectConfigByKey("sys.account.captchaEnabled");
|
String captchaEnabled = selectConfigByKey("sys.account.captchaEnabled");
|
||||||
if (StringUtils.isEmpty(captchaEnabled))
|
if (StringUtils.isEmpty(captchaEnabled)) {
|
||||||
{
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return Convert.toBool(captchaEnabled);
|
return Convert.toBool(captchaEnabled);
|
||||||
@ -103,8 +95,7 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* @return 参数配置集合
|
* @return 参数配置集合
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public List<SysConfig> selectConfigList(SysConfig config)
|
public List<SysConfig> selectConfigList(SysConfig config) {
|
||||||
{
|
|
||||||
return configMapper.selectConfigList(config);
|
return configMapper.selectConfigList(config);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -115,11 +106,9 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* @return 结果
|
* @return 结果
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public int insertConfig(SysConfig config)
|
public int insertConfig(SysConfig config) {
|
||||||
{
|
|
||||||
int row = configMapper.insertConfig(config);
|
int row = configMapper.insertConfig(config);
|
||||||
if (row > 0)
|
if (row > 0) {
|
||||||
{
|
|
||||||
redisCache.setCacheObject(getCacheKey(config.getConfigKey()), config.getConfigValue());
|
redisCache.setCacheObject(getCacheKey(config.getConfigKey()), config.getConfigValue());
|
||||||
}
|
}
|
||||||
return row;
|
return row;
|
||||||
@ -132,17 +121,14 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* @return 结果
|
* @return 结果
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public int updateConfig(SysConfig config)
|
public int updateConfig(SysConfig config) {
|
||||||
{
|
|
||||||
SysConfig temp = configMapper.selectConfigById(config.getConfigId());
|
SysConfig temp = configMapper.selectConfigById(config.getConfigId());
|
||||||
if (!StringUtils.equals(temp.getConfigKey(), config.getConfigKey()))
|
if (!StringUtils.equals(temp.getConfigKey(), config.getConfigKey())) {
|
||||||
{
|
|
||||||
redisCache.deleteObject(getCacheKey(temp.getConfigKey()));
|
redisCache.deleteObject(getCacheKey(temp.getConfigKey()));
|
||||||
}
|
}
|
||||||
|
|
||||||
int row = configMapper.updateConfig(config);
|
int row = configMapper.updateConfig(config);
|
||||||
if (row > 0)
|
if (row > 0) {
|
||||||
{
|
|
||||||
redisCache.setCacheObject(getCacheKey(config.getConfigKey()), config.getConfigValue());
|
redisCache.setCacheObject(getCacheKey(config.getConfigKey()), config.getConfigValue());
|
||||||
}
|
}
|
||||||
return row;
|
return row;
|
||||||
@ -154,13 +140,10 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* @param configIds 需要删除的参数ID
|
* @param configIds 需要删除的参数ID
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public void deleteConfigByIds(Long[] configIds)
|
public void deleteConfigByIds(Long[] configIds) {
|
||||||
{
|
for (Long configId : configIds) {
|
||||||
for (Long configId : configIds)
|
|
||||||
{
|
|
||||||
SysConfig config = selectConfigById(configId);
|
SysConfig config = selectConfigById(configId);
|
||||||
if (StringUtils.equals(UserConstants.YES, config.getConfigType()))
|
if (StringUtils.equals(UserConstants.YES, config.getConfigType())) {
|
||||||
{
|
|
||||||
throw new ServiceException(String.format("内置参数【%1$s】不能删除 ", config.getConfigKey()));
|
throw new ServiceException(String.format("内置参数【%1$s】不能删除 ", config.getConfigKey()));
|
||||||
}
|
}
|
||||||
configMapper.deleteConfigById(configId);
|
configMapper.deleteConfigById(configId);
|
||||||
@ -172,11 +155,9 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* 加载参数缓存数据
|
* 加载参数缓存数据
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public void loadingConfigCache()
|
public void loadingConfigCache() {
|
||||||
{
|
|
||||||
List<SysConfig> configsList = configMapper.selectConfigList(new SysConfig());
|
List<SysConfig> configsList = configMapper.selectConfigList(new SysConfig());
|
||||||
for (SysConfig config : configsList)
|
for (SysConfig config : configsList) {
|
||||||
{
|
|
||||||
redisCache.setCacheObject(getCacheKey(config.getConfigKey()), config.getConfigValue());
|
redisCache.setCacheObject(getCacheKey(config.getConfigKey()), config.getConfigValue());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -185,8 +166,7 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* 清空参数缓存数据
|
* 清空参数缓存数据
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public void clearConfigCache()
|
public void clearConfigCache() {
|
||||||
{
|
|
||||||
Collection<String> keys = redisCache.keys(CacheConstants.SYS_CONFIG_KEY + "*");
|
Collection<String> keys = redisCache.keys(CacheConstants.SYS_CONFIG_KEY + "*");
|
||||||
redisCache.deleteObject(keys);
|
redisCache.deleteObject(keys);
|
||||||
}
|
}
|
||||||
@ -195,8 +175,7 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* 重置参数缓存数据
|
* 重置参数缓存数据
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public void resetConfigCache()
|
public void resetConfigCache() {
|
||||||
{
|
|
||||||
clearConfigCache();
|
clearConfigCache();
|
||||||
loadingConfigCache();
|
loadingConfigCache();
|
||||||
}
|
}
|
||||||
@ -208,12 +187,10 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* @return 结果
|
* @return 结果
|
||||||
*/
|
*/
|
||||||
@Override
|
@Override
|
||||||
public String checkConfigKeyUnique(SysConfig config)
|
public String checkConfigKeyUnique(SysConfig config) {
|
||||||
{
|
|
||||||
Long configId = StringUtils.isNull(config.getConfigId()) ? -1L : config.getConfigId();
|
Long configId = StringUtils.isNull(config.getConfigId()) ? -1L : config.getConfigId();
|
||||||
SysConfig info = configMapper.checkConfigKeyUnique(config.getConfigKey());
|
SysConfig info = configMapper.checkConfigKeyUnique(config.getConfigKey());
|
||||||
if (StringUtils.isNotNull(info) && info.getConfigId().longValue() != configId.longValue())
|
if (StringUtils.isNotNull(info) && info.getConfigId().longValue() != configId.longValue()) {
|
||||||
{
|
|
||||||
return UserConstants.NOT_UNIQUE;
|
return UserConstants.NOT_UNIQUE;
|
||||||
}
|
}
|
||||||
return UserConstants.UNIQUE;
|
return UserConstants.UNIQUE;
|
||||||
@ -225,8 +202,7 @@ public class SysConfigServiceImpl implements ISysConfigService
|
|||||||
* @param configKey 参数键
|
* @param configKey 参数键
|
||||||
* @return 缓存键key
|
* @return 缓存键key
|
||||||
*/
|
*/
|
||||||
private String getCacheKey(String configKey)
|
private String getCacheKey(String configKey) {
|
||||||
{
|
|
||||||
return CacheConstants.SYS_CONFIG_KEY + configKey;
|
return CacheConstants.SYS_CONFIG_KEY + configKey;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -18,4 +18,4 @@ VUE_APP_MQTT_SERVER_URL = ws://localhost:8083/mqtt
|
|||||||
VUE_APP_BAI_DU_AK = 0SD4KrYeMXVu8Ox2pxQGDOw3NmDYiKIw
|
VUE_APP_BAI_DU_AK = 0SD4KrYeMXVu8Ox2pxQGDOw3NmDYiKIw
|
||||||
|
|
||||||
# OSS API 地址(生产环境使用)
|
# OSS API 地址(生产环境使用)
|
||||||
VUE_APP_OSS_API =
|
VUE_APP_OSS_API =
|
||||||
|
|||||||
@ -8,15 +8,15 @@ export function loadBMap() {
|
|||||||
resolve(BMap)
|
resolve(BMap)
|
||||||
}
|
}
|
||||||
// 使用https协议需要添加一下meta标签
|
// 使用https协议需要添加一下meta标签
|
||||||
var protocolStr = document.location.protocol;
|
var protocolStr = document.location.protocol;
|
||||||
if(protocolStr == "https:")
|
if(protocolStr == "https:")
|
||||||
{
|
{
|
||||||
let meta = document.createElement('meta')
|
let meta = document.createElement('meta')
|
||||||
meta.httpEquiv = 'Content-Security-Policy'
|
meta.httpEquiv = 'Content-Security-Policy'
|
||||||
meta.content ='upgrade-insecure-requests'
|
meta.content ='upgrade-insecure-requests'
|
||||||
meta.onerror = reject
|
meta.onerror = reject
|
||||||
document.head.appendChild(meta)
|
document.head.appendChild(meta)
|
||||||
}
|
}
|
||||||
// 引入百度地图
|
// 引入百度地图
|
||||||
let script = document.createElement('script')
|
let script = document.createElement('script')
|
||||||
script.type = 'text/javascript'
|
script.type = 'text/javascript'
|
||||||
@ -25,4 +25,4 @@ export function loadBMap() {
|
|||||||
script.onerror = reject
|
script.onerror = reject
|
||||||
document.head.appendChild(script)
|
document.head.appendChild(script)
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
@ -226,71 +226,6 @@
|
|||||||
</el-row>
|
</el-row>
|
||||||
</el-card>
|
</el-card>
|
||||||
|
|
||||||
<el-card shadow="hover" style="margin: 10px 10px 20px 10px" class="phone-card">
|
|
||||||
<el-row :gutter="40">
|
|
||||||
<el-col :xs="24" :sm="24" :md="10" :lg="10" :xl="10" style="padding: 40px">
|
|
||||||
<div style="padding: 30px; margin: 20px 0; font-size: 14px">
|
|
||||||
<div style="font-size: 28px; font-weight: bold; margin-bottom: 20px">{{ $t('views.index.394840-0') }}</div>
|
|
||||||
<div style="display: table; font-size: 14px; margin-bottom: 10px">
|
|
||||||
<div style="display: table-cell; line-height: 22px">
|
|
||||||
<b style="color: #67c23a; margin-right: 10px">{{ $t('views.index.394840-1') }}</b>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div style="display: table; margin-bottom: 10px">
|
|
||||||
<div style="width: 70px; font-weight: bold; display: table-cell">{{ $t('views.index.394840-2') }}</div>
|
|
||||||
<div style="display: table-cell; line-height: 22px">{{ $t('views.index.394840-3') }}</div>
|
|
||||||
</div>
|
|
||||||
<div style="display: table">
|
|
||||||
<div style="width: 70px; font-weight: bold; display: table-cell">{{ $t('views.index.394840-4') }}</div>
|
|
||||||
<div style="display: table-cell; line-height: 22px">
|
|
||||||
{{ $t('views.index.394840-5') }}
|
|
||||||
<br />
|
|
||||||
<el-link target="_blank" href="https://fastbee.cn/doc/pages/sponsor">{{ $t('views.index.394840-6') }}</el-link>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div style="padding: 30px; font-size: 14px">
|
|
||||||
<div style="float: left; width: 230px">
|
|
||||||
<el-image style="width: 210px" :src="require('@/assets/images/code.jpg')"></el-image>
|
|
||||||
</div>
|
|
||||||
<div style="float: left">
|
|
||||||
<div style="font-size: 18px; font-weight: bold; margin: 16px 0">{{ $t('views.index.394840-7') }}</div>
|
|
||||||
<div style="font-size: 14px; font-weight: bold; margin: 16px 0; color: #f56c6c">{{ $t('views.index.394840-8') }}</div>
|
|
||||||
<div style="display: table; margin-bottom: 10px">
|
|
||||||
<div style="width: 70px; font-weight: bold; display: table-cell">{{ $t('views.index.394840-9') }}</div>
|
|
||||||
<div style="display: table-cell">
|
|
||||||
<el-link target="_blank" href="https://fastbee.cn/">www.fastbee.cn</el-link>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div style="display: table; margin-bottom: 10px">
|
|
||||||
<div style="width: 70px; font-weight: bold; display: table-cell">{{ $t('views.index.394840-10') }}</div>
|
|
||||||
<div style="display: table-cell">
|
|
||||||
<el-link target="_blank" href="https://fastbee.cn/doc">www.fastbee.cn/doc</el-link>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div style="display: table; margin-bottom: 10px">
|
|
||||||
<div style="width: 70px; font-weight: bold; display: table-cell">{{ $t('views.index.394840-11') }}</div>
|
|
||||||
<div style="display: table-cell">
|
|
||||||
<span>QQ 164770707</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div style="display: table; margin-bottom: 15px">
|
|
||||||
<div style="width: 70px; font-weight: bold; display: table-cell">{{ $t('views.index.394840-12') }}</div>
|
|
||||||
<div style="display: table-cell">
|
|
||||||
<el-link target="_blank" href="https://gitee.com/kerwincui/wumei-smart" type="danger">{{ $t('views.index.394840-13') }}</el-link>
|
|
||||||
<el-link target="_blank" href="https://github.com/kerwincui/fastbee" style="margin-left: 20px">{{ $t('views.index.394840-14') }}</el-link>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</el-col>
|
|
||||||
<el-col :xs="24" :sm="24" :md="12" :lg="12" :xl="12" style="padding: 40px">
|
|
||||||
<div class="phone">
|
|
||||||
<iframe src="https://fastbee.cn/h5" id="iframe" frameborder="0" scrolling="auto" height="100%" width="100%" class="phone-container"></iframe>
|
|
||||||
</div>
|
|
||||||
</el-col>
|
|
||||||
</el-row>
|
|
||||||
</el-card>
|
|
||||||
|
|
||||||
<!--通知公告详情 -->
|
<!--通知公告详情 -->
|
||||||
<el-dialog :title="notice.noticeTitle" :visible.sync="open" width="800px" append-to-body>
|
<el-dialog :title="notice.noticeTitle" :visible.sync="open" width="800px" append-to-body>
|
||||||
@ -787,6 +722,9 @@ export default {
|
|||||||
this.$nextTick(() => {
|
this.$nextTick(() => {
|
||||||
loadBMap().then(() => {
|
loadBMap().then(() => {
|
||||||
this.getmap();
|
this.getmap();
|
||||||
|
}).catch((error) => {
|
||||||
|
console.error('百度地图加载失败:', error);
|
||||||
|
this.$message.error('百度地图加载失败,请检查API Key配置。错误信息:' + error.message);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|||||||
@ -47,7 +47,8 @@
|
|||||||
<el-form-item :class="{ 'is-null': true }">
|
<el-form-item :class="{ 'is-null': true }">
|
||||||
<div style="display: flex; text-align: center; justify-content: center">
|
<div style="display: flex; text-align: center; justify-content: center">
|
||||||
<el-link style="float: left; color: #a0a5a8; font-weight: normal" href="https://fastbee.cn/" :underline="false" target="_blank">{{ $t('register.974236-7') }}</el-link>
|
<el-link style="float: left; color: #a0a5a8; font-weight: normal" href="https://fastbee.cn/" :underline="false" target="_blank">{{ $t('register.974236-7') }}</el-link>
|
||||||
<el-link style="float: left; color: #a0a5a8; font-weight: normal; margin-left: 20px" href="https://fastbee.cn/doc" :underline="false" target="_blank">{{ $t('register.974236-8') }}</el-link>
|
<!-- 隐藏查看文档入口 -->
|
||||||
|
<!-- <el-link style="float: left; color: #a0a5a8; font-weight: normal; margin-left: 20px" href="https://fastbee.cn/doc" :underline="false" target="_blank">{{ $t('register.974236-8') }}</el-link> -->
|
||||||
<router-link style="float: left; color: #a0a5a8; font-weight: normal; margin-left: 20px" :to="{ path: '/login', query: this.$route.query }">{{ $t('register.974236-9') }}</router-link>
|
<router-link style="float: left; color: #a0a5a8; font-weight: normal; margin-left: 20px" :to="{ path: '/login', query: this.$route.query }">{{ $t('register.974236-9') }}</router-link>
|
||||||
</div>
|
</div>
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user