name: Backend CI/CD Pipeline on: # push: # branches: # - develop # - main # paths: # - '*-service/**' # - '.github/workflows/backend-cicd.yaml' # - '.github/kustomize/**' # pull_request: # branches: # - develop # - main # paths: # - '*-service/**' workflow_dispatch: inputs: environment: description: 'Target environment' required: true type: choice options: - dev - staging - prod service: description: 'Service to deploy (all for all services)' required: true default: 'all' env: ACR_NAME: acrdigitalgarage01 RESOURCE_GROUP: rg-digitalgarage-01 AKS_CLUSTER: aks-digitalgarage-01 NAMESPACE: kt-event-marketing JDK_VERSION: '21' jobs: detect-changes: name: Detect Changed Services runs-on: ubuntu-latest outputs: services: ${{ steps.detect.outputs.services }} environment: ${{ steps.env.outputs.environment }} steps: - name: Checkout code uses: actions/checkout@v4 with: fetch-depth: 0 - name: Determine environment id: env run: | if [ "${{ github.event_name }}" = "workflow_dispatch" ]; then echo "environment=${{ github.event.inputs.environment }}" >> $GITHUB_OUTPUT elif [ "${{ github.ref }}" = "refs/heads/main" ]; then echo "environment=prod" >> $GITHUB_OUTPUT elif [ "${{ github.ref }}" = "refs/heads/develop" ]; then echo "environment=dev" >> $GITHUB_OUTPUT else echo "environment=dev" >> $GITHUB_OUTPUT fi - name: Detect changed services id: detect run: | if [ "${{ github.event_name }}" = "workflow_dispatch" ] && [ "${{ github.event.inputs.service }}" != "all" ]; then echo "services=[\"${{ github.event.inputs.service }}\"]" >> $GITHUB_OUTPUT elif [ "${{ github.event_name }}" = "workflow_dispatch" ] && [ "${{ github.event.inputs.service }}" = "all" ]; then echo "services=[\"user-service\",\"event-service\",\"ai-service\",\"content-service\",\"distribution-service\",\"participation-service\",\"analytics-service\"]" >> $GITHUB_OUTPUT else CHANGED_SERVICES=$(git diff --name-only ${{ github.event.before }} ${{ github.sha }} | \ grep -E '^(user|event|ai|content|distribution|participation|analytics)-service/' | \ cut -d'/' -f1 | sort -u | \ jq -R -s -c 'split("\n") | map(select(length > 0))') if [ "$CHANGED_SERVICES" = "[]" ] || [ -z "$CHANGED_SERVICES" ]; then echo "services=[\"user-service\",\"event-service\",\"ai-service\",\"content-service\",\"distribution-service\",\"participation-service\",\"analytics-service\"]" >> $GITHUB_OUTPUT else echo "services=$CHANGED_SERVICES" >> $GITHUB_OUTPUT fi fi build-and-push: name: Build and Push - ${{ matrix.service }} needs: detect-changes runs-on: ubuntu-latest strategy: matrix: service: ${{ fromJson(needs.detect-changes.outputs.services) }} steps: - name: Checkout code uses: actions/checkout@v4 - name: Set up JDK ${{ env.JDK_VERSION }} uses: actions/setup-java@v4 with: java-version: ${{ env.JDK_VERSION }} distribution: 'temurin' cache: 'gradle' - name: Grant execute permission for gradlew run: chmod +x gradlew - name: Build with Gradle run: ./gradlew ${{ matrix.service }}:build -x test # - name: Run tests # run: ./gradlew ${{ matrix.service }}:test - name: Build JAR run: ./gradlew ${{ matrix.service }}:bootJar - name: Log in to Azure Container Registry uses: docker/login-action@v3 with: registry: ${{ env.ACR_NAME }}.azurecr.io username: ${{ secrets.ACR_USERNAME }} password: ${{ secrets.ACR_PASSWORD }} - name: Build and push Docker image uses: docker/build-push-action@v5 with: context: ./${{ matrix.service }} file: ./${{ matrix.service }}/Dockerfile push: true tags: | ${{ env.ACR_NAME }}.azurecr.io/kt-event-marketing/${{ matrix.service }}:${{ needs.detect-changes.outputs.environment }} ${{ env.ACR_NAME }}.azurecr.io/kt-event-marketing/${{ matrix.service }}:${{ github.sha }} ${{ env.ACR_NAME }}.azurecr.io/kt-event-marketing/${{ matrix.service }}:latest deploy: name: Deploy to AKS - ${{ needs.detect-changes.outputs.environment }} needs: [detect-changes, build-and-push] runs-on: ubuntu-latest environment: ${{ needs.detect-changes.outputs.environment }} steps: - name: Checkout code uses: actions/checkout@v4 - name: Azure login uses: azure/login@v1 with: creds: ${{ secrets.AZURE_CREDENTIALS }} - name: Get AKS credentials run: | az aks get-credentials \ --resource-group ${{ env.RESOURCE_GROUP }} \ --name ${{ env.AKS_CLUSTER }} \ --overwrite-existing - name: Setup Kustomize uses: imranismail/setup-kustomize@v2 - name: Deploy with Kustomize run: | cd .github/kustomize/overlays/${{ needs.detect-changes.outputs.environment }} kustomize edit set image \ acrdigitalgarage01.azurecr.io/kt-event-marketing/user-service:${{ needs.detect-changes.outputs.environment }} \ acrdigitalgarage01.azurecr.io/kt-event-marketing/event-service:${{ needs.detect-changes.outputs.environment }} \ acrdigitalgarage01.azurecr.io/kt-event-marketing/ai-service:${{ needs.detect-changes.outputs.environment }} \ acrdigitalgarage01.azurecr.io/kt-event-marketing/content-service:${{ needs.detect-changes.outputs.environment }} \ acrdigitalgarage01.azurecr.io/kt-event-marketing/distribution-service:${{ needs.detect-changes.outputs.environment }} \ acrdigitalgarage01.azurecr.io/kt-event-marketing/participation-service:${{ needs.detect-changes.outputs.environment }} \ acrdigitalgarage01.azurecr.io/kt-event-marketing/analytics-service:${{ needs.detect-changes.outputs.environment }} kustomize build . | kubectl apply -f - - name: Wait for deployment rollout run: | for service in $(echo '${{ needs.detect-changes.outputs.services }}' | jq -r '.[]'); do echo "Waiting for ${service} deployment..." kubectl rollout status deployment/${service} -n ${{ env.NAMESPACE }} --timeout=5m done - name: Verify deployment run: | echo "=== Pods Status ===" kubectl get pods -n ${{ env.NAMESPACE }} -l app.kubernetes.io/part-of=kt-event-marketing echo "=== Services ===" kubectl get svc -n ${{ env.NAMESPACE }} echo "=== Ingress ===" kubectl get ingress -n ${{ env.NAMESPACE }} notify: name: Notify Deployment Result needs: [detect-changes, deploy] runs-on: ubuntu-latest if: always() steps: - name: Deployment Success if: needs.deploy.result == 'success' run: | echo "✅ Deployment to ${{ needs.detect-changes.outputs.environment }} succeeded!" echo "Services: ${{ needs.detect-changes.outputs.services }}" - name: Deployment Failure if: needs.deploy.result == 'failure' run: | echo "❌ Deployment to ${{ needs.detect-changes.outputs.environment }} failed!" echo "Services: ${{ needs.detect-changes.outputs.services }}" exit 1