feat(frontend): multi-source/sink WebRTC, graph editor, and headless … #1371
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: Build and Push Docker Image | |
| on: | |
| workflow_dispatch: | |
| inputs: | |
| version: | |
| description: 'Version tag for the Docker image' | |
| required: true | |
| type: string | |
| default: 'latest' | |
| pull_request: | |
| push: | |
| branches: | |
| - main | |
| - runpod-serverless | |
| tags: | |
| - 'v*' | |
| # Permissions for the reusable workflow jobs | |
| permissions: | |
| contents: read | |
| packages: write | |
| pull-requests: write | |
| issues: write | |
| jobs: | |
| # Cloud image - faster, used for PR deploys | |
| build-cloud: | |
| uses: ./.github/workflows/docker-build-image.yml | |
| with: | |
| variant: cloud | |
| suffix: '-cloud' | |
| dockerfile: Dockerfile.cloud | |
| description: Daydream Scope (Cloud) | |
| secrets: inherit | |
| # Standard image - slower, not needed for PR deploys | |
| build-standard: | |
| uses: ./.github/workflows/docker-build-image.yml | |
| with: | |
| variant: standard | |
| suffix: '' | |
| dockerfile: Dockerfile | |
| description: Daydream Scope | |
| secrets: inherit | |
| # PR deploy - only waits for cloud build | |
| deploy-pr: | |
| needs: build-cloud | |
| if: github.event_name == 'pull_request' | |
| runs-on: ubuntu-latest | |
| outputs: | |
| fal_app_id: ${{ steps.deploy.outputs.fal_app_id }} | |
| fal_ws_url: ${{ steps.deploy.outputs.fal_ws_url }} | |
| livepeer_fal_app_id: ${{ steps.deploy_livepeer.outputs.livepeer_fal_app_id }} | |
| livepeer_fal_ws_url: ${{ steps.deploy_livepeer.outputs.livepeer_fal_ws_url }} | |
| steps: | |
| - name: Checkout code | |
| uses: actions/checkout@v4 | |
| with: | |
| ref: ${{ github.event.pull_request.head.sha }} | |
| - name: Set up Python | |
| uses: actions/setup-python@v5 | |
| with: | |
| python-version: '3.12' | |
| - name: Install fal | |
| run: pip install fal | |
| - name: Deploy to fal (PR environment) | |
| id: deploy | |
| env: | |
| FAL_KEY: ${{ secrets.FAL_KEY }} | |
| run: | | |
| set -euo pipefail | |
| PR_NUMBER="${{ needs.build-cloud.outputs.pr_number }}" | |
| APP_NAME="scope-pr-${PR_NUMBER}" | |
| echo "Deploying PR #${PR_NUMBER} to fal as ${APP_NAME}" | |
| fal deploy \ | |
| --app-name "$APP_NAME" \ | |
| --env preview \ | |
| --auth public \ | |
| src/scope/cloud/fal_app.py 2>&1 | tee deploy_output.txt | |
| FAL_APP_ID="daydream/${APP_NAME}--preview" | |
| FAL_WS_URL="wss://fal.run/${FAL_APP_ID}/ws" | |
| echo "fal_app_id=${FAL_APP_ID}" >> $GITHUB_OUTPUT | |
| echo "fal_ws_url=${FAL_WS_URL}" >> $GITHUB_OUTPUT | |
| echo "Deployed to: ${FAL_APP_ID}" | |
| echo "WebSocket URL: ${FAL_WS_URL}" | |
| - name: Deploy Livepeer runner to fal (PR environment) | |
| id: deploy_livepeer | |
| env: | |
| FAL_KEY: ${{ secrets.FAL_KEY }} | |
| run: | | |
| set -euo pipefail | |
| PR_NUMBER="${{ needs.build-cloud.outputs.pr_number }}" | |
| APP_NAME="scope-livepeer-pr-${PR_NUMBER}" | |
| echo "Deploying Livepeer runner for PR #${PR_NUMBER} to fal as ${APP_NAME}" | |
| fal deploy \ | |
| --app-name "$APP_NAME" \ | |
| --env preview \ | |
| --auth private \ | |
| src/scope/cloud/livepeer_fal_app.py 2>&1 | tee deploy_livepeer_output.txt | |
| LIVEPEER_FAL_APP_ID="daydream/${APP_NAME}--preview" | |
| LIVEPEER_FAL_WS_URL="wss://fal.run/${LIVEPEER_FAL_APP_ID}/ws" | |
| echo "livepeer_fal_app_id=${LIVEPEER_FAL_APP_ID}" >> $GITHUB_OUTPUT | |
| echo "livepeer_fal_ws_url=${LIVEPEER_FAL_WS_URL}" >> $GITHUB_OUTPUT | |
| echo "Deployed Livepeer runner to: ${LIVEPEER_FAL_APP_ID}" | |
| echo "Livepeer WebSocket URL: ${LIVEPEER_FAL_WS_URL}" | |
| - name: Comment on PR with deployment info | |
| uses: actions/github-script@v7 | |
| with: | |
| script: | | |
| const prNumber = ${{ github.event.pull_request.number }}; | |
| const falAppId = '${{ steps.deploy.outputs.fal_app_id }}'; | |
| const falWsUrl = '${{ steps.deploy.outputs.fal_ws_url }}'; | |
| const livepeerFalAppId = '${{ steps.deploy_livepeer.outputs.livepeer_fal_app_id }}'; | |
| const livepeerFalWsUrl = '${{ steps.deploy_livepeer.outputs.livepeer_fal_ws_url }}'; | |
| const shortSha = '${{ needs.build-cloud.outputs.short_sha }}'; | |
| const body = `## 🚀 fal.ai Preview Deployment | |
| | | | | |
| |---|---| | |
| | **App ID** | \`${falAppId}\` | | |
| | **WebSocket** | \`${falWsUrl}\` | | |
| | **Commit** | \`${shortSha}\` | | |
| ### Livepeer Runner | |
| | | | | |
| |---|---| | |
| | **App ID** | \`${livepeerFalAppId}\` | | |
| | **WebSocket** | \`${livepeerFalWsUrl}\` | | |
| | **Auth** | \`private\` | | |
| ### Testing Livepeer Mode | |
| \`\`\` | |
| SCOPE_CLOUD_MODE=livepeer SCOPE_CLOUD_APP_ID="${livepeerFalAppId}/ws" uv run daydream-scope | |
| \`\`\` | |
| `; | |
| const { data: comments } = await github.rest.issues.listComments({ | |
| owner: context.repo.owner, | |
| repo: context.repo.repo, | |
| issue_number: prNumber | |
| }); | |
| const existingComment = comments.find(c => | |
| c.user.type === 'Bot' && | |
| c.body.includes('fal.ai Preview Deployment') | |
| ); | |
| if (existingComment) { | |
| await github.rest.issues.updateComment({ | |
| owner: context.repo.owner, | |
| repo: context.repo.repo, | |
| comment_id: existingComment.id, | |
| body | |
| }); | |
| } else { | |
| await github.rest.issues.createComment({ | |
| owner: context.repo.owner, | |
| repo: context.repo.repo, | |
| issue_number: prNumber, | |
| body | |
| }); | |
| } | |