From 4cbc4c70b3ced30317e049f5a63a7924f1716ea1 Mon Sep 17 00:00:00 2001 From: root Date: Tue, 26 Aug 2025 17:51:52 +0800 Subject: [PATCH] 111 --- app/core/device/command_executor.py | 10 +- app/services/auto_discovery_adb_service.py | 6 +- docs/modify.md | 101 +++++++++++++++++++++ 3 files changed, 115 insertions(+), 2 deletions(-) diff --git a/app/core/device/command_executor.py b/app/core/device/command_executor.py index 6dc1e21..b61e727 100644 --- a/app/core/device/command_executor.py +++ b/app/core/device/command_executor.py @@ -118,8 +118,10 @@ class CommandExecutor: logger.info(f"开始执行设备 {device_id} 的命令,命令数量: {len(device_task.commands)}") # 获取设备信息(支持注册设备和自动发现设备) + logger.debug(f"获取设备信息: {device_id}") device = await self.device_manager.get_device_info_unified(device_id) if not device: + logger.warning(f"设备不存在: {device_id}") return DeviceShellResult( device_id=device_id, success=False, @@ -130,17 +132,23 @@ class CommandExecutor: results=[] ) + logger.debug(f"设备信息获取成功: {device_id}, 来源={device.get('source', 'unknown')}, 协议={device.get('protocol_type', 'unknown')}") + # 执行每个命令 command_results = [] - for cmd_task in device_task.commands: + for i, cmd_task in enumerate(device_task.commands): + logger.debug(f"执行命令 {i+1}/{len(device_task.commands)}: {device_id} -> {cmd_task.command}") result = await self._execute_single_command(device, cmd_task) command_results.append(result) + logger.debug(f"命令 {i+1} 执行完成: {device_id} -> {cmd_task.command}, 成功={result.success}") # 统计命令执行结果 total_commands = len(command_results) success_commands = sum(1 for result in command_results if result.success) failed_commands = total_commands - success_commands + logger.info(f"设备命令执行统计: {device_id}, 总数={total_commands}, 成功={success_commands}, 失败={failed_commands}") + # 检查是否所有命令都成功 all_success = all(result.success for result in command_results) diff --git a/app/services/auto_discovery_adb_service.py b/app/services/auto_discovery_adb_service.py index 699545a..0820423 100644 --- a/app/services/auto_discovery_adb_service.py +++ b/app/services/auto_discovery_adb_service.py @@ -424,4 +424,8 @@ class AutoDiscoveryAdbService: except Exception as e: logger.error("获取设备日志失败", device_serial=device_serial, error=str(e)) - return ShellResponse(success=False, output="", error=str(e), exit_code=-1) \ No newline at end of file + return ShellResponse(success=False, output="", error=str(e), exit_code=-1) + + +# 全局自动发现ADB服务实例 +auto_discovery_adb_service = AutoDiscoveryAdbService() \ No newline at end of file diff --git a/docs/modify.md b/docs/modify.md index 3937b7f..552734d 100644 --- a/docs/modify.md +++ b/docs/modify.md @@ -1,5 +1,106 @@ # 修改记录 +## 2025-08-26 修复CommandExecutor设备获取逻辑错误并增强日志记录 + +**问题描述:** +在 `app/core/device/command_executor.py` 的 `_execute_single_command` 方法中,代码尝试访问 `device.source`,但是从 `device_manager.get_device_info_unified()` 返回的是一个字典,而不是对象。这导致错误:"'dict' object has no attribute 'source'"。 + +**问题分析:** +1. `get_device_info_unified` 方法返回的是一个字典,其中包含 `source` 字段 +2. 但在 `command_executor.py` 的第 158 行,代码试图访问 `device.source`,这应该是 `device["source"]` +3. 同样的问题也出现在 `device.device_id` 和 `device.protocol_type` 的访问上 +4. 缺少详细的日志记录,难以跟踪命令执行过程 +5. `auto_discovery_adb_service` 实例没有在模块中创建和导出 + +**修复方案:** +1. 修改 `command_executor.py` 中的设备属性访问方式,从对象属性访问改为字典键访问 +2. 添加详细的日志记录,便于跟踪和调试命令执行过程 +3. 在 `auto_discovery_adb_service.py` 中创建并导出全局实例 + +**修改内容:** + +1. **修复设备属性访问**: +```python +# 修改前:错误的对象属性访问 +if device.source == "registered": + result = await self.device_dispatcher.execute_operation( + device_id=device.device_id, + protocol_type=device.protocol_type, + operation="execute_command", + command=cmd_task.command, + timeout=cmd_task.timeout + ) + +# 修改后:正确的字典键访问 +device_id = device["device_id"] +device_source = device["source"] +command = cmd_task.command + +if device_source == "registered": + result = await self.device_dispatcher.execute_operation( + device_id=device_id, + protocol_type=device["protocol_type"], + operation="execute_command", + command=command, + timeout=cmd_task.timeout + ) +``` + +2. **增强日志记录**: +```python +# 设备信息获取日志 +logger.debug(f"获取设备信息: {device_id}") +logger.debug(f"设备信息获取成功: {device_id}, 来源={device.get('source', 'unknown')}, 协议={device.get('protocol_type', 'unknown')}") + +# 命令执行开始日志 +logger.debug(f"开始执行单个命令: 设备={device_id}, 来源={device_source}, 命令={command}") + +# 设备类型执行日志 +logger.debug(f"注册设备执行命令: {device_id} -> {command}") +logger.debug(f"自动发现设备执行命令: {device_id} -> {command}") + +# 命令执行完成日志 +logger.debug(f"注册设备命令执行完成: {device_id} -> {command}, 结果类型={type(result)}") +logger.debug(f"自动发现设备命令执行完成: {device_id} -> {command}, 结果类型={type(result)}") + +# 命令执行结果日志 +logger.debug(f"命令执行成功: {device_id} -> {command}, 输出长度={len(result.output) if result.output else 0}") +logger.warning(f"命令执行返回格式不符合规范: {device_id} -> {command}, 返回类型={type(result)}") + +# 批量命令执行日志 +logger.debug(f"执行命令 {i+1}/{len(device_task.commands)}: {device_id} -> {cmd_task.command}") +logger.debug(f"命令 {i+1} 执行完成: {device_id} -> {cmd_task.command}, 成功={result.success}") +logger.info(f"设备命令执行统计: {device_id}, 总数={total_commands}, 成功={success_commands}, 失败={failed_commands}") + +# 错误处理日志 +logger.warning(f"设备不存在: {device_id}") +logger.error(f"命令执行失败: {device_id} -> {command}, 错误={e}") +``` + +3. **创建全局实例**: +```python +# 在 app/services/auto_discovery_adb_service.py 文件末尾添加 +# 全局自动发现ADB服务实例 +auto_discovery_adb_service = AutoDiscoveryAdbService() +``` + +**修复效果:** +- ✅ 解决了 "'dict' object has no attribute 'source'" 错误 +- ✅ 修复了设备属性访问方式 +- ✅ 解决了 "cannot import name 'auto_discovery_adb_service'" 导入错误 +- ✅ 添加了详细的调试日志,便于跟踪命令执行过程 +- ✅ 提供了设备信息获取、命令执行、结果统计的完整日志记录 +- ✅ 保持了原有功能的完整性 +- ✅ 支持注册设备和自动发现设备的命令执行 + +**技术说明:** +- 设备信息统一返回字典格式,包含 `source`、`device_id`、`protocol_type` 等字段 +- 注册设备的 `source` 字段值为 "registered" +- 自动发现设备的 `source` 字段值为 "auto_discovered" +- 根据设备来源选择不同的命令执行方式 +- 详细的日志记录帮助快速定位问题和监控执行状态 +- 全局实例的创建确保服务可以被正确导入和使用 + ## 2025-01-XX 重构设备获取逻辑:统一到DeviceManager **问题描述:**