360 lines
14 KiB
JavaScript
360 lines
14 KiB
JavaScript
/**
|
||
* 智能项圈预警API测试脚本
|
||
* @file test-smart-collar-alert-api.js
|
||
* @description 测试智能项圈预警相关的API接口功能
|
||
*/
|
||
|
||
const axios = require('axios');
|
||
|
||
// 配置基础URL
|
||
const BASE_URL = 'http://localhost:5350/api/smart-alerts/public';
|
||
|
||
// 创建axios实例
|
||
const api = axios.create({
|
||
baseURL: BASE_URL,
|
||
timeout: 10000,
|
||
headers: {
|
||
'Content-Type': 'application/json'
|
||
}
|
||
});
|
||
|
||
// 测试结果统计
|
||
let testResults = {
|
||
total: 0,
|
||
passed: 0,
|
||
failed: 0,
|
||
errors: []
|
||
};
|
||
|
||
// 测试辅助函数
|
||
function logTest(testName, success, message = '') {
|
||
testResults.total++;
|
||
if (success) {
|
||
testResults.passed++;
|
||
console.log(`✅ ${testName}: ${message}`);
|
||
} else {
|
||
testResults.failed++;
|
||
testResults.errors.push(`${testName}: ${message}`);
|
||
console.log(`❌ ${testName}: ${message}`);
|
||
}
|
||
}
|
||
|
||
// 测试函数
|
||
async function testGetCollarAlertStats() {
|
||
try {
|
||
console.log('\n=== 测试获取智能项圈预警统计 ===');
|
||
const response = await api.get('/collar/stats');
|
||
|
||
if (response.status === 200 && response.data.success) {
|
||
const data = response.data.data;
|
||
logTest('获取项圈预警统计', true, `成功获取统计,设备总数: ${data.totalDevices}, 预警总数: ${data.totalAlerts}`);
|
||
|
||
// 验证数据结构
|
||
const requiredFields = ['totalDevices', 'lowBattery', 'offline', 'highTemperature', 'abnormalMovement', 'totalAlerts'];
|
||
const hasAllFields = requiredFields.every(field => data.hasOwnProperty(field));
|
||
logTest('统计数据结构验证', hasAllFields, hasAllFields ? '数据结构正确' : '缺少必要字段');
|
||
|
||
// 验证项圈特有字段
|
||
const hasWearOffField = data.hasOwnProperty('wearOff');
|
||
logTest('项圈特有字段验证', hasWearOffField, hasWearOffField ? '包含项圈脱落预警字段' : '缺少项圈脱落预警字段');
|
||
} else {
|
||
logTest('获取项圈预警统计', false, `请求失败: ${response.data.message || '未知错误'}`);
|
||
}
|
||
} catch (error) {
|
||
logTest('获取项圈预警统计', false, `请求异常: ${error.message}`);
|
||
}
|
||
}
|
||
|
||
async function testGetCollarAlerts() {
|
||
try {
|
||
console.log('\n=== 测试获取智能项圈预警列表 ===');
|
||
|
||
// 测试基础列表获取
|
||
const response = await api.get('/collar?page=1&limit=5');
|
||
|
||
if (response.status === 200 && response.data.success) {
|
||
const data = response.data;
|
||
logTest('获取项圈预警列表', true, `成功获取列表,共 ${data.total} 条预警`);
|
||
|
||
// 验证分页信息
|
||
const hasPagination = data.pagination && typeof data.pagination.page === 'number';
|
||
logTest('分页信息验证', hasPagination, hasPagination ? '分页信息正确' : '分页信息缺失');
|
||
|
||
// 验证统计数据
|
||
const hasStats = data.stats && typeof data.stats.lowBattery === 'number';
|
||
logTest('统计信息验证', hasStats, hasStats ? '统计信息正确' : '统计信息缺失');
|
||
|
||
// 验证项圈特有字段
|
||
if (data.data.length > 0) {
|
||
const firstAlert = data.data[0];
|
||
const hasCollarFields = firstAlert.hasOwnProperty('collarNumber') && firstAlert.hasOwnProperty('wearStatus');
|
||
logTest('项圈字段验证', hasCollarFields, hasCollarFields ? '包含项圈特有字段' : '缺少项圈特有字段');
|
||
}
|
||
} else {
|
||
logTest('获取项圈预警列表', false, `请求失败: ${response.data.message || '未知错误'}`);
|
||
}
|
||
} catch (error) {
|
||
logTest('获取项圈预警列表', false, `请求异常: ${error.message}`);
|
||
}
|
||
}
|
||
|
||
async function testGetCollarAlertsWithFilters() {
|
||
try {
|
||
console.log('\n=== 测试项圈预警列表筛选功能 ===');
|
||
|
||
// 测试按预警类型筛选
|
||
const batteryResponse = await api.get('/collar?alertType=battery&limit=3');
|
||
|
||
if (batteryResponse.status === 200 && batteryResponse.data.success) {
|
||
const batteryAlerts = batteryResponse.data.data;
|
||
const allBattery = batteryAlerts.every(alert => alert.alertType === 'battery');
|
||
logTest('按预警类型筛选', allBattery, `筛选结果: ${batteryAlerts.length} 条低电量预警`);
|
||
} else {
|
||
logTest('按预警类型筛选', false, `筛选失败: ${batteryResponse.data.message || '未知错误'}`);
|
||
}
|
||
|
||
// 测试项圈脱落预警筛选
|
||
const wearResponse = await api.get('/collar?alertType=wear&limit=3');
|
||
|
||
if (wearResponse.status === 200 && wearResponse.data.success) {
|
||
const wearAlerts = wearResponse.data.data;
|
||
const allWear = wearAlerts.every(alert => alert.alertType === 'wear');
|
||
logTest('项圈脱落预警筛选', allWear, `筛选结果: ${wearAlerts.length} 条项圈脱落预警`);
|
||
} else {
|
||
logTest('项圈脱落预警筛选', false, `筛选失败: ${wearResponse.data.message || '未知错误'}`);
|
||
}
|
||
|
||
// 测试搜索功能
|
||
const searchResponse = await api.get('/collar?search=COLLAR&limit=3');
|
||
|
||
if (searchResponse.status === 200 && searchResponse.data.success) {
|
||
const searchAlerts = searchResponse.data.data;
|
||
logTest('搜索功能', true, `搜索到 ${searchAlerts.length} 条相关预警`);
|
||
} else {
|
||
logTest('搜索功能', false, `搜索失败: ${searchResponse.data.message || '未知错误'}`);
|
||
}
|
||
} catch (error) {
|
||
logTest('筛选功能测试', false, `请求异常: ${error.message}`);
|
||
}
|
||
}
|
||
|
||
async function testGetCollarAlertById() {
|
||
try {
|
||
console.log('\n=== 测试获取单个项圈预警详情 ===');
|
||
|
||
// 首先获取一个预警ID
|
||
const listResponse = await api.get('/collar?limit=1');
|
||
|
||
if (listResponse.status === 200 && listResponse.data.success && listResponse.data.data.length > 0) {
|
||
const alertId = listResponse.data.data[0].id;
|
||
|
||
// 测试获取详情
|
||
const detailResponse = await api.get(`/collar/${alertId}`);
|
||
|
||
if (detailResponse.status === 200 && detailResponse.data.success) {
|
||
const alert = detailResponse.data.data;
|
||
logTest('获取项圈预警详情', true, `成功获取预警 ${alertId} 的详情`);
|
||
|
||
// 验证详情数据结构
|
||
const hasRequiredFields = alert.id && alert.alertType && alert.alertLevel;
|
||
logTest('详情数据结构验证', hasRequiredFields, hasRequiredFields ? '详情数据结构正确' : '缺少必要字段');
|
||
|
||
// 验证项圈特有字段
|
||
const hasCollarFields = alert.hasOwnProperty('collarNumber') && alert.hasOwnProperty('wearStatus');
|
||
logTest('项圈详情字段验证', hasCollarFields, hasCollarFields ? '包含项圈特有字段' : '缺少项圈特有字段');
|
||
} else {
|
||
logTest('获取项圈预警详情', false, `获取详情失败: ${detailResponse.data.message || '未知错误'}`);
|
||
}
|
||
} else {
|
||
logTest('获取项圈预警详情', false, '没有可用的预警数据用于测试');
|
||
}
|
||
} catch (error) {
|
||
logTest('获取项圈预警详情', false, `请求异常: ${error.message}`);
|
||
}
|
||
}
|
||
|
||
async function testHandleCollarAlert() {
|
||
try {
|
||
console.log('\n=== 测试处理项圈预警功能 ===');
|
||
|
||
// 首先获取一个预警ID
|
||
const listResponse = await api.get('/collar?limit=1');
|
||
|
||
if (listResponse.status === 200 && listResponse.data.success && listResponse.data.data.length > 0) {
|
||
const alertId = listResponse.data.data[0].id;
|
||
|
||
// 测试处理预警
|
||
const handleData = {
|
||
action: 'acknowledged',
|
||
notes: 'API测试处理项圈预警',
|
||
handler: 'test-user'
|
||
};
|
||
|
||
const handleResponse = await api.post(`/collar/${alertId}/handle`, handleData);
|
||
|
||
if (handleResponse.status === 200 && handleResponse.data.success) {
|
||
const result = handleResponse.data.data;
|
||
logTest('处理项圈预警', true, `成功处理预警 ${alertId}`);
|
||
|
||
// 验证处理结果
|
||
const hasProcessedInfo = result.alertId && result.action && result.processedAt;
|
||
logTest('处理结果验证', hasProcessedInfo, hasProcessedInfo ? '处理结果正确' : '处理结果不完整');
|
||
} else {
|
||
logTest('处理项圈预警', false, `处理失败: ${handleResponse.data.message || '未知错误'}`);
|
||
}
|
||
} else {
|
||
logTest('处理项圈预警', false, '没有可用的预警数据用于测试');
|
||
}
|
||
} catch (error) {
|
||
logTest('处理项圈预警', false, `请求异常: ${error.message}`);
|
||
}
|
||
}
|
||
|
||
async function testBatchHandleCollarAlerts() {
|
||
try {
|
||
console.log('\n=== 测试批量处理项圈预警功能 ===');
|
||
|
||
// 首先获取一些预警ID
|
||
const listResponse = await api.get('/collar?limit=3');
|
||
|
||
if (listResponse.status === 200 && listResponse.data.success && listResponse.data.data.length > 0) {
|
||
const alertIds = listResponse.data.data.map(alert => alert.id);
|
||
|
||
// 测试批量处理
|
||
const batchData = {
|
||
alertIds: alertIds,
|
||
action: 'acknowledged',
|
||
notes: 'API批量测试处理项圈预警',
|
||
handler: 'test-user'
|
||
};
|
||
|
||
const batchResponse = await api.post('/collar/batch-handle', batchData);
|
||
|
||
if (batchResponse.status === 200 && batchResponse.data.success) {
|
||
const result = batchResponse.data.data;
|
||
logTest('批量处理项圈预警', true, `成功批量处理 ${result.processedCount} 个预警`);
|
||
|
||
// 验证批量处理结果
|
||
const hasBatchResult = result.processedCount > 0 && Array.isArray(result.results);
|
||
logTest('批量处理结果验证', hasBatchResult, hasBatchResult ? '批量处理结果正确' : '批量处理结果不完整');
|
||
} else {
|
||
logTest('批量处理项圈预警', false, `批量处理失败: ${batchResponse.data.message || '未知错误'}`);
|
||
}
|
||
} else {
|
||
logTest('批量处理项圈预警', false, '没有足够的预警数据用于测试');
|
||
}
|
||
} catch (error) {
|
||
logTest('批量处理项圈预警', false, `请求异常: ${error.message}`);
|
||
}
|
||
}
|
||
|
||
async function testExportCollarAlerts() {
|
||
try {
|
||
console.log('\n=== 测试导出项圈预警数据功能 ===');
|
||
|
||
// 测试JSON格式导出
|
||
const exportResponse = await api.get('/collar/export?format=json&limit=5');
|
||
|
||
if (exportResponse.status === 200 && exportResponse.data.success) {
|
||
const exportData = exportResponse.data.data;
|
||
logTest('导出项圈预警数据', true, `成功导出 ${exportData.length} 条预警数据`);
|
||
|
||
// 验证导出数据
|
||
const hasExportData = Array.isArray(exportData) && exportData.length > 0;
|
||
logTest('导出数据验证', hasExportData, hasExportData ? '导出数据正确' : '导出数据为空');
|
||
|
||
// 验证项圈特有字段
|
||
if (exportData.length > 0) {
|
||
const firstAlert = exportData[0];
|
||
const hasCollarFields = firstAlert.hasOwnProperty('collarNumber') && firstAlert.hasOwnProperty('wearStatus');
|
||
logTest('导出数据项圈字段验证', hasCollarFields, hasCollarFields ? '导出数据包含项圈字段' : '导出数据缺少项圈字段');
|
||
}
|
||
} else {
|
||
logTest('导出项圈预警数据', false, `导出失败: ${exportResponse.data.message || '未知错误'}`);
|
||
}
|
||
} catch (error) {
|
||
logTest('导出项圈预警数据', false, `请求异常: ${error.message}`);
|
||
}
|
||
}
|
||
|
||
async function testErrorHandling() {
|
||
try {
|
||
console.log('\n=== 测试错误处理 ===');
|
||
|
||
// 测试无效的预警ID
|
||
const invalidIdResponse = await api.get('/collar/invalid_id');
|
||
|
||
if (invalidIdResponse.status === 400 || invalidIdResponse.status === 404) {
|
||
logTest('无效ID错误处理', true, '正确处理无效ID错误');
|
||
} else {
|
||
logTest('无效ID错误处理', false, '未正确处理无效ID错误');
|
||
}
|
||
|
||
// 测试无效的筛选参数
|
||
const invalidFilterResponse = await api.get('/collar?alertType=invalid_type');
|
||
|
||
if (invalidFilterResponse.status === 200) {
|
||
logTest('无效筛选参数处理', true, '正确处理无效筛选参数');
|
||
} else {
|
||
logTest('无效筛选参数处理', false, '未正确处理无效筛选参数');
|
||
}
|
||
} catch (error) {
|
||
logTest('错误处理测试', false, `请求异常: ${error.message}`);
|
||
}
|
||
}
|
||
|
||
// 主测试函数
|
||
async function runAllTests() {
|
||
console.log('🚀 开始智能项圈预警API测试...\n');
|
||
|
||
try {
|
||
await testGetCollarAlertStats();
|
||
await testGetCollarAlerts();
|
||
await testGetCollarAlertsWithFilters();
|
||
await testGetCollarAlertById();
|
||
await testHandleCollarAlert();
|
||
await testBatchHandleCollarAlerts();
|
||
await testExportCollarAlerts();
|
||
await testErrorHandling();
|
||
|
||
// 输出测试结果
|
||
console.log('\n' + '='.repeat(50));
|
||
console.log('📊 测试结果汇总:');
|
||
console.log(`总测试数: ${testResults.total}`);
|
||
console.log(`通过: ${testResults.passed} ✅`);
|
||
console.log(`失败: ${testResults.failed} ❌`);
|
||
console.log(`成功率: ${((testResults.passed / testResults.total) * 100).toFixed(2)}%`);
|
||
|
||
if (testResults.errors.length > 0) {
|
||
console.log('\n❌ 失败详情:');
|
||
testResults.errors.forEach((error, index) => {
|
||
console.log(`${index + 1}. ${error}`);
|
||
});
|
||
}
|
||
|
||
if (testResults.failed === 0) {
|
||
console.log('\n🎉 所有测试通过!智能项圈预警API功能正常。');
|
||
} else {
|
||
console.log('\n⚠️ 部分测试失败,请检查相关功能。');
|
||
}
|
||
|
||
} catch (error) {
|
||
console.error('❌ 测试执行异常:', error.message);
|
||
}
|
||
}
|
||
|
||
// 如果直接运行此脚本
|
||
if (require.main === module) {
|
||
runAllTests().catch(console.error);
|
||
}
|
||
|
||
module.exports = {
|
||
runAllTests,
|
||
testGetCollarAlertStats,
|
||
testGetCollarAlerts,
|
||
testGetCollarAlertById,
|
||
testHandleCollarAlert,
|
||
testBatchHandleCollarAlerts,
|
||
testExportCollarAlerts
|
||
};
|