API Gateway 映射模板和访问日志记录变量引用 - Amazon API Gateway
Amazon Web Services 文档中描述的 Amazon Web Services 服务或功能可能因区域而异。要查看适用于中国区域的差异,请参阅 中国的 Amazon Web Services 服务入门 (PDF)

API Gateway 映射模板和访问日志记录变量引用

本部分提供了有关 Amazon API Gateway 定义的用于数据模型、授权方、映射模板和 CloudWatch 访问日志记录的变量和函数的参考信息。有关如何使用这些变量和函数的详细信息,请参阅了解映射模板。有关 Velocity 模板语言 (VTL) 的更多信息,请参阅 VTL 参考

注意

有关 $method$integration 变量,请参阅 Amazon API Gateway API 请求和响应数据映射参考

适用于数据模型、授权方、映射模板和 CloudWatch 访问日志记录的 $context 变量

以下 $context 变量可用于数据模型、授权方、映射模板和 CloudWatch 访问日志记录。API Gateway 可能会添加其他上下文变量。

有关只能在 CloudWatch 访问日志记录中使用的 $context 变量,请参阅仅适用于访问日志记录的 $context 变量

参数 说明
$context.accountId

API 拥有者的 Amazon 账户 ID。

$context.apiId

API Gateway 分配给您的 API 的标识符。

$context.authorizer.claims.property

成功对方法调用方进行身份验证后从 Amazon Cognito 用户池返回的声明的属性。有关更多信息,请参阅 使用 Amazon Cognito 用户池作为授权方控制对 REST API 的访问

注意

调用 $context.authorizer.claims 将返回 null。

$context.authorizer.principalId

与由客户端发送的令牌关联并从 API Gateway Lambda 授权方(以前称为自定义授权方)返回的委托人用户标识。有关更多信息,请参阅 使用 API Gateway Lambda 授权方

$context.authorizer.property

从 API Gateway Lambda 授权方函数返回的 context 映射的指定键/值对的字符串化值。例如,如果授权方返回以下 context 映射:

"context" : { "key": "value", "numKey": 1, "boolKey": true }

调用 $context.authorizer.key 将返回 "value" 字符串,调用 $context.authorizer.numKey 将返回 "1" 字符串,而调用 $context.authorizer.boolKey 将返回 "true" 字符串。

有关更多信息,请参阅 使用 API Gateway Lambda 授权方

$context.awsEndpointRequestId

Amazon 端点的请求 ID。

$context.deploymentId

API 部署的 ID。

$context.domainName

用于调用 API 的完整域名。这应与传入的 Host 标头相同。

$context.domainPrefix

$context.domainName 的第一个标签。

$context.error.message

包含 API Gateway 错误消息的字符串。此变量只能用于 GatewayResponse 正文映射模板中(不由 Velocity 模板语言引擎处理)和访问日志记录中的简单变量替换。有关更多信息,请参阅使用 CloudWatch 指标监控 WebSocket API 执行设置网关响应以自定义错误响应

$context.error.messageString $context.error.message 的带引号的值,即 "$context.error.message"
$context.error.responseType

GatewayResponse类型 此变量只能用于 GatewayResponse 正文映射模板中(不由 Velocity 模板语言引擎处理)和访问日志记录中的简单变量替换。有关更多信息,请参阅使用 CloudWatch 指标监控 WebSocket API 执行设置网关响应以自定义错误响应

$context.error.validationErrorString

包含详细验证错误消息的字符串。

$context.extendedRequestId API Gateway 生成并分配给 API 请求的扩展 ID。扩展请求 ID 包含调试和故障排除的有用信息。
$context.httpMethod

所用的 HTTP 方法。有效值包括:DELETEGETHEADOPTIONSPATCHPOSTPUT

$context.identity.accountId

与请求关联的 Amazon 账户 ID。

$context.identity.apiKey

对于需要 API 密钥的 API 方法,此变量是与该方法请求关联的 API 密钥。对于无需 API 密钥的方法,此变量为 null。有关更多信息,请参阅 创建和使用带 API 密钥的使用计划

$context.identity.apiKeyId 与需要 API 密钥的 API 请求关联的 API 密钥 ID。
$context.identity.caller

签发请求的调用方的委托人标识符。对于使用 IAM 授权的资源支持此项。

$context.identity.cognitoAuthenticationProvider

发出请求的调用方使用的 Amazon Cognito 身份验证提供商的逗号分隔列表。仅当使用 Amazon Cognito 凭证对请求签名时才可用。

例如,对于 Amazon Cognito 身份池中的身份,cognito-idp. region.amazonaws.com/user_pool_id,cognito-idp.region.amazonaws.com/user_pool_id:CognitoSignIn:token subject claim

有关更多信息,请参阅 Amazon Cognito 开发人员指南 中的使用联合身份

$context.identity.cognitoAuthenticationType

发出请求的调用方的 Amazon Cognito 身份验证类型。仅当使用 Amazon Cognito 凭证对请求签名时才可用。可能的值包括经过身份验证的身份的 authenticated 和未经身份验证的身份的 unauthenticated

$context.identity.cognitoIdentityId

发出请求的调用方的 Amazon Cognito 身份 ID。仅当使用 Amazon Cognito 凭证对请求签名时才可用。

$context.identity.cognitoIdentityPoolId

发出请求的调用方的 Amazon Cognito 身份池 ID。仅当使用 Amazon Cognito 凭证对请求签名时才可用。

$context.identity.principalOrgId

Amazon 组织 ID

$context.identity.sourceIp

向 API Gateway 端点发出请求的即时 TCP 连接的源 IP 地址。

$context.identity.clientCert.clientCertPem

客户端在双向 TLS 身份验证过程中提供的 PEM 编码的客户端证书。当客户端使用已启用双向 TLS 的自定义域名访问 API 时提供。仅在双向 TLS 身份验证失败时才出现在访问日志中。

$context.identity.clientCert.subjectDN

客户端提供的证书的主题的可分辨名称。当客户端使用已启用双向 TLS 的自定义域名访问 API 时提供。仅在双向 TLS 身份验证失败时才出现在访问日志中。

$context.identity.clientCert.issuerDN

客户端提供的证书的颁发者的可分辨名称。当客户端使用已启用双向 TLS 的自定义域名访问 API 时提供。仅在双向 TLS 身份验证失败时才出现在访问日志中。

$context.identity.clientCert.serialNumber

证书的序列号。当客户端使用已启用双向 TLS 的自定义域名访问 API 时提供。仅在双向 TLS 身份验证失败时才出现在访问日志中。

$context.identity.clientCert.validity.notBefore

证书无效之前的日期。当客户端使用已启用双向 TLS 的自定义域名访问 API 时提供。仅在双向 TLS 身份验证失败时才出现在访问日志中。

$context.identity.clientCert.validity.notAfter

证书无效后的日期。当客户端使用已启用双向 TLS 的自定义域名访问 API 时提供。仅在双向 TLS 身份验证失败时才出现在访问日志中。

$context.identity.vpcId

向 API Gateway 端点发出请求的 VPC 的 VPC ID。

$context.identity.vpceId

向 API Gateway 端点发出请求的 VPC 端点的 VPC 端点 ID。仅当您具有私有 API 时才会显示。

$context.identity.user

将获得资源访问权限授权的用户的委托人标识符。对于使用 IAM 授权的资源支持此项。

$context.identity.userAgent

API 调用方的 User-Agent 标头。

$context.identity.userArn

身份验证后标识的有效用户的 Amazon Resource Name (ARN)。有关更多信息,请参阅 https://docs.amazonaws.cn/IAM/latest/UserGuide/id_users.html

$context.isCanaryRequest

如果请求定向到金丝雀,将返回 true,如果请求没有定向到金丝雀,将返回 false。仅当您启用金丝雀时才会显示。

$context.path 请求路径。例如,对于 https://{rest-api-id}.execute-api.{region}.amazonaws.com/{stage}/root/child 的非代理请求 URL,$context.path 值为 /{stage}/root/child
$context.protocol 请求的协议,例如,HTTP/1.1
注意

API Gateway API 可以接受 HTTP/2 请求,但 API Gateway 使用 HTTP/1.1 向后端集成发送请求。因此,即使客户端发送的请求使用 HTTP/2,请求协议也会记录为 HTTP/1.1。

$context.requestId

请求的 ID。客户可以覆盖此请求 ID。使用 $context.extendedRequestId 用于 API Gateway 生成的唯一请求 ID。

$context.requestOverride.header.header_name

请求标头覆盖。如果定义此参数,则它将包含要使用的标题,而不是集成请求窗格中定义的 HTTP 标头。有关更多信息,请参阅 使用映射模板覆盖 API 的请求和响应参数以及状态代码

$context.requestOverride.path.path_name

请求路径覆盖。如果定义此参数,则它将包含要使用的请求路径,而不是集成请求窗格中定义的 URL 路径参数。有关更多信息,请参阅 使用映射模板覆盖 API 的请求和响应参数以及状态代码

$context.requestOverride.querystring.querystring_name

请求查询字符串覆盖。如果定义此参数,则它将包含要使用的请求查询字符串,而不是集成请求窗格中定义的 URL 查询字符串参数。有关更多信息,请参阅 使用映射模板覆盖 API 的请求和响应参数以及状态代码

$context.responseOverride.header.header_name 响应标头覆盖。如果定义此参数,则它包含要使用的标头,而不是集成响应窗格中定义为默认映射响应标头。有关更多信息,请参阅 使用映射模板覆盖 API 的请求和响应参数以及状态代码
$context.responseOverride.status 响应状态代码覆盖。如果定义此参数,则它包含要使用的状态代码,而不是集成响应窗格中定义为默认映射方法响应状态。有关更多信息,请参阅 使用映射模板覆盖 API 的请求和响应参数以及状态代码
$context.requestTime CLF 格式的请求时间 (dd/MMM/yyyy:HH:mm:ss +-hhmm)。
$context.requestTimeEpoch Epoch 格式的请求时间,以毫秒为单位。
$context.resourceId

API Gateway 分配给您的资源的标识符。

$context.resourcePath

资源路径。例如,对于 https://{rest-api-id}.execute-api.{region}.amazonaws.com/{stage}/root/child 的非代理请求 URI,$context.resourcePath 值为 /root/child。有关更多信息,请参阅 教程:使用 HTTP 非代理集成构建 REST API

$context.stage

API 请求的部署阶段(例如,BetaProd)。

$context.wafResponseCode

Amazon WAF 中收到的响应:WAF_ALLOWWAF_BLOCK。如果阶段未与 Web ACL 关联,则不会设置。有关更多信息,请参阅 使用 Amazon WAF 保护 API

$context.webaclArn

Web ACL 的完整 ARN,用于决定是允许还是阻止请求。如果阶段未与 Web ACL 关联,则不会设置。有关更多信息,请参阅 使用 Amazon WAF 保护 API

$context 变量模板示例

如果您的 API 方法将结构化数据传递到要求数据采用特定格式的后端,则您可能要在映射模板中使用 $context 变量。

以下示例显示了一个映射模板,该模板将传入的 $context 变量映射到后端变量,这些变量在集成请求负载中的名称稍有不同:

注意

其中一个变量是 API 密钥。此示例假设方法需要 API 密钥。

{ "stage" : "$context.stage", "request_id" : "$context.requestId", "api_id" : "$context.apiId", "resource_path" : "$context.resourcePath", "resource_id" : "$context.resourceId", "http_method" : "$context.httpMethod", "source_ip" : "$context.identity.sourceIp", "user-agent" : "$context.identity.userAgent", "account_id" : "$context.identity.accountId", "api_key" : "$context.identity.apiKey", "caller" : "$context.identity.caller", "user" : "$context.identity.user", "user_arn" : "$context.identity.userArn" }

此映射模板的输出应与以下内容类似:

{ stage: 'prod', request_id: 'abcdefg-000-000-0000-abcdefg', api_id: 'abcd1234', resource_path: '/', resource_id: 'efg567', http_method: 'GET', source_ip: '192.0.2.1', user-agent: 'curl/7.84.0', account_id: '111122223333', api_key: 'MyTestKey', caller: 'ABCD-0000-12345', user: 'ABCD-0000-12345', user_arn: 'arn:aws:sts::111122223333:assumed-role/Admin/carlos-salazar' }

仅适用于访问日志记录的 $context 变量

以下 $context 变量仅适用于访问日志记录。有关更多信息,请参阅 在 API Gateway 中为 REST API 设置 CloudWatch 日志记录。(有关 WebSocket API,请参阅使用 CloudWatch 指标监控 WebSocket API 执行。)

参数 说明
$context.authorize.error 授权错误消息。
$context.authorize.latency 授权延迟时间(以毫秒为单位)。
$context.authorize.status 从授权尝试返回的状态代码。
$context.authorizer.error 从授权方返回的错误消息。
$context.authorizer.integrationLatency 授权方延迟(以毫秒为单位)。
$context.authorizer.integrationStatus 从 Lambda 授权方返回的状态代码。
$context.authorizer.latency 授权方延迟(以毫秒为单位)。
$context.authorizer.requestId Amazon 端点的请求 ID。
$context.authorizer.status 从授权方返回的状态代码。
$context.authenticate.error 从身份验证尝试返回的错误消息。
$context.authenticate.latency 身份验证延迟时间(以毫秒为单位)。
$context.authenticate.status 从身份验证尝试返回的状态代码。
$context.customDomain.basePathMatched

传入请求所匹配的 API 映射路径。适用于客户端使用自定义域名访问 API 的情况。例如,如果客户端向 https://api.example.com/v1/orders/1234 发送请求,且该请求匹配路径为 v1/orders 的 API 映射,则值为 v1/orders。要了解更多信息,请参阅 对 REST API 使用 API 映射

$context.endpointType

API 的端点类型。

$context.integration.error 从集成返回的错误消息。
$context.integration.integrationStatus 对于 Lambda 代理集成,从 Amazon Lambda(而不是从后端 Lambda 函数代码)返回的状态代码。
$context.integration.latency 集成延迟(毫秒)。等效于 $context.integrationLatency
$context.integration.requestId Amazon 端点的请求 ID。等效于 $context.awsEndpointRequestId
$context.integration.status 从集成返回的状态代码。对于 Lambda 代理集成,这是 Lambda 函数代码返回的状态代码。
$context.integrationLatency 集成延迟(毫秒)。
$context.integrationStatus 对于 Lambda 代理集成,此参数表示从 Amazon Lambda Lambda(而不是从后端 Lambda 函数代码)返回的状态代码。
$context.responseLatency 响应延迟(毫秒)。
$context.responseLength 响应负载长度(以字节为单位)。
$context.status 方法响应状态。
$context.waf.error 从 返回的错误消息Amazon WAF
$context.waf.latency Amazon WAF 延迟时间(以毫秒为单位)。
$context.waf.status 从 返回的状态代码Amazon WAF
$context.xrayTraceId

X-Ray 跟踪的跟踪 ID。有关更多信息,请参阅 使用 API Gateway REST API 设置 Amazon X-Ray

$input 变量

$input 变量表示将由映射模板处理的方法请求负载和参数。它可以提供以下函数:

变量和函数 说明
$input.body

以字符串形式返回原始请求负载。

$input.json(x)

此函数计算 JSONPath 表达式并以 JSON 字符串形式返回结果。

例如,$input.json('$.pets') 返回一个表示 pets 结构的 JSON 字符串。

有关 JSONPath 的更多信息,请参阅 JSONPath适用于 Java 的 JSONPath

$input.params()

返回所有请求参数的映射。我们建议您使用 $util.escapeJavaScript 对结果进行清理,以避免潜在的注入攻击。要完全控制请求清理,可以使用没有模板的代理集成,并在集成中处理请求清理。

$input.params(x)

在给定参数名称字符串 x 的情况下,返回路径中的方法请求参数值、查询字符串或标头值(按照该顺序搜索)。我们建议您使用 $util.escapeJavaScript 对参数进行清理,以避免潜在的注入攻击。要完全控制参数清理,可以使用没有模板的代理集成,并在集成中处理请求清理。

$input.path(x)

获取一个 JSONPath 表达式字符串 (x) 并返回结果的 JSON 对象表达式。这样,您便可通过 Apache Velocity 模板语言 (VTL) 在本机访问和操作负载的元素。

例如,如果表达式 $input.path('$.pets') 返回一个如下所示的对象:

[ { "id": 1, "type": "dog", "price": 249.99 }, { "id": 2, "type": "cat", "price": 124.99 }, { "id": 3, "type": "fish", "price": 0.99 } ]

$input.path('$.pets').count() 将返回 "3"

有关 JSONPath 的更多信息,请参阅 JSONPath适用于 Java 的 JSONPath

$input 变量模板示例

以下示例显示了如何在映射模板中使用 $input 变量:您可以使用模拟集成或用于将输入事件返回到 API Gateway 的 Lambda 非代理集成来尝试这些示例。

参数映射模板示例

以下示例将所有请求参数(包括 pathquerystringheader)通过 JSON 负载传递到集成端点:

#set($allParams = $input.params()) { "params" : { #foreach($type in $allParams.keySet()) #set($params = $allParams.get($type)) "$type" : { #foreach($paramName in $params.keySet()) "$paramName" : "$util.escapeJavaScript($params.get($paramName))" #if($foreach.hasNext),#end #end } #if($foreach.hasNext),#end #end } }

对于包含以下输入参数的请求:

  • 名为 myparam 的路径参数

  • 查询字符串参数 querystring1=value1,value2&querystring2=value3

  • 标头 "header1" : "value1""header2" : "value2""header3" : "value3"

此映射模板的输出应与以下内容类似:

{ "params" : { "path" : { "path" : "myparam" } , "querystring" : { "querystring1" : "value1,value2" , "querystring2" : "value3" } , "header" : { "header3" : "value3" , "header2" : "value2" , "header1" : "value1" } } }

JSON 映射模板示例

您可能希望使用 $input 变量来获取查询字符串和请求正文(无论是否使用模型)。您可能还希望获取参数和负载或者负载的子部分。以下三个示例显示如何执行此操作。

以下示例使用映射模板来获取负载的子部分。此示例获取输入参数 name,然后获取整个 POST 正文:

{ "name" : "$input.params('name')", "body" : $input.json('$') }

对于包含查询字符串参数 name=Bella&type=dog 和以下正文的请求:

{ "Price" : "249.99", "Age": "6" }

此映射模板的输出应与以下内容类似:

{ "name" : "Bella", "body" : {"Price":"249.99","Age":"6"} }

如果 JSON 输入包含无法通过 JavaScript 解析的非转义字符,则 API Gateway 可能会返回 400 响应。应用 $util.escapeJavaScript($input.json('$')) 来确保正确解析 JSON 输入。

上面的示例在应用了 $util.escapeJavaScript($input.json('$')) 之后会如下所示:

{ "name" : "$input.params('name')", "body" : $util.escapeJavaScript($input.json('$')) }

在这种情况下,此映射模板的输出应与以下内容类似:

{ "name" : "Bella", "body": {\"Price\":\"249.99\",\"Age\":\"6\"} }

JSONPath 表达式示例

以下示例介绍如何将 JSONPath 表达式传递到 json() 方法。您也可以通过使用句点 . 指定属性,来读取请求正文对象的子部分:

{ "name" : "$input.params('name')", "body" : $input.json('$.Age') }

对于包含查询字符串参数 name=Bella&type=dog 和以下正文的请求:

{ "Price" : "249.99", "Age": "6" }

此映射模板的输出应与以下内容类似:

{ "name" : "Bella", "body" : "6" }

如果方法请求负载包含无法通过 JavaScript 解析的非转义字符,则 API Gateway 可能会返回 400 响应。应用 $util.escapeJavaScript() 来确保正确解析 JSON 输入。

上面的示例在应用了 $util.escapeJavaScript($input.json('$.Age')) 之后会如下所示:

{ "name" : "$input.params('name')", "body" : "$util.escapeJavaScript($input.json('$.Age'))" }

在这种情况下,此映射模板的输出应与以下内容类似:

{ "name" : "Bella", "body": "\"6\"" }

请求和响应示例

以下示例对路径为 /things/{id} 的资源使用 $input.params()$input.path()$input.json()

{ "id" : "$input.params('id')", "count" : "$input.path('$.things').size()", "things" : $input.json('$.things')" }

对于包含路径参数 123 和以下正文的请求:

{ "things": { "1": {}, "2": {}, "3": {} } }

此映射模板的输出应与以下内容类似:

{"id":"123","count":"3","things":{"1":{},"2":{},"3":{}}}

如果方法请求负载包含无法通过 JavaScript 解析的非转义字符,则 API Gateway 可能会返回 400 响应。应用 $util.escapeJavaScript() 来确保正确解析 JSON 输入。

上面的示例在应用了 $util.escapeJavaScript($input.json('$.things')) 之后会如下所示:

{ "id" : "$input.params('id')", "count" : "$input.path('$.things').size()", "things" : "$util.escapeJavaScript($input.json('$.things'))" }

此映射模板的输出应与以下内容类似:

{"id":"123","count":"3","things":"{\"1\":{},\"2\":{},\"3\":{}}"}

有关更多映射示例,请参阅了解映射模板

$stageVariables

阶段变量可用于参数映射和映射模板,并可用作在方法集成中使用的 ARN 和 URL 中的占位符。有关更多信息,请参阅 为 REST API 部署设置阶段变量

语法 描述
$stageVariables.<variable_name>$stageVariables['<variable_name>']${stageVariables['<variable_name>']}

<variable_name> 表示阶段变量名称。

$util 变量

$util 变量包含映射模板中使用的实用程序函数。

注意

除非另行指定,否则默认字符集为 UTF-8。

函数 说明
$util.escapeJavaScript()

使用 JavaScript 字符串规则对字符串中的字符进行转义。

注意

此函数会将任何常规单引号 (') 变成转义单引号 (\')。但是,转义单引号在 JSON 中无效。因此,当此函数的输出用于 JSON 属性时,必须将任何转义单引号 (\') 变回常规单引号 (')。如下例所示:

"input" : "$util.escapeJavaScript(data).replaceAll("\\'","'")"
$util.parseJson()

获取“字符串化的”JSON 并返回结果的对象表示形式。您可以使用此函数的结果通过 Apache Velocity 模板语言 (VTL) 在本机访问和操作负载的元素。例如,如果您具有以下负载:

{"errorMessage":"{\"key1\":\"var1\",\"key2\":{\"arr\":[1,2,3]}}"}

并使用以下映射模板

#set ($errorMessageObj = $util.parseJson($input.path('$.errorMessage'))) { "errorMessageObjKey2ArrVal" : $errorMessageObj.key2.arr[0] }

您将得到以下输出:

{ "errorMessageObjKey2ArrVal" : 1 }
$util.urlEncode()

将字符串转换为“application/x-www-form-urlencoded”格式。

$util.urlDecode()

对“application/x-www-form-urlencoded”字符串进行解码。

$util.base64Encode()

将数据编码为 base64 编码的字符串。

$util.base64Decode()

对 base64 编码字符串中的数据进行解码。