name: Test Proxy SERVER_ROOT_PATH Routing permissions: contents: read on: pull_request: branches: - main - litellm_internal_staging - litellm_oss_branch - "litellm_**" jobs: test-server-root-path: runs-on: ubuntu-latest timeout-minutes: 30 strategy: matrix: root_path: ["/api/v1", "/llmproxy"] steps: - name: Checkout repository uses: actions/checkout@08eba0b27e820071cde6df949e0beb9ba4906955 # v4.3.0 with: persist-credentials: false - name: Free up disk space run: | sudo rm -rf /usr/local/lib/android /usr/share/dotnet /opt/ghc /usr/local/share/boost sudo apt-get clean df -h / - name: Set up Docker Buildx uses: docker/setup-buildx-action@8d2750c68a42422c14e847fe6c8ac0403b4cbd6f # v3.12.0 - name: Build Docker image uses: docker/build-push-action@0adf9959216b96bec444f325f1e493d4aa344497 # v6.14.0 with: context: . file: ./docker/Dockerfile.non_root tags: litellm-test:${{ github.sha }} load: true push: false - name: Start LiteLLM container with SERVER_ROOT_PATH run: | docker run -d \ --name litellm-test \ -p 4000:4000 \ -e SERVER_ROOT_PATH="${{ matrix.root_path }}" \ -e LITELLM_MASTER_KEY="sk-1234" \ litellm-test:${{ github.sha }} \ --detailed_debug - name: Wait for container to be healthy run: | echo "Waiting for LiteLLM to start..." max_attempts=30 attempt=0 while [ $attempt -lt $max_attempts ]; do if docker logs litellm-test 2>&1 | grep -q "Uvicorn running"; then echo "LiteLLM started successfully" break fi attempt=$((attempt + 1)) echo "Attempt $attempt/$max_attempts - waiting for server to start..." sleep 2 done if [ $attempt -eq $max_attempts ]; then echo "Server failed to start within timeout" docker logs litellm-test exit 1 fi sleep 5 - name: Show container logs if: always() run: docker logs litellm-test - name: Test UI endpoint with root path run: | ROOT_PATH="${{ matrix.root_path }}" echo "Testing UI at: http://localhost:4000${ROOT_PATH}/ui/" for i in 1 2 3; do content=$(curl -sL --max-time 5 -H "Authorization: Bearer sk-1234" "http://localhost:4000${ROOT_PATH}/ui/") if echo "$content" | grep -q -E "(html|/dev/null || true ) for source_file in "${microsoft_sources[@]}"; do echo "Disabling unavailable apt source: ${source_file}" sudo mv "${source_file}" "${source_file}.disabled" done - name: Install UI deps and Chromium working-directory: ui/litellm-dashboard run: | npm ci npx playwright install --with-deps chromium - name: Run SERVER_ROOT_PATH redirect e2e working-directory: ui/litellm-dashboard env: SERVER_ROOT_PATH: ${{ matrix.root_path }} run: npx playwright test --config=e2e_tests/serverRootPath.config.ts - name: Upload Playwright artifacts on failure if: failure() uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4.6.2 with: name: playwright-trace-${{ strategy.job-index }} path: ui/litellm-dashboard/test-results/ retention-days: 7 - name: Cleanup if: always() run: | docker stop litellm-test || true docker rm litellm-test || true