为什么无法通过新的Azure门户配置Azure诊断以使用Azure表存储?

时间:2016-03-15 09:04:08

标签: azure logging asp.net-web-api azure-storage azure-diagnostics

我正在开发一个将在Azure中托管的web api。我想使用Azure诊断程序将错误记录到Azure表存储。 在Classic门户中,我可以将日志配置为Azure表存储。

Classic Portal Diagnostic Settings

但是在新的Azure门户中,我唯一的存储选项是使用Blob存储:

New Azure Portal Settings

似乎如果我要使用Web角色,我可以配置数据存储以进行诊断,但在我开发web api时,我不想为每个api创建单独的Web角色这样我就可以登录到天蓝色的桌子了。

有没有办法以编程方式配置azure诊断程序,以便在不使用Web角色的情况下将日志消息传播到特定数据存储?有没有理由为什么新的Azure门户只有blob存储的诊断设置而不是表存储?

我目前可以通过使用经典门户来解决此问题,但我担心诊断的表存储最终会被弃用,因为它尚未包含在新门户的诊断设置中。

2 个答案:

答案 0 :(得分:3)

(我会对这个问题做一些暗示,因为这是我在搜索解决方案时发现的最相关的StackOverflow问题,因为它不再可能通过经典门户网站完成此操作)

免责声明:微软似乎已经删除了在Azure门户中记录到Table的支持,因此我不知道这是否已被弃用或将很快被弃用,但我有一个现在可以使用的解决方案(31.03.2017) ):

有确定日志记录的特定设置,我首先从Azure Powershell github中的问题中找到有关此问题的信息:https://github.com/Azure/azure-powershell/issues/317

我们需要的具体设置是(来自github):

  

AzureTableTraceEnabled = True,& AppSettings有:   DIAGNOSTICS_AZURETABLESASURL

使用(GUI导航)下的优秀资源浏览器(https://resources.azure.com):

  

/订阅/ {subscriptionName} / resourceGroups / {resourceGroupName} /providers/Microsoft.Web/sites/ {SITENAME} /配置/日志

我能够在属性中找到设置AzureTableTraceEnabled。

属性AzureTableTraceEnabled具有Level和sasURL。根据我的经验,更新这两个值(Level ="详细" sasUrl =" someSASurl")将起作用,因为更新sasURL会在appsettings中设置DIAGNOSTICS_AZURETABLESASURL。

我们如何改变这个?我在Powershell中做到了。我首先尝试了cmdlet Get-AzureRmWebApp,但找不到我想要的东西 - 旧的Get-AzureWebSite确实显示了AzureTableTraceEnabled,但我无法让它更新(也许有更多powershell \ azure经验的人可以带来如何输入使用ASM cmdlet执行此操作。)

对我有用的解决方案是通过Set-AzureRmResource命令设置属性,并使用以下设置:

Set-AzureRmResource -PropertyObject $PropertiesObject -ResourceGroupName "$ResourceGroupName" -ResourceType Microsoft.Web/sites/config -ResourceName "$ResourceName/logs" -ApiVersion 2015-08-01 -Force

$ PropertiesObject如下所示:

$PropertiesObject = @{applicationLogs=@{azureTableStorage=@{level="$Level";sasUrl="$SASUrl"}}}

级别对应于"错误","警告","信息","详细"和"关"。

也可以在ARM模板中执行此操作(重要位在站点中日志资源的属性中):

        {
            "apiVersion": "2015-08-01",
            "name": "[variables('webSiteName')]",
            "type": "Microsoft.Web/sites",
            "location": "[resourceGroup().location]",
            "tags": {
                "displayName": "WebApp"
            },
            "dependsOn": [
                "[resourceId('Microsoft.Web/serverfarms/', variables('hostingPlanName'))]"
            ],
            "properties": {
                "name": "[variables('webSiteName')]",
                "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', variables('hostingPlanName'))]"
            },
            "resources": [
            {
                "name": "logs",
                "type": "config",
                "apiVersion": "2015-08-01",
                "dependsOn": [
                    "[resourceId('Microsoft.Web/sites/', variables('webSiteName'))]"
                ],
                "tags": {
                    "displayName": "LogSettings"
                },
                "properties": {
                    "azureTableStorage": {
                        "level": "Verbose",
                        "sasUrl": "SASURL"
                    }
                }
            }
        }

在ARM中执行此操作的问题是,我还没有找到生成正确SAS的方法, 可以提取Azure存储帐户密钥(来自:{{ 3}}):

"properties": {
    "type": "AzureStorage",
        "typeProperties": {
            "connectionString": "[concat('DefaultEndpointsProtocol=https;AccountName=', variables('storageAccountName'),';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', variables('storageAccountName')), providers('Microsoft.Storage', 'storageAccounts').apiVersions[0]).keys[0].value)]"
    }
}

还有一些聪明的方法可以使用链接模板生成它们(来自:ARM - How can I get the access key from a storage account to use in AppSettings later in the template?)。

我采用的当前解决方案(时间限制)是一个自定义的Powershell脚本,看起来像这样:

...
$SASUrl = New-AzureStorageTableSASToken -Name $LogTable -Permission $Permissions -Context $StorageContext -StartTime $StartTime -ExpiryTime $ExpiryTime -FullUri
$PropertiesObject = @{applicationLogs=@{azureTableStorage=@{level="$Level";sasUrl="$SASUrl"}}}
Set-AzureRmResource -PropertyObject $PropertiesObject -ResourceGroupName "$ResourceGroupName" -ResourceType Microsoft.Web/sites/config -ResourceName "$ResourceName/logs" -ApiVersion 2015-08-01 -Force
...

这是一个非常难看的解决方案,因为除了ARM模板之外,它还需要维护一些额外的东西 - 但它很容易,快速,并且在我们等待ARM模板更新时(或者对于比我来,开导我们。)

答案 1 :(得分:2)

我们通常不建议将表用于日志数据 - 它可能导致仅附加模式在规模上对表存储无效。请参阅本指南Table Design Guide中的日志数据反模式。通常我们会看到即使人们认为日志数据是结构化的 - 他们通常会查询它使Blob更有效率。

摘自设计指南:

  

记录数据反模式

     

通常,您应该使用Blob服务而不是Table服务来存储日志数据。

     

背景和问题

     

日志数据的一个常见用例是检索特定日期/时间范围的日志条目选择:例如,您要查找应用程序在15:04和15之间记录的所有错误和关键消息: 06在特定日期。您不希望使用日志消息的日期和时间来确定将日志实体保存到的分区:这会导致热分区,因为在任何给定时间,所有日志实体都将共享相同的PartitionKey值(请参阅参考资料部分)前置/附加反模式)。   ...

     

解决方案

     

上一节强调了尝试使用Table服务存储日志条目的问题,并提出了两个不能令人满意的设计。一种解决方案导致热分区,存在写入日志消息的性能不佳的风险;另一种解决方案导致查询性能较差,因为需要扫描表中的每个分区以检索特定时间跨度的日志消息。 Blob存储为此类场景提供了更好的解决方案,这就是Azure Storage Analytics存储其收集的日志数据的方式。

     

本节概述了Storage Analytics如何将日志数据存储在Blob存储中,作为这种存储您通常按范围查询的数据的方法的说明。

     

Storage Analytics以多个blob中的分隔格式存储日志消息。分隔格式使客户端应用程序可以轻松解析日志消息中的数据。

     

Storage Analytics使用blob的命名约定,使您能够找到包含要搜索的日志消息的Blob(或blob)。例如,名为“queue / 2014/07/31/1800 / 000001.log”的blob包含与2014年7月31日18:00开始的小时的队列服务相关的日志消息。“000001”表示此是这个时期的第一个日志文件。 Storage Analytics还会记录存储在文件中的第一个和最后一个日志消息的时间戳,作为blob元数据的一部分。 blob存储的API使您能够基于名称前缀在容器中找到blob:要查找包含从18:00开始的小时的队列日志数据的所有blob,您可以使用前缀“queue / 2014/07/31 / 1800“。

     

Storage Analytics在内部缓冲日志消息,然后定期更新相应的blob或使用最新一批日志条目创建新的blob。这减少了它必须对blob服务执行的写入次数。

     

如果要在自己的应用程序中实现类似的解决方案,则必须考虑如何管理可靠性(将每个日志条目写入blob存储)与成本和可伸缩性之间的权衡(缓冲应用程序中的更新和将它们分批写入blob存储区。)

     

问题和注意事项

     

在决定如何存储日志数据时,请考虑以下几点:

     
      
  • 如果您创建的表设计可以避免潜在的热门分区,您可能会发现无法有效地访问日志数据。

  •   
  • 要处理日志数据,客户端通常需要加载许多记录。

  •   
  • 虽然日志数据通常是结构化的,但blob存储可能是更好的解决方案。

  •