【新增功能】 数据接收,JSON 标准格式数据接收
This commit is contained in:
parent
8c84ac9d8a
commit
3dafd31da6
|
@ -0,0 +1,27 @@
|
||||||
|
package cn.iocoder.yudao.module.iot.dal.dataobject.tdengine;
|
||||||
|
|
||||||
|
import cn.iocoder.yudao.module.iot.domain.BaseEntity;
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public class TableDO extends BaseEntity {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 超级表普通列字段的值
|
||||||
|
* 值需要与创建超级表时普通列字段的数据类型对应上
|
||||||
|
*/
|
||||||
|
private List<TdFieldDO> schemaFieldValues;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 超级表标签字段的值
|
||||||
|
* 值需要与创建超级表时标签字段的数据类型对应上
|
||||||
|
*/
|
||||||
|
private List<TdFieldDO> tagsFieldValues;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 表名称
|
||||||
|
*/
|
||||||
|
private String tableName;
|
||||||
|
}
|
|
@ -15,18 +15,23 @@ public class TableData {
|
||||||
*/
|
*/
|
||||||
private List<String> schemaFieldList;
|
private List<String> schemaFieldList;
|
||||||
|
|
||||||
/**
|
|
||||||
* 超级表标签字段的值
|
|
||||||
* 值需要与创建超级表时标签字段的数据类型对应上
|
|
||||||
*/
|
|
||||||
private List<Object> tagsValueList;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 超级表普通列字段的值
|
* 超级表普通列字段的值
|
||||||
* 值需要与创建超级表时普通列字段的数据类型对应上
|
* 值需要与创建超级表时普通列字段的数据类型对应上
|
||||||
*/
|
*/
|
||||||
private List<Object> schemaValueList;
|
private List<Object> schemaValueList;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 超级表标签字段的名称
|
||||||
|
*/
|
||||||
|
private List<String> tagsFieldList;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 超级表标签字段的值
|
||||||
|
* 值需要与创建超级表时标签字段的数据类型对应上
|
||||||
|
*/
|
||||||
|
private List<Object> tagsValueList;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 表名称
|
* 表名称
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -19,6 +19,11 @@ public class TdFieldDO {
|
||||||
*/
|
*/
|
||||||
private String fieldName;
|
private String fieldName;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 字段值
|
||||||
|
*/
|
||||||
|
private Object fieldValue;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 字段类型
|
* 字段类型
|
||||||
*/
|
*/
|
||||||
|
@ -28,4 +33,15 @@ public class TdFieldDO {
|
||||||
* 字段长度
|
* 字段长度
|
||||||
*/
|
*/
|
||||||
private Integer dataLength = 0;
|
private Integer dataLength = 0;
|
||||||
|
|
||||||
|
public TdFieldDO(String fieldName, String dataType, Integer dataLength) {
|
||||||
|
this.fieldName = fieldName;
|
||||||
|
this.dataType = dataType;
|
||||||
|
this.dataLength = dataLength;
|
||||||
|
}
|
||||||
|
|
||||||
|
public TdFieldDO(String fieldName, Object fieldValue) {
|
||||||
|
this.fieldName = fieldName;
|
||||||
|
this.fieldValue = fieldValue;
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -55,4 +55,7 @@ public interface IotThinkModelFunctionMapper extends BaseMapperX<IotThinkModelFu
|
||||||
IotThinkModelFunctionDO::getName, name);
|
IotThinkModelFunctionDO::getName, name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
default List<IotThinkModelFunctionDO> selectListByProductKey(String productKey){
|
||||||
|
return selectList(IotThinkModelFunctionDO::getProductKey, productKey);
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -1,9 +1,9 @@
|
||||||
package cn.iocoder.yudao.module.iot.dal.tdengine;
|
package cn.iocoder.yudao.module.iot.dal.tdengine;
|
||||||
|
|
||||||
|
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.TableDO;
|
||||||
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.TdFieldDO;
|
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.TdFieldDO;
|
||||||
import cn.iocoder.yudao.module.iot.domain.FieldsVo;
|
import cn.iocoder.yudao.module.iot.domain.FieldsVo;
|
||||||
import cn.iocoder.yudao.module.iot.domain.SelectDto;
|
import cn.iocoder.yudao.module.iot.domain.SelectDto;
|
||||||
import cn.iocoder.yudao.module.iot.domain.TableDto;
|
|
||||||
import cn.iocoder.yudao.module.iot.domain.TagsSelectDao;
|
import cn.iocoder.yudao.module.iot.domain.TagsSelectDao;
|
||||||
import cn.iocoder.yudao.module.iot.domain.visual.SelectVisualDto;
|
import cn.iocoder.yudao.module.iot.domain.visual.SelectVisualDto;
|
||||||
import com.baomidou.dynamic.datasource.annotation.DS;
|
import com.baomidou.dynamic.datasource.annotation.DS;
|
||||||
|
@ -86,9 +86,20 @@ public interface TdEngineMapper {
|
||||||
@Param("superTableName") String superTableName,
|
@Param("superTableName") String superTableName,
|
||||||
@Param("field") TdFieldDO field);
|
@Param("field") TdFieldDO field);
|
||||||
|
|
||||||
void createTable(TableDto tableDto);
|
/**
|
||||||
|
* 创建表 - 创建超级表的子表
|
||||||
|
* @param tableDO 表信息
|
||||||
|
*/
|
||||||
|
@InterceptorIgnore(tenantLine = "true")
|
||||||
|
void createTable(TableDO tableDO);
|
||||||
|
|
||||||
void insertData(TableDto tableDto);
|
/**
|
||||||
|
* 插入数据 - 指定列插入数据
|
||||||
|
*
|
||||||
|
* @param tableDto 数据
|
||||||
|
*/
|
||||||
|
@InterceptorIgnore(tenantLine = "true")
|
||||||
|
void insertData(TableDO tableDto);
|
||||||
|
|
||||||
List<Map<String, Object>> selectByTimestamp(SelectDto selectDto);
|
List<Map<String, Object>> selectByTimestamp(SelectDto selectDto);
|
||||||
|
|
||||||
|
|
|
@ -6,6 +6,7 @@ import jakarta.annotation.Resource;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import org.eclipse.paho.client.mqttv3.MqttClient;
|
import org.eclipse.paho.client.mqttv3.MqttClient;
|
||||||
import org.eclipse.paho.client.mqttv3.MqttMessage;
|
import org.eclipse.paho.client.mqttv3.MqttMessage;
|
||||||
|
import org.springframework.scheduling.annotation.Async;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
// TODO @芋艿:在瞅瞅
|
// TODO @芋艿:在瞅瞅
|
||||||
|
@ -24,6 +25,7 @@ public class EmqxServiceImpl implements EmqxService {
|
||||||
|
|
||||||
// TODO 多线程处理消息
|
// TODO 多线程处理消息
|
||||||
@Override
|
@Override
|
||||||
|
@Async
|
||||||
public void subscribeCallback(String topic, MqttMessage mqttMessage) {
|
public void subscribeCallback(String topic, MqttMessage mqttMessage) {
|
||||||
log.info("收到消息,主题: {}, 内容: {}", topic, new String(mqttMessage.getPayload()));
|
log.info("收到消息,主题: {}, 内容: {}", topic, new String(mqttMessage.getPayload()));
|
||||||
// 根据不同的主题,处理不同的业务逻辑
|
// 根据不同的主题,处理不同的业务逻辑
|
||||||
|
|
|
@ -34,6 +34,6 @@ public class IotDeviceDataServiceImpl implements IotDeviceDataService {
|
||||||
.deviceName(deviceName)
|
.deviceName(deviceName)
|
||||||
.deviceKey(device.getDeviceKey())
|
.deviceKey(device.getDeviceKey())
|
||||||
.build();
|
.build();
|
||||||
thingModelMessageService.saveThingModelMessage(thingModelMessage);
|
thingModelMessageService.saveThingModelMessage(device,thingModelMessage);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,6 +20,7 @@ import org.springframework.transaction.annotation.Transactional;
|
||||||
import org.springframework.validation.annotation.Validated;
|
import org.springframework.validation.annotation.Validated;
|
||||||
|
|
||||||
import java.time.LocalDateTime;
|
import java.time.LocalDateTime;
|
||||||
|
import java.util.Objects;
|
||||||
import java.util.UUID;
|
import java.util.UUID;
|
||||||
|
|
||||||
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
|
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
|
||||||
|
@ -213,10 +214,30 @@ public class IotDeviceServiceImpl implements IotDeviceService {
|
||||||
@Override
|
@Override
|
||||||
public void updateDeviceStatus(IotDeviceStatusUpdateReqVO updateReqVO) {
|
public void updateDeviceStatus(IotDeviceStatusUpdateReqVO updateReqVO) {
|
||||||
// 校验存在
|
// 校验存在
|
||||||
validateDeviceExists(updateReqVO.getId());
|
IotDeviceDO iotDeviceDO = validateDeviceExists(updateReqVO.getId());
|
||||||
|
|
||||||
// 更新状态和更新时间
|
// 更新状态和更新时间
|
||||||
IotDeviceDO updateObj = BeanUtils.toBean(updateReqVO, IotDeviceDO.class);
|
IotDeviceDO updateObj = BeanUtils.toBean(updateReqVO, IotDeviceDO.class);
|
||||||
|
|
||||||
|
// 以前是未激活,现在是上线,设置设备激活时间
|
||||||
|
if (Objects.equals(iotDeviceDO.getStatus(), IotDeviceStatusEnum.INACTIVE.getStatus())
|
||||||
|
&& Objects.equals(updateObj.getStatus(), IotDeviceStatusEnum.ONLINE.getStatus())) {
|
||||||
|
updateObj.setActiveTime(LocalDateTime.now());
|
||||||
|
}
|
||||||
|
|
||||||
|
// 如果是上线,设置上线时间
|
||||||
|
if (Objects.equals(updateObj.getStatus(), IotDeviceStatusEnum.ONLINE.getStatus())) {
|
||||||
|
updateObj.setLastOnlineTime(LocalDateTime.now());
|
||||||
|
}
|
||||||
|
|
||||||
|
// 如果是离线,设置离线时间
|
||||||
|
if (Objects.equals(updateObj.getStatus(), IotDeviceStatusEnum.OFFLINE.getStatus())) {
|
||||||
|
updateObj.setLastOfflineTime(LocalDateTime.now());
|
||||||
|
}
|
||||||
|
|
||||||
|
// 设置状态更新时间
|
||||||
|
updateObj.setStatusLastUpdateTime(LocalDateTime.now());
|
||||||
|
|
||||||
deviceMapper.updateById(updateObj);
|
deviceMapper.updateById(updateObj);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -60,27 +60,10 @@ public class IotDbStructureDataServiceImpl implements IotDbStructureDataService
|
||||||
dataType("NCHAR").
|
dataType("NCHAR").
|
||||||
dataLength(64).
|
dataLength(64).
|
||||||
build());
|
build());
|
||||||
// 年
|
|
||||||
tagsFields.add(TdFieldDO.builder().
|
tagsFields.add(TdFieldDO.builder().
|
||||||
fieldName("year").
|
fieldName("device_type").
|
||||||
dataType("INT").
|
dataType("INT").
|
||||||
build());
|
build());
|
||||||
// 月
|
|
||||||
tagsFields.add(TdFieldDO.builder().
|
|
||||||
fieldName("month").
|
|
||||||
dataType("INT").
|
|
||||||
build());
|
|
||||||
// 日
|
|
||||||
tagsFields.add(TdFieldDO.builder().
|
|
||||||
fieldName("day").
|
|
||||||
dataType("INT").
|
|
||||||
build());
|
|
||||||
// 时
|
|
||||||
tagsFields.add(TdFieldDO.builder().
|
|
||||||
fieldName("hour").
|
|
||||||
dataType("INT").
|
|
||||||
build());
|
|
||||||
|
|
||||||
|
|
||||||
// 4. 获取超级表的名称
|
// 4. 获取超级表的名称
|
||||||
String superTableName = getProductPropertySTableName(deviceType, thingModel.getProductKey());
|
String superTableName = getProductPropertySTableName(deviceType, thingModel.getProductKey());
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
package cn.iocoder.yudao.module.iot.service.tdengine;
|
package cn.iocoder.yudao.module.iot.service.tdengine;
|
||||||
|
|
||||||
|
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.TableDO;
|
||||||
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.TdFieldDO;
|
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.TdFieldDO;
|
||||||
import cn.iocoder.yudao.module.iot.domain.SelectDto;
|
import cn.iocoder.yudao.module.iot.domain.SelectDto;
|
||||||
import cn.iocoder.yudao.module.iot.domain.TableDto;
|
|
||||||
import cn.iocoder.yudao.module.iot.domain.TagsSelectDao;
|
import cn.iocoder.yudao.module.iot.domain.TagsSelectDao;
|
||||||
import cn.iocoder.yudao.module.iot.domain.visual.SelectVisualDto;
|
import cn.iocoder.yudao.module.iot.domain.visual.SelectVisualDto;
|
||||||
|
|
||||||
|
@ -70,17 +70,15 @@ public interface IotTdEngineService {
|
||||||
* 创建表
|
* 创建表
|
||||||
*
|
*
|
||||||
* @param tableDto 表信息
|
* @param tableDto 表信息
|
||||||
* @throws Exception 异常
|
|
||||||
*/
|
*/
|
||||||
void createTable(TableDto tableDto) throws Exception;
|
void createTable(TableDO tableDto);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 插入数据
|
* 插入数据
|
||||||
*
|
*
|
||||||
* @param tableDto 表信息
|
* @param tableDto 表信息
|
||||||
* @throws Exception 异常
|
|
||||||
*/
|
*/
|
||||||
void insertData(TableDto tableDto) throws Exception;
|
void insertData(TableDO tableDto);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 根据时间戳查询数据
|
* 根据时间戳查询数据
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
package cn.iocoder.yudao.module.iot.service.tdengine;
|
package cn.iocoder.yudao.module.iot.service.tdengine;
|
||||||
|
|
||||||
|
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.TableDO;
|
||||||
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.TdFieldDO;
|
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.TdFieldDO;
|
||||||
import cn.iocoder.yudao.module.iot.dal.tdengine.TdEngineMapper;
|
import cn.iocoder.yudao.module.iot.dal.tdengine.TdEngineMapper;
|
||||||
import cn.iocoder.yudao.module.iot.domain.SelectDto;
|
import cn.iocoder.yudao.module.iot.domain.SelectDto;
|
||||||
import cn.iocoder.yudao.module.iot.domain.TableDto;
|
|
||||||
import cn.iocoder.yudao.module.iot.domain.TagsSelectDao;
|
import cn.iocoder.yudao.module.iot.domain.TagsSelectDao;
|
||||||
import cn.iocoder.yudao.module.iot.domain.visual.SelectVisualDto;
|
import cn.iocoder.yudao.module.iot.domain.visual.SelectVisualDto;
|
||||||
import jakarta.annotation.Resource;
|
import jakarta.annotation.Resource;
|
||||||
|
@ -31,12 +31,12 @@ public class IotTdEngineServiceImpl implements IotTdEngineService {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void createTable(TableDto tableDto) {
|
public void createTable(TableDO tableDto) {
|
||||||
tdEngineMapper.createTable(tableDto);
|
tdEngineMapper.createTable(tableDto);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void insertData(TableDto tableDto) {
|
public void insertData(TableDO tableDto) {
|
||||||
tdEngineMapper.insertData(tableDto);
|
tdEngineMapper.insertData(tableDto);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
package cn.iocoder.yudao.module.iot.service.tdengine;
|
package cn.iocoder.yudao.module.iot.service.tdengine;
|
||||||
|
|
||||||
|
import cn.iocoder.yudao.module.iot.dal.dataobject.device.IotDeviceDO;
|
||||||
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.ThingModelMessage;
|
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.ThingModelMessage;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -10,7 +11,8 @@ public interface IotThingModelMessageService {
|
||||||
/**
|
/**
|
||||||
* 保存物模型消息
|
* 保存物模型消息
|
||||||
*
|
*
|
||||||
|
* @param device 设备
|
||||||
* @param thingModelMessage 物模型消息
|
* @param thingModelMessage 物模型消息
|
||||||
*/
|
*/
|
||||||
void saveThingModelMessage(ThingModelMessage thingModelMessage);
|
void saveThingModelMessage(IotDeviceDO device,ThingModelMessage thingModelMessage);
|
||||||
}
|
}
|
|
@ -1,13 +1,127 @@
|
||||||
package cn.iocoder.yudao.module.iot.service.tdengine;
|
package cn.iocoder.yudao.module.iot.service.tdengine;
|
||||||
|
|
||||||
|
import cn.iocoder.yudao.framework.tenant.core.aop.TenantIgnore;
|
||||||
|
import cn.iocoder.yudao.module.iot.controller.admin.device.vo.IotDeviceStatusUpdateReqVO;
|
||||||
|
import cn.iocoder.yudao.module.iot.dal.dataobject.device.IotDeviceDO;
|
||||||
|
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.FieldParser;
|
||||||
|
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.TableDO;
|
||||||
|
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.TdFieldDO;
|
||||||
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.ThingModelMessage;
|
import cn.iocoder.yudao.module.iot.dal.dataobject.tdengine.ThingModelMessage;
|
||||||
|
import cn.iocoder.yudao.module.iot.dal.dataobject.thinkmodelfunction.IotThinkModelFunctionDO;
|
||||||
|
import cn.iocoder.yudao.module.iot.enums.device.IotDeviceStatusEnum;
|
||||||
|
import cn.iocoder.yudao.module.iot.enums.product.IotProductFunctionTypeEnum;
|
||||||
|
import cn.iocoder.yudao.module.iot.service.device.IotDeviceService;
|
||||||
|
import cn.iocoder.yudao.module.iot.service.thinkmodelfunction.IotThinkModelFunctionService;
|
||||||
|
import jakarta.annotation.Resource;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
@Slf4j
|
||||||
@Service
|
@Service
|
||||||
public class IotThingModelMessageServiceImpl implements IotThingModelMessageService {
|
public class IotThingModelMessageServiceImpl implements IotThingModelMessageService {
|
||||||
|
|
||||||
|
@Value("${spring.datasource.dynamic.datasource.tdengine.url}")
|
||||||
|
private String url;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private IotThinkModelFunctionService iotThinkModelFunctionService;
|
||||||
|
@Resource
|
||||||
|
private IotDeviceService iotDeviceService;
|
||||||
|
@Resource
|
||||||
|
private IotTdEngineService iotTdEngineService;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void saveThingModelMessage(ThingModelMessage thingModelMessage) {
|
@TenantIgnore
|
||||||
// TODO 芋艿,后续实现
|
public void saveThingModelMessage(IotDeviceDO device, ThingModelMessage thingModelMessage) {
|
||||||
|
// 判断设备状态,如果为未激活状态,创建数据表
|
||||||
|
if (device.getStatus().equals(0)) {
|
||||||
|
// 创建设备数据表
|
||||||
|
createDeviceTable(device.getDeviceType(), device.getProductKey(), device.getDeviceName(), device.getDeviceKey());
|
||||||
|
// 更新设备状态
|
||||||
|
IotDeviceStatusUpdateReqVO updateReqVO = new IotDeviceStatusUpdateReqVO();
|
||||||
|
updateReqVO.setId(device.getId());
|
||||||
|
updateReqVO.setStatus(IotDeviceStatusEnum.ONLINE.getStatus());
|
||||||
|
iotDeviceService.updateDeviceStatus(updateReqVO);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 1. 获取设备属性
|
||||||
|
Map<String, Object> params = thingModelMessage.dataToMap();
|
||||||
|
|
||||||
|
// 2. 物模型校验,过滤非物模型属性
|
||||||
|
List<IotThinkModelFunctionDO> thinkModelFunctionListByProductKey = iotThinkModelFunctionService.getThinkModelFunctionListByProductKey(thingModelMessage.getProductKey());
|
||||||
|
|
||||||
|
// 2.1 筛选是属性 IotProductFunctionTypeEnum
|
||||||
|
thinkModelFunctionListByProductKey.removeIf(iotThinkModelFunctionDO -> !iotThinkModelFunctionDO.getType().equals(IotProductFunctionTypeEnum.PROPERTY.getType()));
|
||||||
|
if (thinkModelFunctionListByProductKey.isEmpty()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
// 2.2 获取属性名称
|
||||||
|
Map<String, String> thingModelProperties = thinkModelFunctionListByProductKey.stream().collect(Collectors.toMap(IotThinkModelFunctionDO::getIdentifier, IotThinkModelFunctionDO::getName));
|
||||||
|
|
||||||
|
// 4. 保存属性记录
|
||||||
|
List<TdFieldDO> schemaFieldValues = new ArrayList<>();
|
||||||
|
|
||||||
|
// 1. 设置字段名
|
||||||
|
schemaFieldValues.add(new TdFieldDO("time", thingModelMessage.getTime()));
|
||||||
|
|
||||||
|
// 2. 遍历新属性
|
||||||
|
params.forEach((key, val) -> {
|
||||||
|
if (thingModelProperties.containsKey(key)) {
|
||||||
|
schemaFieldValues.add(new TdFieldDO(key.toLowerCase(), val));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// 3. 保存设备属性
|
||||||
|
TableDO tableData = new TableDO();
|
||||||
|
tableData.setDataBaseName(url.substring(url.lastIndexOf("/") + 1));
|
||||||
|
tableData.setSuperTableName(getProductPropertySTableName(device.getDeviceType(), device.getProductKey()));
|
||||||
|
tableData.setTableName("device_" + device.getProductKey().toLowerCase() + "_" + device.getDeviceName().toLowerCase());
|
||||||
|
tableData.setSchemaFieldValues(schemaFieldValues);
|
||||||
|
|
||||||
|
// 4. 保存数据
|
||||||
|
iotTdEngineService.insertData(tableData);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void createDeviceTable(Integer deviceType, String productKey, String deviceName, String deviceKey) {
|
||||||
|
List<TdFieldDO> tagsFieldValues = new ArrayList<>();
|
||||||
|
String SuperTableName = getProductPropertySTableName(deviceType, productKey);
|
||||||
|
List<Map<String, Object>> maps = iotTdEngineService.describeSuperTable(url.substring(url.lastIndexOf("/") + 1), SuperTableName);
|
||||||
|
if (maps != null) {
|
||||||
|
List<Map<String, Object>> taggedNotesList = maps.stream().filter(map -> "TAG".equals(map.get("note"))).toList();
|
||||||
|
tagsFieldValues = FieldParser.parse(taggedNotesList.stream()
|
||||||
|
.map(map -> List.of(map.get("field"), map.get("type"), map.get("length")))
|
||||||
|
.collect(Collectors.toList()));
|
||||||
|
for (TdFieldDO tagsFieldValue : tagsFieldValues) {
|
||||||
|
switch (tagsFieldValue.getFieldName()) {
|
||||||
|
case "product_key" -> tagsFieldValue.setFieldValue(productKey);
|
||||||
|
case "device_key" -> tagsFieldValue.setFieldValue(deviceKey);
|
||||||
|
case "device_name" -> tagsFieldValue.setFieldValue(deviceName);
|
||||||
|
case "device_type" -> tagsFieldValue.setFieldValue(deviceType);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 1. 创建设备数据表
|
||||||
|
String tableName = "device_" + productKey.toLowerCase() + "_" + deviceName.toLowerCase();
|
||||||
|
TableDO tableDto = new TableDO();
|
||||||
|
tableDto.setDataBaseName(url.substring(url.lastIndexOf("/") + 1));
|
||||||
|
tableDto.setSuperTableName(SuperTableName);
|
||||||
|
tableDto.setTableName(tableName);
|
||||||
|
tableDto.setTagsFieldValues(tagsFieldValues);
|
||||||
|
iotTdEngineService.createTable(tableDto);
|
||||||
|
}
|
||||||
|
|
||||||
|
static String getProductPropertySTableName(Integer deviceType, String productKey) {
|
||||||
|
return switch (deviceType) {
|
||||||
|
case 1 -> String.format("gateway_sub_%s", productKey).toLowerCase();
|
||||||
|
case 2 -> String.format("gateway_%s", productKey).toLowerCase();
|
||||||
|
default -> String.format("device_%s", productKey).toLowerCase();
|
||||||
|
};
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -68,4 +68,12 @@ public interface IotThinkModelFunctionService {
|
||||||
* @param productId 产品编号
|
* @param productId 产品编号
|
||||||
*/
|
*/
|
||||||
void createSuperTableDataModel(Long productId);
|
void createSuperTableDataModel(Long productId);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获得产品物模型列表
|
||||||
|
*
|
||||||
|
* @param productKey 产品 Key
|
||||||
|
* @return 产品物模型列表
|
||||||
|
*/
|
||||||
|
List<IotThinkModelFunctionDO> getThinkModelFunctionListByProductKey(String productKey);
|
||||||
}
|
}
|
|
@ -199,6 +199,11 @@ public class IotThinkModelFunctionServiceImpl implements IotThinkModelFunctionSe
|
||||||
dbStructureDataService.createSuperTableDataModel(product, functionList);
|
dbStructureDataService.createSuperTableDataModel(product, functionList);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<IotThinkModelFunctionDO> getThinkModelFunctionListByProductKey(String productKey) {
|
||||||
|
return thinkModelFunctionMapper.selectListByProductKey(productKey);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 创建默认的事件和服务
|
* 创建默认的事件和服务
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -110,30 +110,27 @@
|
||||||
</foreach>
|
</foreach>
|
||||||
</update>
|
</update>
|
||||||
|
|
||||||
|
<!-- CREATE TABLE [IF NOT EXISTS] tb_name USING stb_name TAGS (tag_value1, ...);-->
|
||||||
<update id="createTable">
|
<update id="createTable">
|
||||||
create table
|
CREATE TABLE IF NOT EXISTS ${dataBaseName}.${tableName}
|
||||||
if not exists #{dataBaseName}.#{tableName}
|
USING ${dataBaseName}.${superTableName}
|
||||||
using #{dataBaseName}.#{superTableName}
|
<foreach item="item" collection="tagsFieldValues" separator="," open="(" close=")">
|
||||||
tags
|
${item.fieldName}
|
||||||
<foreach item="item" collection="tagsFieldValues" separator=","
|
</foreach>
|
||||||
open="(" close=")" index="">
|
TAGS
|
||||||
|
<foreach item="item" collection="tagsFieldValues" separator="," open="(" close=")">
|
||||||
#{item.fieldValue}
|
#{item.fieldValue}
|
||||||
</foreach>
|
</foreach>
|
||||||
</update>
|
</update>
|
||||||
|
|
||||||
|
<!-- insert into d1004 (ts, voltage, phase) values("2018-10-04 14:38:06", 223, 0.29) -->
|
||||||
<insert id="insertData">
|
<insert id="insertData">
|
||||||
insert into #{dataBaseName}.#{tableName}
|
INSERT INTO ${dataBaseName}.${tableName}
|
||||||
<foreach item="item" collection="schemaFieldValues" separator=","
|
<foreach item="item" collection="schemaFieldValues" separator=","
|
||||||
open="(" close=")" index="">
|
open="(" close=")" index="">
|
||||||
#{item.fieldName}
|
${item.fieldName}
|
||||||
</foreach>
|
</foreach>
|
||||||
using #{dataBaseName}.#{superTableName}
|
VALUES
|
||||||
tags
|
|
||||||
<foreach item="item" collection="tagsFieldValues" separator=","
|
|
||||||
open="(" close=")" index="">
|
|
||||||
#{item.fieldValue}
|
|
||||||
</foreach>
|
|
||||||
values
|
|
||||||
<foreach item="item" collection="schemaFieldValues" separator=","
|
<foreach item="item" collection="schemaFieldValues" separator=","
|
||||||
open="(" close=")" index="">
|
open="(" close=")" index="">
|
||||||
#{item.fieldValue}
|
#{item.fieldValue}
|
||||||
|
|
Loading…
Reference in New Issue