> ## Documentation Index
> Fetch the complete documentation index at: https://docs.casebender.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Deploy to Azure

> Deploy CaseBender on Microsoft Azure

<Warning>
  Reference architecture only. This page is not a production-certified deployment
  procedure and predates the current activation, image-pinning, secret-management,
  and network-isolation baseline. Use the [supported on-premises guide](/en/quickstart)
  or complete an enterprise architecture review before deployment.
</Warning>

## Overview

This guide walks you through deploying CaseBender on Azure using pre-built Docker images with Azure Container Apps and managed services.

## Prerequisites

1. [Azure Account](https://azure.microsoft.com/)
2. [Azure CLI](https://docs.microsoft.com/en-us/cli/azure/install-azure-cli) installed
3. [Docker](https://docs.docker.com/get-docker/) installed

## Step 1: Initial Setup

### Install and Configure Azure CLI

<CodeGroup>
  ```bash macOS theme={null}
  # Using Homebrew
  brew install azure-cli

  # Login to Azure

  az login

  # Configure Docker for ACR

  az acr login --name casebenderacr

  ```

  ```bash Linux theme={null}
  # Install Azure CLI
  curl -sL https://aka.ms/InstallAzureCLIDeb | sudo bash

  # Login to Azure
  az login

  # Configure Docker for ACR
  az acr login --name casebenderacr
  ```

  ```powershell Windows theme={null}
  # Using winget
  winget install -e --id Microsoft.AzureCLI

  # Login to Azure
  az login

  # Configure Docker for ACR
  az acr login --name casebenderacr
  ```
</CodeGroup>

### Initialize Project

```bash theme={null}
# Set variables
RESOURCE_GROUP="casebender-rg"
LOCATION="eastus"

# Create resource group
az group create --name $RESOURCE_GROUP --location $LOCATION

# Enable required services
az provider register --namespace Microsoft.ContainerRegistry
az provider register --namespace Microsoft.App
az provider register --namespace Microsoft.Storage
```

## Step 2: Set Up Azure Infrastructure

### Create Storage Account

```bash theme={null}
# Create storage account
az storage account create \
  --name casebenderstorage \
  --resource-group $RESOURCE_GROUP \
  --location $LOCATION \
  --sku Standard_LRS \
  --encryption-services blob

# Create blob container
az storage container create \
  --name casebender \
  --account-name casebenderstorage \
  --auth-mode key \
  --public-access off

# Get storage account key
STORAGE_KEY=$(az storage account keys list \
  --account-name casebenderstorage \
  --resource-group $RESOURCE_GROUP \
  --query '[0].value' -o tsv)

# Create managed identity for storage access
az identity create \
  --name casebender-storage-identity \
  --resource-group $RESOURCE_GROUP

# Get managed identity ID
IDENTITY_ID=$(az identity show \
  --name casebender-storage-identity \
  --resource-group $RESOURCE_GROUP \
  --query id -o tsv)

# Assign Storage Blob Data Contributor role
az role assignment create \
  --assignee-object-id $(az identity show --name casebender-storage-identity --resource-group $RESOURCE_GROUP --query principalId -o tsv) \
  --role "Storage Blob Data Contributor" \
  --scope $(az storage account show --name casebenderstorage --resource-group $RESOURCE_GROUP --query id -o tsv)
```

### Set Up Azure Database for PostgreSQL

```bash theme={null}
# Create PostgreSQL server
az postgres flexible-server create \
  --resource-group $RESOURCE_GROUP \
  --name casebender-db \
  --admin-user superadmin \
  --admin-password <your-secure-password> \
  --sku-name Standard_B2s \
  --storage-size 32 \
  --version 14

# Create database
az postgres flexible-server db create \
  --resource-group $RESOURCE_GROUP \
  --server-name casebender-db \
  --database-name casebender
```

### Set Up Azure Cache for Redis

```bash theme={null}
# Create Redis cache
az redis create \
  --resource-group $RESOURCE_GROUP \
  --name casebender-redis \
  --sku Basic \
  --vm-size c0 \
  --location $LOCATION
```

## Step 3: Create and Configure Container Registry

```bash theme={null}
# Create Azure Container Registry
az acr create \
  --resource-group $RESOURCE_GROUP \
  --name casebenderacr \
  --sku Standard \
  --admin-enabled true

# Get registry credentials
ACR_USERNAME=$(az acr credential show --name casebenderacr --query username -o tsv)
ACR_PASSWORD=$(az acr credential show --name casebenderacr --query "passwords[0].value" -o tsv)

# Pull CaseBender images
docker pull casebender/casebender:latest
docker pull casebender/workflow-processor:latest
docker pull casebender/misp-processor:latest

# Tag images for ACR
docker tag casebender/casebender:latest casebenderacr.azurecr.io/casebender/app:latest
docker tag casebender/workflow-processor:latest casebenderacr.azurecr.io/casebender/workflow-processor:latest
docker tag casebender/misp-processor:latest casebenderacr.azurecr.io/casebender/misp-processor:latest

# Push images to ACR
docker push casebenderacr.azurecr.io/casebender/app:latest
docker push casebenderacr.azurecr.io/casebender/workflow-processor:latest
docker push casebenderacr.azurecr.io/casebender/misp-processor:latest
```

## Step 4: Deploy Services

### Create Container Apps Environment

```bash theme={null}
# Create Container Apps environment
az containerapp env create \
  --name casebender-env \
  --resource-group $RESOURCE_GROUP \
  --location $LOCATION

# Create main application
az containerapp create \
  --name casebender-app \
  --resource-group $RESOURCE_GROUP \
  --environment casebender-env \
  --image casebenderacr.azurecr.io/casebender/app:latest \
  --target-port 3000 \
  --ingress external \
  --registry-server casebenderacr.azurecr.io \
  --registry-username $ACR_USERNAME \
  --registry-password $ACR_PASSWORD \
  --user-assigned-identity $IDENTITY_ID \
  --env-vars \
    AUTH_SECRET=<your-auth-secret> \
    AUTH_SALT=<your-auth-salt> \
    POSTGRES_PRISMA_URL="postgresql://superadmin:<password>@casebender-db.postgres.database.azure.com:5432/casebender" \
    REDIS_URL="redis://casebender-redis.redis.cache.windows.net:6380?ssl=true&password=<redis-key>" \
    AZURE_STORAGE_ACCOUNT="casebenderstorage" \
    AZURE_STORAGE_CONTAINER="casebender" \
    AZURE_STORAGE_CONNECTION_STRING="DefaultEndpointsProtocol=https;AccountName=casebenderstorage;AccountKey=${STORAGE_KEY};EndpointSuffix=core.windows.net"

# Create workflow processor
az containerapp create \
  --name workflow-processor \
  --resource-group $RESOURCE_GROUP \
  --environment casebender-env \
  --image casebenderacr.azurecr.io/casebender/workflow-processor:latest \
  --registry-server casebenderacr.azurecr.io \
  --registry-username $ACR_USERNAME \
  --registry-password $ACR_PASSWORD \
  --min-replicas 1 \
  --max-replicas 1 \
  --env-vars \
    POSTGRES_PRISMA_URL="postgresql://superadmin:<password>@casebender-db.postgres.database.azure.com:5432/casebender" \
    REDIS_URL="redis://casebender-redis.redis.cache.windows.net:6380?ssl=true&password=<redis-key>"

# Create MISP processor
az containerapp create \
  --name misp-processor \
  --resource-group $RESOURCE_GROUP \
  --environment casebender-env \
  --image casebenderacr.azurecr.io/casebender/misp-processor:latest \
  --registry-server casebenderacr.azurecr.io \
  --registry-username $ACR_USERNAME \
  --registry-password $ACR_PASSWORD \
  --min-replicas 1 \
  --max-replicas 1 \
  --env-vars \
    POSTGRES_PRISMA_URL="postgresql://superadmin:<password>@casebender-db.postgres.database.azure.com:5432/casebender" \
    REDIS_URL="redis://casebender-redis.redis.cache.windows.net:6380?ssl=true&password=<redis-key>"
```

## Step 5: Set Up Azure Front Door

```bash theme={null}
# Create Front Door profile
az afd profile create \
  --profile-name casebender-afd \
  --resource-group $RESOURCE_GROUP \
  --sku Standard_AzureFrontDoor

# Create endpoint
az afd endpoint create \
  --endpoint-name casebender \
  --profile-name casebender-afd \
  --resource-group $RESOURCE_GROUP

# Create origin group
az afd origin-group create \
  --origin-group-name casebender-origin-group \
  --profile-name casebender-afd \
  --resource-group $RESOURCE_GROUP \
  --probe-path "/" \
  --probe-protocol Http \
  --probe-request-type GET

# Add origin
az afd origin create \
  --origin-group-name casebender-origin-group \
  --origin-name casebender-origin \
  --profile-name casebender-afd \
  --resource-group $RESOURCE_GROUP \
  --host-name <your-container-app-url> \
  --origin-host-header <your-container-app-url> \
  --priority 1 \
  --weight 1000 \
  --enabled-state Enabled
```

## Step 6: Configure Custom Domain (Optional)

```bash theme={null}
# Add custom domain to Front Door
az afd custom-domain create \
  --custom-domain-name casebender-domain \
  --host-name your-domain.com \
  --profile-name casebender-afd \
  --resource-group $RESOURCE_GROUP \
  --minimum-tls-version TLS12

# Enable HTTPS
az afd custom-domain enable-https \
  --custom-domain-name casebender-domain \
  --profile-name casebender-afd \
  --resource-group $RESOURCE_GROUP
```

## Monitoring and Maintenance

### Set Up Application Insights

```bash theme={null}
# Create Application Insights
az monitor app-insights component create \
  --app casebender-insights \
  --location $LOCATION \
  --resource-group $RESOURCE_GROUP \
  --application-type web

# Get instrumentation key
az monitor app-insights component show \
  --app casebender-insights \
  --resource-group $RESOURCE_GROUP \
  --query instrumentationKey \
  --output tsv
```

### Configure Alerts

```bash theme={null}
# Create action group
az monitor action-group create \
  --name casebender-alerts \
  --resource-group $RESOURCE_GROUP \
  --action email admin email@yourdomain.com

# Create alert rule
az monitor metrics alert create \
  --name "high-cpu-usage" \
  --resource-group $RESOURCE_GROUP \
  --scopes <container-app-resource-id> \
  --condition "avg CPU > 80" \
  --window-size 5m \
  --evaluation-frequency 1m \
  --action <action-group-id>
```

### View Logs

```bash theme={null}
# View container app logs
az containerapp logs show \
  --name casebender-app \
  --resource-group $RESOURCE_GROUP \
  --follow
```

## Scaling Configuration

```bash theme={null}
# Configure scaling rules
az containerapp update \
  --name casebender-app \
  --resource-group $RESOURCE_GROUP \
  --min-replicas 1 \
  --max-replicas 10 \
  --scale-rule-name http-rule \
  --scale-rule-type http \
  --scale-rule-http-concurrency 50
```

## Backup and Disaster Recovery

### Configure Database Backups

```bash theme={null}
# Enable automated backups
az postgres flexible-server update \
  --resource-group $RESOURCE_GROUP \
  --name casebender-db \
  --backup-retention 7
```

### Configure Geo-Replication

```bash theme={null}
# Create secondary region resources
az postgres flexible-server replica create \
  --name casebender-db-secondary \
  --source-server casebender-db \
  --resource-group $RESOURCE_GROUP \
  --location westus
```

## Security Best Practices

1. Enable Azure Defender for all services
2. Implement Azure Private Link
3. Use Managed Identities
4. Regular security assessments
5. Enable diagnostic logging

## Cost Optimization

1. Use consumption plan for Container Apps
2. Implement auto-scaling rules
3. Choose appropriate service tiers
4. Monitor usage patterns
5. Use Azure Reserved Instances

## Next Steps

* Set up CI/CD with Azure DevOps
* Implement comprehensive monitoring
* Configure disaster recovery
* Review security compliance
