记录代理

如需在代理部署后使用 Cloud Logging,请使用以下方法之一:

  • stdout / stderr:默认情况下(无需任何额外设置),写入 stdout 和 stderr 的日志将分别路由到日志 ID reasoning_engine_stdoutreasoning_engine_stderr。限制是它们必须是文本。
  • Python 日志记录:内置的 Python 日志记录器可以与 Cloud Logging 集成。与写入 stdout 或 stderr 相比,此方法支持结构化日志,并且只需进行最少的设置。
  • Cloud Logging 客户端:用户可以写入结构化日志,并完全控制记录器(例如,设置 logName 和资源类型)。

为代理写入日志

为代理写入日志时,请确定以下内容:

  • 严重程度:例如信息、警告、错误
  • 载荷:日志的内容(例如文本或 JSON)
  • 其他字段:用于在日志之间进行关联(例如跟踪记录/span、标记、标签)

例如,在开发代理时,记录每个查询的输入内容:

stdout 或 stderr

from typing import Dict

class MyAgent:

    def set_up(self):
        # No set up required. The logs from stdout and stderr are routed to
        # `reasoning_engine_stdout` and `reasoning_engine_stderr` respectively.
        pass

    def query(self, input: Dict):
        import sys

        print(
            f"input: {input}",
            file=sys.stdout,  # or sys.stderr
        )

Python 日志记录

from typing import Dict

class MyAgent:

    def set_up(self):
        import os
        import google.cloud.logging

        self.logging_client = google.cloud.logging.Client(project="PROJECT_ID")
        self.logging_client.setup_logging(
            name="LOG_ID",  # the ID of the logName in Cloud Logging.
            resource=google.cloud.logging.Resource(
                type="aiplatform.googleapis.com/ReasoningEngine",
                labels={
                    "location": "LOCATION",
                    "resource_container": "PROJECT_ID",
                    "reasoning_engine_id": os.environ.get("GOOGLE_CLOUD_AGENT_ENGINE_ID", ""),
                },
            ),
        )

    def query(self, input: Dict):
        import logging
        import json

        logging_extras = {
            "labels": {"foo": "bar"},
            "trace": "TRACE_ID",
        }

        logging.info( # or .warning(), .error()
            json.dumps(input),
            extra=logging_extras,
        )

Cloud Logging 客户端

from typing import Dict

class MyAgent:

    def set_up(self):
        import os
        import google.cloud.logging

        self.logging_client = google.cloud.logging.Client(project="PROJECT_ID")
        self.logger = self.logging_client.logger(
            name="LOG_ID",  # the ID of the logName in Cloud Logging.
            resource=google.cloud.logging.Resource(
                type="aiplatform.googleapis.com/ReasoningEngine",
                labels={
                    "location": "LOCATION",
                    "resource_container": "PROJECT_ID",
                    "reasoning_engine_id": os.environ.get("GOOGLE_CLOUD_AGENT_ENGINE_ID", ""),
                },
            ),
        )

    def query(self, input: Dict):
        logging_extras = {
            "labels": {"foo": "bar"},
            "trace": "TRACE_ID",
        }

        self.logger.log_struct(
            input,
            severity="INFO",  # or "DEBUG", "WARNING", "ERROR", "CRITICAL"
            **logging_extras,
        )

当代理被部署查询时,它会生成日志条目。例如,以下代码

remote_agent = agent_engines.create(
    MyAgent(),
    requirements=["cloudpickle==3", "google-cloud-logging"],
)

remote_agent.query(input={"hello": "world"})

将生成如下所示的日志条目:

stdout 或 stderr

{
  "insertId": "67a3bb3b000cc2df444361ab",
  "textPayload": "input: {'hello': 'world'}",
  "resource": {
    "type": "aiplatform.googleapis.com/ReasoningEngine",
    "labels": {
      "location": "LOCATION",
      "resource_container": "PROJECT_ID",
      "reasoning_engine_id": "RESOURCE_ID"
    }
  },
  "timestamp": "2025-02-05T19:25:47.836319Z",
  "logName": "projects/PROJECT_ID/logs/aiplatform.googleapis.com%2Freasoning_engine_stdout",  # or `*_stderr`
  "receiveTimestamp": "2025-02-05T19:25:47.842550772Z"
}

Python 日志记录

{
  "insertId": "1ek9a2jfqh777z",
  "jsonPayload": {"hello": "world"},
  "resource": {
    "type": "aiplatform.googleapis.com/ReasoningEngine",
    "labels": {
      "location": "LOCATION",
      "resource_container": "PROJECT_ID",
      "reasoning_engine_id": "RESOURCE_ID",
    }
  },
  "timestamp": "2025-02-05T20:30:19.348067Z",
  "severity": "INFO",
  "labels": {
    "foo": "bar",
    "python_logger": "root",
  },
  "logName": "projects/PROJECT_ID/logs/LOG_ID",
  "trace": "TRACE_ID",
  "receiveTimestamp": "2025-01-30T21:38:50.776813191Z"
}

Cloud Logging 客户端

{
  "insertId": "1ek9a2jfqh777z",
  "jsonPayload": {"hello": "world"},
  "resource": {
    "type": "aiplatform.googleapis.com/ReasoningEngine",
    "labels": {
      "location": "LOCATION",
      "resource_container": "PROJECT_ID",
      "reasoning_engine_id": "RESOURCE_ID",
    }
  },
  "timestamp": "2025-01-30T21:38:50.776813191Z",
  "severity": "INFO",
  "labels": {"foo": "bar"},
  "logName": "projects/PROJECT_ID/logs/LOG_ID",
  "trace": "TRACE_ID",
  "receiveTimestamp": "2025-01-30T21:38:50.776813191Z"
}

查看代理的日志

您可以使用 Logs Explorer 查看日志条目:

  1. 如需获得在Logs Explorer中查看日志的权限,请让您的管理员为您授予项目的Logs Viewer角色 (roles/logging.viewer)。

  2. 在 Google Cloud 控制台中前往 Logs Explorer

    转到日志浏览器

  3. 选择页面顶部的 Google Cloud 项目(对应于 PROJECT_ID)。

  4. 资源类型中,选择 Vertex AI Reasoning Engine

构建查询

您可以使用 Logs Explorer 逐步构建查询。查询通常是根据以下因素构建的:

  • 时间轴:用于根据时间搜索相关日志条目
  • 范围:用于根据规范属性搜索相关日志条目
    • 资源:将其与项目中的其他类型资源区分开来。
      • type:在 Logs Explorer 中显示为“Vertex AI Reasoning Engine”,在日志条目中显示为 "aiplatform.googleapis.com/ReasoningEngine"
      • labels:对于位置 (LOCATION)、项目 PROJECT_ID 和资源 RESOURCE_ID
    • logName:日志条目所属的日志:
      • 构建时的日志条目的日志 ID 为 reasoning_engine_build
      • stdoutstderr 的日志条目分别具有日志 ID reasoning_engine_stdoutreasoning_engine_stderr
      • 来自 Python 日志记录或 Cloud Logging 客户端的日志条目将具有基于为代理写入日志中的代码的自定义日志 ID。
    • 跟踪记录span:用于跟踪查询时的日志。
    • 严重程度:日志条目的严重程度。
    • insertId:日志条目的唯一标识符。
  • labels:键值对映射,用于提供有关日志条目的其他信息。这些标签可以是用户定义的,也可以是系统定义的,可用于对日志进行分类,并在 Logs Explorer 中更轻松地搜索日志。
  • 载荷:日志条目的内容。

以下示例展示了如何使用 RESOURCE_ID 查询已部署代理的所有 INFO 日志:

resource.labels.reasoning_engine_id=RESOURCE_ID AND
severity=INFO

您可以在 Logs Explorer 中查看该日志:

https://console.cloud.google.com/logs/query;query=severity%3DINFO%0Aresource.labels.reasoning_engine_id%3D%22RESOURCE_ID%22;duration=DURATION?project=PROJECT_ID

其中,查询已进行适当的网址编码,其他参数如下所示:

  • DURATION:例如,PT30M 表示过去 30 分钟(或 PT10M 表示过去 10 分钟),以及
  • PROJECT_ID: Google Cloud 项目。

如需了解详情,请参阅使用 Logging 查询语言构建和保存查询

查询代理的日志

如需以程序化方式查询日志,有两种常见选择:

Python

from google.cloud import logging

logging_client = logging.Client(project="PROJECT_ID")
logger = logging_client.logger("LOG_ID")  # E.g. "logging_client"
print("Listing entries for logger {}:".format(logger.name))
for entry in logger.list_entries(
    filter_="resource.labels.reasoning_engine_id=RESOURCE_ID"  # Optional
):
    timestamp = entry.timestamp.isoformat()
    print("* {}: {}".format(timestamp, entry.payload))

每个 entry 都将对应于一个 LogEntry。 如需详细了解 logger.list_entries 的输入参数,请参阅 API 参考文档

SQL

日志视图

SELECT *
FROM `PROJECT_ID.LOCATION.BUCKET_ID.LOG_VIEW_ID`

分析视图

SELECT *
FROM `analytics_view.PROJECT_ID.LOCATION.ANALYTICS_VIEW_ID`