みち草

Azure中心にまとめる技術情報ブログ

コピペで使える Azure Resource Graph サンプル クエリ

はじめに

今回は、Azure のリソース検索に便利な Resource Graph のクエリについてです。

Resource Graph は特定のリソースを検出するうえで非常に便利ですが、 KQL を扱う必要があり、最初のうちはとっつきにくいところがあります。

ということで、コピペでそのまま使えるものをいくつかサンプルとして挙げてみます。

IaaS 系中心ですが、そのまま使用する、ちょっと手を加える、書き方を知るなど、何かしらの参考になれば幸いです。

目次

KQL リファレンス

関数の説明までは載せていないので、KQL のリファレンスを貼っておきます。

以下を参照してもらったり、コメント(先頭にダブルスラッシュでコメント化) したり、値を変えたりして。

docs.microsoft.com

もしくはこっちを参照すれば大体載っていると思います。
※左の縦メニューの中に型とか演算子とかいろいろ

docs.microsoft.com

SQL がわかる方はここを見ると KQL の理解が早いかもしれません。

docs.microsoft.com

Resource Graph クエリ サンプル

Compute 系

OS 種類別の VM 台数

OS 別の集計

Resources
| where type =~ 'Microsoft.Compute/virtualMachines'
| summarize count() by tostring(properties.storageProfile.osDisk.osType)

実行結果

ResourceGraph1

VM の情報と、使用している Dedicated Host 名
Resources
| where type =~ "Microsoft.Compute/virtualmachines"
| project name, resourceGroup, subscriptionId,  dedicatedHost=split(properties.host.id,"/")[8]

実行結果

サイズ別 VM 台数を、降順で表示

サイズ別の集計

resources
| where type =~ "Microsoft.Compute/VirtualMachines"
| summarize count() by tostring(properties.hardwareProfile.vmSize)
| sort by count_ desc 

実行結果

Storage 系

古いスナップショットの上位 10 個

使われず置いたままのスナップショット検索に。

Resources
| where type =~ "Microsoft.Compute/snapshots"
| project name, resourceGroup,properties.timeCreated
| sort by tostring(properties_timeCreated) asc
| take 10

実行結果

ResourceGraph2

未接続の管理ディスク

使われず置いたままの管理ディスク検索に。

Resources
| where type =~ "Microsoft.Compute/disks"
| where properties.diskState == "Unattached"

実行結果

ResourceGraph3

"Blob パブリック アクセスを許可" 設定が有効のストレージ アカウント

ストレージアカウント側の "パブリック アクセス許可" が有効なだけで、 実際にパブリック公開しているかどうかはコンテナー側の設定によります。

Resources
| where type =~ "Microsoft.Storage/storageaccounts"
| where properties.allowBlobPublicAccess == true

実行結果

ResourceGraph5

各ストレージ アカウントの "安全な転送が必要" と "Blob パブリックアクセスを許可"、"TLS の最小バージョン" の設定値

原因がわかりませんが、稀に設定値が空欄となり表示されないリソースがあります。
※作成時期が古いものだとなるかも?

Resources
| where type =~ "Microsoft.Storage/storageaccounts"
| project name, resourceGroup, properties.supportsHttpsTrafficOnly, properties.allowBlobPublicAccess, properties.minimumTlsVersion

実行結果

ResourceGraph6

Network 系

未接続のパブリック IP アドレス

使われず置いたままのパブリック IP アドレス検索に。

Resources
| where type =~ "Microsoft.Network/publicipaddresses"
| where isnull(properties.ipConfiguration)

実行結果

ResourceGraph4

Small もしくはインスタンスが 1 台以下の Application Gateway

Small 、もしくはインスタンスが 1 台以下の場合、Application Gateway の SLA 対象外です。

Resources
| where type =~ "Microsoft.Network/applicationgateways"
| where properties.sku.name == "Standard_Small" or properties.sku.capacity <= 1
| project name, properties.sku.name, properties.sku.capacity
| sort by tostring(properties_sku_name), tostring(properties_sku_capacity) asc

実行結果

ResourceGraph7

"高速ネットワーク" が無効なネットワーク インターフェイス

これだと NIC の設定値を見ているだけなので、どの VM かがわかりづらいです。
次に VM テーブルとの join 版を掲載しています。

Resources
| where type =~ "Microsoft.Network/NetworkInterfaces"
| where properties.enableAcceleratedNetworking == "false"
| project name, subscriptionId, properties.enableAcceleratedNetworking

実行結果

ResourceGraph8

各 VM のネットワーク インターフェイス名と "高速ネットワーク" の設定値 (join 版)

VM のテーブルと NIC のテーブルを join することで、どの VM のどの NIC かがわかりやすくなります。 ※複数 NIC の場合は考慮していません。

resources
| where type =~ "Microsoft.Compute/virtualmachines"
| project name, resourceGroup, size=tostring(properties.hardwareProfile.vmSize), subscriptionId, nic=tostring(split(properties.networkProfile.networkInterfaces[0].id, "/")[8])
| join kind = leftouter ( resources| where type =~ "Microsoft.Network/NetworkInterfaces") on $left.nic == $right.name
| project vm=name,subscriptionId, resourceGroup, nic, size, enableAcceleratedNetworking=properties.enableAcceleratedNetworking

実行結果

ResourceGraph9

Basic ロードバランサー

リタイアする Basic ロードバランサーの発見用に

Resources
| where type =~ "Microsoft.Network/Loadbalancers"
| where sku.name == "Basic"

実行結果

バックエンド プールが空の Application Gateway

使われず置いたままの Application Gateway 検索に。

resources
| where type =~ "Microsoft.Network/applicationGateways"
| where properties.backendAddressPools.properties.backendAddresses == ""

実行結果

Basic SKU のパブリック IP アドレス、ロードバランサー

リタイアに向けての検出用

resources
| where type == "microsoft.network/publicipaddresses" or type == "microsoft.network/loadbalancers"
| where sku.name == "Basic"

実行結果

ネットワーク インターフェースごとの、DNS 設定

個別設定の把握用

resources
| where type =~ "Microsoft.Network/networkinterfaces"
| project id, name, resourceGroup, DNS=properties.dnsSettings.dnsServers

実行結果

送信元を Any で許可している受信規則を持つ NSG とそのルール情報

広く許可し過ぎなルールを発見したいときに

resources
| where type =~ "Microsoft.Network/networksecuritygroups"
| mv-expand rule = properties.securityRules
| where tostring(rule.properties.sourceAddressPrefix) == "*" and tostring(rule.properties.access) == "Allow" and tostring(rule.properties.direction) == "Inbound"
| project id, name, resourceGroup, subscriptionId, ruleName = rule.name, rule

実行結果

Azure FW とそのプライベート IP アドレス

Azure FW 毎にプライベート IP アドレスを確認するのが面倒なときに

resources
| where type =~ "Microsoft.Network/azurefirewalls"
| mv-expand  ipCnof = properties.ipConfigurations
| extend fwIp = ipCnof.properties.privateIPAddress
| project id, name, resourceGroup, fwIp

実行結果

Application Gateway と、そのバックエンドに指定されている IP アドレス

どんな IP が指定されていたっけ?というのをまとめて確認したいときに

resources
| where type =~ "Microsoft.Network/applicationgateways"
| where location == "japaneast"
| mv-expand backendPool = properties.backendAddressPools
| mv-expand backendAddresses = backendPool.properties.backendAddresses
| extend backendAddress = tostring(backendAddresses.ipAddress)
| project id, name, resourceGroup, backendAddress

実行結果

その他

Notification Id 毎の Azure リソースのメンテナンス情報
maintenanceresources
| extend p = parse_json(properties)
| mvexpand d = p.value
| project  notificationId=properties.value[0].notificationId, id=substring(id, 0, indexof(id, "/providers/Microsoft.Maintenance")), resourceGroup, subscriptionId, status=d.status, detail=d

実行結果
メンテナンス対象リソースがないため取れたら追加

メンテナンス対象のリソースとその日時など

メンテナンス対象とその状況取得用

maintenanceresources
| mv-expand properties.value
| project notificationId=properties_value.notificationId, resourceId=properties_value.properties.resourceId ,resourceGroup, location, subscriptionId, Status=properties_value.status, StartTimeUtc=properties_value.startTimeUtc, endTimeUtc=properties_value.endTimeUtc, impactType=properties_value.impactType
| where Status != "Completed"

実行結果

こっちのサポート チームブログを見た方がいろいろ載ってていいかも

jpaztech.github.io

終わりに

今回はサンプル集としての記事でした。
クエリについては習うより慣れろで実際に動かしてみるのが一番かと思いますので、リファレンスを見つつ実際に動かしてみてください。

関数を使いこなせればもっといろいろできて楽しそうなのですが、自分でもまだそこまで扱えておらず join をちょっと試したくらい…
同じような、使ってみたいけどよーわからん、という方の参考になれば嬉しいです。
また、今後新しいクエリを作成できたら、更新していきたいと思います。