deploy #6236
This file contains 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: CI | |
on: | |
merge_group: | |
pull_request: | |
push: | |
branches: [main, dev] | |
workflow_dispatch: | |
concurrency: | |
group: ${{ github.ref }} | |
cancel-in-progress: true | |
jobs: | |
# set yarn cache | |
cache-deps: | |
runs-on: self-hosted | |
steps: | |
- uses: actions/checkout@v4 | |
with: | |
submodules: recursive | |
- name: Setup Environment | |
uses: ./.github/actions/setup-env | |
with: | |
build-nextjs: true | |
env: | |
YARN_ENABLE_HARDENED_MODE: 0 | |
- name: Show github refs | |
run: | | |
echo github.ref=${{ github.ref }} | |
echo github.head_ref=${{ github.head_ref }} | |
unit-tests: | |
name: Unit Tests | |
runs-on: self-hosted | |
needs: [cache-deps] | |
env: | |
ANVIL_MAINNET_FORK_URL: ${{ secrets.CI_ANVIL_MAINNET_FORK_URL }} | |
ANVIL_BASE_FORK_URL: ${{ secrets.CI_ANVIL_BASE_FORK_URL }} | |
FOUNDRY_BASE_SEPOLIA_RPC_URL: ${{ secrets.CI_FOUNDRY_BASE_SEPOLIA_RPC_URL }} | |
YARN_ENABLE_HARDENED_MODE: 0 | |
steps: | |
- name: Install Tilt | |
id: tilt | |
shell: bash | |
run: | | |
cd /tmp | |
curl -fsSL https://raw.githubusercontent.com/tilt-dev/tilt/master/scripts/install.sh | bash | |
- name: Add hosts to /etc/hosts | |
run: | | |
sudo su | |
if grep -q "host.docker.internal" /etc/hosts; then | |
echo "Hosts file already contains host.docker.internal" | |
else | |
echo "127.0.0.1 host.docker.internal" | sudo tee -a /etc/hosts | |
fi | |
- uses: actions/checkout@v4 | |
with: | |
submodules: recursive | |
- name: Set up Homebrew | |
id: set-up-homebrew | |
uses: Homebrew/actions/setup-homebrew@master | |
- name: Brew Bundle | |
id: brew-bundle | |
run: | | |
brew bundle | |
brew cleanup | |
- name: Setup Environment | |
uses: ./.github/actions/setup-env | |
env: | |
YARN_ENABLE_HARDENED_MODE: 0 | |
with: | |
yarn-install: false | |
- name: Load Next.js Build Cache | |
uses: actions/download-artifact@v4 | |
with: | |
name: nextjs-build | |
path: ${{ github.workspace }}/apps/next/.next | |
# - name: Snaplet Login | |
# shell: bash | |
# run: bunx snaplet auth login ${{ secrets.CI_SNAPLET_AUTH_TOKEN }} | |
- name: Tilt CI | |
id: tilt-ci | |
shell: bash | |
run: tilt ci unit-tests --timeout=10m | |
- name: Lint | |
run: yarn lint | |
- name: Tilt Down | |
# always run tilt down if tilt ci started | |
if: always() && steps.tilt-ci.outcome != 'skipped' | |
shell: bash | |
run: tilt down | |
# @todo anvil fixtures cause dirty repo, but only in github actions 😢 | |
- name: All Changes Committed | |
shell: bash | |
run: git diff # --exit-code | |
playwright-tests: | |
name: Playwright Tests | |
runs-on: self-hosted | |
needs: [cache-deps] | |
env: | |
ANVIL_MAINNET_FORK_URL: ${{ secrets.CI_ANVIL_MAINNET_FORK_URL }} | |
ANVIL_BASE_FORK_URL: ${{ secrets.CI_ANVIL_BASE_FORK_URL }} | |
YARN_ENABLE_HARDENED_MODE: 0 | |
# for writing PR comments | |
permissions: | |
pull-requests: write | |
timeout-minutes: 40 | |
steps: | |
- name: Install Tilt | |
id: tilt | |
shell: bash | |
run: | | |
cd /tmp | |
curl -fsSL https://raw.githubusercontent.com/tilt-dev/tilt/master/scripts/install.sh | bash | |
- name: Add hosts to /etc/hosts | |
run: | | |
sudo su | |
if grep -q "host.docker.internal" /etc/hosts; then | |
echo "Hosts file already contains host.docker.internal" | |
else | |
echo "127.0.0.1 host.docker.internal" | sudo tee -a /etc/hosts | |
fi | |
- uses: actions/checkout@v4 | |
with: | |
submodules: recursive | |
- name: Set up Homebrew | |
id: set-up-homebrew | |
uses: Homebrew/actions/setup-homebrew@master | |
- name: Brew Bundle | |
id: brew-bundle | |
run: | | |
brew bundle | |
brew cleanup | |
- name: Setup Environment | |
uses: ./.github/actions/setup-env | |
env: | |
YARN_ENABLE_HARDENED_MODE: 0 | |
- name: Load Next.js Build Cache | |
uses: actions/download-artifact@v4 | |
with: | |
name: nextjs-build | |
path: ${{ github.workspace }}/apps/next/.next | |
# - name: Snaplet Login | |
# shell: bash | |
# run: bunx snaplet auth login ${{ secrets.CI_SNAPLET_AUTH_TOKEN }} | |
- name: Install Playwright Dependencies | |
run: yarn playwright playwright install --with-deps | |
# @todo anvil fixtures cause dirty repo, but only in github actions 😢 | |
# - name: All Changes Committed | |
# shell: bash | |
# run: git diff --exit-code | |
# this is on purpose so we get github annotations | |
- name: Build Next.js | |
shell: bash | |
run: | | |
tilt ci yarn:install # install and setup env | |
yarn web:docker:build # build nextjs docker image | |
- name: Playwright Tests | |
id: playwright | |
shell: bash | |
run: | | |
# set debug logs if runner.debug is set | |
# if [ "${{runner.debug}}" == "1" ]; then | |
# export DEBUG="test:*,app:*,api:*,next:*" | |
# fi | |
export DEBUG="api:*,app:*,test:*,-test:fixtures:snaplet:*" | |
nohup tilt up playwright:deps & | |
tilt_pid=$! | |
echo "Tilt process started with PID: $tilt_pid" | |
echo waiting for tilt to be ready | |
for i in {1..10}; do | |
curl -s http://localhost:10350 > /dev/null && break || echo "Attempt $i failed, trying again..." | |
sleep 1 | |
done | |
sleep 1 | |
echo tilt is ready | |
max_attempts=60 | |
wait_timeout=7 | |
for ((i=1; i<=max_attempts; i++)); do | |
echo "Attempt $i: Waiting for tilt with timeout ${wait_timeout}s" | |
# Check if the Tilt process is still running | |
if ! ps -p $tilt_pid > /dev/null; then | |
echo "Tilt process (PID: $tilt_pid) is no longer running, exiting" | |
exit 1 | |
fi | |
# Check if any targets are in error | |
has_errors=$(tilt dump engine | jq ' | |
.ManifestTargets | |
| to_entries | |
| map( | |
select( | |
.value.State.RuntimeState.Status == "error" or | |
(.value.State.BuildHistory | length > 0 and .[0].Error != null) | |
) | |
) | |
| length > 0 | |
') | |
if [ "$has_errors" = "true" ]; then | |
echo "There are targets in error status:" | |
tilt dump engine | jq ' | |
.ManifestTargets | |
| to_entries | |
| map( | |
select( | |
.value.State.RuntimeState.Status == "error" or | |
(.value.State.BuildHistory | length > 0 and .[0].Error != null) | |
) | |
) | |
| map(.key) | |
' | |
exit 1 | |
fi | |
if tilt wait --timeout "${wait_timeout}s" --for=condition=Ready "uiresource/playwright:deps"; then | |
echo "Tilt is ready" | |
break | |
else | |
echo "Tilt not ready, retrying..." | |
if [ "${{runner.debug}}" == "1" ]; then | |
tilt dump engine | jq ' | |
.ManifestTargets | |
| to_entries | |
| map({key: (.value.State.RuntimeState.Status // "in_progress"), value: .key}) | |
| group_by(.key) | |
| map({key: .[0].key, value: map(.value)}) | |
| from_entries | |
' | |
fi | |
fi | |
if ((i == max_attempts)); then | |
echo "Reached maximum attempts, exiting" | |
exit 1 | |
fi | |
done | |
yarn playwright test | |
- name: Playwright Markdown Report | |
if: always() && steps.playwright.outcome != 'skipped' | |
id: playwright-md-report | |
shell: bash | |
run: | | |
echo "Markdown report:" | |
echo "------------------" | |
bun run packages/playwright/bin/report-markdown.ts > playwright-report.md | |
cat playwright-report.md | |
echo "------------------" | |
echo "Markdown report end" | |
- uses: mshick/add-pr-comment@v2 | |
if: always() && steps.playwright.outcome != 'skipped' | |
with: | |
message-id: playwright-report | |
refresh-message-position: true | |
message-path: | | |
playwright-report.md | |
- name: Tilt Down | |
# always run tilt down if tilt ci started | |
if: always() && steps.playwright.outcome != 'skipped' | |
shell: bash | |
run: tilt down | |
- name: Playwright Report | |
uses: actions/upload-artifact@v4 | |
if: always() && steps.playwright.outcome == 'failure' | |
with: | |
name: playwright-report | |
path: packages/playwright/playwright-report/ | |
retention-days: 30 | |
- name: Playwright Test Results | |
uses: actions/upload-artifact@v4 | |
if: always() && steps.playwright.outcome == 'failure' | |
with: | |
name: playwright-test-results | |
path: packages/playwright/test-results/ | |
retention-days: 30 | |
vercel-deploy-preview: | |
# **always** skip if on dev and main since it will be deployed with another workflow | |
if: ${{ github.ref != 'refs/heads/dev' && github.ref != 'refs/heads/main' && github.head_ref != 'dev' && github.head_ref != 'main' }} | |
runs-on: ubuntu-latest | |
needs: [cache-deps] | |
permissions: | |
pull-requests: write | |
env: | |
VERCEL_ORG_ID: ${{ secrets.VERCEL_ORG_ID }} | |
VERCEL_PROJECT_ID: ${{ secrets.VERCEL_PROJECT_ID }} | |
steps: | |
- uses: actions/checkout@v4 | |
with: | |
submodules: recursive | |
- name: Setup Environment | |
uses: ./.github/actions/setup-env | |
with: | |
yarn-install: false | |
env: | |
YARN_ENABLE_HARDENED_MODE: 0 | |
- name: Load Next.js Build Cache | |
uses: actions/download-artifact@v4 | |
with: | |
name: nextjs-build | |
path: ${{ github.workspace }}/apps/next/.next | |
- name: Extract branch name | |
id: extract-branch | |
uses: ./.github/actions/extract-branch | |
- name: Set Public Hostname | |
id: public-hostname | |
run: echo "public-hostname=sendapp-${{steps.extract-branch.outputs.branch}}-0xsend.vercel.app" >> $GITHUB_OUTPUT | |
- name: Vercel Deploy Preview with Supabase Branch | |
if: github.base_ref == 'dev' | |
id: vercel-deploy-with-branch | |
uses: ./.github/actions/vercel-deploy | |
with: | |
vercel-token: ${{ secrets.VERCEL_TOKEN }} | |
public-hostname: ${{ steps.public-hostname.outputs.public-hostname }} | |
deploy-preview-extra-args: >- | |
-e SUPABASE_DB_URL="${{ secrets.STAGING_SUPABASE_DB_URL }}" | |
-e SUPABASE_JWT_SECRET="${{ secrets.STAGING_SUPABASE_JWT_SECRET }}" | |
-e SUPABASE_SERVICE_ROLE="${{ secrets.STAGING_SUPABASE_SERVICE_ROLE }}" | |
-e NEXT_PUBLIC_SUPABASE_URL="https://${{ secrets.STAGING_SUPABASE_PROJECT_ID }}.supabase.co" | |
-e NEXT_PUBLIC_SUPABASE_PROJECT_ID="${{ secrets.STAGING_SUPABASE_PROJECT_ID }}" | |
-e NEXT_PUBLIC_SUPABASE_GRAPHQL_URL="https://${{ secrets.STAGING_SUPABASE_PROJECT_ID }}.supabase.co/graphql" | |
-e NEXT_PUBLIC_BASE_CHAIN_ID="84532" | |
-e NEXT_PUBLIC_MAINNET_CHAIN_ID="11155111" | |
-e NEXT_PUBLIC_BASE_RPC_URL="${{ secrets.BASE_SEPOLIA_RPC_URL }}" | |
-e NEXT_PUBLIC_MAINNET_RPC_URL="https://ethereum-sepolia-rpc.publicnode.com" | |
-e NEXT_PUBLIC_SUPABASE_ANON_KEY="eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJzdXBhYmFzZSIsInJlZiI6InVncXRvdWxleGh2YWhldnN5c3VxIiwicm9sZSI6ImFub24iLCJpYXQiOjE2OTMwOTE5MzUsImV4cCI6MjAwODY2NzkzNX0.RL8W-jw2rsDhimYl8KklF2B9bNTPQ-Kj5zZA0XlufUA" | |
env: | |
VERCEL_ORG_ID: ${{ secrets.VERCEL_ORG_ID }} | |
VERCEL_PROJECT_ID: ${{ secrets.VERCEL_PROJECT_ID }} | |
VERCEL_GIT_COMMIT_SHA: ${{ github.sha }} | |
VERCEL_GIT_COMMIT_REF: ${{ github.head_ref }} | |
VERCEL_GIT_PULL_REQUEST_ID: ${{ github.event.pull_request.number }} | |
SUPABASE_DB_URL: ${{ secrets.STAGING_SUPABASE_DB_URL }} | |
SUPABASE_JWT_SECRET: ${{ secrets.STAGING_SUPABASE_JWT_SECRET }} | |
SUPABASE_SERVICE_ROLE: ${{ secrets.STAGING_SUPABASE_SERVICE_ROLE }} | |
NEXT_PUBLIC_SUPABASE_URL: https://${{ secrets.STAGING_SUPABASE_PROJECT_ID }}.supabase.co | |
NEXT_PUBLIC_SUPABASE_PROJECT_ID: ${{ secrets.STAGING_SUPABASE_PROJECT_ID }} | |
NEXT_PUBLIC_SUPABASE_GRAPHQL_URL: https://${{ secrets.STAGING_SUPABASE_PROJECT_ID }}.supabase.co/graphql | |
NEXT_PUBLIC_BASE_CHAIN_ID: 84532 | |
NEXT_PUBLIC_MAINNET_CHAIN_ID: 11155111 | |
NEXT_PUBLIC_BASE_RPC_URL: ${{ secrets.BASE_SEPOLIA_RPC_URL }} | |
NEXT_PUBLIC_MAINNET_RPC_URL: https://ethereum-sepolia-rpc.publicnode.com | |
NEXT_PUBLIC_SUPABASE_ANON_KEY: eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJzdXBhYmFzZSIsInJlZiI6InVncXRvdWxleGh2YWhldnN5c3VxIiwicm9sZSI6ImFub24iLCJpYXQiOjE2OTMwOTE5MzUsImV4cCI6MjAwODY2NzkzNX0.RL8W-jw2rsDhimYl8KklF2B9bNTPQ-Kj5zZA0XlufUA | |
- name: Vercel Deploy Preview | |
if: github.base_ref != 'dev' | |
id: vercel-deploy-preview | |
uses: ./.github/actions/vercel-deploy | |
with: | |
vercel-token: ${{ secrets.VERCEL_TOKEN }} | |
public-hostname: ${{ steps.public-hostname.outputs.public-hostname }} | |
env: | |
VERCEL_ORG_ID: ${{ secrets.VERCEL_ORG_ID }} | |
VERCEL_PROJECT_ID: ${{ secrets.VERCEL_PROJECT_ID }} | |
VERCEL_GIT_COMMIT_SHA: ${{ github.sha }} | |
VERCEL_GIT_COMMIT_REF: ${{ github.head_ref }} | |
VERCEL_GIT_PULL_REQUEST_ID: ${{ github.event.pull_request.number }} | |
- uses: mshick/add-pr-comment@v2 | |
if: github.base_ref == 'dev' | |
with: | |
message-id: vercel-preview-url | |
refresh-message-position: true | |
message: | | |
Vercel Unique URL: [${{ steps.vercel-deploy-with-branch.outputs.deployment-url }}](${{ steps.vercel-deploy-with-branch.outputs.deployment-url }}) | |
Vercel Preview URL: [${{ steps.public-hostname.outputs.public-hostname }}](https://${{ steps.public-hostname.outputs.public-hostname }}/) | |
Last Commit: ${{ github.event.pull_request.head.sha }} | |
- uses: mshick/add-pr-comment@v2 | |
if: github.base_ref != 'dev' | |
with: | |
message-id: vercel-preview-url | |
refresh-message-position: true | |
message: | | |
Vercel Unique URL: [${{ steps.vercel-deploy-preview.outputs.deployment-url }}](${{ steps.vercel-deploy-preview.outputs.deployment-url }}) | |
Vercel Preview URL: [${{ steps.public-hostname.outputs.public-hostname }}](https://${{ steps.public-hostname.outputs.public-hostname }}/) | |
Last Commit: ${{ github.event.pull_request.head.sha }} |