Skip to content

Bump validator from 13.12.0 to 13.15.20 in /archive/nodeapp-1 #9

Bump validator from 13.12.0 to 13.15.20 in /archive/nodeapp-1

Bump validator from 13.12.0 to 13.15.20 in /archive/nodeapp-1 #9

name: Node.js CI/CD to Azure
# Teaching example for GitHub Actions with Azure deployment
on:
push:
branches: [ main, master ]
paths:
- 'nodeapp-1/**'
- '.github/workflows/node-azure-deploy.yml'
pull_request:
branches: [ main, master ]
workflow_dispatch:
inputs:
environment:
description: 'Environment to deploy to'
required: true
default: 'development'
type: choice
options:
- development
- staging
- production
env:
NODE_VERSION: '18.x'
AZURE_WEBAPP_NAME: 'webapp-az400-demo'
AZURE_WEBAPP_PACKAGE_PATH: './nodeapp-1'
WORKING_DIRECTORY: 'nodeapp-1'
jobs:
# ========================================
# JOB 1: BUILD AND TEST
# ========================================
build:
name: Build and Test
runs-on: ubuntu-latest
steps:
- name: 📥 Checkout code
uses: actions/checkout@v4
- name: 🔧 Setup Node.js ${{ env.NODE_VERSION }}
uses: actions/setup-node@v4
with:
node-version: ${{ env.NODE_VERSION }}
cache: 'npm'
cache-dependency-path: '${{ env.WORKING_DIRECTORY }}/package-lock.json'
- name: 📦 Install dependencies
run: npm ci
working-directory: ${{ env.WORKING_DIRECTORY }}
- name: 🔒 Security audit
run: npm audit --audit-level=high
working-directory: ${{ env.WORKING_DIRECTORY }}
continue-on-error: true
- name: 🧹 Lint code
run: npm run lint
working-directory: ${{ env.WORKING_DIRECTORY }}
- name: 🧪 Run tests with Mocha
run: npm test
working-directory: ${{ env.WORKING_DIRECTORY }}
- name: 📊 Upload test results
uses: actions/upload-artifact@v4
if: always()
with:
name: mochawesome-report
path: ${{ env.WORKING_DIRECTORY }}/mochawesome-report
retention-days: 7
- name: 📤 Upload artifact for deployment
uses: actions/upload-artifact@v4
with:
name: node-app
path: ${{ env.WORKING_DIRECTORY }}
retention-days: 5
# ========================================
# JOB 2: DEPLOY TO DEVELOPMENT
# ========================================
deploy-dev:
name: Deploy to Development
runs-on: ubuntu-latest
needs: build
if: github.event_name == 'push' && github.ref == 'refs/heads/main'
environment:
name: development
url: ${{ steps.deploy-to-webapp.outputs.webapp-url }}
steps:
- name: 📥 Download artifact
uses: actions/download-artifact@v4
with:
name: node-app
path: ./app
- name: 🔐 Login to Azure
uses: azure/login@v1
with:
creds: ${{ secrets.AZURE_CREDENTIALS }}
- name: 🚀 Deploy to Azure Web App
id: deploy-to-webapp
uses: azure/webapps-deploy@v3
with:
app-name: ${{ env.AZURE_WEBAPP_NAME }}-dev
package: ./app
startup-command: 'npm start'
- name: 🔥 Smoke test
run: |
sleep 30
response=$(curl -s -o /dev/null -w "%{http_code}" https://${{ env.AZURE_WEBAPP_NAME }}-dev.azurewebsites.net)
if [ $response -eq 200 ]; then
echo "✅ Smoke test passed!"
else
echo "❌ Smoke test failed with status code: $response"
exit 1
fi
# ========================================
# JOB 3: DEPLOY TO STAGING
# ========================================
deploy-staging:
name: Deploy to Staging
runs-on: ubuntu-latest
needs: deploy-dev
environment:
name: staging
url: ${{ steps.deploy-to-webapp.outputs.webapp-url }}
steps:
- name: 📥 Checkout for tests
uses: actions/checkout@v4
- name: 📥 Download artifact
uses: actions/download-artifact@v4
with:
name: node-app
path: ./app
- name: 🔐 Login to Azure
uses: azure/login@v1
with:
creds: ${{ secrets.AZURE_CREDENTIALS }}
- name: 🚀 Deploy to staging slot
id: deploy-to-webapp
uses: azure/webapps-deploy@v3
with:
app-name: ${{ env.AZURE_WEBAPP_NAME }}
slot-name: staging
package: ./app
- name: 🧪 Run integration tests
run: |
cd ${{ env.WORKING_DIRECTORY }}
npm ci
export TEST_URL=https://${{ env.AZURE_WEBAPP_NAME }}-staging.azurewebsites.net
npm test
continue-on-error: true
# ========================================
# JOB 4: DEPLOY TO PRODUCTION
# ========================================
deploy-prod:
name: Deploy to Production
runs-on: ubuntu-latest
needs: deploy-staging
environment:
name: production
url: ${{ steps.swap-slots.outputs.webapp-url }}
steps:
- name: 🔐 Login to Azure
uses: azure/login@v1
with:
creds: ${{ secrets.AZURE_CREDENTIALS }}
- name: 🔄 Swap staging to production
id: swap-slots
run: |
az webapp deployment slot swap \
--resource-group rg-az400-demo \
--name ${{ env.AZURE_WEBAPP_NAME }} \
--slot staging \
--target-slot production
echo "webapp-url=https://${{ env.AZURE_WEBAPP_NAME }}.azurewebsites.net" >> $GITHUB_OUTPUT
- name: 🏷️ Create release tag
if: success()
uses: actions/github-script@v7
with:
script: |
const tag = `v${context.runNumber}`;
await github.rest.git.createRef({
owner: context.repo.owner,
repo: context.repo.repo,
ref: `refs/tags/${tag}`,
sha: context.sha
});
console.log(`✅ Created tag: ${tag}`);
# ========================================
# REUSABLE WORKFLOW: SECURITY SCAN
# ========================================
security-scan:
name: Security Scanning
runs-on: ubuntu-latest
if: github.event_name == 'pull_request'
steps:
- name: 📥 Checkout code
uses: actions/checkout@v4
- name: 🔍 Run Dependabot scan
uses: github/super-linter@v5
env:
DEFAULT_BRANCH: main
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
VALIDATE_JAVASCRIPT_ES: true
VALIDATE_JSON: true
VALIDATE_YAML: true