配置 DICOM Pub/Sub 通知

本页面介绍了如何使用 Pub/Sub 获取有关 DICOM 存储区中临床事件的通知。当新的 DICOM 实例存储在 DICOM 存储区中或从 Cloud Storage 导入时,您可以接收 Pub/Sub 通知。

您可以使用 Pub/Sub 通知来实现多种用途,例如触发下游处理或分析新数据。例如,当有新数据可用于训练时,机器学习模型可以接收通知,并生成数据洞见来改善患者护理。

下图显示了 Pub/Sub 通知的生成和发布方式。

DICOM Pub/Sub 通知。

图 1. 接收有关 DICOM 存储区中临床事件的 Pub/Sub 通知。

图 1 显示了以下步骤:

  1. 调用方发出存储或导入 DICOM 实例的请求。
  2. DICOM 存储区接收请求,创建 Pub/Sub 消息,然后将其发送到 DICOM 存储区上配置的 Pub/Sub 主题。
  3. Pub/Sub 将消息转发给附加到主题的订阅。
  4. 订阅者会收到来自订阅的消息。每个订阅可以有一个或多个订阅者(提高并行性)。

准备工作

  1. 创建一个主题
  2. 创建拉取订阅

添加 Pub/Sub 发布商权限

如需将消息从 Cloud Healthcare API 发布到 Pub/Sub,您必须将 pubsub.publisher 角色添加到项目的 Cloud Healthcare Service Agent 服务账号。如需了解详情,请参阅 DICOM、FHIR 和 HL7v2 存储区 Pub/Sub 权限

通知格式和内容

Pub/Sub 通知包含一个 Message 对象,其中包含有关临床事件的信息。Message 对象类似于以下内容:

{
  "message": {
    "attributes": {
      "action": "ACTION",
      "lastUpdatedTime": "RFC_1123_FORMAT_DATETIME",
      "storeName": "projects/PROJECT_ID/locations/LOCATION/datasets/DATASET_ID/dicomStores/DICOM_STORE_ID",
      "studyInstanceUID": "STUDY_UID",
      "seriesInstanceUID": "SERIES_UID",
      "sopInstanceUID": "INSTANCE_UID",
      "versionId": "VERSION_ID",
      "modality": "MODALITY",
      "storageClass": "STORAGE_CLASS",
      "previousStorageClass": "PREVIOUS_STORAGE_CLASS"
    },
    "data": "BASE_64_ENCODED_DATA",
    "messageId": "MESSAGE_ID",
    "publishTime": "YYYY-MM-DDTHH:MM:SS+ZZ:ZZ"
  }
}

如需详细了解每条 Pub/Sub 消息中包含的字段,请参阅 ReceivedMessagePubsubMessage

下表介绍了 attributes 对象中的每个字段:

属性 说明 示例
action DICOM 资源上发生的操作。可能的值包括:
  • StoreInstances
  • ImportDicomData
  • SetBlobSettings
  • DeleteInstances
StoreInstances
lastUpdatedTime DICOM 资源最近一次修改的时间戳。时间戳采用 RFC 1123 格式。 Mon, 01 Jan 2020 00:00:00 UTC
storeName 发生操作的 DICOM 存储区的完整资源名称。 projects/my-project/locations/us/datasets/my-dataset/dicomStores/my-dicom-store
studyInstanceUID DICOM 研究实例唯一标识符 (UID)。 1.2.3.4.5.6
seriesInstanceUID DICOM 系列实例唯一标识符 (UID)。 1.2.3.4.5.6
sopInstanceUID DICOM SOP 实例唯一标识符 (UID)。 1.2.3.4.5.6
versionId 发生相应操作的 DICOM 资源的最新版本的 ID。 MTY4MzA2MDQzOTI5NjIxMDAwMA
modality 相应 DICOM 资源的模态标记。可能的值包括但不限于:
  • CT
  • MR
  • MG
CT
storageClass DICOM 资源的存储类别。可能的值包括:
  • STANDARD
  • NEARLINE
  • COLDLINE
  • ARCHIVE
STANDARD
previousStorageClass 相应 DICOM 资源之前的存储类别。可能的值包括:
  • STANDARD
  • NEARLINE
  • COLDLINE
  • ARCHIVE
NEARLINE

下表介绍了 message 对象中的其余字段:

字段 说明
data 以下标识符的 base64 编码字符串:projects/PROJECT_ID/locations/LOCATION/datasets/DATASET_ID/dicomStores/DICOM_STORE_ID/dicomWeb/studies/STUDY_UID/series/SERIES_UID/instances/INSTANCE_UID
messageId Pub/Sub 消息的标识符。
publishTime Pub/Sub 服务器发布消息的时间。

配置和查看通知

本部分介绍了如何对 DICOM 存储区启用 Pub/Sub 通知、存储或导入 DICOM 实例以发布通知,以及查看通知。

配置 DICOM 存储区

以下示例展示了如何在 DICOM 存储区中启用 Pub/Sub 通知,以便在存储或从 Cloud Storage 导入新的 DICOM 实例时收到通知。

REST

使用 projects.locations.datasets.dicomStores.patch 方法。

NotificationConfig.sendForBulkImport 的值为 true,因此在从 Cloud Storage 导入数据时会发送通知。

在使用任何请求数据之前,请先进行以下替换:

  • PROJECT_ID:您的 Google Cloud 项目的 ID
  • LOCATION:数据集位置
  • DATASET_ID:DICOM 存储区的父数据集
  • DICOM_STORE_ID:DICOM 存储区 ID
  • PUBSUB_TOPIC:当数据存储区中发生事件时,消息发布到的 Pub/Sub 主题

请求 JSON 正文:

{
  "notificationConfig": {
    "pubsubTopic": "projects/PROJECT_ID/topics/PUBSUB_TOPIC",
    "sendForBulkImport": "true"
  }
}

如需发送请求,请选择以下方式之一:

curl

将请求正文保存在名为 request.json 的文件中。在终端中运行以下命令,在当前目录中创建或覆盖此文件:

cat > request.json << 'EOF'
{
  "notificationConfig": {
    "pubsubTopic": "projects/PROJECT_ID/topics/PUBSUB_TOPIC",
    "sendForBulkImport": "true"
  }
}
EOF

然后,执行以下命令以发送 REST 请求:

curl -X PATCH \
-H "Authorization: Bearer $(gcloud auth print-access-token)" \
-H "Content-Type: application/json; charset=utf-8" \
-d @request.json \
"https://healthcare.googleapis.com/v1/projects/PROJECT_ID/locations/LOCATION/datasets/DATASET_ID/dicomStores/DICOM_STORE_ID?updateMask=notificationConfig"

PowerShell

将请求正文保存在名为 request.json 的文件中。在终端中运行以下命令,在当前目录中创建或覆盖此文件:

@'
{
  "notificationConfig": {
    "pubsubTopic": "projects/PROJECT_ID/topics/PUBSUB_TOPIC",
    "sendForBulkImport": "true"
  }
}
'@  | Out-File -FilePath request.json -Encoding utf8

然后,执行以下命令以发送 REST 请求:

$cred = gcloud auth print-access-token
$headers = @{ "Authorization" = "Bearer $cred" }

Invoke-WebRequest `
-Method PATCH `
-Headers $headers `
-ContentType: "application/json; charset=utf-8" `
-InFile request.json `
-Uri "https://healthcare.googleapis.com/v1/projects/PROJECT_ID/locations/LOCATION/datasets/DATASET_ID/dicomStores/DICOM_STORE_ID?updateMask=notificationConfig" | Select-Object -Expand Content

API Explorer

复制请求正文并打开方法参考页面。APIs Explorer 面板会在页面右侧打开。您可以与此工具进行交互以发送请求。 将请求正文粘贴到此工具中,填写任何其他必填字段,然后点击执行

您应该会收到类似如下所示的响应。

如果您在 DicomStore 资源中配置了任何字段,它们也会出现在响应中。

gcloud

运行 gcloud healthcare dicom-stores update 命令。

在使用下面的命令数据之前,请先进行以下替换:

  • PROJECT_ID:您的 Google Cloud 项目的 ID
  • LOCATION:数据集位置
  • DATASET_ID:DICOM 存储区的父数据集
  • DICOM_STORE_ID:DICOM 存储区 ID
  • PUBSUB_TOPIC:当数据存储区中发生事件时,消息发布到的 Pub/Sub 主题

执行以下命令:

Linux、macOS 或 Cloud Shell

gcloud healthcare dicom-stores update DICOM_STORE_ID \
  --dataset=DATASET_ID \
  --location=LOCATION \
  --pubsub-topic=projects/PROJECT_ID/topics/PUBSUB_TOPIC \
  --send-for-bulk-import

Windows (PowerShell)

gcloud healthcare dicom-stores update DICOM_STORE_ID `
  --dataset=DATASET_ID `
  --location=LOCATION `
  --pubsub-topic=projects/PROJECT_ID/topics/PUBSUB_TOPIC `
  --send-for-bulk-import

Windows (cmd.exe)

gcloud healthcare dicom-stores update DICOM_STORE_ID ^
  --dataset=DATASET_ID ^
  --location=LOCATION ^
  --pubsub-topic=projects/PROJECT_ID/topics/PUBSUB_TOPIC ^
  --send-for-bulk-import

您应该会收到类似如下所示的响应:

响应

Updated dicomStore [DICOM_STORE_ID].
...
name: projects/PROJECT_ID/locations/LOCATION/datasets/DATASET_ID/dicomStores/DICOM_STORE_ID
notificationConfig:
  pubsubTopic: projects/PROJECT_ID/topics/PUBSUB_TOPIC
  sendForBulkImport: true

存储或导入 DICOM 实例,并查看 Pub/Sub 通知

如需存储或导入 DICOM 实例并拉取生成的 Pub/Sub 消息,请完成以下步骤:

  1. 存储导入 DICOM 实例。该请求会导致 Cloud Healthcare API 向配置的 Pub/Sub 主题发布消息。

  2. 撤回消息。如果您在单个请求中导入多个 DICOM 实例,系统会为每个 DICOM 实例生成一条消息。

    如需查看拉取 Pub/Sub 消息所需的 Identity and Access Management 权限,请参阅 Pub/Sub 访问权限控制

    REST

    使用 projects.subscriptions.pull 方法。 以下示例使用 ?maxMessages=10 查询参数来指定请求中要返回的最大消息数。根据您的用例调整此值。

    在使用任何请求数据之前,请先进行以下替换:

    • PROJECT_ID:您的 Google Cloud 项目的 ID
    • PUBSUB_SUBSCRIPTION_ID:附加到 DICOM 存储区上配置的 Pub/Sub 主题的订阅的 ID

    如需发送请求,请选择以下方式之一:

    curl

    执行以下命令:

    curl -X POST \
    -H "Authorization: Bearer $(gcloud auth print-access-token)" \
    -H "Content-Type: application/json; charset=utf-8" \
    -d "" \
    "https://pubsub.googleapis.com/v1/projects/PROJECT_ID/subscriptions/PUBSUB_SUBSCRIPTION_ID:pull?maxMessages=10"

    PowerShell

    执行以下命令:

    $cred = gcloud auth print-access-token
    $headers = @{ "Authorization" = "Bearer $cred" }

    Invoke-WebRequest `
    -Method POST `
    -Headers $headers `
    -Uri "https://pubsub.googleapis.com/v1/projects/PROJECT_ID/subscriptions/PUBSUB_SUBSCRIPTION_ID:pull?maxMessages=10" | Select-Object -Expand Content

    API Explorer

    打开方法参考页面。APIs Explorer 面板会在页面右侧打开。您可以与此工具进行交互以发送请求。 填写所有必填字段,然后点击执行

    您应该收到类似以下内容的 JSON 响应:

    gcloud

    运行 gcloud pubsub subscriptions pull 命令。

    此示例使用了以下 Google Cloud CLI 标志:

    • --limit=10:最多返回 10 条消息。根据您的用例调整此值。
    • --format=json:以 JSON 格式呈现输出。
    • --auto-ack:自动确认拉取的每条消息。

    在使用下面的命令数据之前,请先进行以下替换:

    • PROJECT_ID:您的 Google Cloud 项目的 ID
    • PUBSUB_SUBSCRIPTION_ID:附加到 DICOM 存储区上配置的 Pub/Sub 主题的订阅的 ID

    执行以下命令:

    Linux、macOS 或 Cloud Shell

    gcloud pubsub subscriptions pull \
        projects/PROJECT_ID/subscriptions/PUBSUB_SUBSCRIPTION_ID \
        --limit=10 \
        --auto-ack \
        --format=json

    Windows (PowerShell)

    gcloud pubsub subscriptions pull `
        projects/PROJECT_ID/subscriptions/PUBSUB_SUBSCRIPTION_ID `
        --limit=10 `
        --auto-ack `
        --format=json

    Windows (cmd.exe)

    gcloud pubsub subscriptions pull ^
        projects/PROJECT_ID/subscriptions/PUBSUB_SUBSCRIPTION_ID ^
        --limit=10 ^
        --auto-ack ^
        --format=json

    您应该会收到类似如下所示的响应:

    [
      {
        "ackId": "RFAGFixdRkhRNxkIaFEOT14jPzUgKEUaAggUBXx9cEFLdVhUcGhRDRlyfWB9bQ5GAgpGWixfURsHaE5tdR",
        "ackStatus": "SUCCESS",
        "message": {
          "attributes": {
            "action": "ImportDicomData",
            "lastUpdatedTime": "YYYY-MM-DDTHH:MM:SS+ZZ:ZZ",
            "storeName": "projects/PROJECT_ID/locations/LOCATION/datasets/DATASET_ID/dicomStores/DICOM_STORE_ID",
            "studyInstanceUID": "1.3.6.1.4.1.1129.5.111396399361969898205364400549799252857604",
            "seriesInstanceUID": "1.3.6.1.4.1.1129.5.111396399361969898205364400549799252857605",
            "sopInstanceUID": "1.3.6.1.4.1.1129.5.111396399361969898205364400549799252857606",
            "versionId": "MTY4MzA2MDQzOTI5NjIxMDAwMA",
            "modality": "CT",
            "storageClass": "STANDARD",
          },
          "data": "cHJvamVjdHMvbXlwcm9qZWN0L2xvY2F0aW9ucy91cy1jZW50cmFsMS9kYXRhc2V0cy9teS1kYXRhc2V0L2RpY29tU3RvcmVzL215LWRpY29tLXN0b3JlL2RpY29tV2ViL3N0dWRpZXMvMS4zLjYuMS40LjEuMTExMjkuNS41LjExMTM5NjM5OTM2MTk2OTg5ODIwNTM2NDQwMDU0OTc5OTI1Mjg1NzYwNC9zZXJpZXMvMS4zLjYuMS40LjEuMTExMjkuNS41LjE5NTYyODIxMzY5NDMwMDQ5ODk0Njc2MDc2NzQ4MTI5MTI2MzUxMTcyNC9pbnN0YW5jZXMvMS4zLjYuMS40LjEuMTExMjkuNS41LjE1Mzc1MTAwOTgzNTEwNzYxNDY2NjgzNDU2MzI5NDY4NDMzOTc0NjQ4MA==",
          "messageId": "7586159156345265",
          "publishTime": "YYYY-MM-DDTHH:MM:SS+ZZ:ZZ"
        }
      }
    ]
    

Cloud Healthcare API 和 Pub/Sub 消息存储政策

为确保 Cloud Healthcare API 数据与 Pub/Sub 消息中的关联数据位于同一区域,您必须设置 Pub/Sub 消息存储政策

您必须为数据存储区中配置的 Pub/Sub 主题明确设置消息存储政策,才能确保数据保留在同一区域中。例如,如果 Cloud Healthcare API 数据集和 FHIR 存储区位于 us-central1,则消息存储政策必须仅允许 us-central1 区域。

如需配置消息存储政策,请参阅配置消息存储政策

排查遗漏的 Pub/Sub 消息问题

如果无法将通知发布到 Pub/Sub,则 Cloud Logging 会记录错误。如需了解详情,请参阅在 Cloud Logging 中查看错误日志

如果错误生成率超过限制,则超出此限制的错误不会提交到 Cloud Logging。

后续步骤