Skip to main content

CI/CD Overview

TalentG uses GitHub Actions for continuous integration and Vercel for continuous deployment, ensuring reliable and automated software delivery.

Pipeline Architecture

GitHub Actions Workflows

Main CI/CD Pipeline

# .github/workflows/ci-cd.yml
name: CI/CD Pipeline

on:
  push:
    branches: [main, staging]
  pull_request:
    branches: [main]

env:
  NODE_VERSION: '18'
  PNPM_VERSION: '8'

jobs:
  # Code Quality Checks
  quality:
    runs-on: ubuntu-latest
    steps:
      - name: Checkout code
        uses: actions/checkout@v4

      - name: Setup Node.js
        uses: actions/setup-node@v4
        with:
          node-version: ${{ env.NODE_VERSION }}

      - name: Setup pnpm
        uses: pnpm/action-setup@v2
        with:
          version: ${{ env.PNPM_VERSION }}

      - name: Get pnpm store directory
        shell: bash
        run: echo "STORE_PATH=$(pnpm store path --silent)" >> $GITHUB_ENV

      - name: Setup pnpm cache
        uses: actions/cache@v3
        with:
          path: ${{ env.STORE_PATH }}
          key: ${{ runner.os }}-pnpm-store-${{ hashFiles('**/pnpm-lock.yaml') }}
          restore-keys: |
            ${{ runner.os }}-pnpm-store-

      - name: Install dependencies
        run: pnpm install --frozen-lockfile

      - name: Type check
        run: pnpm type-check

      - name: Lint code
        run: pnpm lint

      - name: Format check
        run: pnpm format:check

  # Unit and Integration Tests
  test:
    runs-on: ubuntu-latest
    needs: quality
    services:
      postgres:
        image: postgres:15
        env:
          POSTGRES_PASSWORD: postgres
          POSTGRES_DB: test_db
        options: >-
          --health-cmd pg_isready
          --health-interval 10s
          --health-timeout 5s
          --health-retries 5
        ports:
          - 5432:5432

    steps:
      - name: Checkout code
        uses: actions/checkout@v4

      - name: Setup Node.js
        uses: actions/setup-node@v4
        with:
          node-version: ${{ env.NODE_VERSION }}

      - name: Setup pnpm
        uses: pnpm/action-setup@v2
        with:
          version: ${{ env.PNPM_VERSION }}

      - name: Install dependencies
        run: pnpm install --frozen-lockfile

      - name: Run unit tests
        run: pnpm test:unit
        env:
          NODE_ENV: test
          DATABASE_URL: postgresql://postgres:postgres@localhost:5432/test_db

      - name: Run integration tests
        run: pnpm test:integration
        env:
          NODE_ENV: test
          DATABASE_URL: postgresql://postgres:postgres@localhost:5432/test_db
          TEST_SUPABASE_URL: ${{ secrets.TEST_SUPABASE_URL }}
          TEST_SUPABASE_ANON_KEY: ${{ secrets.TEST_SUPABASE_ANON_KEY }}

      - name: Upload coverage reports
        uses: codecov/codecov-action@v3
        with:
          file: ./coverage/lcov.info
          flags: unittests
          name: codecov-umbrella

  # End-to-End Tests
  e2e:
    runs-on: ubuntu-latest
    needs: test
    steps:
      - name: Checkout code
        uses: actions/checkout@v4

      - name: Setup Node.js
        uses: actions/setup-node@v4
        with:
          node-version: ${{ env.NODE_VERSION }}

      - name: Setup pnpm
        uses: pnpm/action-setup@v2
        with:
          version: ${{ env.PNPM_VERSION }}

      - name: Install dependencies
        run: pnpm install --frozen-lockfile

      - name: Install Playwright browsers
        run: pnpm exec playwright install --with-deps

      - name: Run E2E tests
        run: pnpm test:e2e
        env:
          NODE_ENV: test
          TEST_SUPABASE_URL: ${{ secrets.TEST_SUPABASE_URL }}
          TEST_SUPABASE_ANON_KEY: ${{ secrets.TEST_SUPABASE_ANON_KEY }}

      - name: Upload E2E test results
        uses: actions/upload-artifact@v3
        if: failure()
        with:
          name: playwright-report
          path: playwright-report/
          retention-days: 30

  # Security Scanning
  security:
    runs-on: ubuntu-latest
    needs: quality
    steps:
      - name: Checkout code
        uses: actions/checkout@v4

      - name: Setup Node.js
        uses: actions/setup-node@v4
        with:
          node-version: ${{ env.NODE_VERSION }}

      - name: Setup pnpm
        uses: pnpm/action-setup@v2
        with:
          version: ${{ env.PNPM_VERSION }}

      - name: Install dependencies
        run: pnpm install --frozen-lockfile

      - name: Run security audit
        run: pnpm audit --audit-level moderate

      - name: Run Snyk security scan
        uses: snyk/actions/node@master
        env:
          SNYK_TOKEN: ${{ secrets.SNYK_TOKEN }}
        with:
          args: --severity-threshold=high

  # Build and Deploy
  deploy:
    runs-on: ubuntu-latest
    needs: [test, e2e, security]
    if: github.ref == 'refs/heads/main' || github.ref == 'refs/heads/staging'
    
    steps:
      - name: Checkout code
        uses: actions/checkout@v4

      - name: Setup Node.js
        uses: actions/setup-node@v4
        with:
          node-version: ${{ env.NODE_VERSION }}

      - name: Setup pnpm
        uses: pnpm/action-setup@v2
        with:
          version: ${{ env.PNPM_VERSION }}

      - name: Install dependencies
        run: pnpm install --frozen-lockfile

      - name: Build application
        run: pnpm build
        env:
          NODE_ENV: production
          NEXT_PUBLIC_SUPABASE_URL: ${{ secrets.NEXT_PUBLIC_SUPABASE_URL }}
          NEXT_PUBLIC_SUPABASE_ANON_KEY: ${{ secrets.NEXT_PUBLIC_SUPABASE_ANON_KEY }}

      - name: Deploy to Vercel
        uses: amondnet/vercel-action@v25
        with:
          vercel-token: ${{ secrets.VERCEL_TOKEN }}
          vercel-org-id: ${{ secrets.VERCEL_ORG_ID }}
          vercel-project-id: ${{ secrets.VERCEL_PROJECT_ID }}
          vercel-args: ${{ github.ref == 'refs/heads/main' && '--prod' || '' }}

      - name: Run health checks
        run: |
          sleep 30
          curl -f ${{ github.ref == 'refs/heads/main' && 'https://talentg.vercel.app' || 'https://talentg-staging.vercel.app' }}/api/health

Pull Request Workflow

# .github/workflows/pr-checks.yml
name: Pull Request Checks

on:
  pull_request:
    types: [opened, synchronize, reopened]

jobs:
  pr-checks:
    runs-on: ubuntu-latest
    steps:
      - name: Checkout code
        uses: actions/checkout@v4

      - name: Setup Node.js
        uses: actions/setup-node@v4
        with:
          node-version: '18'

      - name: Setup pnpm
        uses: pnpm/action-setup@v2
        with:
          version: '8'

      - name: Install dependencies
        run: pnpm install --frozen-lockfile

      - name: Type check
        run: pnpm type-check

      - name: Lint code
        run: pnpm lint

      - name: Format check
        run: pnpm format:check

      - name: Run tests
        run: pnpm test:unit

      - name: Build check
        run: pnpm build

  # Code quality analysis
  code-quality:
    runs-on: ubuntu-latest
    steps:
      - name: Checkout code
        uses: actions/checkout@v4
        with:
          fetch-depth: 0

      - name: SonarCloud Scan
        uses: SonarSource/sonarcloud-github-action@master
        env:
          GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
          SONAR_TOKEN: ${{ secrets.SONAR_TOKEN }}

Deployment Strategy

Environment Promotion

Branch Strategy

BranchEnvironmentTriggerPurpose
mainProductionPushStable releases
stagingStagingPushPre-production testing
feature/*PreviewPRFeature development
hotfix/*ProductionPushCritical fixes

Deployment Process

  1. Code Push: Developer pushes to branch
  2. Quality Gates: Automated tests and checks
  3. Build: Application compilation and optimization
  4. Deploy: Vercel deployment with zero downtime
  5. Health Check: Post-deployment verification
  6. Notification: Team notification of deployment status

Quality Gates

Automated Checks

  • Code Quality: ESLint, Prettier, TypeScript
  • Test Coverage: Unit, integration, and E2E tests
  • Security: Vulnerability scanning and audit
  • Performance: Build time and bundle size checks
  • Dependencies: Outdated package detection

Manual Approvals

  • Code Review: At least 2 approvals required
  • Security Review: For security-sensitive changes
  • Architecture Review: For major structural changes
  • Product Review: For user-facing features

Environment Configuration

Development Environment

# .env.development
NODE_ENV=development
NEXT_PUBLIC_APP_URL=http://localhost:3000
NEXT_PUBLIC_SUPABASE_URL=your_dev_supabase_url
NEXT_PUBLIC_SUPABASE_ANON_KEY=your_dev_anon_key
LOG_LEVEL=debug
ENABLE_ANALYTICS=false

Staging Environment

# .env.staging
NODE_ENV=staging
NEXT_PUBLIC_APP_URL=https://talentg-staging.vercel.app
NEXT_PUBLIC_SUPABASE_URL=your_staging_supabase_url
NEXT_PUBLIC_SUPABASE_ANON_KEY=your_staging_anon_key
LOG_LEVEL=info
ENABLE_ANALYTICS=true

Production Environment

# .env.production
NODE_ENV=production
NEXT_PUBLIC_APP_URL=https://talentg.vercel.app
NEXT_PUBLIC_SUPABASE_URL=your_prod_supabase_url
NEXT_PUBLIC_SUPABASE_ANON_KEY=your_prod_anon_key
LOG_LEVEL=warn
ENABLE_ANALYTICS=true

Monitoring & Alerting

Deployment Monitoring

# .github/workflows/monitor.yml
name: Deployment Monitoring

on:
  workflow_run:
    workflows: ["CI/CD Pipeline"]
    types: [completed]

jobs:
  monitor:
    runs-on: ubuntu-latest
    if: ${{ github.event.workflow_run.conclusion == 'success' }}
    
    steps:
      - name: Health Check
        run: |
          curl -f https://talentg.vercel.app/api/health
          
      - name: Performance Check
        run: |
          curl -w "@curl-format.txt" -o /dev/null -s https://talentg.vercel.app
          
      - name: Notify Team
        uses: 8398a7/action-slack@v3
        with:
          status: ${{ job.status }}
          channel: '#deployments'
          webhook_url: ${{ secrets.SLACK_WEBHOOK }}

Alert Configuration

# .github/workflows/alerts.yml
name: Alerts

on:
  schedule:
    - cron: '*/5 * * * *' # Every 5 minutes

jobs:
  health-check:
    runs-on: ubuntu-latest
    steps:
      - name: Check Application Health
        id: health
        run: |
          response=$(curl -s -o /dev/null -w "%{http_code}" https://talentg.vercel.app/api/health)
          if [ $response -ne 200 ]; then
            echo "status=failure" >> $GITHUB_OUTPUT
            exit 1
          else
            echo "status=success" >> $GITHUB_OUTPUT
          fi
          
      - name: Send Alert
        if: steps.health.outputs.status == 'failure'
        uses: 8398a7/action-slack@v3
        with:
          status: failure
          channel: '#alerts'
          webhook_url: ${{ secrets.SLACK_WEBHOOK }}
          text: '🚨 TalentG production health check failed!'

Rollback Strategy

Automatic Rollback

# .github/workflows/rollback.yml
name: Automatic Rollback

on:
  workflow_run:
    workflows: ["Deployment Monitoring"]
    types: [completed]

jobs:
  rollback:
    runs-on: ubuntu-latest
    if: ${{ github.event.workflow_run.conclusion == 'failure' }}
    
    steps:
      - name: Rollback to Previous Version
        uses: amondnet/vercel-action@v25
        with:
          vercel-token: ${{ secrets.VERCEL_TOKEN }}
          vercel-org-id: ${{ secrets.VERCEL_ORG_ID }}
          vercel-project-id: ${{ secrets.VERCEL_PROJECT_ID }}
          vercel-args: '--rollback'
          
      - name: Notify Team
        uses: 8398a7/action-slack@v3
        with:
          status: ${{ job.status }}
          channel: '#alerts'
          webhook_url: ${{ secrets.SLACK_WEBHOOK }}
          text: '🔄 Automatic rollback initiated due to health check failure'

Manual Rollback

# Rollback via Vercel CLI
vercel rollback [deployment-url]

# Rollback via GitHub Actions
gh workflow run rollback.yml -f environment=production

Best Practices

Code Quality

  1. Pre-commit Hooks: Run linting and formatting
  2. Branch Protection: Require PR reviews and status checks
  3. Automated Testing: Comprehensive test coverage
  4. Code Review: Peer review for all changes

Deployment Safety

  1. Feature Flags: Gradual feature rollouts
  2. Health Checks: Post-deployment verification
  3. Monitoring: Real-time application monitoring
  4. Rollback Plan: Quick rollback capability

Security

  1. Secret Management: Secure environment variables
  2. Dependency Scanning: Regular security audits
  3. Access Control: Limited deployment permissions
  4. Audit Logging: Track all deployment activities

Troubleshooting

Common Issues

  1. Build Failures: Check dependencies and environment variables
  2. Test Failures: Review test logs and fix failing tests
  3. Deployment Issues: Verify Vercel configuration and secrets
  4. Health Check Failures: Check application logs and database connectivity

Debug Commands

# Check deployment status
vercel ls

# View deployment logs
vercel logs [deployment-url]

# Check application health
curl https://talentg.vercel.app/api/health

# View GitHub Actions logs
gh run list --workflow=ci-cd.yml
gh run view [run-id]

Performance Optimization

Build Optimization

// next.config.js
const nextConfig = {
  experimental: {
    optimizeCss: true,
    optimizePackageImports: ['@supabase/supabase-js'],
  },
  compiler: {
    removeConsole: process.env.NODE_ENV === 'production',
  },
  images: {
    formats: ['image/webp', 'image/avif'],
  },
}

CI/CD Optimization

  1. Parallel Jobs: Run independent jobs in parallel
  2. Caching: Cache dependencies and build artifacts
  3. Incremental Builds: Only build changed components
  4. Resource Optimization: Use appropriate runner sizes
Monitoring: All deployments are monitored through Vercel Analytics, GitHub Actions, and custom health checks. Alerts are sent to the team via Slack for any issues.