azureazure-api-managementibm-api-management

Azure API management configuring external caching policy


We are using Azure API Management to publish, monitor and maintain APIs. Also we have implemented B2C login for Authentication and Authorization.

I'm trying to configure external cache for APIs. Somehow caching policy is not working. I refer following link https://learn.microsoft.com/en-us/azure/api-management/api-management-sample-cache-by-key

Based on logged in user tenant id, we want to store the template in cache and retrieve later for next request. Here is the policy I have written.

<policies>
    <inbound>
        <set-variable name="tenantId" value="@(context.Request.Headers.GetValueOrDefault("Authorization","").Split(' ')[1].AsJwt()?.Subject)" />
        <cache-lookup-value key="@("templates-" + context.Variables["tenantId"])" variable-name="templates" />
        <choose>
            <when condition="@(!context.Variables.ContainsKey("tenantId"))">
                <send-request mode="new" response-variable-name="templateResponse" timeout="15" ignore-error="true">
                    <set-url>https://abc.azure-api.net/api/notification/templates/?api-version=v1</set-url>
                    <set-method>GET</set-method>
                </send-request>
                <set-variable name="templates" value="@(((IResponse)context.Variables["templateResponse"]).Body.As<string>())" />
                <cache-store-value key="@("templates-" + context.Variables["tenantId"])" value="@((string)context.Variables["templates"])" duration="10000" />
            </when>
        </choose>
        <base />
    </inbound>
    <backend>
        <base />
    </backend>
    <outbound>
        <base />
    </outbound>
    <on-error>
        <base />
    </on-error>
</policies>

Solution

  • I made some mistake while writing policy. Here is the corrected policy.

    <policies>
        <inbound>
            <set-variable name="userId" value="@(context.Request.Headers.GetValueOrDefault("Authorization","").Split(' ')[1].AsJwt()?.Subject)" />
            <cache-lookup-value key="@("templates-" + context.Variables["userId"])" variable-name="templates" caching-type="external" />
            <choose>
                <when condition="@(!context.Variables.ContainsKey("templates"))">
                    <send-request mode="new" response-variable-name="templateResponse" timeout="15" ignore-error="true">
                        <set-url>https://appname.azurewebsites.net/api/templates</set-url>
                        <set-method>GET</set-method>
                        <set-header name="Authorization" exists-action="override">
                            <value>@(context.Request.Headers.GetValueOrDefault("Authorization",""))</value>
                        </set-header>
                    </send-request>
                    <set-variable name="templates" value="@(((IResponse)context.Variables["templateResponse"]).Body.As<string>())" />
                    <cache-store-value key="@("templates-" + context.Variables["userId"])" value="@((string)context.Variables["templates"])" duration="10000" />
                </when>
            </choose>
            <base />
        </inbound>
        <backend>
            <base />
        </backend>
        <outbound>
            <set-body>@((string)context.Variables["templates"])</set-body>
            <base />
        </outbound>
        <on-error>
            <base />
        </on-error>
    </policies>