Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 7 additions & 8 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,12 +27,12 @@ Unlike implicit (best-effort) caching that some endpoints do opportunistically,

### How Azure delivers it

Azure exposes explicit caching through a dedicated resource provider — **`Microsoft.AzureContextCache`** — that lives **in your subscription, in your region, under your RBAC**. An Azure OpenAI deployment opts in by setting a single property, `properties.contextCacheContainerId`, on the deployment resource. Once linked, every chat/completion request sent to that deployment automatically benefits from the cache — no SDK changes, no extra headers.
Azure exposes explicit caching through the Storage resource provider — **`Microsoft.Storage`** — that lives **in your subscription, in your region, under your RBAC**. An Azure OpenAI deployment opts in by setting a single property, `properties.contextCacheContainerId`, on the deployment resource. Once linked, every chat/completion request sent to that deployment automatically benefits from the cache — no SDK changes, no extra headers.

| Concept | Azure resource |
|---|---|
| Cache **namespace** for an org/team | `Microsoft.AzureContextCache/accounts` |
| Cache **storage unit** for a specific model | `Microsoft.AzureContextCache/accounts/containers` |
| Cache **namespace** for an org/team | `Microsoft.Storage/contextCaches` |
| Cache **storage unit** for a specific model | `Microsoft.Storage/contextCaches/contextCacheContainers` |
| **AOAI deployment** that uses the cache | `Microsoft.CognitiveServices/accounts/deployments` with `properties.contextCacheContainerId` |

This quickstart packages all three (plus the AOAI account itself) into one ARM template so you can be sending cache-aware requests in about two minutes.
Expand Down Expand Up @@ -62,7 +62,7 @@ flowchart LR
end

subgraph CACHEBOX["⚡ Azure Context Cache"]
ACC["Microsoft.AzureContextCache/accounts<br/>kind = Regional"]:::cache
ACC["Microsoft.Storage/contextCaches<br/>kind = Regional"]:::cache
CONT["Container<br/><b>default-container</b><br/>model gpt-5.4 · TTL 7d"]:::cache
ACC --- CONT
end
Expand Down Expand Up @@ -110,8 +110,7 @@ Click **Review + create → Create**. When it finishes, the deployment **Outputs
The preview features below must be `Registered` before the deployment can succeed. You only need to do this **one time** per subscription:

```bash
az provider register --namespace Microsoft.AzureContextCache
az feature register --namespace Microsoft.AzureContextCache --name EnablePreview
az provider register --namespace Microsoft.Storage
az feature register --namespace Microsoft.CognitiveServices --name OpenAI.ContextCacheAllowed
```

Expand All @@ -128,8 +127,8 @@ Both features are **gated** — if a status stays `Pending` for more than a few
| # | Resource | Type | Defaults |
|---|---|---|---|
| 1 | Azure OpenAI account | `Microsoft.CognitiveServices/accounts` | kind `OpenAI`, SKU `S0`, public access on |
| 2 | Context Cache account | `Microsoft.AzureContextCache/accounts` | `accountKind = Regional` |
| 3 | Cache container | `Microsoft.AzureContextCache/accounts/containers` | model `gpt-5.4`, provider `OpenAI`, `timeToLive = 7d` |
| 2 | Context Cache account | `Microsoft.Storage/contextCaches` | `accountKind = Regional` |
| 3 | Cache container | `Microsoft.Storage/contextCaches/contextCacheContainers` | model `gpt-5.4`, provider `OpenAI`, `timeToLive = 7d` |
| 4 | AOAI deployment **linked to (3)** | `Microsoft.CognitiveServices/accounts/deployments` (api `2026-03-15-preview`) | `Standard` / capacity `100`, model `gpt-5.4` v `2026-03-05-contextcache`, `contextCacheContainerId` pre-wired |

All four are created in a single ARM deployment, in the same region, in the resource group you pick. No portal click-through, no follow-up CLI.
Expand Down
10 changes: 5 additions & 5 deletions azuredeploy.json
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@
"skuName": "Standard",
"skuCapacity": 100,
"timeToLiveDays": 7,
"containerResourceId": "[resourceId('Microsoft.AzureContextCache/accounts/containers', variables('cacheAccountName'), variables('cacheContainerName'))]",
"containerResourceId": "[resourceId('Microsoft.Storage/contextCaches/contextCacheContainers', variables('cacheAccountName'), variables('cacheContainerName'))]",
"effectivePrincipalId": "[if(empty(parameters('principalId')), deployer().objectId, parameters('principalId'))]",
"assignRole": "[and(variables('createAoai'), not(empty(variables('effectivePrincipalId'))))]",
"openAiUserRoleId": "5e0bd9bd-7b93-4f28-af87-19fc36ad61bd",
Expand Down Expand Up @@ -84,7 +84,7 @@
},
{
"comments": "2. Context Cache account.",
"type": "Microsoft.AzureContextCache/accounts",
"type": "Microsoft.Storage/contextCaches",
"apiVersion": "2026-01-01-preview",
"name": "[variables('cacheAccountName')]",
"location": "[resourceGroup().location]",
Expand All @@ -96,11 +96,11 @@
},
{
"comments": "3. Context Cache container bound to the chosen model.",
"type": "Microsoft.AzureContextCache/accounts/containers",
"type": "Microsoft.Storage/contextCaches/contextCacheContainers",
"apiVersion": "2026-01-01-preview",
"name": "[concat(variables('cacheAccountName'), '/', variables('cacheContainerName'))]",
"dependsOn": [
"[resourceId('Microsoft.AzureContextCache/accounts', variables('cacheAccountName'))]"
"[resourceId('Microsoft.Storage/contextCaches', variables('cacheAccountName'))]"
],
"properties": {
"description": "[concat('Prompt cache container for ', variables('modelName'))]",
Expand All @@ -116,7 +116,7 @@
"name": "[concat(variables('aoaiAccountName'), '/', variables('aoaiDeploymentName'))]",
"dependsOn": [
"[resourceId('Microsoft.CognitiveServices/accounts', variables('aoaiAccountName'))]",
"[resourceId('Microsoft.AzureContextCache/accounts/containers', variables('cacheAccountName'), variables('cacheContainerName'))]"
"[resourceId('Microsoft.Storage/contextCaches/contextCacheContainers', variables('cacheAccountName'), variables('cacheContainerName'))]"
],
"sku": {
"name": "[variables('skuName')]",
Expand Down
4 changes: 2 additions & 2 deletions bicep/main.bicep
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ resource aoai 'Microsoft.CognitiveServices/accounts@2024-10-01' existing = {
name: aoaiAccountName
}

resource cacheAccount 'Microsoft.AzureContextCache/accounts@2026-01-01-preview' = {
resource cacheAccount 'Microsoft.Storage/contextCaches@2026-01-01-preview' = {
name: cacheAccountName
location: location
tags: tags
Expand All @@ -55,7 +55,7 @@ resource cacheAccount 'Microsoft.AzureContextCache/accounts@2026-01-01-preview'
}
}

resource cacheContainer 'Microsoft.AzureContextCache/accounts/containers@2026-01-01-preview' = {
resource cacheContainer 'Microsoft.Storage/contextCaches/contextCacheContainers@2026-01-01-preview' = {
parent: cacheAccount
name: cacheContainerName
properties: {
Expand Down
4 changes: 2 additions & 2 deletions scripts/cleanup.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -105,8 +105,8 @@ if (-not $PSCmdlet.ShouldProcess("$ResourceGroup/$CacheAccountName + $AoaiAccoun
return
}

$cacheContainerId = "/subscriptions/$SubscriptionId/resourceGroups/$ResourceGroup/providers/Microsoft.AzureContextCache/accounts/$CacheAccountName/containers/$CacheContainerName"
$cacheAccountId = "/subscriptions/$SubscriptionId/resourceGroups/$ResourceGroup/providers/Microsoft.AzureContextCache/accounts/$CacheAccountName"
$cacheContainerId = "/subscriptions/$SubscriptionId/resourceGroups/$ResourceGroup/providers/Microsoft.Storage/contextCaches/$CacheAccountName/contextCacheContainers/$CacheContainerName"
$cacheAccountId = "/subscriptions/$SubscriptionId/resourceGroups/$ResourceGroup/providers/Microsoft.Storage/contextCaches/$CacheAccountName"
$aoaiDeploymentId = "/subscriptions/$SubscriptionId/resourceGroups/$ResourceGroup/providers/Microsoft.CognitiveServices/accounts/$AoaiAccountName/deployments/$AoaiDeploymentName"
$aoaiAccountId = "/subscriptions/$SubscriptionId/resourceGroups/$ResourceGroup/providers/Microsoft.CognitiveServices/accounts/$AoaiAccountName"

Expand Down
7 changes: 3 additions & 4 deletions scripts/quickstart.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@
.DESCRIPTION
Single-script equivalent of the "Deploy to Azure" portal flow. Walks through:
1. Login / subscription selection.
2. Resource provider + preview-feature registration (Microsoft.AzureContextCache,
Microsoft.AzureContextCache/EnablePreview, Microsoft.CognitiveServices/OpenAI.ContextCacheAllowed).
2. Resource provider + preview-feature registration (Microsoft.Storage,
Microsoft.CognitiveServices/OpenAI.ContextCacheAllowed).
Auto-registers anything not yet 'Registered' and waits for it.
3. Resource group create (if missing).
4. ARM template deploy (azure-context-cache-quickstart/azuredeploy.json) - auto-grants
Expand Down Expand Up @@ -167,9 +167,8 @@ if ($NamePrefix -and ($NamePrefix -notmatch '^[a-z0-9]{3,12}$')) {
Write-Step "Validating RP + preview-feature registration"

$checks = @(
@{ Kind='provider'; Namespace='Microsoft.AzureContextCache'; Name=$null }
@{ Kind='provider'; Namespace='Microsoft.Storage'; Name=$null }
@{ Kind='provider'; Namespace='Microsoft.CognitiveServices'; Name=$null }
@{ Kind='feature'; Namespace='Microsoft.AzureContextCache'; Name='EnablePreview' }
@{ Kind='feature'; Namespace='Microsoft.CognitiveServices'; Name='OpenAI.ContextCacheAllowed' }
)

Expand Down
20 changes: 6 additions & 14 deletions scripts/register-providers.ps1
Original file line number Diff line number Diff line change
@@ -1,12 +1,10 @@
#requires -Version 7.0
<#
.SYNOPSIS
Registers the Microsoft.AzureContextCache resource provider and the EnablePreview feature flag.
Registers the Microsoft.Storage resource provider.

.DESCRIPTION
Run this once per subscription before deploying any azure-context-cache-quickstart template.
The EnablePreview feature is gated. After registering, email azurecontextcacherp@microsoft.com
to request approval if your subscription is not yet allow-listed.

.PARAMETER SubscriptionId
Target Azure subscription ID. Optional; the currently selected az subscription is used if omitted.
Expand All @@ -26,11 +24,8 @@ if ($SubscriptionId) {
az account set --subscription $SubscriptionId | Out-Null
}

Write-Host "Registering resource provider Microsoft.AzureContextCache..." -ForegroundColor Cyan
az provider register --namespace Microsoft.AzureContextCache | Out-Null

Write-Host "Registering preview feature Microsoft.AzureContextCache/EnablePreview..." -ForegroundColor Cyan
az feature register --namespace Microsoft.AzureContextCache --name EnablePreview | Out-Null
Write-Host "Registering resource provider Microsoft.Storage..." -ForegroundColor Cyan
az provider register --namespace Microsoft.Storage | Out-Null

Write-Host "Registering preview feature Microsoft.CognitiveServices/OpenAI.ContextCacheAllowed..." -ForegroundColor Cyan
az feature register --namespace Microsoft.CognitiveServices --name OpenAI.ContextCacheAllowed | Out-Null
Expand All @@ -40,22 +35,19 @@ az provider register --namespace Microsoft.CognitiveServices | Out-Null

Write-Host ""
Write-Host "Current registration status:" -ForegroundColor Yellow
$providerState = az provider show --namespace Microsoft.AzureContextCache --query registrationState -o tsv
$featureState = az feature show --namespace Microsoft.AzureContextCache --name EnablePreview --query properties.state -o tsv
$providerState = az provider show --namespace Microsoft.Storage --query registrationState -o tsv
$aoaiFeatState = az feature show --namespace Microsoft.CognitiveServices --name OpenAI.ContextCacheAllowed --query properties.state -o tsv
$csProviderState = az provider show --namespace Microsoft.CognitiveServices --query registrationState -o tsv

Write-Host (" Provider Microsoft.AzureContextCache : {0}" -f $providerState)
Write-Host (" Feature EnablePreview : {0}" -f $featureState)
Write-Host (" Provider Microsoft.Storage : {0}" -f $providerState)
Write-Host (" Provider Microsoft.CognitiveServices : {0}" -f $csProviderState)
Write-Host (" Feature OpenAI.ContextCacheAllowed : {0}" -f $aoaiFeatState)

$allGood = ($providerState -eq 'Registered') -and ($featureState -eq 'Registered') -and ($csProviderState -eq 'Registered') -and ($aoaiFeatState -eq 'Registered')
$allGood = ($providerState -eq 'Registered') -and ($csProviderState -eq 'Registered') -and ($aoaiFeatState -eq 'Registered')

if (-not $allGood) {
Write-Host ""
Write-Host "Registration is asynchronous. Re-run this script in a few minutes if any state is still 'Registering'." -ForegroundColor Yellow
Write-Host "If a gated feature stays 'Pending', email azurecontextcacherp@microsoft.com for approval." -ForegroundColor Yellow
}
else {
Write-Host ""
Expand Down
Loading