You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python调用Azure Graph API获取资源组标签的分页处理求助

解决Azure Resource Graph API分页获取全量资源组标签的问题

问题场景

在Azure门户Graph Explorer中执行以下Kusto查询可返回租户内2000+条资源组标签数据:

resourcecontainers
| where type == 'microsoft.resources/subscriptions/resourcegroups'
| extend dates=format_datetime(now(), "yyyy-MM-dd")
| join kind=leftouter (
    resourcecontainers
    | where type == 'microsoft.resources/subscriptions'
    | project SubscriptionName=name, subscriptionId)
    on subscriptionId
| project SubscriptionName, subscriptionId, resourceGroup, 
    financial_contact=tags.financial_contact, security_contact=tags.security_contact

但使用下方Python脚本调用时,仅返回530条结果,响应中skip_token为None,尝试skip/limit参数未解决分页问题,无法获取全量数据:

from azure.identity import DefaultAzureCredential
from azure.mgmt.resourcegraph import ResourceGraphClient
from azure.mgmt.resource import ResourceManagementClient
from azure.mgmt.resourcegraph.models import *
import json

# Initialize Azure credentials
credentials = DefaultAzureCredential()

# Initialize Resource Graph client
resource_graph_client = ResourceGraphClient(credentials)
skip = 0
result = []


query_code = f"""
resourcecontainers
| where type == 'microsoft.resources/subscriptions/resourcegroups'
| extend dates=format_datetime(now(), "yyyy-MM-dd")
| join kind=leftouter (
    resourcecontainers
    | where type == 'microsoft.resources/subscriptions'
    | project SubscriptionName=name, subscriptionId)
    on subscriptionId
| project SubscriptionName, subscriptionId, resourceGroup, 
   financial_contact=tags.financial_contact, security_contact=tags.security_contact,
    environment=tags.environment,
    version=tags.version, dates, type, location, id_prefix=id
"""


query = QueryRequest(
            query= query_code 
)
query_response = resource_graph_client.resources(query)
query_response_str = str(query_response)
json_data = json.dumps(query_response_str)

json_data = json.loads(json_data)



output_file = "resource_groups_tags.txt"
with open(output_file, "w") as f:
    json.dump(json_data, f, indent=4)

响应示例:

{'additional_properties': {}, 'total_records': 530, 'count': 530, 'result_truncated': 'false', 'skip_token': None, 'data': [{'SubscriptionName': '...'}]}

问题原因

  1. 原代码未实现循环分页逻辑,仅发起一次请求,未利用skip_token获取后续数据
  2. 错误地将QueryResponse对象转成字符串再序列化,破坏了原有数据结构
  3. 未设置QueryRequestOptions指定每页最大返回条数(默认值可能限制了单页数量)

修正后的代码

以下代码实现了完整的分页逻辑,通过循环检查skip_token获取全量数据:

from azure.identity import DefaultAzureCredential
from azure.mgmt.resourcegraph import ResourceGraphClient
from azure.mgmt.resourcegraph.models import QueryRequest, QueryRequestOptions
import json

# 初始化凭据和客户端
credentials = DefaultAzureCredential()
resource_graph_client = ResourceGraphClient(credentials)

# 定义查询语句
query_code = """
resourcecontainers
| where type == 'microsoft.resources/subscriptions/resourcegroups'
| extend dates=format_datetime(now(), "yyyy-MM-dd")
| join kind=leftouter (
    resourcecontainers
    | where type == 'microsoft.resources/subscriptions'
    | project SubscriptionName=name, subscriptionId)
    on subscriptionId
| project SubscriptionName, subscriptionId, resourceGroup, 
   financial_contact=tags.financial_contact, security_contact=tags.security_contact,
    environment=tags.environment,
    version=tags.version, dates, type, location, id_prefix=id
"""

# 初始化结果列表和分页参数
all_results = []
skip_token = None

# 循环分页获取数据
while True:
    # 构造查询请求,设置每页最大返回1000条(Azure Resource Graph单页最大支持1000条)
    request_options = QueryRequestOptions(
        skip_token=skip_token,
        top=1000
    )
    query_request = QueryRequest(
        query=query_code,
        options=request_options
    )
    
    # 发起查询请求
    response = resource_graph_client.resources(query_request)
    
    # 将当前页数据加入结果列表
    all_results.extend(response.data)
    
    # 检查是否还有后续数据
    if not response.skip_token:
        break
    skip_token = response.skip_token

# 将结果写入JSON文件
output_file = "resource_groups_tags_full.json"
with open(output_file, "w", encoding="utf-8") as f:
    json.dump(all_results, f, indent=4, ensure_ascii=False)

print(f"全量数据已写入文件,共{len(all_results)}条记录")

关键说明

  • 分页逻辑:通过while循环持续检查response.skip_token,只要存在就继续发起请求,直到skip_token为None
  • 单页条数设置:通过QueryRequestOptions的top参数设置单页最大返回1000条(Azure Resource Graph的单页上限),减少请求次数
  • 数据处理:直接访问response.data获取结构化数据,避免原代码中字符串转义导致的数据损坏
  • 权限验证:确保使用的DefaultAzureCredential对应的账号拥有租户内所有订阅的Reader或更高权限,避免因权限不足导致部分资源组无法返回

内容的提问来源于stack exchange,提问作者Louey

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.23 22:08:21