如何从 Azure IoT 设备收集调试日志

选择编程语言

若要排查设备问题,有时从设备收集低级别的调试日志会很有用。 本文介绍如何从设备 SDK 捕获调试日志。 本文中所述的步骤假设你可以直接或远程访问设备。

警告

如果你要与支持工程师共享日志或将其添加到 GitHub 问题中,请务必删除任何机密信息,例如连接字符串。

捕获跟踪日志

若要从 Azure IoT 中心客户端连接捕获跟踪数据,请使用客户端 logtrace 选项。

可以使用便捷层或低级层来设置选项:

// Convenience layer for device client
IOTHUB_CLIENT_RESULT IoTHubDeviceClient_SetOption(IOTHUB_DEVICE_CLIENT_HANDLE iotHubClientHandle, const char* optionName, const void* value);

// Lower layer for device client
IOTHUB_CLIENT_RESULT IoTHubDeviceClient_LL_SetOption(IOTHUB_DEVICE_CLIENT_LL_HANDLE iotHubClientHandle, const char* optionName, const void* value);

pnp_temperature_controller.c 示例中的以下示例演示了如何使用便捷层启用跟踪捕获:

static bool g_hubClientTraceEnabled = true;

...

else if ((iothubClientResult = IoTHubDeviceClient_LL_SetOption(deviceClient, OPTION_LOG_TRACE, &g_hubClientTraceEnabled)) != IOTHUB_CLIENT_OK)
{
    LogError("Unable to set logging option, error=%d", iothubClientResult);
    result = false;
}

跟踪输出将写入到 stdout

若要详细了解如何从 C SDK 捕获和查看跟踪数据,请参阅 IoT 中心设备和模块客户端选项

在 Windows 上捕获跟踪数据

在 Windows 上,适用于 .NET 的 Azure IoT SDK 使用适用于 Windows 的事件跟踪 (ETW) 导出跟踪数据。 SDK 存储库包含用于启动和停止捕获的 PowerShell 脚本

在设备上提升的 PowerShell 提示符下运行以下脚本。 iot_providers.txt 文件列出了 IoT SDK 提供程序的 GUID。 若要在名为 iot.etl 的文件中开始捕获跟踪数据,请运行以下命令:

.\iot_startlog.ps1 -Output iot.etl -ProviderFile .\iot_providers.txt -TraceName IotTrace

若要停止捕获,请运行以下命令:

 .\iot_stoplog.ps1 -TraceName IotTrace

若要详细了解如何从 .NET SDK 捕获和查看跟踪数据,请参阅捕获跟踪

在 Linux 上捕获跟踪数据

在 Linux 上,可以使用 dotnet-trace 工具捕获跟踪数据。 若要安装该工具,请运行以下命令:

dotnet tool install --global dotnet-trace

在可以收集跟踪之前,需要获取设备客户端应用程序的进程 ID。 若要列出设备上的进程,请运行以下命令:

dotnet-trace ps

以下示例输出包含进程 ID 为 24987 的 TemperatureController 设备客户端进程:

24772  dotnet                 /usr/share/dotnet/dotnet                 dotnet run
25206  dotnet                 /usr/share/dotnet/dotnet                 dotnet trace ps
24987  TemperatureController  /bin/Debug/net6.0/TemperatureController

若要将此进程的跟踪数据捕获到名为 device.nettrace 的文件中,请运行以下命令:

dotnet-trace collect --process-id 24987 --output device.nettrace --providers Microsoft-Azure-Devices-Device-Client

providers 参数是逗号分隔的事件提供程序列表。 以下列表显示了 Azure IoT SDK 提供程序:

  • Microsoft-Azure-Devices-Device-Client
  • Microsoft-Azure-Devices-Service-Client
  • Microsoft-Azure-Devices-Provisioning-Client
  • Microsoft-Azure-Devices-Provisioning-Transport-Amqp
  • Microsoft-Azure-Devices-Provisioning-Transport-Http
  • Microsoft-Azure-Devices-Provisioning-Transport-Mqtt.
  • Microsoft-Azure-Devices-Security-Tpm

若要详细了解如何从 .NET SDK 捕获和查看跟踪数据,请参阅捕获跟踪

适用于 Java 的 Azure IoT SDK 使用 SLF4j 导出跟踪数据。 SDK 中包含的示例使用以下属性文件配置 SLF4j:src/main/resources/log4j2.properties。 每个示例中的属性文件将配置向控制台记录日志的设置:

status = error
name = Log4j2PropertiesConfig

appenders = console

appender.console.type = Console
appender.console.name = LogToConsole
appender.console.layout.type = PatternLayout
appender.console.layout.pattern = %d %p (%t) [%c] - %m%n

rootLogger.level = debug
rootLogger.appenderRefs = stdout
rootLogger.appenderRef.stdout.ref = LogToConsole

若要将 SDK 的调试消息记录到某个文件,可使用以下配置:

status = error
name = Log4j2PropertiesConfig

# Log file location - choose a suitable path for your OS
property.filePath = c/temp/logs

appenders = console,file

appender.console.type = Console
appender.console.name = LogToConsole
appender.console.layout.type = PatternLayout
appender.console.layout.pattern = %d %p (%t) [%c] - %m%n

appender.file.type = File
appender.file.name = LogToFile
appender.file.fileName = ${filePath}/device.log
appender.file.layout.type = PatternLayout
appender.file.layout.pattern = %d %p (%t) [%c] - %m%n

loggers.file
logger.file.name = com.microsoft.azure.sdk.iot
logger.file.level = debug
logger.file.appenderRefs = logfile
logger.file.appenderRef.logfile.ref = LogToFile

rootLogger.level = debug
rootLogger.appenderRefs = stdout
rootLogger.appenderRef.stdout.ref = LogToConsole

若要详细了解如何从 Java SDK 捕获和查看跟踪数据,请参阅 Azure IoT SDK 日志记录

适用于 Node.js 的 Azure IoT SDK 使用调试库捕获跟踪日志。 可以使用 DEBUG 环境变量控制跟踪。

若要从 SDK 和低级别 MQTT 库捕获跟踪信息,请在运行设备代码之前设置以下环境变量:

export DEBUG=azure*,mqtt*

提示

如果使用的是 AMQP 协议,请使用 rhea* 从低级别库捕获跟踪信息。

若要将跟踪数据捕获到名为 trace.log 的文件,请使用如下命令:

node pnp_temperature_controller.js 2> trace.log

若要详细了解如何从 Node.js SDK 捕获和查看跟踪数据,请参阅故障排除指南 - 设备

适用于 Python 的 Azure IoT SDK 使用日志记录模块捕获跟踪日志。 使用日志记录配置文件控制跟踪。 如果使用 SDK 中的某个示例,可能需要修改代码以从某个文件加载日志记录配置:

替换以下行:

logging.basicConfig(level=logging.ERROR)

替换为以下行:

logging.config.fileConfig('logging.conf')

创建名为 logging.conf 的文件。 以下示例从文件中带有前缀 azure.iot.device 的所有模块捕获调试信息:

[loggers]
keys=root,azure

[handlers]
keys=consoleHandler,fileHandler

[formatters]
keys=simpleFormatter

[logger_root]
level=ERROR
handlers=consoleHandler

[logger_azure]
level=DEBUG
handlers=fileHandler
qualname=azure.iot.device
propagate=0

[handler_consoleHandler]
class=StreamHandler
level=DEBUG
formatter=simpleFormatter
args=(sys.stdout,)

[handler_fileHandler]
class=FileHandler
level=DEBUG
formatter=simpleFormatter
args=('device.log', 'w')

[formatter_simpleFormatter]
format=%(asctime)s - %(name)s - %(levelname)s - %(message)s

若要详细了解如何从 Python SDK 捕获和查看跟踪数据,请参阅在适用于 Python 的 Azure 库中配置日志记录

若要从适用于 Embedded C 的 Azure SDK 库捕获嵌入式 IoT 设备的跟踪信息,请在设备代码中添加一个用于处理跟踪消息的回调函数。 例如,回调函数可以写入控制台并将消息保存到某个文件中。

以下示例演示如何修改 paho_iot_hub_sas_telemetry_sample.c,以捕获跟踪信息并将其写入控制台:

#include <azure/core/az_log.h>

...

static void write_log_message(az_log_classification, az_span);

...

int main(void)
{
  az_log_set_message_callback(write_log_message);

  ...
}

static void write_log_message(az_log_classification classification, az_span message)
{
   (void)classification;
   printf("TRACE:\t\t%.*s\n", az_span_size(message), az_span_ptr(message));
}

若要详细了解如何在 Embedded C SDK 中捕获和筛选跟踪数据,请参阅日志记录 SDK 操作

后续步骤

如果需要更多帮助,可以通过 Microsoft Q&A 和 Stack Overflow 论坛联系 Azure 专家。 或者,你也可以提出 Azure 支持事件。 请转到 Azure 支持站点并选择 获取支持