OpenRouter 安全与可观测

OpenRouter 安全与可观测

Snowflake

4 分钟阅读

Snowflake

将追踪发送到 Snowflake

Snowflake 是云数据仓库平台。OpenRouter 可以将追踪直接流式写入你的 Snowflake 数据库,用于自定义分析、长期存储和商业智能。

第 1 步:创建追踪表

在连接 OpenRouter 之前,先在 Snowflake 数据库中创建 OPENROUTER_TRACES 表。配置该目标端时,可在 OpenRouter 控制台中找到确切的 SQL:

Snowflake 表设置

第 2 步:创建访问凭据

在 Snowflake UI 的 设置 > 身份验证(Settings > Authentication) 下,生成具有 ACCOUNTADMIN 权限的 可编程访问令牌(Programmatic Access Token)

Snowflake PAT

第 3 步:在 OpenRouter 中启用广播

前往 设置 > 可观测性(Settings > Observability),打开 启用广播(Enable Broadcast) 开关。

启用广播

第 4 步:配置 Snowflake

点击 Snowflake 旁的编辑图标,并填写:

  • Account:你的 Snowflake 账户标识符(例如 eac52885.us-east-1)。可在 Snowflake 实例 URL 末尾找到账户区域和账户编号:https://app.snowflake.com/us-east-1/eac52885;两者合在一起就是账户标识符。
  • Token:你的可编程访问令牌。
  • Database:目标数据库名称(默认:SNOWFLAKE_LEARNING_DB)。
  • Schema:目标模式名称(默认:PUBLIC)。
  • Table:表名(默认:OPENROUTER_TRACES)。
  • Warehouse:计算仓库名称(默认:COMPUTE_WH)。

第 5 步:测试并保存

点击 测试连接(Test Connection) 验证配置。仅当测试通过时才会保存配置。

第 6 步:发送测试追踪

通过 OpenRouter 发出一次 API 请求,然后查询 Snowflake 表以确认已收到该追踪。

Snowflake 测试追踪

查询示例

按模型分析费用

SELECT
  DATE_TRUNC('day', TIMESTAMP) as day,
  MODEL,
  SUM(TOTAL_COST) as total_cost,
  SUM(TOTAL_TOKENS) as total_tokens,
  COUNT(*) as request_count
FROM OPENROUTER_TRACES
WHERE TIMESTAMP >= DATEADD(day, -30, CURRENT_TIMESTAMP())
  AND STATUS = 'ok'
  AND SPAN_TYPE = 'GENERATION'
GROUP BY day, MODEL
ORDER BY day DESC, total_cost DESC;

用户活动分析

SELECT
  USER_ID,
  COUNT(DISTINCT TRACE_ID) as trace_count,
  COUNT(DISTINCT SESSION_ID) as session_count,
  SUM(TOTAL_TOKENS) as total_tokens,
  SUM(TOTAL_COST) as total_cost,
  AVG(DURATION_MS) as avg_duration_ms
FROM OPENROUTER_TRACES
WHERE TIMESTAMP >= DATEADD(day, -7, CURRENT_TIMESTAMP())
  AND SPAN_TYPE = 'GENERATION'
GROUP BY USER_ID
ORDER BY total_cost DESC;

错误分析

SELECT
  TRACE_ID,
  TIMESTAMP,
  MODEL,
  LEVEL,
  FINISH_REASON,
  METADATA as user_metadata,
  INPUT,
  OUTPUT
FROM OPENROUTER_TRACES
WHERE STATUS = 'error'
  AND TIMESTAMP >= DATEADD(hour, -1, CURRENT_TIMESTAMP())
ORDER BY TIMESTAMP DESC;

模型服务提供商性能对比

SELECT
  PROVIDER_NAME,
  MODEL,
  AVG(DURATION_MS) as avg_duration_ms,
  PERCENTILE_CONT(0.5) WITHIN GROUP (ORDER BY DURATION_MS) as p50_duration_ms,
  PERCENTILE_CONT(0.95) WITHIN GROUP (ORDER BY DURATION_MS) as p95_duration_ms,
  COUNT(*) as request_count
FROM OPENROUTER_TRACES
WHERE TIMESTAMP >= DATEADD(day, -7, CURRENT_TIMESTAMP())
  AND STATUS = 'ok'
  AND SPAN_TYPE = 'GENERATION'
GROUP BY PROVIDER_NAME, MODEL
HAVING request_count >= 10
ORDER BY avg_duration_ms;

按 API 密钥统计用量

SELECT
  API_KEY_NAME,
  COUNT(DISTINCT TRACE_ID) as trace_count,
  SUM(TOTAL_COST) as total_cost,
  SUM(PROMPT_TOKENS) as prompt_tokens,
  SUM(COMPLETION_TOKENS) as completion_tokens
FROM OPENROUTER_TRACES
WHERE TIMESTAMP >= DATEADD(day, -30, CURRENT_TIMESTAMP())
  AND SPAN_TYPE = 'GENERATION'
GROUP BY API_KEY_NAME
ORDER BY total_cost DESC;

访问 VARIANT 列

SELECT
  TRACE_ID,
  METADATA:custom_field::STRING as custom_value,
  ATTRIBUTES:"gen_ai.request.model"::STRING as requested_model
FROM OPENROUTER_TRACES
WHERE METADATA:custom_field IS NOT NULL;

解析输入消息

SELECT
  TRACE_ID,
  INPUT:messages[0]:role::STRING as first_message_role,
  INPUT:messages[0]:content::STRING as first_message_content
FROM OPENROUTER_TRACES
WHERE SPAN_TYPE = 'GENERATION';

表结构设计

类型化列

该表结构将常用查询字段提取为类型化列,以便高效筛选和聚合:

  • 标识符:TRACE_ID、USER_ID、SESSION_ID 等
  • 时间戳:用于时间序列分析
  • 模型信息:用于费用和性能分析
  • 指标:用于计费的 Token 与费用

VARIANT 列

访问频率较低、结构可变的数据存储在 VARIANT 列中:

  • ATTRIBUTES:完整的 OTEL 属性集
  • INPUT/OUTPUT:可变的消息结构
  • METADATA:用户定义的键值
  • MODEL_PARAMETERS:模型特定配置

这种设计在查询性能、表结构灵活性和存储效率之间取得平衡。

自定义元数据

trace 字段中的自定义元数据存储在 METADATA VARIANT 列中。你可以使用 Snowflake 的半结构化数据函数进行查询。

支持的元数据键

Snowflake 映射说明
trace_idTRACE_ID column / METADATA:trace_id用于归组的自定义追踪标识符
trace_nameMETADATA:trace_name追踪的自定义名称
span_nameMETADATA:span_name中间 Span 的名称
generation_nameMETADATA:generation_nameLLM 生成的名称

示例

{
  "model": "openai/gpt-4o",
  "messages": [{ "role": "user", "content": "Forecast next quarter revenue..." }],
  "user": "user_12345",
  "session_id": "session_abc",
  "trace": {
    "trace_name": "Revenue Forecasting",
    "generation_name": "Generate Forecast",
    "department": "finance",
    "quarter": "Q2-2026",
    "model_version": "v3"
  }
}

查询自定义元数据

使用 Snowflake 的 VARIANT 列语法查询自定义元数据:

SELECT
  TRACE_ID,
  METADATA:department::STRING as department,
  METADATA:quarter::STRING as quarter,
  METADATA:model_version::STRING as model_version,
  TOTAL_COST,
  TOTAL_TOKENS
FROM OPENROUTER_TRACES
WHERE METADATA:department IS NOT NULL
  AND SPAN_TYPE = 'GENERATION'
ORDER BY TIMESTAMP DESC;

补充说明

  • user 字段会映射到类型化列 USER_ID
  • session_id 字段会映射到类型化列 SESSION_ID
  • trace 中的所有自定义元数据键都存储在 METADATA VARIANT 列中,便于灵活查询
  • 你可以为频繁查询的元数据字段创建物化视图以提高性能

隐私模式

当该目标端启用 隐私模式 时,追踪中会排除提示词和补全内容。其余追踪数据——Token 用量、费用、时间信息、模型信息以及自定义元数据——仍会正常发送。详情见 隐私模式