监控资产更改

本页面介绍如何创建和管理项目的 Feed。

概览

如需接收有关资源和政策更改的实时通知,您可以创建并订阅 Feed。配置 Feed 时,您可以指定希望监控组织、文件夹、项目中或特定资源的受支持资源类型、IAM 政策、访问权限政策和组织政策的更改。此外,您可以向 Feed 添加条件,以便仅在资产发生某些类型的更改时接收通知。配置 Feed 后,只要指定资产发生更改,您将立即收到通知,通知通过 Pub/Sub发送,格式设置为 TemporalAsset。实时通知会连接到您现有的工作负载。通过此功能,您可以合并操作,例如创建 Cloud Functions 函数,以在检测到资源更改后逆转更改。

准备工作

  1. 为您的项目启用 Cloud Asset API

  2. (可选)如果您需要使用服务帐号访问 Cloud Asset API,且项目中还没有服务帐号,请创建一个新的服务帐号

  3. 向您的用户或服务帐号授予调用 API 以获取实时 Feed 的权限。每项操作都需要以下权限:

    权限 说明
    cloudasset.feeds.create 并且 cloudasset.assets.exportResource 创建 Feed
    cloudasset.feeds.update 并且 cloudasset.assets.exportResource 更新 Feed
    cloudasset.feeds.delete 删除 Feed
    cloudasset.feeds.get 获取 Feed
    cloudasset.feeds.list 列出 Feed

    Cloud Asset Owner (roles/cloudasset.owner) 角色授予与 Cloud Asset API 相关的所有权限,包括上表中列出的权限。如需详细了解角色和权限,请参阅了解角色配置权限

  4. 如果您还没有 Pub/Sub 主题,请创建 Pub/Sub 主题

  5. (可选)如果 Pub/Sub 主题所在的项目不是您从中调用 API 的已启用 Cloud Asset API 的使用方项目,请确保 service-API_ENABLED_PROJECT_NUMBER@gcp-sa-cloudasset.iam.gserviceaccount.com 服务帐号对该主题具有 pubsub.topics.publish 权限。

    如需自动创建此服务帐号并向其授予必要的权限,您可以调用 ExportAssetsCreateFeed

    如需手动创建此服务帐号,请执行以下操作:

      gcloud beta services identity create --service=cloudasset.googleapis.com --project=PROJECT_ID
      gcloud projects add-iam-policy-binding PROJECT_ID --member=serviceAccount:service-API_ENABLED_PROJECT_NUMBER@gcp-sa-cloudasset.iam.gserviceaccount.com --role=roles/cloudasset.serviceAgent
    

    如需手动向服务帐号授予发布权限,请执行以下操作:

      gcloud pubsub topics add-iam-policy-binding TOPIC_NAME --member=serviceAccount:service-API_ENABLED_PROJECT_NUMBER@gcp-sa-cloudasset.iam.gserviceaccount.com --role=roles/pubsub.publisher
    

设置您的环境

GCLOUD

  1. 如果您尚未安装 Google Cloud CLI,请在本地客户端上安装 Google Cloud CLI

  2. 如果您已安装 Google Cloud CLI,请将所有已安装的组件更新到最新版本。

  3. 为您的项目启用 Resource Manager API

API

  1. 要设置新的 Compute Engine 虚拟机实例,请转到“创建实例”页面,然后选择您项目中的服务帐号。

  2. 访问权限范围下方,选择允许所有 Cloud API 的全面访问权限

  3. 通过点击创建,启动您的实例。

  4. 转到虚拟机实例页面。

  5. 点击实例列表旁边的 SSH,以打开连接到实例的 Web SSH 客户端。

  6. 在网络 SSH 客户端上,通过调用以下命令,为您的服务帐号生成身份验证令牌:

    TOKEN=$(gcloud auth application-default print-access-token)
    

以下 API 调用假设您要创建和管理某个项目的 Feed。如需为组织或文件夹创建和管理 Feed,请将 /projects/PROJECT_NUMBER/ 替换为 /organizations/ORGANIZATION_NUMBER//folders/FOLDER_NUMBER/

创建 Feed

您可以为一个资产创建最多 200 个 Feed。此限制仅适用于直接跟踪该资产的 Feed,而不会计入其子资源的 Feed。例如,如果您的某个组织下有 10 个项目,每个项目最多可以有 200 个 Feed,则该组织最多可以有 200 个 Feed。

要创建 Feed,可以使用以下选项:

  • FEED_ID 是客户分配的唯一资产 Feed 标识符。 必填。
  • ASSET_NAME 是您要接收其更改通知的资产全名的列表。 至少需要 [ASSET_NAME, ASSET_TYPE] 中的一项。
  • ASSET_TYPE 是您要接收其更改通知的资产类型的列表。 至少需要 [ASSET_NAME, ASSET_TYPE] 中的一项。
  • CONTENT_TYPE 是您希望接收变更通知的资产内容类型。如果未指定,则通知将仅包含资产名称和资产类型。
  • TOPIC_NAME 是发布通知的 Pub/Sub 主题的名称。 必填。
  • CONDITION_TITLE 是要应用于 Feed 的条件的标题。
  • CONDITION_DESCRIPTION 是要应用于 Feed 的条件的说明。
  • CONDITION_EXPRESSION 是要应用于 Feed 的条件的表达式。

GCLOUD

使用 gcloud asset feeds create 命令为项目、文件夹和组织创建 Feed:

  • 项目:

    gcloud asset feeds create FEED_ID --project=PROJECT_ID --asset-names="ASSET_NAME"
    --content-type=CONTENT_TYPE --asset-types="ASSET_TYPE"
    --pubsub-topic="TOPIC_NAME" --condition-title="CONDITION_TITLE"
    --condition-description="CONDITION_DESCRIPTION"
    --condition-expression="CONDITION_EXPRESSION"
    

  • 文件夹:

    gcloud asset feeds create FEED_ID --folder=FOLDER_ID --asset-names="ASSET_NAME"
    --content-type=CONTENT_TYPE --asset-types="ASSET_TYPE"
    --pubsub-topic="TOPIC_NAME" --condition-title="CONDITION_TITLE"
    --condition-description="CONDITION_DESCRIPTION"
    --condition-expression="CONDITION_EXPRESSION"
    

  • 组织:

    gcloud asset feeds create FEED_ID --organization=ORGANIZATION_ID --asset-names="ASSET_NAME"
    --content-type=CONTENT_TYPE --asset-types="ASSET_TYPE"
    --pubsub-topic="TOPIC_NAME" --condition-title="CONDITION_TITLE"
    --condition-description="CONDITION_DESCRIPTION"
    --condition-expression="CONDITION_EXPRESSION"
    

API

使用 feeds.create() API 为项目、文件夹和组织创建 Feed:

  • 项目:
    curl -H "Authorization: Bearer $TOKEN" \
      -H "Content-Type: application/json" -X POST \
      -d '{"feedId": "FEED_ID",
           "feed": { "assetNames": ["ASSET_NAME"],
           "assetTypes": ["ASSET_TYPE"], "contentType": "CONTENT_TYPE",
           "feedOutputConfig": {"pubsubDestination": {"topic":"TOPIC_NAME"}},
           "condition": {"title": "CONDITION_TITLE",
           "description": "CONDITION_DESCRIPTION",
           "expression": "CONDITION_EXPRESSION"}}}' \
      https://cloudasset.googleapis.com/v1/projects/PROJECT_NUMBER/feeds
    
  • 文件夹:
    curl -H "Authorization: Bearer $TOKEN" \
      -H "Content-Type: application/json" -X POST \
      -d '{"feedId": "FEED_ID",
           "feed": { "assetNames": ["ASSET_NAME"],
           "assetTypes": ["ASSET_TYPE"], "contentType": "CONTENT_TYPE",
           "feedOutputConfig": {"pubsubDestination": {"topic":"TOPIC_NAME"}},
           "condition": {"title": "CONDITION_TITLE",
           "description": "CONDITION_DESCRIPTION",
           "expression": "CONDITION_EXPRESSION"}}}' \
      https://cloudasset.googleapis.com/v1/folders/FOLDER_NUMBER/feeds
    
  • 组织:
    curl -H "Authorization: Bearer $TOKEN" \
      -H "Content-Type: application/json" -X POST \
      -d '{"feedId": "FEED_ID",
           "feed": { "assetNames": ["ASSET_NAME"],
           "assetTypes": ["ASSET_TYPE"], "contentType": "CONTENT_TYPE",
           "feedOutputConfig": {"pubsubDestination": {"topic":"TOPIC_NAME"}},
           "condition": {"title": "CONDITION_TITLE",
           "description": "CONDITION_DESCRIPTION",
           "expression": "CONDITION_EXPRESSION"}}}' \
      https://cloudasset.googleapis.com/v1/organizations/ORGANIZATION_NUMBER/feeds
    

Cloud Asset Inventory 会在至少匹配 Feed 的一个 ASSET 参数并且匹配条件表达式(如果已指定)的资产上设置通知。例如,指定 ASSET_TYPEASSET_NAMECONDITION_EXPRESSION 将在匹配 ASSET_TYPEASSET_NAME,并且满足 CONDITION_EXPRESSION 的资产上设置通知。

以下命令会在 quick_start_bucket Cloud Storage 存储分区或任何 BigQuery 表中的内容发生更改时,从 quick_start_topic Pub/Sub 主题创建通知:

GCLOUD

 gcloud asset feeds create quick_start_feed --project=PROJECT_ID --asset-names="//storage.googleapis.com/quick_start_bucket"
  --content-type=resource --asset-types="bigquery.googleapis.com/Table"
  --pubsub-topic="projects/PROJECT_ID/topics/quick_start_topic"
 

API

 curl -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" -X POST \
  -d '{"feedId": "quick_start_feed",
       "feed": { "assetNames": ["storage.googleapis.com/quick_start_bucket"],
       "assetTypes": ["bigquery.googleapis.com/Table"],
       "contentType": "RESOURCE",
       "feedOutputConfig": {"pubsubDestination": {"topic":"projects/PROJECT_ID/topics/quick_start_topic"}}}}' \
        https://cloudasset.googleapis.com/v1/projects/PROJECT_NUMBER/feeds
 

ASSET_TYPE 字段也支持正则表达式。当其资产类型以“compute.googleapis.com”开头的资源中的内容更改时,以下命令会从 quick_start_topic Pub/Sub 主题创建通知。如需查看所有受支持的正则表达式语法,请参阅 RE2

GCLOUD

 gcloud asset feeds create quick_start_feed --project=PROJECT_ID
  --content-type=resource --asset-types="compute.googleapis.com.*"
  --pubsub-topic="projects/PROJECT_ID/topics/quick_start_topic"
 

API

 curl -H "Authorization: Bearer $TOKEN" 
-H "Content-Type: application/json" -X POST
-d '{"feedId": "quick_start_feed", "feed": { "assetTypes": ["compute.googleapis.com.*"], "contentType": "RESOURCE", "feedOutputConfig": {"pubsubDestination": {"topic":"projects/PROJECT_ID/topics/quick_start_topic"}}}}'
https://cloudasset.googleapis.com/v1/projects/PROJECT_NUMBER/feeds

要获取您创建的 Feed,请使用以下命令:

GCLOUD

 gcloud asset feeds describe FEED_ID --project=PROJECT_ID
 

API

 curl -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  https://cloudasset.googleapis.com/v1/projects/PROJECT_NUMBER/feeds/FEED_ID
 

Feed 按以下格式返回,其中 FULL_NAME_FEED 是 Feed 标识符及其资源父级:

{
  "name": "FULL_NAME_FEED",
  "assetTypes": ["ASSET_TYPES"],
  "assetNames": ["ASSET_NAMES"],
  "contentType": "CONTENT_TYPES",
  "feedOutputConfig": {
    "pubsubDestination": {
      "topic": "TOPIC_NAME"
    }
  },
  "condition": {
    "title": "CONDITION_TITLE",
    "description": "CONDITION_DESCRIPTION",
    "expression": "CONDITION_EXPRESSION"
  }
}

接收更新

创建 Feed 后,订阅您在 Feed 中指定的 Pub/Sub 主题的更新。新 Feed 最长可能需要 10 分钟才能开始发送通知。每当匹配 assetNamesassetTypes 并且满足 condition 的资产发生更改,通知就会发出。

发布到 Pub/Sub 主题的消息将采用 TemporalAsset 格式。以下是 RESOURCE 内容类型的示例消息。

{
  "asset": {
    "ancestors": [
      "projects/[PROJECT_NUMBER]",
      "folders/[FOLDER_NUMBER]",
      "organizations/[ORGANIZATION_NUMBER]"
    ],
    "assetType": "[ASSET_TYPE]",
    "name": "[ASSET_NAME]",
    "resource": {
      "data": {
        ...detailed resource metadata...
      },
      "discoveryDocumentUri": "[DISCOVERY_URI]",
      "discoveryName": "[DISCOVERY_NAME]",
      "location": "[LOCATION]",
      "parent": "[PARENT_ASSET_NAME]",
      "version": "[VERSION]"
    },
    "updateTime": "[UPDATE_TIME]"
  },
  "priorAsset": {
    ...prior asset information...
  },
  "priorAssetState": "[PRIOR_ASSET_STATE]",
  "window": {
    "startTime": "[UPDATE_TIME]"
  }
}

如需详细了解 Pub/Sub 或如何设置订阅者,请参阅 Pub/Sub 指南

管理 Feed

获取 Feed

要获取特定 Feed,请使用以下命令:

GCLOUD

gcloud asset feeds describe FEED_ID --project=PROJECT_ID

API

 curl -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" -X GET \
  https://cloudasset.googleapis.com/v1/projects/PROJECT_NUMBER/feeds/FEED_ID
 

列出 Feed

如需列出项目、文件夹或组织的所有 Feed,请使用以下命令:

GCLOUD

gcloud asset feeds list --project=PROJECT_ID

API

 curl -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" -X GET \
  https://cloudasset.googleapis.com/v1/projects/PROJECT_NUMBER/feeds
 

更新 Feed

要更新 Feed 的特性,您需要在 update_mask 中指定特性路径以及该特性的值。以下命令可更新项目的 Feed 的 assetNamestopic 值。

GCLOUD

gcloud asset feeds update FEED_ID --project=PROJECT_ID --add-asset-names=ASSET_NAME
   --pubsub-topic="TOPIC"

API

 curl -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" -X PATCH \
  -d '{"feed": {"assetNames": [ASSET_NAME], "feedOutputConfig": {"pubsubDestination": {"topic":TOPIC}}},
       "update_mask": {"paths": ["asset_names", "feed_output_config.pubsub_destination.topic"]}}' \
  https://cloudasset.googleapis.com/v1/projects/PROJECT_NUMBER/feeds/FEED_ID
 

删除 Feed

如果您不想再收到资产更改通知,请使用以下命令删除项目的 Feed。

GCLOUD

gcloud asset feeds delete FEED_ID --project=PROJECT_ID

API

 curl -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" -X DELETE \
  https://cloudasset.googleapis.com/v1/projects/PROJECT_NUMBER/feeds/FEED_ID
 

已知限制

  • 任何 Feed 创建、更新或删除操作最长可能需要 10 分钟才能生效。

  • 创建 Feed 的使用方项目必须比 Feed 存在时间更长,因为用于发布到目标 Pub/Sub 主题的服务帐号位于使用方项目中。如果使用方项目已删除,则 Cloud Asset Inventory 无法发布到目标。该 Feed 将不再起作用,而且会在项目删除后尽快删除。

问题排查

本部分介绍如何排查常见问题。

创建或更新 Feed 失败

如果创建或更新 Feed 失败,则可能是由权限问题导致的。每个 Feed 创建或更新请求都包含三个部分:用于调用 API 的使用方项目、要监控的目标父级以及用于接收通知的目标 Pub/Sub 主题。

要创建或更新 Feed,您需要具备以下权限:

  • 调用者或服务帐号必须在目标父级(可以是项目、文件夹或组织)中拥有资源权限
  • 已启用 Cloud Asset API 的使用方项目中的资产服务帐号 (service-PROJECT_NUMBER@gcp-sa-cloudasset.iam.gserviceaccount.com) 必须具有目标 Pub/Sub 主题的 pubsub.topics.publish 权限。

包含 does not have permission 的错误消息可能表示用户或服务帐号没有资源权限。详细了解所需权限

包含 Fail to use [TOPIC_NAME] as feed output destination 的错误消息可能表示该消息在发布到 Feed 输出目标中指定的主题时出现问题。要解决该问题,请执行以下操作:

  • 如果您使用的是 Google Cloud CLI,请确保您使用的是正确的项目:
    gcloud config list project
    
  • 确保您已指定正确的主题名称
  • 确保服务帐号 (service-[PROJECT_NUMBER]@gcp-sa-cloudasset.iam.gserviceaccount.com) 对主题具有 pubsub.topics.publish 权限,其中 [PROJECT_NUMBER] 是您要从其中创建 Feed 并启用了 Cloud Asset Inventory 的项目的项目编号。

接收资源更新或 IAM 政策更新失败

如果您没有收到资源或 IAM 政策更新的通知,验证以下配置详情有助于解决此问题:

  • 确保资产的元数据已更改。只有当受支持的资源类型的元数据更改后,实时 Feed 才会发送更新;将新文件上传到 Cloud Storage 存储分区这类操作不会触发元数据更改。
  • 请确保您的资产符合 Feed 中指定的条件之一,即资产名称和资产类型。
  • 检查日志以了解向主题发布更新时是否出现错误。

使用 Cloud Logging

本部分介绍如何设置和查看 Cloud Asset Inventory 实时 Feed 的日志记录。

当实时 Feed 无法通过 Pub/Sub 发送资源或 IAM 政策更新时,Cloud Asset Inventory 会通过 Logging 记录错误状态和消息。Logging 默认启用。了解 Google Cloud 的运维套件价格

查看 Google Cloud 的运维套件日志

如需查看日志,请转到日志浏览器

实时 Feed 日志记录按 Pub/Sub 主题编入索引。如需查看所有日志,请从第一个下拉菜单中选择 Cloud Pub/Sub 主题 > 所有主题 ID。如需查看 Feed 中指定的主题的日志,请从列表中选择一个主题 ID。

日志字段强制采用 UTF-8 编码。非 UTF-8 字符将被替换为问号。

记录的信息

实时 Feed 日志条目包含以下类型的信息:

  • 大多数 Google Cloud 日志中显示的常规信息,例如严重性、项目 ID、项目编号或时间戳。
  • jsonPayload 中的实时 Feed 日志字段,其中包含发布资源或 IAM 政策更新时的资产名称、Feed 输出配置、错误状态。

下表显示了每个字段包含的信息种类。

字段 类型和说明
name

string

Feed 的全名。格式为以下格式之一:
  • projects/{project_number}/feeds/{feed_id}
  • folders/{folder_number}/feeds/{feed_id}
  • organizations/{organization_number}/feeds/{client-assigned_feed_identifier}
asset_name

string

接收更新的资产的全名。例如://compute.googleapis.com/projects/my_project_123/zones/zone1/instances/instance1

如需了解详情,请参阅资源名称

feed_output_config

FeedOutputConfig

Feed 输出配置,用于定义资产更新发布到的位置。

condition

Expr

Feed 条件,用于确定是否应发布资源更新。

error_status

Status

Feed 发布素材资源更新失败的状态。