Irminsul / deploy_azure.sh
MukulRay's picture
docs: overhaul README, add DEPLOYMENT.md, deploy_azure.sh, .env.example
3fbe97b
#!/bin/bash
# ─────────────────────────────────────────────────────────────────────────────
# deploy_azure.sh β€” One-shot Azure Container Apps deployment for Irminsul
#
# Prerequisites:
# - Azure CLI installed: https://learn.microsoft.com/en-us/cli/azure/install-azure-cli
# - Logged in: az login
# - Subscription active: az account show
#
# Usage:
# export PINECONE_API_KEY=your_key
# export GROQ_API_KEY=your_key
# chmod +x deploy_azure.sh
# ./deploy_azure.sh
#
# What this script does:
# 1. Creates a resource group in East US
# 2. Creates an Azure Container Registry (ACR)
# 3. Builds the Docker image via ACR Tasks (no local Docker build needed)
# 4. Creates a Container Apps environment
# 5. Deploys the container with secrets injected as env vars
# 6. Prints the live HTTPS URL
#
# Cost note:
# This stack (Groq backend, no GPU) runs on a consumption-plan Container App.
# Estimated cost: ~$0/month on free tier (180,000 vCPU-seconds/month free).
# GPU-accelerated inference (local Llama backend) requires NC-series instances
# (~$0.50-1.50/hr) which is not cost-effective for a portfolio project.
# See DEPLOYMENT.md for the full cost analysis.
# ─────────────────────────────────────────────────────────────────────────────
set -e # exit on any error
# ── Configuration ──────────────────────────────────────────────────────────────
RESOURCE_GROUP="irminsul-rg"
LOCATION="eastus"
ACR_NAME="irminsulacr" # must be globally unique, lowercase alphanumeric
ENVIRONMENT="irminsul-env"
APP_NAME="irminsul"
IMAGE_TAG="latest"
# ── Validate required secrets ──────────────────────────────────────────────────
if [[ -z "$PINECONE_API_KEY" ]]; then
echo "ERROR: PINECONE_API_KEY environment variable is not set."
echo " export PINECONE_API_KEY=your_key"
exit 1
fi
if [[ -z "$GROQ_API_KEY" ]]; then
echo "ERROR: GROQ_API_KEY environment variable is not set."
echo " export GROQ_API_KEY=your_key"
exit 1
fi
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
echo " Irminsul β€” Azure Container Apps Deployment"
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
echo ""
# ── Step 1: Resource Group ─────────────────────────────────────────────────────
echo "[1/5] Creating resource group: $RESOURCE_GROUP"
az group create \
--name "$RESOURCE_GROUP" \
--location "$LOCATION" \
--output none
echo " βœ“ Resource group ready"
# ── Step 2: Azure Container Registry ──────────────────────────────────────────
echo "[2/5] Creating container registry: $ACR_NAME"
az acr create \
--resource-group "$RESOURCE_GROUP" \
--name "$ACR_NAME" \
--sku Basic \
--admin-enabled true \
--output none
echo " βœ“ ACR created"
# ── Step 3: Build image via ACR Tasks (cloud build β€” no local Docker needed) ───
echo "[3/5] Building Docker image via ACR Tasks..."
echo " This uploads your source code to Azure and builds in the cloud."
az acr build \
--registry "$ACR_NAME" \
--image "${APP_NAME}:${IMAGE_TAG}" \
.
echo " βœ“ Image built and pushed: ${ACR_NAME}.azurecr.io/${APP_NAME}:${IMAGE_TAG}"
# ── Step 4: Container Apps Environment ────────────────────────────────────────
echo "[4/5] Creating Container Apps environment: $ENVIRONMENT"
az containerapp env create \
--name "$ENVIRONMENT" \
--resource-group "$RESOURCE_GROUP" \
--location "$LOCATION" \
--output none
echo " βœ“ Environment ready"
# ── Step 5: Deploy Container App ──────────────────────────────────────────────
echo "[5/5] Deploying container app: $APP_NAME"
# Get ACR credentials for pulling the image
ACR_LOGIN_SERVER=$(az acr show --name "$ACR_NAME" --query loginServer --output tsv)
ACR_USERNAME=$(az acr credential show --name "$ACR_NAME" --query username --output tsv)
ACR_PASSWORD=$(az acr credential show --name "$ACR_NAME" --query "passwords[0].value" --output tsv)
az containerapp create \
--name "$APP_NAME" \
--resource-group "$RESOURCE_GROUP" \
--environment "$ENVIRONMENT" \
--image "${ACR_LOGIN_SERVER}/${APP_NAME}:${IMAGE_TAG}" \
--registry-server "$ACR_LOGIN_SERVER" \
--registry-username "$ACR_USERNAME" \
--registry-password "$ACR_PASSWORD" \
--target-port 8000 \
--ingress external \
--min-replicas 0 \
--max-replicas 3 \
--cpu 1.0 \
--memory 2.0Gi \
--env-vars \
PINECONE_API_KEY=secretref:pinecone-key \
GROQ_API_KEY=secretref:groq-key \
PINECONE_INDEX=llmops-rag \
LLM_BACKEND=groq \
EMBED_MODEL=sentence-transformers/all-MiniLM-L6-v2 \
--secrets \
pinecone-key="$PINECONE_API_KEY" \
groq-key="$GROQ_API_KEY" \
--output none
echo " βœ“ Container app deployed"
# ── Print live URL ─────────────────────────────────────────────────────────────
LIVE_URL=$(az containerapp show \
--name "$APP_NAME" \
--resource-group "$RESOURCE_GROUP" \
--query "properties.configuration.ingress.fqdn" \
--output tsv)
echo ""
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
echo " Deployment complete!"
echo ""
echo " Live URL: https://${LIVE_URL}"
echo " Health: https://${LIVE_URL}/health"
echo " API docs: https://${LIVE_URL}/docs"
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
echo ""
echo " To tear down everything and stop billing:"
echo " az group delete --name $RESOURCE_GROUP --yes --no-wait"
echo ""