Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
56 changes: 32 additions & 24 deletions .github/workflows/ci_e2e_walletkit.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -22,11 +22,6 @@ on:
required: false
default: 'pay'
type: string
app-id:
description: 'App bundle ID / package name for Maestro'
required: false
default: 'com.walletconnect.web3wallet.rnsample.internal'
type: string
platform:
description: 'Platform to run tests on'
required: false
Expand All @@ -39,7 +34,7 @@ on:

env:
MAESTRO_TAGS: ${{ inputs.maestro-tags || 'pay' }}
MAESTRO_APP_ID: ${{ inputs.app-id || 'com.walletconnect.web3wallet.rnsample.internal' }}
MAESTRO_APP_ID: com.walletconnect.web3wallet.rnsample.internal
ROOT_PATH: wallets/rn_cli_wallet

jobs:
Expand All @@ -63,6 +58,11 @@ jobs:
sudo xcode-select -s "$XCODE_PATH"
xcodebuild -version

- name: Setup SSH for Match
uses: webfactory/ssh-agent@v0.9.0
with:
ssh-private-key: ${{ secrets.MATCH_SSH_KEY }}

- name: Setup
uses: ./.github/actions/ci-setup
with:
Expand All @@ -76,6 +76,7 @@ jobs:
fi
echo "${{ secrets.WALLETKIT_ENV_FILE }}" > ${{ env.ROOT_PATH }}/.env
echo "ENV_TEST_PRIVATE_KEY=${{ secrets.TEST_WALLET_PRIVATE_KEY }}" >> ${{ env.ROOT_PATH }}/.env
echo "ENV_TEST_MODE=true" >> ${{ env.ROOT_PATH }}/.env

- name: Install Ruby
uses: ruby/setup-ruby@v1
Expand Down Expand Up @@ -114,6 +115,11 @@ jobs:
BUILD_FOR_SIMULATOR: true
PODS_CACHE_HIT: ${{ steps.pods-cache.outputs.cache-hit }}
SENTRY_DISABLE_AUTO_UPLOAD: true
APPLE_KEY_ID: ${{ secrets.APPLE_KEY_ID }}
APPLE_KEY_CONTENT: ${{ secrets.APPLE_KEY_CONTENT }}
APPLE_ISSUER_ID: ${{ secrets.APPLE_ISSUER_ID }}
MATCH_GIT_URL: ${{ secrets.MATCH_GIT_URL }}
MATCH_PASSWORD: ${{ secrets.MATCH_KEYCHAIN_PASSWORD }}

- name: Find .app path
run: |
Expand All @@ -136,22 +142,18 @@ jobs:
curl -fsSL "https://get.maestro.mobile.dev" | bash
echo "$HOME/.maestro/bin" >> "$GITHUB_PATH"

- name: Create payment via API
id: payment
run: bash scripts/create-payment.sh
env:
WPAY_CUSTOMER_KEY: ${{ secrets.WPAY_CUSTOMER_KEY }}
WPAY_MERCHANT_ID: ${{ secrets.WPAY_MERCHANT_ID }}

- name: Set payment URL in simulator clipboard
run: echo "${{ steps.payment.outputs.gateway_url }}" | xcrun simctl pbcopy "$DEVICE_ID"

- name: Run Maestro tests
id: maestro
run: |
set -o pipefail
maestro test \
--env APP_ID="${{ env.MAESTRO_APP_ID }}" \
--env WPAY_CUSTOMER_KEY_MULTI_KYC="${{ secrets.WPAY_CUSTOMER_KEY_MULTI_KYC }}" \
--env WPAY_MERCHANT_ID_MULTI_KYC="${{ secrets.WPAY_MERCHANT_ID_MULTI_KYC }}" \
--env WPAY_CUSTOMER_KEY_MULTI_NOKYC="${{ secrets.WPAY_CUSTOMER_KEY_MULTI_NOKYC }}" \
--env WPAY_MERCHANT_ID_MULTI_NOKYC="${{ secrets.WPAY_MERCHANT_ID_MULTI_NOKYC }}" \
--env WPAY_CUSTOMER_KEY_SINGLE_NOKYC="${{ secrets.WPAY_CUSTOMER_KEY_SINGLE_NOKYC }}" \
--env WPAY_MERCHANT_ID_SINGLE_NOKYC="${{ secrets.WPAY_MERCHANT_ID_SINGLE_NOKYC }}" \
--include-tags "${{ env.MAESTRO_TAGS }}" \
--test-output-dir maestro-artifacts \
--debug-output maestro-artifacts \
Expand Down Expand Up @@ -251,6 +253,12 @@ jobs:
- name: Accept Android Licenses
uses: SimonMarquis/android-accept-licenses@8d8deab5b7ab2aaea9ed69f0b802e53173f21fd1 # v1

- name: Add Secrets file
run: echo "${{ secrets.ANDROID_SECRETS_FILE }}" > ${{ env.ROOT_PATH }}/android/secrets.properties

- name: Add Keystore file
run: echo ${{ secrets.WC_INTERNAL_KEYSTORE }} | base64 --decode >> ${{ env.ROOT_PATH }}/android/app/${{ vars.WC_INTERNAL_KEYSTORE_NAME }}.keystore

- name: Optimize Gradle for CI
run: |
echo "org.gradle.jvmargs=-Xmx4096m -XX:MaxMetaspaceSize=1024m" >> ${{ env.ROOT_PATH }}/android/gradle.properties
Expand All @@ -276,6 +284,12 @@ jobs:
id: build
run: cd ${{ env.ROOT_PATH }} && export SENTRY_DISABLE_AUTO_UPLOAD=true && yarn run android:build:internal

- name: Free disk space
run: |
sudo rm -rf /usr/share/dotnet /usr/local/lib/android/sdk/ndk /opt/ghc /usr/local/share/boost
sudo apt-get clean
df -h

- name: Enable KVM
run: |
echo 'KERNEL=="kvm", GROUP="kvm", MODE="0666", OPTIONS+="static_node=kvm"' | sudo tee /etc/udev/rules.d/99-kvm4all.rules
Expand All @@ -287,13 +301,6 @@ jobs:
curl -fsSL "https://get.maestro.mobile.dev" | bash
echo "$HOME/.maestro/bin" >> "$GITHUB_PATH"

- name: Create payment via API
id: payment
run: bash scripts/create-payment.sh
env:
WPAY_CUSTOMER_KEY: ${{ secrets.WPAY_CUSTOMER_KEY }}
WPAY_MERCHANT_ID: ${{ secrets.WPAY_MERCHANT_ID }}

- name: Run E2E tests on Android Emulator
id: maestro
uses: reactivecircus/android-emulator-runner@70f4dee990796918b78d040e3278474bdbd348a7 # v2
Expand All @@ -303,14 +310,15 @@ jobs:
target: default
avd-name: test_device
ram-size: 4096M
disk-size: 4096M
heap-size: 576M
emulator-boot-timeout: 900
force-avd-creation: false
emulator-options: -no-snapshot-save -no-window -gpu swiftshader_indirect -noaudio -no-boot-anim -no-snapshot-load
disable-animations: true
script: |
adb install ${{ env.ROOT_PATH }}/android/app/build/outputs/apk/internal/app-internal.apk
$HOME/.maestro/bin/maestro test --env APP_ID="${{ env.MAESTRO_APP_ID }}" --env GATEWAY_URL="${{ steps.payment.outputs.gateway_url }}" --include-tags "${{ env.MAESTRO_TAGS }}" --test-output-dir maestro-artifacts --debug-output maestro-artifacts .maestro/ >maestro-output.log 2>&1; echo $? > maestro-exit-code
$HOME/.maestro/bin/maestro test --env APP_ID="${{ env.MAESTRO_APP_ID }}" --env WPAY_CUSTOMER_KEY_MULTI_KYC="${{ secrets.WPAY_CUSTOMER_KEY_MULTI_KYC }}" --env WPAY_MERCHANT_ID_MULTI_KYC="${{ secrets.WPAY_MERCHANT_ID_MULTI_KYC }}" --env WPAY_CUSTOMER_KEY_MULTI_NOKYC="${{ secrets.WPAY_CUSTOMER_KEY_MULTI_NOKYC }}" --env WPAY_MERCHANT_ID_MULTI_NOKYC="${{ secrets.WPAY_MERCHANT_ID_MULTI_NOKYC }}" --env WPAY_CUSTOMER_KEY_SINGLE_NOKYC="${{ secrets.WPAY_CUSTOMER_KEY_SINGLE_NOKYC }}" --env WPAY_MERCHANT_ID_SINGLE_NOKYC="${{ secrets.WPAY_MERCHANT_ID_SINGLE_NOKYC }}" --include-tags "${{ env.MAESTRO_TAGS }}" --test-output-dir maestro-artifacts --debug-output maestro-artifacts .maestro/ >maestro-output.log 2>&1; echo $? > maestro-exit-code
cat maestro-output.log
exit $(cat maestro-exit-code)

Expand Down
67 changes: 57 additions & 10 deletions .github/workflows/e2e-balance-check.yml
Original file line number Diff line number Diff line change
Expand Up @@ -11,10 +11,12 @@ permissions:
env:
BASE_USDC: '0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913'
BASE_RPC: 'https://mainnet.base.org'
OP_USDC: '0x0b2C639c533813f4Aa9D7837CAf62653d097Ff85'
OP_RPC: 'https://mainnet.optimism.io'

jobs:
check-balance:
name: Check E2E Wallet USDC Balance
name: Check E2E Wallet Balances
runs-on: ubuntu-latest
env:
SLACK_FAUCETBOT_WEBHOOK_URL: ${{ secrets.SLACK_FAUCETBOT_WEBHOOK_URL }}
Expand All @@ -27,13 +29,13 @@ jobs:
run: |
BALANCE=$(cast call --rpc-url "$BASE_RPC" "$BASE_USDC" \
"balanceOf(address)(uint256)" \
"${{ vars.TEST_WALLET_ADDRESS }}" | awk '{print $1}')
"${{ vars.TEST_WALLET_ADDRESS }}" | tr -d '[:space:]')
echo "balance=$BALANCE" >> $GITHUB_OUTPUT
BALANCE_HUMAN=$(echo "scale=2; $BALANCE / 1000000" | bc)
echo "USDC on Base: $BALANCE_HUMAN ($BALANCE raw)"

- name: Prepare alert
id: alert
- name: Prepare USDC alert
id: usdc_alert
run: |
BALANCE="${{ steps.usdc_balance.outputs.balance }}"
THRESHOLD="${{ vars.USDC_THRESHOLD_UNITS || '500000' }}"
Expand All @@ -47,22 +49,67 @@ jobs:
echo "::warning::$ALERT_TEXT"
fi

- name: Send Slack alert
- name: Send Slack alert (USDC)
if: |
steps.alert.outputs.should_alert == 'true' &&
steps.usdc_alert.outputs.should_alert == 'true' &&
env.SLACK_FAUCETBOT_WEBHOOK_URL != ''
uses: slackapi/slack-github-action@b0fa283ad8fea605de13dc3f449259339835fc52 # v2.1.0
with:
webhook: ${{ env.SLACK_FAUCETBOT_WEBHOOK_URL }}
webhook-type: incoming-webhook
payload: |
{
"text": "${{ steps.alert.outputs.text }}"
"text": "${{ steps.usdc_alert.outputs.text }}"
}

- name: Skip Slack alert (no webhook)
- name: Skip Slack alert (USDC - no webhook)
if: |
steps.alert.outputs.should_alert == 'true' &&
steps.usdc_alert.outputs.should_alert == 'true' &&
env.SLACK_FAUCETBOT_WEBHOOK_URL == ''
run: |
echo "::warning::SLACK_FAUCETBOT_WEBHOOK_URL not configured, skipping alert"
echo "::warning::SLACK_FAUCETBOT_WEBHOOK_URL not configured, skipping USDC alert"

- name: Check USDC balance on Optimism
id: op_usdc_balance
run: |
BALANCE=$(cast call --rpc-url "$OP_RPC" "$OP_USDC" \
"balanceOf(address)(uint256)" \
"${{ vars.TEST_WALLET_ADDRESS }}" | tr -d '[:space:]')
echo "balance=$BALANCE" >> $GITHUB_OUTPUT
BALANCE_HUMAN=$(echo "scale=2; $BALANCE / 1000000" | bc)
echo "USDC on Optimism: $BALANCE_HUMAN ($BALANCE raw)"

- name: Prepare USDC on Optimism alert
id: op_usdc_alert
run: |
BALANCE="${{ steps.op_usdc_balance.outputs.balance }}"
THRESHOLD="${{ vars.USDC_THRESHOLD_UNITS || '500000' }}"
if [ "$BALANCE" -lt "$THRESHOLD" ]; then
BALANCE_HUMAN=$(echo "scale=2; $BALANCE / 1000000" | bc)
THRESHOLD_HUMAN=$(echo "scale=2; $THRESHOLD / 1000000" | bc)
ALERT_TEXT="[request] Can i have ${THRESHOLD_HUMAN} USDC on Optimism in wallet: \
${{ vars.TEST_WALLET_ADDRESS }}"
echo "should_alert=true" >> "$GITHUB_OUTPUT"
echo "text=$ALERT_TEXT" >> "$GITHUB_OUTPUT"
echo "::warning::$ALERT_TEXT"
fi

- name: Send Slack alert (USDC on Optimism)
if: |
steps.op_usdc_alert.outputs.should_alert == 'true' &&
env.SLACK_FAUCETBOT_WEBHOOK_URL != ''
uses: slackapi/slack-github-action@b0fa283ad8fea605de13dc3f449259339835fc52 # v2.1.0
with:
webhook: ${{ env.SLACK_FAUCETBOT_WEBHOOK_URL }}
webhook-type: incoming-webhook
payload: |
{
"text": "${{ steps.op_usdc_alert.outputs.text }}"
}

- name: Skip Slack alert (USDC on Optimism - no webhook)
if: |
steps.op_usdc_alert.outputs.should_alert == 'true' &&
env.SLACK_FAUCETBOT_WEBHOOK_URL == ''
run: |
echo "::warning::SLACK_FAUCETBOT_WEBHOOK_URL not configured, skipping Optimism USDC alert"
30 changes: 30 additions & 0 deletions .maestro/flows/pay_confirm_and_verify.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
appId: ${APP_ID}
---
# Shared flow: Tap Pay, verify loading, wait for success, tap "Got it!"

# On review screen, tap Pay button
- extendedWaitUntil:
visible:
id: "pay-button-pay"
timeout: 10000
- tapOn:
id: "pay-button-pay"

# Verify confirming screen (optional — may flash by quickly)
- runFlow:
when:
visible:
id: "pay-loading-message"
commands:
- assertVisible:
id: "pay-loading-message"

# Wait for success screen (generous timeout for on-chain confirmation)
- extendedWaitUntil:
visible:
id: "pay-result-success-icon"
timeout: 30000

# Tap "Got it!" button
- tapOn:
id: "pay-button-result-action"
36 changes: 36 additions & 0 deletions .maestro/flows/pay_open_and_paste_url.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
appId: ${APP_ID}
---
# Shared flow: Launch wallet, open scanner, paste payment URL, wait for merchant info
# Requires: ${output.gateway_url} to be set by a prior runScript step

# Launch wallet app
- launchApp:
appId: ${APP_ID}
permissions:
all: allow

# Tap scan button to open scanner options modal
- tapOn:
id: "button-scan"

# Type the payment URL into the test input field
- tapOn:
id: "input-paste-url"

# Dismiss iOS keyboard language prompt if it appears
- runFlow:
when:
visible: "Continue"
commands:
- tapOn: "Continue"

- inputText: ${output.gateway_url}
- pressKey: Enter
- tapOn:
id: "button-submit-url"

# Wait for payment options to load with merchant info
- extendedWaitUntil:
visible:
id: "pay-merchant-info"
timeout: 15000
13 changes: 13 additions & 0 deletions .maestro/flows/pay_open_via_deeplink.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
appId: ${APP_ID}
---
# Shared flow: Open payment URL via deep link and wait for merchant info
# Requires: ${output.gateway_url} to be set by a prior runScript step

# Open the payment URL as a deep link
- openLink: ${output.gateway_url}

# Wait for payment options to load with merchant info
- extendedWaitUntil:
visible:
id: "pay-merchant-info"
timeout: 15000
Loading
Loading