리소스는 일상적인 사용, 다시 구성 및 재배치 과정을 통해 변경됩니다. 대부분의 변경은 의도적이지만 때로는 그렇지 않습니다. 마케팅 목록의 구성원을 관리할 수 있습니다.
- Azure Resource Manager 속성에서 변경이 탐지된 시기를 확인합니다.
- 속성 변경 세부 정보 보기
- 구독, 관리 그룹 또는 테넌트 전반에 걸쳐 대규모로 변경 내용 쿼리
이 문서에서는 다음에 대해 알아봅니다.
- 페이로드 JSON의 모양입니다.
- CLI, PowerShell 또는 Azure Portal을 사용하여 Resource Graph를 통해 리소스 변경 내용을 쿼리하는 방법입니다.
- 리소스 변경 내용을 쿼리하기 위한 쿼리 예 및 모범 사례입니다.
- 변경 분석은 변경 행위자 기능을 사용합니다.
-
changedBy
: 애플리케이션 ID 또는 승인된 사용자의 전자 메일 주소와 같은 리소스 변경을 시작한 사람입니다. -
clientType
: 변경 작업을 수행한 클라이언트입니다(예: Azure Portal). -
operation
: 호출된 작업입니다(예:Microsoft.Compute/virtualmachines/write
).operation
리소스 변경 데이터의 필드는 변경을 시작하는 데 사용되는 Azure 역할 기반 액세스 제어 권한을 나타냅니다.
-
필수 조건
- Azure PowerShell을 사용하여 Azure Resource Graph를 쿼리하려면 모듈을 추가합니다.
- Azure CLI를 사용하여 Azure Resource Graph를 쿼리하려면 확장을 추가합니다.
변경 이벤트 속성 이해
리소스를 만들거나 업데이트하거나 삭제하면 수정된 리소스를 확장하고 변경된 속성을 나타내는 새 변경 리소스(Microsoft.Resources/changes
)가 만들어집니다. 변경 기록은 5분 이내에 사용할 수 있어야 합니다. 일부 변경 세부 정보는 다른 변경 내용 앞에 표시할 수 있습니다. 다음 예 JSON 페이로드는 변경 리소스 속성을 보여 줍니다.
{
"targetResourceId": "/subscriptions/11111111-1111-1111-1111-111111111111/resourceGroups/myResourceGroup/providers/microsoft.compute/virtualmachines/myVM",
"targetResourceType": "microsoft.compute/virtualmachines",
"changeType": "Update",
"changeAttributes": {
"previousResourceSnapshotId": "11111111111111111111_22222222-3333-aaaa-bbbb-444444444444_5555555555_6666666666",
"newResourceSnapshotId": "33333333333333333333_44444444-5555-ffff-gggg-666666666666_7777777777_8888888888",
"correlationId": "11111111-1111-1111-1111-111111111111",
"changedByType": "User",
"changesCount": 2,
"clientType": "Azure Portal",
"changedBy": "john@contoso.com",
"operation": "microsoft.compute/virtualmachines/write",
"timestamp": "2024-06-12T13:26:17.347+00:00"
},
"changes": {
"properties.provisioningState": {
"newValue": "Succeeded",
"previousValue": "Updating",
"isTruncated": "true"
},
"tags.key1": {
"newValue": "NewTagValue",
"previousValue": "null",
}
}
}
변경 리소스 속성에 대한 전체 참조 가이드를 참조하세요.
operation
리소스 변경 데이터의 필드는 변경을 시작하는 데 사용되는 Azure 역할 기반 액세스 제어 권한을 나타냅니다. 이 필드는 항상 수행된 실제 작업을 설명하는 것이 아니라 사용된 권한(권한 부여 작업)을 설명합니다. 예를 들어 Microsoft.Compute/virtualmachines/write
작업에 PUT/providers/Microsoft.Compute/virtualmachines
대한 사용 권한에 해당합니다.
리소스에서 캡처된 변경 유형(예: 만들기, 삭제, 업데이트)을 이해하려면 필드 대신 변경 시작에 사용되는 Azure 역할 기반 액세스 제어 권한을 나타내는 필드 대신 operation
필드를 사용하는 changeType
것이 좋습니다.
클라이언트 유형이 알려진 clientType
경우 필드에 "Azure Portal"과 같은 클라이언트 이름이 표시됩니다. 클라이언트가 제공되었지만 알 수 없는 경우 필드에 클라이언트 애플리케이션 ID가 표시됩니다.
참고 항목
스냅샷은 현재 삭제된 리소스에 대해 지원되지 않습니다.
: Delete가 있는 changeType
레코드의 changesCount
경우 리소스 자체가 삭제되고 남은 속성이 없으므로 0으로 표시됩니다. 다음과 같은 changeType
레코드의 changesCount
경우 리소스를 만드는 동안 모든 리소스 속성이 수정되고 모든 속성 변경을 로깅하면 너무 많은 노이즈가 발생하므로 0으로 표시됩니다.
새 속성이 도입되면 변경 내용으로 표시되지 않습니다. 예를 들어 새 API 버전에서 새 속성을 도입할 때 이 문제가 발생할 수 있습니다. 마찬가지로 새 키가 값 없이 태그에 추가되면 이러한 변경 내용이 표시되지 않습니다.
쿼리 실행
resourcechanges
테이블의 테넌트 기반 Resource Graph 쿼리를 사용해 보세요. 쿼리는 가장 최근 Azure 리소스 변경 내용 중 처음 5개를 변경 시간, 변경 유형, 대상 리소스 ID, 대상 리소스 종류 및 각 변경 레코드의 변경 세부 정보와 함께 반환
# Login first with az login if not using Cloud Shell
# Run Azure Resource Graph query
az graph query -q 'resourcechanges | project properties.changeAttributes.timestamp, properties.changeType, properties.targetResourceId, properties.targetResourceType, properties.changes | limit 5'
이 쿼리를 업데이트하여 timestamp 속성에 대해 보다 사용자 친화적인 열 이름을 지정할 수 있습니다.
# Run Azure Resource Graph query with 'extend'
az graph query -q 'resourcechanges | extend changeTime=todatetime(properties.changeAttributes.timestamp) | project changeTime, properties.changeType, properties.targetResourceId, properties.targetResourceType, properties.changes | limit 5'
쿼리 결과를 가장 최근 변경 내용으로 제한하려면 쿼리를 사용자 정의 order by
속성인 changeTime
로 업데이트합니다.
# Run Azure Resource Graph query with 'order by'
az graph query -q 'resourcechanges | extend changeTime=todatetime(properties.changeAttributes.timestamp) | project changeTime, properties.changeType, properties.targetResourceId, properties.targetResourceType, properties.changes | order by changeTime desc | limit 5'
각각 또는 -ManagementGroup
매개 변수를 사용하여 -Subscription
또는 구독별로 쿼리할 수도 있습니다.
참고 항목
사용자에게 액세스 권한이 이미 있는 구독에서 쿼리가 결과를 반환하지 않는 경우 Search-AzGraph
PowerShell cmdlet은 기본 컨텍스트에서 구독으로 기본 설정됩니다.
Resource Graph Explorer는 일부 쿼리의 결과를 Azure 대시 보드에 고정할 수 있는 차트로 변환하는 깔끔한 인터페이스도 제공합니다.
쿼리 리소스 변경
Resource Graph를 사용하면 resourcechanges
, resourcecontainerchanges
또는 healthresourcechanges
테이블을 쿼리하여 변경 리소스 속성을 기준으로 필터링하거나 정렬할 수 있습니다. 다음 예에서는 resourcechanges
테이블을 쿼리하지만 resourcecontainerchanges
또는 healthresourcechanges
테이블에도 적용될 수 있습니다.
예제
리소스의 변경 내용을 쿼리하고 분석하기 전에 다음 모범 사례를 검토합니다.
- 특정 시간 창에서 변경 이벤트를 쿼리하고 변경 세부 정보 평가
- 이 쿼리는 인시던트 관리 중에 잠재적으로 관련된 변경 내용을 이해하는 데 가장 효과적입니다.
- 최신 CMDB(구성 관리 데이터베이스)를 유지합니다.
- 예약된 빈도에 따라 모든 리소스와 전체 속성 집합을 새로 고치는 대신 변경 내용만 수신하게 됩니다.
- 리소스가 준수 상태를 변경했을 때 변경되었을 수 있는 다른 속성을 이해합니다.
- 이러한 추가 속성을 평가하면 Azure Policy 정의를 통해 관리해야 할 수 있는 다른 속성에 대한 인사이트를 제공할 수 있습니다.
- 쿼리 명령의 순서는 중요합니다. 다음 예에서
order by
는limit
명령 앞에 와야 합니다.-
order by
명령은 변경 시간을 기준으로 쿼리 결과를 정렬합니다. - 그런 다음
limit
명령은 순서가 지정된 결과를 제한하여 가장 최근 결과 5개를 가져올 수 있도록 합니다.
-
-
알 수 없음은 무엇을 의미하나요?
- 인식할 수 없는 클라이언트에서 변경이 발생하면 알 수 없음이 표시됩니다. 클라이언트는 원래 변경 요청과 연결된 사용자 에이전트 및 클라이언트 애플리케이션 ID를 기반으로 인식됩니다.
-
시스템은 무엇을 의미하나요?
- 직접 사용자 작업과 상관 관계가 없는 백그라운드 변경이 발생한 경우 시스템은
changedBy
값으로 표시됩니다.
- 직접 사용자 작업과 상관 관계가 없는 백그라운드 변경이 발생한 경우 시스템은
지난 24시간 동안의 모든 변경 내용
resourcechanges
| extend changeTime = todatetime(properties.changeAttributes.timestamp), targetResourceId = tostring(properties.targetResourceId),
changeType = tostring(properties.changeType), correlationId = properties.changeAttributes.correlationId,
changedProperties = properties.changes, changeCount = properties.changeAttributes.changesCount
| where changeTime > ago(1d)
| order by changeTime desc
| project changeTime, targetResourceId, changeType, correlationId, changeCount, changedProperties
특정 리소스 그룹에서 삭제된 리소스
resourcechanges
| where resourceGroup == "myResourceGroup"
| extend changeTime = todatetime(properties.changeAttributes.timestamp), targetResourceId = tostring(properties.targetResourceId),
changeType = tostring(properties.changeType), correlationId = properties.changeAttributes.correlationId
| where changeType == "Delete"
| order by changeTime desc
| project changeTime, resourceGroup, targetResourceId, changeType, correlationId
특정 속성 값에 대한 변경 내용
resourcechanges
| extend provisioningStateChange = properties.changes["properties.provisioningState"], changeTime = todatetime(properties.changeAttributes.timestamp), targetResourceId = tostring(properties.targetResourceId), changeType = tostring(properties.changeType)
| where isnotempty(provisioningStateChange)and provisioningStateChange.newValue == "Succeeded"
| order by changeTime desc
| project changeTime, targetResourceId, changeType, provisioningStateChange.previousValue, provisioningStateChange.newValue
지난 7일 동안의 변경 내용: 사용자 및 클라이언트 및 주문 수별 변경
resourcechanges
| extend changeTime = todatetime(properties.changeAttributes.timestamp),
targetResourceId = tostring(properties.targetResourceId),
changeType = tostring(properties.changeType), changedBy = tostring(properties.changeAttributes.changedBy),
changedByType = properties.changeAttributes.changedByType,
clientType = tostring(properties.changeAttributes.clientType)
| where changeTime > ago(7d)
| project changeType, changedBy, changedByType, clientType
| summarize count() by changedBy, changeType, clientType
| order by count_ desc
가상 머신 크기 변경
resourcechanges
| extend vmSize = properties.changes["properties.hardwareProfile.vmSize"], changeTime = todatetime(properties.changeAttributes.timestamp), targetResourceId = tostring(properties.targetResourceId), changeType = tostring(properties.changeType)
| where isnotempty(vmSize)
| order by changeTime desc
| project changeTime, targetResourceId, changeType, properties.changes, previousSize = vmSize.previousValue, newSize = vmSize.newValue
변경 유형 및 구독 이름별 변경 횟수
resourcechanges
| extend changeType = tostring(properties.changeType), changeTime = todatetime(properties.changeAttributes.timestamp), targetResourceType=tostring(properties.targetResourceType)
| summarize count() by changeType, subscriptionId
| join (resourcecontainers | where type=='microsoft.resources/subscriptions' | project SubscriptionName=name, subscriptionId) on subscriptionId
| project-away subscriptionId, subscriptionId1
| order by count_ desc
특정 태그로 만들어진 리소스에 대한 최신 리소스 변경 내용
resourcechanges
|extend targetResourceId = tostring(properties.targetResourceId), changeType = tostring(properties.changeType), createTime = todatetime(properties.changeAttributes.timestamp)
| where createTime > ago(7d) and changeType == "Create" or changeType == "Update" or changeType == "Delete"
| project targetResourceId, changeType, createTime
| join ( resources | extend targetResourceId=id) on targetResourceId
| where tags ['Environment'] =~ 'prod'
| order by createTime desc
| project createTime, id, resourceGroup, type