Standard V2/Basic V2版API Management策略配置异常排查
问题分析与解决方案
核心问题:空引用异常
你的策略代码中存在未处理的空引用场景,这是导致Standard V2/Basic V2版本报错的根本原因:
- 当请求触发第一个
<choose>块中的<return-response>时(比如access-token缺少Bearer前缀、未携带access-token或access_token参数),<send-request>不会执行,validationResponse变量不会被创建。 - 第二个
<choose>块直接尝试访问validationResponse的StatusCode属性,此时response为null,会触发空引用异常。 - Consumption/Developer版本的APIM运行时可能对这类空引用有容错处理,而Standard/Basic V2版本的运行时更严格,直接抛出异常导致策略执行失败。
修正后的策略代码
添加validationResponse的null判断,确保只有变量存在时才执行后续校验:
<policies> <inbound> <choose> <when condition="@(context.Request.Headers.ContainsKey("access-token"))"> <choose> <when condition="@(context.Request.Headers["access-token"][0].StartsWith("Bearer "))"> <send-request mode="new" response-variable-name="validationResponse"> <set-url>https://its-example-url</set-url> <set-method>POST</set-method> <set-header name="Authorization" exists-action="override"> <value>@(context.Request.Headers["access-token"][0].Replace("Bearer ", ""))</value> </set-header> </send-request> </when> <otherwise> <return-response> <set-status code="400" reason="Bad Request" /> <set-header name="Content-Type" exists-action="override"> <value>text/plain</value> </set-header> <set-body>Esta faltando o Bearer no valor da chave 'access-token', na header!</set-body> </return-response> </otherwise> </choose> </when> <otherwise> <choose> <when condition="@(context.Request.Url.Query.ContainsKey("access_token"))"> <send-request mode="new" response-variable-name="validationResponse"> <set-url>https://its-example-url</set-url> <set-method>POST</set-method> <set-header name="Authorization" exists-action="override"> <value>@(context.Request.Url.Query.GetValueOrDefault("access_token", ""))</value> </set-header> </send-request> </when> <otherwise> <return-response> <set-status code="400" reason="Bad Request" /> <set-header name="Content-Type" exists-action="override"> <value>text/plain</value> </set-header> <set-body>Esta faltando o parametro access_token!</set-body> </return-response> </otherwise> </choose> </otherwise> </choose> <choose> <!-- 先判断validationResponse是否存在且不为null --> <when condition="@(context.Variables.ContainsKey("validationResponse") && context.Variables.GetValueOrDefault<IResponse>("validationResponse", null) != null && (int)context.Variables.GetValueOrDefault<IResponse>("validationResponse", null).StatusCode != 200)"> <return-response> <set-status code="@((int)context.Variables.GetValueOrDefault<IResponse>("validationResponse", null).StatusCode)" /> <set-header name="Content-Type" exists-action="override"> <value>application/json</value> </set-header> <set-body>@(context.Variables.GetValueOrDefault<IResponse>("validationResponse", null).Body.As<string>())</set-body> </return-response> </when> </choose> <cors> <allowed-origins> <origin>*</origin> </allowed-origins> <allowed-methods> <method>GET</method> <method>POST</method> </allowed-methods> <allowed-headers> <header>Authorization</header> <header>access-token</header> <header>Content-Type</header> </allowed-headers> </cors> </inbound> <backend> <base /> </backend> <outbound> <base /> </outbound> <on-error> <base /> </on-error> </policies>
额外优化建议
- 避免重复获取
validationResponse变量,可以使用临时变量简化代码:<when condition="@( context.Variables.ContainsKey("validationResponse") && { var response = context.Variables.GetValueOrDefault<IResponse>("validationResponse", null); return response != null && (int)response.StatusCode != 200; } )"> - 访问Header时,建议先确认索引存在(比如
context.Request.Headers["access-token"].Any()),避免因Header存在但无值导致的异常。
内容的提问来源于stack exchange,提问作者Pedro Henrique G Ramalho
相关产品推荐
相关产品推荐

