diff --git a/src/api/iot/device/modbus/config/index.ts b/src/api/iot/device/modbus/config/index.ts new file mode 100644 index 00000000..fa0e0a80 --- /dev/null +++ b/src/api/iot/device/modbus/config/index.ts @@ -0,0 +1,29 @@ +import request from '@/config/axios' + +/** Modbus 连接配置 VO */ +export interface DeviceModbusConfigVO { + id?: number // 主键 + deviceId: number // 设备编号 + ip: string // Modbus 服务器 IP 地址 + port: number // Modbus 服务器端口 + slaveId: number // 从站地址 + timeout: number // 连接超时时间,单位:毫秒 + retryInterval: number // 重试间隔,单位:毫秒 + status: number // 状态 +} + +/** Modbus 连接配置 API */ +export const DeviceModbusConfigApi = { + /** 获取设备的 Modbus 连接配置 */ + getModbusConfig: async (deviceId: number) => { + return await request.get({ + url: `/iot/device-modbus-config/get`, + params: { deviceId } + }) + }, + + /** 保存 Modbus 连接配置 */ + saveModbusConfig: async (data: DeviceModbusConfigVO) => { + return await request.post({ url: `/iot/device-modbus-config/save`, data }) + } +} diff --git a/src/api/iot/device/modbus/point/index.ts b/src/api/iot/device/modbus/point/index.ts new file mode 100644 index 00000000..5dc05d1c --- /dev/null +++ b/src/api/iot/device/modbus/point/index.ts @@ -0,0 +1,48 @@ +import request from '@/config/axios' + +/** Modbus 点位配置 VO */ +export interface DeviceModbusPointVO { + id?: number // 主键 + deviceId: number // 设备编号 + thingModelId: number // 物模型属性编号 + identifier: string // 属性标识符 + name: string // 属性名称 + functionCode: number // Modbus 功能码 + registerAddress: number // 寄存器起始地址 + registerCount: number // 寄存器数量 + byteOrder: string // 字节序 + rawDataType: string // 原始数据类型 + scale: number // 缩放因子 + pollInterval: number // 轮询间隔,单位:毫秒 + status: number // 状态 +} + +/** Modbus 点位配置 API */ +export const DeviceModbusPointApi = { + /** 获取设备的 Modbus 点位分页 */ + getModbusPointPage: async (params: any) => { + return await request.get({ url: `/iot/device-modbus-point/page`, params }) + }, + + /** 获取 Modbus 点位详情 */ + getModbusPoint: async (id: number) => { + return await request.get({ + url: `/iot/device-modbus-point/get?id=${id}` + }) + }, + + /** 创建 Modbus 点位配置 */ + createModbusPoint: async (data: DeviceModbusPointVO) => { + return await request.post({ url: `/iot/device-modbus-point/create`, data }) + }, + + /** 更新 Modbus 点位配置 */ + updateModbusPoint: async (data: DeviceModbusPointVO) => { + return await request.put({ url: `/iot/device-modbus-point/update`, data }) + }, + + /** 删除 Modbus 点位配置 */ + deleteModbusPoint: async (id: number) => { + return await request.delete({ url: `/iot/device-modbus-point/delete?id=${id}` }) + } +} diff --git a/src/views/iot/device/device/detail/DeviceModbusConfig.vue b/src/views/iot/device/device/detail/DeviceModbusConfig.vue new file mode 100644 index 00000000..d380fb2d --- /dev/null +++ b/src/views/iot/device/device/detail/DeviceModbusConfig.vue @@ -0,0 +1,262 @@ + + + + diff --git a/src/views/iot/device/device/detail/DeviceModbusConfigForm.vue b/src/views/iot/device/device/detail/DeviceModbusConfigForm.vue new file mode 100644 index 00000000..0e9572a6 --- /dev/null +++ b/src/views/iot/device/device/detail/DeviceModbusConfigForm.vue @@ -0,0 +1,160 @@ + + + + diff --git a/src/views/iot/device/device/detail/DeviceModbusPointForm.vue b/src/views/iot/device/device/detail/DeviceModbusPointForm.vue new file mode 100644 index 00000000..db0b7b52 --- /dev/null +++ b/src/views/iot/device/device/detail/DeviceModbusPointForm.vue @@ -0,0 +1,315 @@ + + + + diff --git a/src/views/iot/device/device/detail/index.vue b/src/views/iot/device/device/detail/index.vue index 3ec756b5..5c44c94b 100644 --- a/src/views/iot/device/device/detail/index.vue +++ b/src/views/iot/device/device/detail/index.vue @@ -36,6 +36,18 @@ @success="getDeviceData" /> + + + @@ -50,6 +62,7 @@ import DeviceDetailsThingModel from './DeviceDetailsThingModel.vue' import DeviceDetailsMessage from './DeviceDetailsMessage.vue' import DeviceDetailsSimulator from './DeviceDetailsSimulator.vue' import DeviceDetailConfig from './DeviceDetailConfig.vue' +import DeviceModbusConfig from './DeviceModbusConfig.vue' defineOptions({ name: 'IoTDeviceDetail' }) diff --git a/src/views/iot/utils/constants.ts b/src/views/iot/utils/constants.ts index fe6db188..259f5dce 100644 --- a/src/views/iot/utils/constants.ts +++ b/src/views/iot/utils/constants.ts @@ -541,3 +541,71 @@ export const JSON_PARAMS_EXAMPLE_VALUES = { [IoTDataSpecsDataTypeEnum.ARRAY]: { display: '[]', value: [] }, DEFAULT: { display: '""', value: '' } } as const + +// ========== Modbus 相关常量 ========== + +/** Modbus 功能码枚举 */ +export const ModbusFunctionCodeEnum = { + READ_COILS: 1, // 读线圈 + READ_DISCRETE_INPUTS: 2, // 读离散输入 + READ_HOLDING_REGISTERS: 3, // 读保持寄存器 + READ_INPUT_REGISTERS: 4 // 读输入寄存器 +} as const + +/** Modbus 功能码选项 */ +export const ModbusFunctionCodeOptions = [ + { value: 1, label: '01 - 读线圈 (Coils)', description: '可读写布尔值' }, + { value: 2, label: '02 - 读离散输入 (Discrete Inputs)', description: '只读布尔值' }, + { value: 3, label: '03 - 读保持寄存器 (Holding Registers)', description: '可读写16位数据' }, + { value: 4, label: '04 - 读输入寄存器 (Input Registers)', description: '只读16位数据' } +] + +/** Modbus 原始数据类型枚举 */ +export const ModbusRawDataTypeEnum = { + INT16: 'INT16', + UINT16: 'UINT16', + INT32: 'INT32', + UINT32: 'UINT32', + FLOAT: 'FLOAT', + DOUBLE: 'DOUBLE', + BOOLEAN: 'BOOLEAN', + STRING: 'STRING' +} as const + +/** Modbus 原始数据类型选项 */ +export const ModbusRawDataTypeOptions = [ + { value: 'INT16', label: 'INT16', description: '有符号16位整数', registerCount: 1 }, + { value: 'UINT16', label: 'UINT16', description: '无符号16位整数', registerCount: 1 }, + { value: 'INT32', label: 'INT32', description: '有符号32位整数', registerCount: 2 }, + { value: 'UINT32', label: 'UINT32', description: '无符号32位整数', registerCount: 2 }, + { value: 'FLOAT', label: 'FLOAT', description: '32位浮点数', registerCount: 2 }, + { value: 'DOUBLE', label: 'DOUBLE', description: '64位浮点数', registerCount: 4 }, + { value: 'BOOLEAN', label: 'BOOLEAN', description: '布尔值', registerCount: 1 }, + { value: 'STRING', label: 'STRING', description: '字符串', registerCount: 0 } +] + +/** Modbus 字节序选项 - 16位 */ +export const ModbusByteOrder16Options = [ + { value: 'AB', label: 'AB', description: '大端序' }, + { value: 'BA', label: 'BA', description: '小端序' } +] + +/** Modbus 字节序选项 - 32位 */ +export const ModbusByteOrder32Options = [ + { value: 'ABCD', label: 'ABCD', description: '大端序' }, + { value: 'CDAB', label: 'CDAB', description: '大端字交换' }, + { value: 'DCBA', label: 'DCBA', description: '小端序' }, + { value: 'BADC', label: 'BADC', description: '小端字交换' } +] + +/** 根据数据类型获取字节序选项 */ +export const getByteOrderOptions = (rawDataType: string) => { + if (['INT32', 'UINT32', 'FLOAT'].includes(rawDataType)) { + return ModbusByteOrder32Options + } + if (rawDataType === 'DOUBLE') { + // 64位暂时复用32位字节序 + return ModbusByteOrder32Options + } + return ModbusByteOrder16Options +}