348 lines
10 KiB
JavaScript
348 lines
10 KiB
JavaScript
/**
|
||
* 设备监控管理API - 后台管理
|
||
* 提供设备状态监控和管理功能
|
||
*/
|
||
|
||
const Framework = require("../../framework/node-core-framework.js");
|
||
|
||
module.exports = {
|
||
/**
|
||
* @swagger
|
||
* /admin_api/device/list:
|
||
* post:
|
||
* summary: 获取设备列表
|
||
* description: 分页获取所有设备列表(管理后台)
|
||
* tags: [后台-设备管理]
|
||
* requestBody:
|
||
* required: true
|
||
* content:
|
||
* application/json:
|
||
* schema:
|
||
* type: object
|
||
* properties:
|
||
* page:
|
||
* type: integer
|
||
* description: 页码
|
||
* pageSize:
|
||
* type: integer
|
||
* description: 每页数量
|
||
* isOnline:
|
||
* type: boolean
|
||
* description: 是否在线(可选)
|
||
* healthStatus:
|
||
* type: string
|
||
* description: 健康状态(可选)
|
||
* responses:
|
||
* 200:
|
||
* description: 获取成功
|
||
*/
|
||
/**
|
||
* @swagger
|
||
* /admin_api/device/detail:
|
||
* post:
|
||
* summary: 获取设备详情
|
||
* description: 根据设备SN码获取设备详细信息
|
||
* tags: [后台-设备管理]
|
||
* requestBody:
|
||
* required: true
|
||
* content:
|
||
* application/json:
|
||
* schema:
|
||
* type: object
|
||
* required:
|
||
* - deviceSn
|
||
* properties:
|
||
* deviceSn:
|
||
* type: string
|
||
* description: 设备SN码
|
||
* responses:
|
||
* 200:
|
||
* description: 获取成功
|
||
*/
|
||
'POST /device/detail': async (ctx) => {
|
||
const models = Framework.getModels();
|
||
const { pla_account } = models;
|
||
const body = ctx.getBody();
|
||
const { deviceSn } = body;
|
||
|
||
if (!deviceSn) {
|
||
return ctx.fail('设备SN码不能为空');
|
||
}
|
||
|
||
// 从 pla_account 获取账号信息(包含 is_online 和 is_logged_in)
|
||
const account = await pla_account.findOne({
|
||
where: { sn_code: deviceSn }
|
||
});
|
||
|
||
if (!account) {
|
||
return ctx.fail('设备不存在');
|
||
}
|
||
|
||
const accountData = account.toJSON();
|
||
|
||
// 组合返回数据(直接从数据库读取 is_online 和 is_logged_in)
|
||
const deviceData = {
|
||
sn_code: accountData.sn_code,
|
||
device_id: accountData.device_id,
|
||
deviceName: accountData.name || accountData.sn_code,
|
||
platform: accountData.platform_type,
|
||
isOnline: accountData.is_online === 1,
|
||
is_online: accountData.is_online === 1,
|
||
is_logged_in: accountData.is_logged_in === 1,
|
||
isRunning: false, // 不再维护运行状态
|
||
lastHeartbeatTime: null, // 不再从内存读取
|
||
accountName: accountData.name,
|
||
platform_type: accountData.platform_type,
|
||
is_enabled: accountData.is_enabled
|
||
};
|
||
|
||
return ctx.success(deviceData);
|
||
},
|
||
|
||
'POST /device/list': async (ctx) => {
|
||
const models = Framework.getModels();
|
||
const { pla_account, op } = models;
|
||
const body = ctx.getBody();
|
||
const { isOnline, healthStatus, platform, searchText} = ctx.getBody();
|
||
|
||
// 获取分页参数
|
||
const { limit, offset } = ctx.getPageSize();
|
||
|
||
// 从 pla_account 查询账号
|
||
const where = { is_delete: 0 };
|
||
if (platform) where.platform_type = platform;
|
||
|
||
// 支持搜索设备名称或SN码
|
||
if (searchText) {
|
||
where[op.or] = [
|
||
{ name: { [op.like]: `%${searchText}%` } },
|
||
{ sn_code: { [op.like]: `%${searchText}%` } }
|
||
];
|
||
}
|
||
|
||
// 在线状态筛选(直接查询数据库)
|
||
if (isOnline !== undefined) {
|
||
where.is_online = isOnline ? 1 : 0;
|
||
}
|
||
|
||
const result = await pla_account.findAndCountAll({
|
||
where,
|
||
limit,
|
||
offset,
|
||
order: [['id', 'DESC']]
|
||
});
|
||
|
||
// 组合数据(直接从数据库读取)
|
||
const list = result.rows.map(account => {
|
||
const accountData = account.toJSON();
|
||
return {
|
||
sn_code: accountData.sn_code,
|
||
device_id: accountData.device_id,
|
||
deviceName: accountData.name || accountData.sn_code,
|
||
platform: accountData.platform_type,
|
||
isOnline: accountData.is_online === 1,
|
||
isRunning: false,
|
||
lastHeartbeatTime: null,
|
||
accountName: accountData.name,
|
||
platform_type: accountData.platform_type,
|
||
is_enabled: accountData.is_enabled
|
||
};
|
||
});
|
||
|
||
return ctx.success({
|
||
total: result.count,
|
||
list: list
|
||
});
|
||
},
|
||
|
||
/**
|
||
* @swagger
|
||
* /admin_api/device/overview:
|
||
* get:
|
||
* summary: 获取设备概览
|
||
* description: 获取所有设备的统计概览
|
||
* tags: [后台-设备管理]
|
||
* responses:
|
||
* 200:
|
||
* description: 获取成功
|
||
*/
|
||
'GET /device/overview': async (ctx) => {
|
||
const models = Framework.getModels();
|
||
const { pla_account } = models;
|
||
|
||
// 从 pla_account 获取账号统计(直接查询数据库)
|
||
const totalDevices = await pla_account.count({ where: { is_delete: 0 } });
|
||
const onlineDevices = await pla_account.count({ where: { is_delete: 0, is_online: 1 } });
|
||
const runningDevices = 0; // 不再维护运行状态
|
||
const healthyDevices = onlineDevices; // 简化处理,在线即健康
|
||
const warningDevices = 0;
|
||
const errorDevices = 0;
|
||
|
||
// 获取最近离线的设备(从数据库查询)
|
||
const offlineAccounts = await pla_account.findAll({
|
||
where: { is_delete: 0, is_online: 0 },
|
||
limit: 5,
|
||
order: [['id', 'DESC']]
|
||
});
|
||
|
||
const offlineDevicesList = offlineAccounts.map(account => ({
|
||
sn_code: account.sn_code,
|
||
deviceName: account.name || account.sn_code,
|
||
lastOfflineTime: null,
|
||
lastError: ''
|
||
}));
|
||
|
||
return ctx.success({
|
||
totalDevices,
|
||
onlineDevices,
|
||
offlineDevices: totalDevices - onlineDevices,
|
||
runningDevices,
|
||
idleDevices: onlineDevices - runningDevices,
|
||
healthyDevices,
|
||
warningDevices,
|
||
errorDevices,
|
||
onlineRate: totalDevices > 0 ? ((onlineDevices / totalDevices) * 100).toFixed(2) : 0,
|
||
healthyRate: totalDevices > 0 ? ((healthyDevices / totalDevices) * 100).toFixed(2) : 0,
|
||
averageHealthScore: '100.00', // 简化处理
|
||
recentOffline: offlineDevicesList
|
||
});
|
||
},
|
||
|
||
/**
|
||
* @swagger
|
||
* /admin_api/device/update-config:
|
||
* post:
|
||
* summary: 更新设备配置
|
||
* description: 更新指定设备的配置信息,保存到 pla_account 表的 deliver_config 字段
|
||
* tags: [后台-设备管理]
|
||
* requestBody:
|
||
* required: true
|
||
* content:
|
||
* application/json:
|
||
* schema:
|
||
* type: object
|
||
* required:
|
||
* - sn_code
|
||
* - deliver_config
|
||
* properties:
|
||
* sn_code:
|
||
* type: string
|
||
* description: 设备SN码
|
||
* deliver_config:
|
||
* type: object
|
||
* description: 投递配置数据
|
||
* responses:
|
||
* 200:
|
||
* description: 更新成功
|
||
*/
|
||
'POST /device/update-config': async (ctx) => {
|
||
const models = Framework.getModels();
|
||
const body = ctx.getBody();
|
||
const { sn_code, deliver_config } = body;
|
||
|
||
if (!sn_code) {
|
||
return ctx.fail('设备SN码不能为空');
|
||
}
|
||
|
||
if (!deliver_config) {
|
||
return ctx.fail('配置数据不能为空');
|
||
}
|
||
|
||
// 从 pla_account 获取账号
|
||
const { pla_account } = models;
|
||
const account = await pla_account.findOne({ where: { sn_code } });
|
||
if (!account) {
|
||
return ctx.fail('设备不存在');
|
||
}
|
||
|
||
// 更新 pla_account 表的 deliver_config 字段
|
||
await pla_account.update(
|
||
{
|
||
deliver_config: deliver_config,
|
||
auto_deliver: deliver_config.auto_delivery ? 1 : 0
|
||
},
|
||
{ where: { id: account.id } }
|
||
);
|
||
|
||
return ctx.success({ message: '设备配置更新成功' });
|
||
},
|
||
|
||
/**
|
||
* @swagger
|
||
* /admin_api/device/reset-error:
|
||
* post:
|
||
* summary: 重置设备错误
|
||
* description: 清除设备的错误信息和计数
|
||
* tags: [后台-设备管理]
|
||
* requestBody:
|
||
* required: true
|
||
* content:
|
||
* application/json:
|
||
* schema:
|
||
* type: object
|
||
* required:
|
||
* - sn_code
|
||
* properties:
|
||
* sn_code:
|
||
* type: string
|
||
* description: 设备SN码
|
||
* responses:
|
||
* 200:
|
||
* description: 重置成功
|
||
*/
|
||
'POST /device/reset-error': async (ctx) => {
|
||
// device_status 表已移除,此功能暂时禁用
|
||
// 如果需要重置错误,可以在 account_config 表中添加错误信息字段
|
||
return ctx.success({ message: '设备错误重置功能已禁用(device_status 表已移除)' });
|
||
},
|
||
|
||
/**
|
||
* @swagger
|
||
* /admin_api/device/delete:
|
||
* post:
|
||
* summary: 删除设备
|
||
* description: 删除指定的设备记录
|
||
* tags: [后台-设备管理]
|
||
* requestBody:
|
||
* required: true
|
||
* content:
|
||
* application/json:
|
||
* schema:
|
||
* type: object
|
||
* required:
|
||
* - sn_code
|
||
* properties:
|
||
* sn_code:
|
||
* type: string
|
||
* description: 设备SN码
|
||
* responses:
|
||
* 200:
|
||
* description: 删除成功
|
||
*/
|
||
'POST /device/delete': async (ctx) => {
|
||
// device_status 表已移除,删除设备功能改为删除账号
|
||
// 如果需要删除设备,应该删除对应的 pla_account 记录
|
||
const models = Framework.getModels();
|
||
const { pla_account } = models;
|
||
const body = ctx.getBody();
|
||
const { sn_code } = body;
|
||
|
||
if (!sn_code) {
|
||
return ctx.fail('设备SN码不能为空');
|
||
}
|
||
|
||
// 软删除账号(设置 is_delete = 1)
|
||
const result = await pla_account.update(
|
||
{ is_delete: 1 },
|
||
{ where: { sn_code } }
|
||
);
|
||
|
||
if (result[0] === 0) {
|
||
return ctx.fail('设备不存在');
|
||
}
|
||
|
||
return ctx.success({ message: '设备删除成功' });
|
||
}
|
||
};
|
||
|