name: PR Playwright Deploy and Comment on: workflow_run: workflows: ["Tests CI"] types: [requested, completed] env: DATE_FORMAT: '+%m/%d/%Y, %I:%M:%S %p' jobs: deploy-reports: runs-on: ubuntu-latest if: github.repository == 'Comfy-Org/ComfyUI_frontend' && github.event.workflow_run.event == 'pull_request' && github.event.action == 'completed' permissions: actions: read strategy: fail-fast: false matrix: browser: [chromium, chromium-2x, chromium-0.5x, mobile-chrome] steps: - name: Get PR info id: pr-info uses: actions/github-script@v7 with: script: | const { data: pullRequests } = await github.rest.pulls.list({ owner: context.repo.owner, repo: context.repo.repo, state: 'open', head: `${context.repo.owner}:${context.payload.workflow_run.head_branch}`, }); if (pullRequests.length === 0) { console.log('No open PR found for this branch'); return { number: null, sanitized_branch: null }; } const pr = pullRequests[0]; console.log(`โœ… Found PR #${pr.number} for branch: ${context.payload.workflow_run.head_branch}`); console.log(`PR number is: ${pr.number}`); const branchName = context.payload.workflow_run.head_branch; const sanitizedBranch = branchName.toLowerCase().replace(/[^a-z0-9-]/g, '-').replace(/--+/g, '-').replace(/^-|-$/g, ''); return { number: pr.number, sanitized_branch: sanitizedBranch }; - name: Set project name if: fromJSON(steps.pr-info.outputs.result).number != null id: project-name run: | if [ "${{ matrix.browser }}" = "chromium-0.5x" ]; then echo "name=comfyui-playwright-chromium-0-5x" >> $GITHUB_OUTPUT else echo "name=comfyui-playwright-${{ matrix.browser }}" >> $GITHUB_OUTPUT fi echo "branch=${{ fromJSON(steps.pr-info.outputs.result).sanitized_branch }}" >> $GITHUB_OUTPUT - name: Download playwright report if: fromJSON(steps.pr-info.outputs.result).number != null uses: actions/download-artifact@v4 with: github-token: ${{ secrets.GITHUB_TOKEN }} run-id: ${{ github.event.workflow_run.id }} name: playwright-report-${{ matrix.browser }} path: playwright-report - name: Install Wrangler if: fromJSON(steps.pr-info.outputs.result).number != null run: npm install -g wrangler - name: Deploy to Cloudflare Pages (${{ matrix.browser }}) if: fromJSON(steps.pr-info.outputs.result).number != null id: cloudflare-deploy continue-on-error: true run: | # Retry logic for wrangler deploy (3 attempts) RETRY_COUNT=0 MAX_RETRIES=3 SUCCESS=false DEPLOYMENT_URL="" while [ $RETRY_COUNT -lt $MAX_RETRIES ] && [ $SUCCESS = false ]; do RETRY_COUNT=$((RETRY_COUNT + 1)) echo "Deployment attempt $RETRY_COUNT of $MAX_RETRIES..." # Capture wrangler output to extract deployment URL OUTPUT=$(npx wrangler pages deploy playwright-report --project-name=${{ steps.project-name.outputs.name }} --branch=${{ steps.project-name.outputs.branch }} 2>&1) EXIT_CODE=$? echo "$OUTPUT" if [ $EXIT_CODE -eq 0 ]; then SUCCESS=true echo "Deployment successful on attempt $RETRY_COUNT" # Extract the deployment URL from wrangler output # Look for the URL in various formats that wrangler might output DEPLOYMENT_URL=$(echo "$OUTPUT" | grep -oE 'https://[a-z0-9.-]+\.pages\.dev(/[^[:space:]]*)?$' | head -1) if [ -z "$DEPLOYMENT_URL" ]; then # Try another pattern if the first one fails DEPLOYMENT_URL=$(echo "$OUTPUT" | grep -oE 'https://[^[:space:]]+\.pages\.dev' | head -1) fi if [ -n "$DEPLOYMENT_URL" ]; then echo "Deployment URL: $DEPLOYMENT_URL" echo "url=$DEPLOYMENT_URL" >> $GITHUB_OUTPUT else echo "Warning: Could not extract deployment URL from wrangler output" # Construct expected URL as fallback FALLBACK_URL="https://${{ steps.project-name.outputs.name }}-${{ steps.project-name.outputs.branch }}.pages.dev" echo "Using fallback URL: $FALLBACK_URL" echo "url=$FALLBACK_URL" >> $GITHUB_OUTPUT fi else echo "Deployment failed on attempt $RETRY_COUNT" if [ $RETRY_COUNT -lt $MAX_RETRIES ]; then echo "Retrying in 10 seconds..." sleep 10 fi fi done if [ $SUCCESS = false ]; then echo "All deployment attempts failed" exit 1 fi env: CLOUDFLARE_API_TOKEN: ${{ secrets.CLOUDFLARE_API_TOKEN }} CLOUDFLARE_ACCOUNT_ID: ${{ secrets.CLOUDFLARE_ACCOUNT_ID }} - name: Save deployment info if: fromJSON(steps.pr-info.outputs.result).number != null && always() run: | # Read test exit code from the artifact TEST_EXIT_CODE="1" if [ -f "playwright-report/test-exit-code.txt" ]; then TEST_EXIT_CODE=$(cat playwright-report/test-exit-code.txt) fi # Use deployment URL if available, otherwise use a fallback URL="${{ steps.cloudflare-deploy.outputs.url }}" if [ -z "$URL" ] || [ "${{ steps.cloudflare-deploy.outcome }}" != "success" ]; then URL="https://${{ steps.project-name.outputs.name }}-${{ steps.project-name.outputs.branch }}.pages.dev" fi echo "${{ matrix.browser }}|$TEST_EXIT_CODE|$URL" > deployment-info.txt echo "Saved deployment info: ${{ matrix.browser }}|$TEST_EXIT_CODE|$URL" - name: Upload deployment info if: fromJSON(steps.pr-info.outputs.result).number != null && always() uses: actions/upload-artifact@v4 with: name: deployment-info-${{ matrix.browser }} path: deployment-info.txt retention-days: 1 comment-tests-starting: runs-on: ubuntu-latest if: github.repository == 'Comfy-Org/ComfyUI_frontend' && github.event.workflow_run.event == 'pull_request' && github.event.action == 'requested' permissions: pull-requests: write actions: read steps: - name: Get PR number id: pr uses: actions/github-script@v7 with: script: | const { data: pullRequests } = await github.rest.pulls.list({ owner: context.repo.owner, repo: context.repo.repo, state: 'open', head: `${context.repo.owner}:${context.payload.workflow_run.head_branch}`, }); if (pullRequests.length === 0) { console.log('No open PR found for this branch'); return null; } const prNumber = pullRequests[0].number; console.log(`โœ… Found PR #${prNumber} for branch: ${context.payload.workflow_run.head_branch}`); return prNumber; - name: Get completion time id: completion-time run: echo "time=$(date -u '${{ env.DATE_FORMAT }}')" >> $GITHUB_OUTPUT - name: Generate comment body for start if: steps.pr.outputs.result != 'null' id: comment-body-start run: | echo "" > comment.md echo "## ๐ŸŽญ Playwright Test Results" >> comment.md echo "" >> comment.md echo "comfy-loading-gif **Tests are starting...** " >> comment.md echo "" >> comment.md echo "โฐ Started at: ${{ steps.completion-time.outputs.time }} UTC" >> comment.md echo "" >> comment.md echo "### ๐Ÿš€ Running Tests" >> comment.md echo "- ๐Ÿงช **chromium**: Running tests..." >> comment.md echo "- ๐Ÿงช **chromium-0.5x**: Running tests..." >> comment.md echo "- ๐Ÿงช **chromium-2x**: Running tests..." >> comment.md echo "- ๐Ÿงช **mobile-chrome**: Running tests..." >> comment.md echo "" >> comment.md echo "---" >> comment.md echo "โฑ๏ธ Please wait while tests are running across all browsers..." >> comment.md - name: Comment PR - Tests Started if: steps.pr.outputs.result != 'null' uses: edumserrano/find-create-or-update-comment@82880b65c8a3a6e4c70aa05a204995b6c9696f53 # v3.0.0 with: issue-number: ${{ steps.pr.outputs.result }} body-includes: '' comment-author: 'github-actions[bot]' edit-mode: replace body-path: comment.md comment-tests-completed: runs-on: ubuntu-latest needs: deploy-reports if: github.repository == 'Comfy-Org/ComfyUI_frontend' && github.event.workflow_run.event == 'pull_request' && github.event.action == 'completed' && always() permissions: pull-requests: write actions: read steps: - name: Get PR number id: pr uses: actions/github-script@v7 with: script: | const { data: pullRequests } = await github.rest.pulls.list({ owner: context.repo.owner, repo: context.repo.repo, state: 'open', head: `${context.repo.owner}:${context.payload.workflow_run.head_branch}`, }); if (pullRequests.length === 0) { console.log('No open PR found for this branch'); return null; } const prNumber = pullRequests[0].number; console.log(`โœ… Found PR #${prNumber} for branch: ${context.payload.workflow_run.head_branch}`); return prNumber; - name: Download all deployment info if: steps.pr.outputs.result != 'null' uses: actions/download-artifact@v4 with: github-token: ${{ secrets.GITHUB_TOKEN }} run-id: ${{ github.event.workflow_run.id }} pattern: deployment-info-* merge-multiple: true path: deployment-info - name: Get completion time id: completion-time run: echo "time=$(date -u '${{ env.DATE_FORMAT }}')" >> $GITHUB_OUTPUT - name: Generate comment body for completion if: steps.pr.outputs.result != 'null' id: comment-body-completed run: | echo "" > comment.md echo "## ๐ŸŽญ Playwright Test Results" >> comment.md echo "" >> comment.md # Check if all tests passed ALL_PASSED=true for file in deployment-info/*.txt; do if [ -f "$file" ]; then browser=$(basename "$file" .txt) info=$(cat "$file") exit_code=$(echo "$info" | cut -d'|' -f2) if [ "$exit_code" != "0" ]; then ALL_PASSED=false break fi fi done if [ "$ALL_PASSED" = "true" ]; then echo "โœ… **All tests passed across all browsers!**" >> comment.md else echo "โŒ **Some tests failed!**" >> comment.md fi echo "" >> comment.md echo "โฐ Completed at: ${{ steps.completion-time.outputs.time }} UTC" >> comment.md echo "" >> comment.md echo "### ๐Ÿ“Š Test Reports by Browser" >> comment.md for file in deployment-info/*.txt; do if [ -f "$file" ]; then browser=$(basename "$file" .txt) info=$(cat "$file") exit_code=$(echo "$info" | cut -d'|' -f2) url=$(echo "$info" | cut -d'|' -f3) # Validate URLs before using them in comments sanitized_url=$(echo "$url" | grep -E '^https://[a-z0-9.-]+\.pages\.dev(/.*)?$' || echo "INVALID_URL") if [ "$sanitized_url" = "INVALID_URL" ]; then echo "Invalid deployment URL detected: $url" url="#" # Use safe fallback fi if [ "$exit_code" = "0" ]; then status="โœ…" else status="โŒ" fi echo "- $status **$browser**: [View Report]($url)" >> comment.md fi done echo "" >> comment.md echo "---" >> comment.md if [ "$ALL_PASSED" = "true" ]; then echo "๐ŸŽ‰ Your tests are passing across all browsers!" >> comment.md else echo "โš ๏ธ Please check the test reports for details on failures." >> comment.md fi - name: Comment PR - Tests Complete if: steps.pr.outputs.result != 'null' uses: edumserrano/find-create-or-update-comment@82880b65c8a3a6e4c70aa05a204995b6c9696f53 # v3.0.0 with: issue-number: ${{ steps.pr.outputs.result }} body-includes: '' comment-author: 'github-actions[bot]' edit-mode: replace body-path: comment.md