Integration
Github Integration
GitHub Integration (Source Code Integration)
✅ What it is
Connect Azure DevOps Pipeline to GitHub repo so CI/CD triggers on code push/PR.
✅ Steps
Go to Pipelines → Create Pipeline
Choose GitHub
Sign in → Authorize Azure DevOps
Select your repo
Choose pipeline template or write your own YAML
Set trigger in YAML:
trigger: branches: include: - main
⭐ Why this approach?
GitHub is standard source control.
Azure DevOps can auto-trigger pipelines.
Secure connection via OAuth + PAT.
Best for teams using GitHub + Azure ecosystem.
ACR Integration
“If I create a Docker Registry → ACR service connection using Service Principal, and I put
dockerRegistryServiceConnection: 'service-principle-id'in my pipeline… Is this enough to connect my private ACR to Azure DevOps?”
✅ YES — That is 100% enough.
No extra steps. No extra variables. No extra secrets.
What this does:
Azure DevOps creates a Service Principal (SPN) in Azure AD
It gives it AcrPush permission on your ACR
Azure DevOps stores the clientId + clientSecret securely inside the service connection
Go to project setting > pipeline > service connection > new service connection

click on docker hub/registry > next > select Azure container registry
select authentication method as service principle


i am giving sample example as we create connection we get service principle id and we need to add it in pipeline.yml
dockerRegistryServiceConnection: 'service-principle-id'
What is WIF (Workload Identity Federation)?
WIF replaces:
❌ Service Principal + Client Secret (old method) ❌ Admin user login (very insecure)
With:
✅ Azure DevOps → Azure AD → ACR using an identity token instead of a password.
How WIF Works (Simple Explanation)
1️⃣ Your Azure DevOps pipeline automatically generates a short-lived OIDC token
This token is valid for a few minutes.
2️⃣ Azure AD app (you create it) has a Federated Credential
It says:
“If the token comes from this Azure DevOps pipeline, I trust it.”
3️⃣ Azure AD issues an access token without needing a password
4️⃣ Azure DevOps uses this access token to log in to ACR
No secret is ever stored.
Note: Similar to AWS OIDC connection that make trust relation between like eg github and ACR
here Azure devops - azure AD - ACR
Self-Hosted Agent
Yes — every Azure DevOps organization gets free hosted agents.
🌟 Free Tier
1800 minutes/month (30 hours)
For public projects → Unlimited free minutes
For private projects → Limited minutes as above
agent vm can be selfhosted or microft hosted
vmimagename: ubuntu-latest
own agent
pool:
name: "azureagent"
Setup self-hosted agent
go to project setting > pipeline > agent pool > add agent pool

go to created agent pool under agent add new agent

select os and run command on agent server

create PAT token for agnet to give granular permission
go to user setting > security > personal acces token select scope, permission


paste token and register agent


similar to github runner and run this as backround by adding as a service
install docker on agent server
Key Vault Integration
what we can store in key vault
Snyk Token
SonarQube Token
DockerHub Token
GitHub PAT
Jira API Token
Slack Webhook Token
Datadog / New Relic API Keys
AWS Access Key / Secret Key
GCP Service Account JSON
Azure Storage Account Keys (if absolutely needed)
PostgreSQL username/password
MySQL username/password
MongoDB connection strings
Redis password
Azure AD App Registration Client Secret
OAuth Secrets
JWT Signing Secrets
OAuth Refresh Tokens
TLS/SSL Certificates
Private Keys
SSH Keys (if needed for automation)
Below are the complete, latest (2025) and correct steps to integrate Azure Key Vault with Azure DevOps pipelines, using both methods:
✔ (A) Service Principal method (older but easier)
✔ (B) Workload Identity Federation (WIF) (recommended, secure, secretless)
And I will give you:
Steps in Azure
Steps in Azure DevOps
Pipeline YAML examples
Permissions needed
Verification steps
Everything from scratch.
🚀 OPTION A — Key Vault Integration using Service Principal (SPN)
(Simple + works in all Azure DevOps accounts)
🟦 STEP 1 — Create a Service Principal
Run in Azure CLI:
az ad sp create-for-rbac --name "azuredevops-keyvault" --sdk-authIt returns:
clientId
clientSecret
tenantId
subscriptionIdSave these.
🟦 STEP 2 — Give SPN access to Key Vault (RBAC or Access Policy)
Method 1 — RBAC (Recommended)
az role assignment create \
--role "Key Vault Secrets User" \
--assignee <clientId> \
--scope /subscriptions/<SUB>/resourceGroups/<RG>/providers/Microsoft.KeyVault/vaults/<KV_NAME>Method 2 — Access Policy (older way)
az keyvault set-policy \
--name <KV_NAME> \
--spn <clientId> \
--secret-permissions get list🟦 STEP 3 — Create Azure DevOps Service Connection (SPN based)
Go:
Project Settings → Service Connections → New → Azure Resource Manager → Choose:
Service principal (manual)Enter:
clientId
clientSecret
tenantId
subscriptionId
Name the connection:
keyvault-sp-connection🟦 STEP 4 — Use Key Vault in Pipeline
Example to fetch secrets:
steps:
- task: AzureKeyVault@2
inputs:
azureSubscription: 'keyvault-sp-connection'
KeyVaultName: 'my-key-vault'
SecretsFilter: '*'
RunAsPreJob: trueAzure DevOps automatically:
✔ logs in using the SPN ✔ fetches Key Vault secrets ✔ stores them as pipeline variables
Usage:
- script: echo $(my-secret)🟩 SPN METHOD COMPLETE (Working & Common)
🚀 OPTION B — Key Vault Integration using WIF (Workload Identity Federation)
(Latest, secure, recommended by Microsoft for 2024–2025)
🟦 STEP 1 — Create an Azure AD App Registration
az ad app create --display-name "devops-wif-kv"Store App ID:
APP_ID=$(az ad app list --display-name "devops-wif-kv" --query "[0].appId" -o tsv)🟦 STEP 2 — Add Federated Credential
Replace:
<ORG>(DevOps org name)<PROJECT><REPO>main(branch)
az ad app federated-credential create \
--id $APP_ID \
--issuer "https://vstoken.dev.azure.com/<ORG>/" \
--subject "repo:<ORG>/<PROJECT>/<REPO>:ref:refs/heads/main" \
--audience "api://AzureADTokenExchange" \
--name "devops-kv-wif"This step tells Azure AD:
“Trust OIDC tokens from this Azure DevOps repo & branch.”
🟦 STEP 3 — Give App Access to Key Vault
RBAC (recommended)
az role assignment create \
--role "Key Vault Secrets User" \
--assignee $APP_ID \
--scope /subscriptions/<SUB>/resourceGroups/<RG>/providers/Microsoft.KeyVault/vaults/<KV_NAME>🟦 STEP 4 — Create Azure DevOps Service Connection (OIDC/WIF)
Go:
Azure DevOps → Project Settings → Service Connections → Azure Resource Manager → Workload Identity Federation
Select:
Subscription
App Registration (
devops-wif-kv)Complete setup
Name the connection:
keyvault-wif-connection🟦 STEP 5 — Use WIF to access Key Vault in pipeline
steps:
- task: AzureKeyVault@2
inputs:
azureSubscription: 'keyvault-wif-connection'
KeyVaultName: 'my-key-vault'
SecretsFilter: '*'
RunAsPreJob: true✔ No secrets stored ✔ No SPN password ✔ Azure DevOps authenticates using OIDC ✔ Azure AD validates ✔ Secrets retrieved securely
🟩 WIF METHOD COMPLETE
🟦 What Secrets Look Like in Pipeline?
Before task:
##[debug] Secret 'my-secret' was found in Key VaultUse it:
- script: echo $(my-secret)🟦 Which Method Should You Use? Summary
SPN (client secret)
Classic method, simplest
🔶 Medium
❌ Old method
SPN (certificate)
Enterprises
🟡 Good
❌ Old
WIF (OIDC)
Modern CI/CD (Azure DevOps 2024+)
🟢 Very High
✔ Best Method
🟦 COMPLETE PIPELINE EXAMPLE (WIF + Key Vault)
pool:
vmImage: ubuntu-latest
steps:
- task: AzureKeyVault@2
inputs:
azureSubscription: 'keyvault-wif-connection'
KeyVaultName: 'my-key-vault'
SecretsFilter: '*'
RunAsPreJob: true
- script: |
echo "Secret from Key Vault: $(database-password)"
echo "Secret from Key Vault: $(api-key)"🟦 Verify WIF is working
Run pipeline → should see:
✔ Connected with Workload Identity Federation ✔ Key Vault secrets fetched ✔ No passwords stored anywhere
🎯 If you want, I can also give:
Key Vault Integration with Terraform + WIF
Key Vault Integration with AKS (CSI Driver)
Key Vault Integration with .NET / Node / Python apps
Key Vault with ARM / Bicep pipelines
Just tell me “Give Key Vault + Terraform WIF example” or anything else.
Scanning Tool - Snyk
CVE = Common Vulnerabilities and Exposures
CVE is a public list of known security vulnerabilities in software, libraries, operating systems, and hardware.
Each vulnerability gets a unique CVE ID, which makes it easy for security teams worldwide to track and fix issues.
CVE-2021-44228
This is the famous Log4j / Log4Shell vulnerability.
2021 → year discovered
44228 → unique identifier9.0 – 10
Critical
7.0 – 8.9
High
4.0 – 6.9
Medium
0.1 – 3.9
Low
0.0
Informational

CVE-285
A specific vulnerability ID.
CVSS 9.3
Severity score, out of 10.
FIX: snyk suggests the exact version upgrade:
✔ Upgrade [email protected] → fixes 1 issue ✔ Upgrade [email protected] → fixes 1 issue (major)
Snyk Code (SAST) → Static Application Security Testing
Tools used (SonarQube, Snyk, OWASP ZAP)
SAST analyzes the source code, bytecode, or binaries without executing them to find security vulnerabilities early in development.
Catch security issues before runtime
Identify code-level flaws (SQL injection, XSS, insecure config)
DAST (Dynamic Application Security Testing)
DAST tests a running application from the outside, simulating real attacks to find runtime vulnerabilities.
Identify issues visible only when the app is running
Test API/website like an attacker would
Catch runtime problems (auth bypass, insecure headers, exposed APIs)
Snyk Open Source (SCA) → dependency vulnerability & license scan
Scans your dependencies (packages/libraries) for vulnerabilities & license issues
Looks at your package.json, requirements.txt, pom.xml, go.mod, etc.
Detects vulnerabilities in the open-source packages you use.
Flags license risks (GPL, AGPL, etc.) used in enterprises.
Snyk Container Scan → scan your Docker image after build
Scans your Docker image after it is built
Scans the entire container image, including:
Base image (Ubuntu, Alpine, Node, Python)
System libraries
OS packages (apk, apt, yum)
Application binaries inside the image
Your Docker image may contain:
Vulnerable OS packages
Old base images
Misconfigurations
High-risk binaries
Even if your app code is safe, your container might be exploitable.
trigger:
- main
pool:
vmImage: 'ubuntu-latest'
variables:
imageName: 'myapp'
tag: '$(Build.BuildId)'
steps:
# 1. Pull secrets from Key Vault
- task: AzureKeyVault@2
inputs:
azureSubscription: 'my-azure-service-connection'
KeyVaultName: 'my-keyvault'
SecretsFilter: 'snyk-token'
RunAsPreJob: true
# 2. Install Snyk CLI
- script: |
echo "Installing Snyk CLI..."
curl -sL https://static.snyk.io/cli/latest/snyk-linux -o snyk
chmod +x snyk
mv snyk /usr/local/bin/
displayName: 'Install Snyk CLI'
# 3. Authenticate Snyk
- script: |
snyk auth $(snyk-token)
displayName: 'Authenticate Snyk'
# 4. SAST scan (Snyk Code)
- script: |
snyk code test --severity-threshold=low
displayName: 'Snyk Code (SAST)'
# 5. SCA scan - dependencies
- script: |
snyk test --all-projects --severity-threshold=low
displayName: 'Snyk Open Source (SCA)'
# 6. Build Docker Image
- task: Docker@2
inputs:
repository: 'acrname.azurecr.io/$(imageName)'
command: 'build'
Dockerfile: '**/Dockerfile'
tags: '$(tag)'
displayName: 'Build Docker Image'
# 7. Scan Docker Image with Snyk Container
- script: |
snyk container test acrname.azurecr.io/$(imageName):$(tag) \
--severity-threshold=low
displayName: 'Snyk Container Scan'
# 8. Push Image to ACR
- task: Docker@2
inputs:
containerRegistry: 'acr-service-connection'
repository: 'acrname.azurecr.io/$(imageName)'
command: 'push'
tags: '$(tag)'
displayName: 'Push Docker Image'
Let’s break everything simply, clearly, and exactly as shown in your screenshot.
Your Snyk dashboard currently shows 3 types of scans:
package.json → SCA (Software Composition Analysis)
Code analysis → SAST (Static Application Security Testing)
Dockerfile → Container Security Scan (Container Vulnerability Scan)
Below is the meaning of each + how to integrate all of them in Azure DevOps + how to use Azure Key Vault for secrets.
✅ 1. What Each Snyk Scan Type Means
A. SAST → Static Application Security Testing
This checks your source code for vulnerabilities:
✔ Insecure coding patterns ✔ SQL injection ✔ Hardcoded secrets ✔ Bad authentication logic ✔ Unsafe APIs
In your screenshot → This is shown as “Code analysis”
B. SCA → Software Composition Analysis
This scans your dependencies: Example:
package.json (npm)
requirements.txt (Python)
pom.xml (Java)
It checks:
✔ CVE vulnerabilities ✔ License issues ✔ Deprecated packages ✔ Fix available updates
In your screenshot → package.json is SCA.
C. Container Security Scan
This scans:
✔ Your Dockerfile ✔ Your final built image (base image + OS packages)
It detects:
CVEs in Ubuntu/Alpine/Node base images
OS vulnerabilities
Misconfigurations
Insecure Dockerfile instructions
In your screenshot → Dockerfile is the container security scan.
🧩 Summary Table
SAST
Scan source code for insecure patterns
Code analysis
SCA
Scan dependencies inside package.json
package.json
Container Scan
Scan Dockerfile & built images
Dockerfile
🔥 How to Run All 3 Scans in Azure DevOps Pipeline
You need:
Snyk token stored in Azure Key Vault
Azure DevOps pipeline with 3 snyk commands:
snyk test→ SASTsnyk test --file=package.json→ SCAsnyk container test→ container image scan
🔐 2. Storing Snyk Token in Azure Key Vault
Step 1 — Add secret in Key Vault
Name it:
SNYK_TOKENValue → Your Snyk token.
Step 2 — Give Azure DevOps access
Add managed identity or service principal of DevOps to Key Vault.
Permission needed:
GetList
🚀 3. Azure DevOps YAML Pipeline for All Snyk Scans
Here is the complete working CI pipeline:
trigger:
- main
pool:
vmImage: 'ubuntu-latest'
variables:
SNYK_TOKEN: $(snyk-token) # Fetched from Key Vault
steps:
# 1️⃣ Azure Key Vault
- task: AzureKeyVault@2
inputs:
azureSubscription: 'My-Service-Connection'
KeyVaultName: 'my-keyvault'
SecretsFilter: 'SNYK_TOKEN'
RunAsPreJob: true
# 2️⃣ Install Snyk CLI
- script: |
npm install -g snyk
displayName: 'Install Snyk CLI'
# 3️⃣ Authenticate Snyk
- script: |
snyk auth $(SNYK_TOKEN)
displayName: 'Authenticate Snyk'
# 4️⃣ Run SCA (dependencies)
- script: |
snyk test --file=package.json --severity-threshold=medium
displayName: 'SCA Scan - package.json'
# 5️⃣ Run SAST (source code)
- script: |
snyk code test
displayName: 'SAST Scan - Static Code'
# 6️⃣ Run Container Scan
- script: |
docker build -t myapp:latest .
snyk container test myapp:latest
displayName: 'Container Scan'💡 This Pipeline Scans Everything:
SAST
snyk code test
SCA
snyk test --file=package.json
Container
snyk container test myapp:latest
🏢 How Enterprises Use This (Real DevSecOps Flow)
PR Pipeline
SAST + SCA
Fail PR if critical vulnerabilities
CI Pipeline
Build image
Container scan
SCA scan
CD Pipeline
Deploy only if no critical vulnerabilities
Integrate with Azure Policy or GATE
Key Vault
All tokens (Snyk, SonarQube, DockerHub, ACR) stored here.
If you want next:
I can give you:
✅ A complete DevSecOps CI/CD pipeline ✅ How to add Snyk PR comments in Azure Repos ✅ Best practice folder structure Just tell me!
Notification - MS Teams
Here is the full, correct, up-to-date guide for connecting Azure DevOps → Microsoft Teams for notifications (Build, Release, PR, Work Items, Alerts, etc.)
✅ How to Connect Azure DevOps with Microsoft Teams for Notifications
There are two official methods:
METHOD 1 — Azure DevOps App (Recommended)
(MOST COMMON, supports PR, Work items, Pipeline events)
Steps
1. Install Azure DevOps App in Teams
Open Microsoft Teams
Go to Apps
Search → Azure DevOps
Click Add
2. Configure Team / Channel
Open your Team → Channel
Click … (More options)
Choose Connectors
Search for Azure DevOps
Click Configure
3. Connect your Azure DevOps Org
You will be prompted for:
Azure DevOps Organization
Azure DevOps Project
The event type (Build, PR, Workitem, Release, etc.)
4. Select Notifications to Receive
You can subscribe to:
Build completed
When pipelines finish
Release deployed
CD release events
Pull request created/updated/merged
PR changes
Work item created/updated
Tasks, bugs
Code pushed to repo
Git push
Pipeline failed
Fail events
5. Save – Done!
Teams will now show automated DevOps messages.
METHOD 2 — Service Hooks (Webhooks)
Used when you want custom JSON payloads.
Steps:
Go to Azure DevOps → Project Settings
Select Service Hooks
Click Create subscription
Choose Microsoft Teams
Select repository/pipeline/work item
Paste the Teams Incoming Webhook URL
Finish setup
🔥 What You Can Automate with DevOps → Teams
Pipeline Notifications
Build success/failure
Release deployment
Stage approvals
Repository Notifications
New PR
PR merge
New commit
Branch creation
Work Item Notifications
Bug created
Task assigned
Work item updated
🔄 Comparison: Which Method Should You Use?
Azure DevOps Teams App (Connector)
Normal notifications
Easy setup, official
Limited customization
Service Hooks (Webhook)
Custom alerts
JSON payloads, flexible
More setup
Power Automate
Complex workflows
Push to Teams + other apps
Requires Flow
🧪 Example Notification in Teams
A real message you get after setup:
⚡ BONUS: Enable Approvals in Teams for Azure DevOps
You can send approval requests (YAML environments) directly to Teams.
Steps:
Go to Environment → Approvals & Checks
Add Microsoft Teams Approval
Select the Team & Channel
Now Team members can click Approve / Reject directly in Teams.
🎯 Summary
Pipeline notifications
✅
PR notifications
✅
Work item notifications
✅
Code push
✅
Deployment approvals
✅
Custom JSON alerts
via Service Hooks
If you want, I can also provide:
✅ Step-by-step screenshots ✅ YAML examples for sending pipeline status to Teams ✅ Best practice setup for DevOps notifications
Would you like that?
Last updated