Deploying Frontend / Backend to Staging #12464
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: Deploy Frontend / Backend to Environment | |
| on: | |
| push: | |
| branches: | |
| - main | |
| tags: | |
| - v* | |
| - legacy-signer/v* | |
| workflow_dispatch: | |
| inputs: | |
| network: | |
| required: true | |
| type: choice | |
| description: 'Select the network to deploy to.' | |
| options: | |
| - staging | |
| - beta | |
| - test_fe_1 | |
| - test_fe_2 | |
| - test_fe_3 | |
| - test_fe_4 | |
| - test_fe_5 | |
| - test_fe_6 | |
| - test_be_1 | |
| - audit | |
| canister: | |
| required: true | |
| type: choice | |
| description: 'Select the canister to deploy.' | |
| options: | |
| - frontend | |
| - backend | |
| - signer_frontend | |
| - legacy_signer_frontend | |
| force-backend: | |
| required: false | |
| type: boolean | |
| description: 'Force backend deployment even if no changes are detected.' | |
| default: false | |
| env-override: | |
| required: false | |
| type: string | |
| description: | | |
| Optional .env contents (KEY=VALUE, one per line). | |
| Only applied when network is test_* or audit. | |
| workflow_call: | |
| inputs: | |
| workflow-call: | |
| description: 'To distinguish workflow_call from regular calls' | |
| required: false | |
| type: boolean | |
| default: true | |
| network: | |
| required: true | |
| type: string | |
| canister: | |
| required: false | |
| type: string | |
| default: frontend | |
| secrets: | |
| VITE_ETHERSCAN_API_KEY_STAGING: | |
| required: true | |
| VITE_INFURA_API_KEY_STAGING: | |
| required: true | |
| VITE_ALCHEMY_API_KEY_STAGING: | |
| required: true | |
| VITE_ALCHEMY_API_KEY_TEST_FE: | |
| required: true | |
| VITE_QUICKNODE_API_KEY_STAGING: | |
| required: true | |
| VITE_WALLET_CONNECT_PROJECT_ID_STAGING: | |
| required: true | |
| VITE_COINGECKO_API_KEY_STAGING: | |
| required: true | |
| VITE_PLAUSIBLE_ENABLED_STAGING: | |
| required: true | |
| VITE_EARNING_ENABLED_STAGING: | |
| required: true | |
| VITE_AI_ASSISTANT_CONSOLE_ENABLED_STAGING: | |
| required: true | |
| VITE_UNIVERSAL_SCANNER_ENABLED_STAGING: | |
| required: true | |
| VITE_OCP_PAY_WITH_BTC_ENABLED_STAGING: | |
| required: true | |
| VITE_ONRAMPER_API_KEY_DEV_STAGING: | |
| required: true | |
| VITE_ONRAMPER_API_KEY_PROD_STAGING: | |
| required: true | |
| VITE_AUTH_ALTERNATIVE_ORIGINS_STAGING: | |
| required: true | |
| DFX_DEPLOY_KEY_STAGING: | |
| required: true | |
| VITE_ETHERSCAN_API_KEY_BETA: | |
| required: true | |
| VITE_INFURA_API_KEY_BETA: | |
| required: true | |
| VITE_ALCHEMY_API_KEY_BETA: | |
| required: true | |
| VITE_QUICKNODE_API_KEY_BETA: | |
| required: true | |
| VITE_WALLET_CONNECT_PROJECT_ID_BETA: | |
| required: true | |
| VITE_COINGECKO_API_KEY_BETA: | |
| required: true | |
| VITE_AUTH_ALTERNATIVE_ORIGINS_BETA: | |
| required: true | |
| VITE_ONRAMPER_API_KEY_DEV_BETA: | |
| required: true | |
| VITE_PLAUSIBLE_ENABLED_BETA: | |
| required: true | |
| VITE_EARNING_ENABLED_BETA: | |
| required: true | |
| VITE_AI_ASSISTANT_CONSOLE_ENABLED_BETA: | |
| required: true | |
| VITE_UNIVERSAL_SCANNER_ENABLED_BETA: | |
| required: true | |
| VITE_OCP_PAY_WITH_BTC_ENABLED_BETA: | |
| required: true | |
| VITE_ONRAMPER_API_KEY_PROD_BETA: | |
| required: true | |
| DFX_DEPLOY_KEY_BETA: | |
| required: true | |
| run-name: >- | |
| ${{ | |
| github.event_name == 'push' && github.ref_type == 'branch' && 'Deploying Frontend / Backend to Staging' | |
| || github.event_name == 'push' && github.ref_type == 'tag' && startsWith(github.ref, 'refs/tags/legacy-signer/') && format('Deploying Legacy Signer Frontend to Beta ({0})', github.ref_name) | |
| || github.event_name == 'push' && github.ref_type == 'tag' && 'Deploying Frontend / Backend to Beta' | |
| || github.event.inputs.canister == 'backend' && github.event.inputs.force-backend == 'true' && format('Deploying {0} to {1} and force backend = {2}', inputs.canister, inputs.network, inputs.force-backend) | |
| || format('Deploying {0} to {1}', inputs.canister, inputs.network) }} | |
| concurrency: | |
| group: ${{ github.workflow }}-${{ github.ref }}-${{ github.event_name }}-${{ github.event.inputs.network }}-${{ github.event.inputs.canister }} | |
| cancel-in-progress: false | |
| permissions: {} | |
| env: | |
| DFX_WARNING: '-mainnet_plaintext_identity' | |
| jobs: | |
| deployment: | |
| runs-on: ubuntu-24.04 | |
| permissions: | |
| contents: read | |
| steps: | |
| - name: Determine Deployment Network | |
| run: | | |
| echo "deploy_frontend=false" >> $GITHUB_ENV | |
| echo "deploy_backend=false" >> $GITHUB_ENV | |
| echo "deploy_signer=false" >> $GITHUB_ENV | |
| echo "deploy_all_signers=false" >> $GITHUB_ENV | |
| if [ "$WORKFLOW_CALL" == "true" ]; then | |
| echo "NETWORK=$NETWORK_CALL" >> $GITHUB_ENV | |
| echo "CANISTER=$CANISTER_CALL" >> $GITHUB_ENV | |
| case "$CANISTER_CALL" in | |
| signer_frontend|legacy_signer_frontend) | |
| echo "deploy_signer=true" >> $GITHUB_ENV | |
| ;; | |
| *) | |
| echo "deploy_frontend=true" >> $GITHUB_ENV | |
| echo "deploy_backend=true" >> $GITHUB_ENV | |
| ;; | |
| esac | |
| elif [ "${{ github.event_name }}" == "push" ]; then | |
| if [ "$REF_TYPE" == "branch" ]; then | |
| echo "NETWORK=staging" >> $GITHUB_ENV | |
| echo "CANISTER=frontend" >> $GITHUB_ENV | |
| echo "deploy_frontend=true" >> $GITHUB_ENV | |
| echo "deploy_backend=true" >> $GITHUB_ENV | |
| echo "deploy_all_signers=true" >> $GITHUB_ENV | |
| elif [ "$REF_TYPE" == "tag" ]; then | |
| echo "NETWORK=beta" >> $GITHUB_ENV | |
| if [[ "$GIT_REF" == refs/tags/legacy-signer/* ]]; then | |
| echo "CANISTER=legacy_signer_frontend" >> $GITHUB_ENV | |
| echo "deploy_signer=true" >> $GITHUB_ENV | |
| else | |
| echo "CANISTER=frontend" >> $GITHUB_ENV | |
| echo "deploy_frontend=true" >> $GITHUB_ENV | |
| echo "deploy_backend=true" >> $GITHUB_ENV | |
| echo "deploy_all_signers=true" >> $GITHUB_ENV | |
| fi | |
| else | |
| echo "Error: Unsupported ref type." | |
| exit 1 | |
| fi | |
| elif [ "${{ github.event_name }}" == "workflow_dispatch" ]; then | |
| echo "NETWORK=$NETWORK" >> $GITHUB_ENV | |
| echo "CANISTER=$CANISTER" >> $GITHUB_ENV | |
| if [ "$CANISTER" = "frontend" ]; then | |
| echo "deploy_frontend=true" >> $GITHUB_ENV | |
| fi | |
| if [ "$CANISTER" = "backend" ]; then | |
| echo "deploy_backend=true" >> $GITHUB_ENV | |
| fi | |
| if [ "$CANISTER" = "signer_frontend" ] || [ "$CANISTER" = "legacy_signer_frontend" ]; then | |
| echo "deploy_signer=true" >> $GITHUB_ENV | |
| fi | |
| else | |
| echo "Error: Unsupported event type." | |
| exit 1 | |
| fi | |
| env: | |
| GIT_REF: ${{ github.ref }} | |
| REF_TYPE: ${{ github.ref_type }} | |
| NETWORK: ${{ github.event.inputs.network }} | |
| CANISTER: ${{ github.event.inputs.canister }} | |
| WORKFLOW_CALL: ${{ inputs.workflow-call }} | |
| NETWORK_CALL: ${{ inputs.network }} | |
| CANISTER_CALL: ${{ inputs.canister }} | |
| - name: Check release policy | |
| run: | | |
| if [[ "$NETWORK" == "staging" ]] && [[ "$REF" != "refs/heads/main" ]] ; then | |
| echo "Only the main branch may be deployed to staging." | |
| exit 1 | |
| fi | |
| if [[ "$NETWORK" = test_fe_* ]] && [[ "$CANISTER" != "frontend" ]] ; then | |
| echo "deploy_backend=false" >> $GITHUB_ENV | |
| echo "Only a frontend may be deployed to test_fe_* networks" | |
| exit 1 | |
| fi | |
| if [[ "$NETWORK" = test_be_* ]] && [[ "$CANISTER" != "backend" ]] ; then | |
| echo "deploy_frontend=false" >> $GITHUB_ENV | |
| echo "Only a backend may be deployed to test_be_* networks" | |
| exit 1 | |
| fi | |
| if [[ "$CANISTER" = signer_* ]] || [[ "$CANISTER" = legacy_signer_* ]]; then | |
| if [[ "$NETWORK" = test_* ]] || [[ "$NETWORK" = "audit" ]]; then | |
| echo "Signer canisters cannot be deployed to test/audit networks." | |
| exit 1 | |
| fi | |
| fi | |
| env: | |
| REF: ${{ github.ref }} | |
| - name: Checkout | |
| uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2 | |
| with: | |
| fetch-depth: 2 | |
| persist-credentials: false | |
| - name: Fetch base branch | |
| run: | | |
| git fetch origin "$BASE_REF:$BASE_REF" | |
| env: | |
| BASE_REF: ${{ github.base_ref }} | |
| - name: Set Output Variables Based on Network (with optional overrides) | |
| id: set-outputs | |
| run: | | |
| # Parse optional .env overrides into an associative array | |
| declare -A OV | |
| parse_overrides() { | |
| local raw="$1" | |
| # normalize CRLF | |
| raw="${raw//$'\r'/}" | |
| while IFS= read -r line; do | |
| # skip blanks and comments | |
| [[ -z "$line" || "$line" =~ ^[[:space:]]*# ]] && continue | |
| # allow KEY='VALUE with = inside' | |
| local key val | |
| key="${line%%=*}" | |
| val="${line#*=}" | |
| # trim spaces | |
| key="$(echo "$key" | sed 's/^[[:space:]]*//;s/[[:space:]]*$//')" | |
| val="$(echo "$val" | sed 's/^[[:space:]]*//;s/[[:space:]]*$//')" | |
| # strip surrounding quotes | |
| if [[ "$val" =~ ^\"(.*)\"$ ]]; then val="${BASH_REMATCH[1]}"; fi | |
| if [[ "$val" =~ ^\'(.*)\'$ ]]; then val="${BASH_REMATCH[1]}"; fi | |
| [[ -n "$key" ]] && OV["$key"]="$val" | |
| done <<< "$raw" | |
| } | |
| # Hide all override values (and raw lines) in logs | |
| mask_overrides() { | |
| # Mask the full raw input lines too (defense-in-depth) | |
| while IFS= read -r line; do | |
| [[ -n "$line" ]] && echo "::add-mask::$line" | |
| done <<< "${ENV_OVERRIDE:-}" | |
| # Mask each value | |
| for v in "${OV[@]}"; do | |
| [[ -n "$v" ]] && echo "::add-mask::$v" | |
| done | |
| } | |
| # Only allow overrides for test_* or audit | |
| if ([[ "$NETWORK" = test_* ]] || [[ "$NETWORK" = "audit" ]]) && [[ -n "${ENV_OVERRIDE:-}" ]]; then | |
| parse_overrides "$ENV_OVERRIDE" | |
| mask_overrides | |
| echo "Overrides provided; applying permitted keys." | |
| fi | |
| # Prefer override if present, else default | |
| get() { | |
| local key="$1" default="$2" | |
| if [[ ${OV[$key]+isset} ]]; then | |
| echo "${OV[$key]}" | |
| else | |
| echo "$default" | |
| fi | |
| } | |
| # Select ALCHEMY per network | |
| if [[ "$NETWORK" = test_* ]] || [[ "$NETWORK" = "audit" ]]; then | |
| echo "VITE_ALCHEMY_API_KEY=$(get VITE_ALCHEMY_API_KEY "$VITE_ALCHEMY_API_KEY_TEST_FE")" >> $GITHUB_OUTPUT | |
| elif [[ "$NETWORK" == "staging" ]]; then | |
| echo "VITE_ALCHEMY_API_KEY=$VITE_ALCHEMY_API_KEY_STAGING" >> $GITHUB_OUTPUT | |
| elif [[ "$NETWORK" == "beta" ]]; then | |
| echo "VITE_ALCHEMY_API_KEY=$VITE_ALCHEMY_API_KEY_BETA" >> $GITHUB_OUTPUT | |
| fi | |
| # For staging/test/audit common vars default to STAGING, but allow overrides: | |
| if [[ "$NETWORK" == "staging" ]] || [[ "$NETWORK" = test_* ]] || [[ "$NETWORK" = "audit" ]]; then | |
| { | |
| echo "VITE_ETHERSCAN_API_KEY=$(get VITE_ETHERSCAN_API_KEY "$VITE_ETHERSCAN_API_KEY_STAGING")" | |
| echo "VITE_INFURA_API_KEY=$(get VITE_INFURA_API_KEY "$VITE_INFURA_API_KEY_STAGING")" | |
| echo "VITE_QUICKNODE_API_KEY=$(get VITE_QUICKNODE_API_KEY "$VITE_QUICKNODE_API_KEY_STAGING")" | |
| echo "VITE_WALLET_CONNECT_PROJECT_ID=$(get VITE_WALLET_CONNECT_PROJECT_ID "$VITE_WALLET_CONNECT_PROJECT_ID_STAGING")" | |
| echo "VITE_COINGECKO_API_KEY=$(get VITE_COINGECKO_API_KEY "$VITE_COINGECKO_API_KEY_STAGING")" | |
| echo "VITE_ONRAMPER_API_KEY_DEV=$(get VITE_ONRAMPER_API_KEY_DEV "$VITE_ONRAMPER_API_KEY_DEV_STAGING")" | |
| echo "VITE_ONRAMPER_API_KEY_PROD=$(get VITE_ONRAMPER_API_KEY_PROD "$VITE_ONRAMPER_API_KEY_PROD_STAGING")" | |
| echo "VITE_PLAUSIBLE_ENABLED=$(get VITE_PLAUSIBLE_ENABLED "$VITE_PLAUSIBLE_ENABLED_STAGING")" | |
| echo "VITE_EARNING_ENABLED=$(get VITE_EARNING_ENABLED "$VITE_EARNING_ENABLED_STAGING")" | |
| echo "VITE_AI_ASSISTANT_CONSOLE_ENABLED=$(get VITE_AI_ASSISTANT_CONSOLE_ENABLED "$VITE_AI_ASSISTANT_CONSOLE_ENABLED_STAGING")" | |
| echo "VITE_UNIVERSAL_SCANNER_ENABLED=$(get VITE_UNIVERSAL_SCANNER_ENABLED "$VITE_UNIVERSAL_SCANNER_ENABLED_STAGING")" | |
| echo "VITE_OCP_PAY_WITH_BTC_ENABLED=$(get VITE_OCP_PAY_WITH_BTC_ENABLED "$VITE_OCP_PAY_WITH_BTC_ENABLED_STAGING")" | |
| } >> $GITHUB_OUTPUT | |
| # Special handling for AUTH_ALTERNATIVE_ORIGINS: | |
| # If override provided, use it as-is. Else keep your existing substitution. | |
| if [[ -n "${OV[VITE_AUTH_ALTERNATIVE_ORIGINS]+x}" ]]; then | |
| echo "VITE_AUTH_ALTERNATIVE_ORIGINS=${OV[VITE_AUTH_ALTERNATIVE_ORIGINS]}" >> $GITHUB_OUTPUT | |
| else | |
| if [[ "$NETWORK" == "staging" ]]; then | |
| echo "VITE_AUTH_ALTERNATIVE_ORIGINS=$VITE_AUTH_ALTERNATIVE_ORIGINS_STAGING" >> $GITHUB_OUTPUT | |
| else | |
| SUBDOMAIN="fe${NETWORK#test_fe_}" # E.g. test_fe_1 -> fe1 | |
| echo "VITE_AUTH_ALTERNATIVE_ORIGINS=$(echo "$VITE_AUTH_ALTERNATIVE_ORIGINS_STAGING" | sed "s/staging/$SUBDOMAIN/g")" >> $GITHUB_OUTPUT | |
| fi | |
| fi | |
| { | |
| echo "DFX_DEPLOY_KEY<<EOF" | |
| echo "$DFX_DEPLOY_KEY_STAGING" | |
| echo "EOF" | |
| } >> "$GITHUB_OUTPUT" | |
| elif [[ "$NETWORK" == "beta" ]]; then | |
| { | |
| echo "VITE_ETHERSCAN_API_KEY=$VITE_ETHERSCAN_API_KEY_BETA" | |
| echo "VITE_INFURA_API_KEY=$VITE_INFURA_API_KEY_BETA" | |
| echo "VITE_QUICKNODE_API_KEY=$VITE_QUICKNODE_API_KEY_BETA" | |
| echo "VITE_WALLET_CONNECT_PROJECT_ID=$VITE_WALLET_CONNECT_PROJECT_ID_BETA" | |
| echo "VITE_COINGECKO_API_KEY=$VITE_COINGECKO_API_KEY_BETA" | |
| echo "VITE_AUTH_ALTERNATIVE_ORIGINS=$VITE_AUTH_ALTERNATIVE_ORIGINS_BETA" | |
| echo "VITE_ONRAMPER_API_KEY_DEV=$VITE_ONRAMPER_API_KEY_DEV_BETA" | |
| echo "VITE_ONRAMPER_API_KEY_PROD=$VITE_ONRAMPER_API_KEY_PROD_BETA" | |
| echo "VITE_PLAUSIBLE_ENABLED=$VITE_PLAUSIBLE_ENABLED_BETA" | |
| echo "VITE_EARNING_ENABLED=$VITE_EARNING_ENABLED_BETA" | |
| echo "VITE_AI_ASSISTANT_CONSOLE_ENABLED=$VITE_AI_ASSISTANT_CONSOLE_ENABLED_BETA" | |
| echo "VITE_UNIVERSAL_SCANNER_ENABLED=$VITE_UNIVERSAL_SCANNER_ENABLED_BETA" | |
| echo "VITE_OCP_PAY_WITH_BTC_ENABLED=$VITE_OCP_PAY_WITH_BTC_ENABLED_BETA" | |
| } >> $GITHUB_OUTPUT | |
| { | |
| echo "DFX_DEPLOY_KEY<<EOF" | |
| echo "$DFX_DEPLOY_KEY_BETA" | |
| echo "EOF" | |
| } >> "$GITHUB_OUTPUT" | |
| fi | |
| env: | |
| ENV_OVERRIDE: ${{ github.event.inputs.env-override }} | |
| VITE_ETHERSCAN_API_KEY_STAGING: ${{ secrets.VITE_ETHERSCAN_API_KEY_STAGING }} | |
| VITE_INFURA_API_KEY_STAGING: ${{ secrets.VITE_INFURA_API_KEY_STAGING }} | |
| VITE_ALCHEMY_API_KEY_STAGING: ${{ secrets.VITE_ALCHEMY_API_KEY_STAGING }} | |
| VITE_ALCHEMY_API_KEY_TEST_FE: ${{ secrets.VITE_ALCHEMY_API_KEY_TEST_FE }} | |
| VITE_QUICKNODE_API_KEY_STAGING: ${{ secrets.VITE_QUICKNODE_API_KEY_STAGING }} | |
| VITE_WALLET_CONNECT_PROJECT_ID_STAGING: ${{ secrets.VITE_WALLET_CONNECT_PROJECT_ID_STAGING }} | |
| VITE_COINGECKO_API_KEY_STAGING: ${{ secrets.VITE_COINGECKO_API_KEY_STAGING }} | |
| VITE_PLAUSIBLE_ENABLED_STAGING: ${{ secrets.VITE_PLAUSIBLE_ENABLED_STAGING }} | |
| VITE_EARNING_ENABLED_STAGING: ${{ secrets.VITE_EARNING_ENABLED_STAGING }} | |
| VITE_AI_ASSISTANT_CONSOLE_ENABLED_STAGING: ${{ secrets.VITE_AI_ASSISTANT_CONSOLE_ENABLED_STAGING }} | |
| VITE_UNIVERSAL_SCANNER_ENABLED_STAGING: ${{ secrets.VITE_UNIVERSAL_SCANNER_ENABLED_STAGING }} | |
| VITE_OCP_PAY_WITH_BTC_ENABLED_STAGING: ${{ secrets.VITE_OCP_PAY_WITH_BTC_ENABLED_STAGING }} | |
| VITE_ONRAMPER_API_KEY_DEV_STAGING: ${{ secrets.VITE_ONRAMPER_API_KEY_DEV_STAGING }} | |
| VITE_ONRAMPER_API_KEY_PROD_STAGING: ${{ secrets.VITE_ONRAMPER_API_KEY_PROD_STAGING }} | |
| VITE_AUTH_ALTERNATIVE_ORIGINS_STAGING: ${{ secrets.VITE_AUTH_ALTERNATIVE_ORIGINS_STAGING }} | |
| DFX_DEPLOY_KEY_STAGING: ${{ secrets.DFX_DEPLOY_KEY_STAGING }} | |
| VITE_ETHERSCAN_API_KEY_BETA: ${{ secrets.VITE_ETHERSCAN_API_KEY_BETA }} | |
| VITE_INFURA_API_KEY_BETA: ${{ secrets.VITE_INFURA_API_KEY_BETA }} | |
| VITE_ALCHEMY_API_KEY_BETA: ${{ secrets.VITE_ALCHEMY_API_KEY_BETA }} | |
| VITE_QUICKNODE_API_KEY_BETA: ${{ secrets.VITE_QUICKNODE_API_KEY_BETA }} | |
| VITE_WALLET_CONNECT_PROJECT_ID_BETA: ${{ secrets.VITE_WALLET_CONNECT_PROJECT_ID_BETA }} | |
| VITE_COINGECKO_API_KEY_BETA: ${{ secrets.VITE_COINGECKO_API_KEY_BETA }} | |
| VITE_AUTH_ALTERNATIVE_ORIGINS_BETA: ${{ secrets.VITE_AUTH_ALTERNATIVE_ORIGINS_BETA }} | |
| VITE_ONRAMPER_API_KEY_DEV_BETA: ${{ secrets.VITE_ONRAMPER_API_KEY_DEV_BETA }} | |
| VITE_PLAUSIBLE_ENABLED_BETA: ${{ secrets.VITE_PLAUSIBLE_ENABLED_BETA }} | |
| VITE_EARNING_ENABLED_BETA: ${{ secrets.VITE_EARNING_ENABLED_BETA }} | |
| VITE_AI_ASSISTANT_CONSOLE_ENABLED_BETA: ${{ secrets.VITE_AI_ASSISTANT_CONSOLE_ENABLED_BETA }} | |
| VITE_UNIVERSAL_SCANNER_ENABLED_BETA: ${{ secrets.VITE_UNIVERSAL_SCANNER_ENABLED_BETA }} | |
| VITE_OCP_PAY_WITH_BTC_ENABLED_BETA: ${{ secrets.VITE_OCP_PAY_WITH_BTC_ENABLED_BETA }} | |
| VITE_ONRAMPER_API_KEY_PROD_BETA: ${{ secrets.VITE_ONRAMPER_API_KEY_PROD_BETA }} | |
| DFX_DEPLOY_KEY_BETA: ${{ secrets.DFX_DEPLOY_KEY_BETA }} | |
| - name: Fail if no Identity is provided | |
| run: | | |
| if [ -z "$DFX_DEPLOY_KEY" ]; then | |
| echo "Error: DFX_DEPLOY_KEY for $NETWORK is not set or is empty. Please provide the deployment identity key." | |
| exit 1 | |
| fi | |
| env: | |
| DFX_DEPLOY_KEY: ${{ steps.set-outputs.outputs.DFX_DEPLOY_KEY }} | |
| - name: Restore cargo cache | |
| uses: actions/cache@cdf6c1fa76f9f475f3d7449005a359c84ca0f306 # v5.0.3 | |
| with: | |
| path: | | |
| /home/runner/.cargo/registry | |
| /home/runner/.cargo/git | |
| target/ | |
| ~/.cargo/bin/ | |
| key: ${{ runner.os }}-deploy-cargo-${{ hashFiles('Cargo.toml', 'Cargo.lock', 'rust-toolchain.toml', 'src/backend/**/*', 'src/shared/**/*') }} | |
| restore-keys: | | |
| ${{ runner.os }}-deploy-cargo- | |
| - name: Prepare | |
| uses: ./.github/actions/prepare | |
| - name: Set up DFX | |
| uses: dfinity/setup-dfx@e50c04f104ee4285ec010f10609483cf41e4d365 # main | |
| env: | |
| DFX_DEPLOY_KEY: ${{ steps.set-outputs.outputs.DFX_DEPLOY_KEY }} | |
| - name: Install key | |
| run: | | |
| key_pem=$(mktemp) | |
| printenv "DFX_DEPLOY_KEY" > "$key_pem" | |
| dfx identity import --storage-mode=plaintext --force default "$key_pem" | |
| rm "$key_pem" | |
| dfx identity use default | |
| dfx identity get-principal | |
| env: | |
| DFX_DEPLOY_KEY: ${{ steps.set-outputs.outputs.DFX_DEPLOY_KEY }} | |
| - name: Pre-build | |
| run: npm run build | |
| env: | |
| VITE_ETHERSCAN_API_KEY: ${{ steps.set-outputs.outputs.VITE_ETHERSCAN_API_KEY }} | |
| VITE_INFURA_API_KEY: ${{ steps.set-outputs.outputs.VITE_INFURA_API_KEY }} | |
| VITE_ALCHEMY_API_KEY: ${{ steps.set-outputs.outputs.VITE_ALCHEMY_API_KEY }} | |
| VITE_QUICKNODE_API_KEY: ${{ steps.set-outputs.outputs.VITE_QUICKNODE_API_KEY }} | |
| VITE_WALLET_CONNECT_PROJECT_ID: ${{ steps.set-outputs.outputs.VITE_WALLET_CONNECT_PROJECT_ID }} | |
| VITE_COINGECKO_API_KEY: ${{ steps.set-outputs.outputs.VITE_COINGECKO_API_KEY }} | |
| VITE_PLAUSIBLE_ENABLED: ${{ steps.set-outputs.outputs.VITE_PLAUSIBLE_ENABLED }} | |
| VITE_EARNING_ENABLED: ${{ steps.set-outputs.outputs.VITE_EARNING_ENABLED }} | |
| VITE_AI_ASSISTANT_CONSOLE_ENABLED: ${{ steps.set-outputs.outputs.VITE_AI_ASSISTANT_CONSOLE_ENABLED }} | |
| VITE_UNIVERSAL_SCANNER_ENABLED: ${{ steps.set-outputs.outputs.VITE_UNIVERSAL_SCANNER_ENABLED }} | |
| VITE_OCP_PAY_WITH_BTC_ENABLED: ${{ steps.set-outputs.outputs.VITE_OCP_PAY_WITH_BTC_ENABLED }} | |
| VITE_ONRAMPER_API_KEY_DEV: ${{ steps.set-outputs.outputs.VITE_ONRAMPER_API_KEY_DEV }} | |
| VITE_ONRAMPER_API_KEY_PROD: ${{ steps.set-outputs.outputs.VITE_ONRAMPER_API_KEY_PROD }} | |
| VITE_AUTH_ALTERNATIVE_ORIGINS: ${{ steps.set-outputs.outputs.VITE_AUTH_ALTERNATIVE_ORIGINS }} | |
| - name: Deploy Frontend to Environment | |
| run: | | |
| if [ "$deploy_frontend" == "true" ]; then | |
| dfx deploy frontend --network "$NETWORK" --no-asset-upgrade | |
| fi | |
| if [ "$deploy_all_signers" == "true" ]; then | |
| dfx deploy signer_frontend --network "$NETWORK" --no-asset-upgrade | |
| dfx deploy legacy_signer_frontend --network "$NETWORK" --no-asset-upgrade | |
| elif [ "$deploy_signer" == "true" ]; then | |
| dfx deploy "$CANISTER" --network "$NETWORK" --no-asset-upgrade | |
| fi | |
| env: | |
| VITE_ETHERSCAN_API_KEY: ${{ steps.set-outputs.outputs.VITE_ETHERSCAN_API_KEY }} | |
| VITE_INFURA_API_KEY: ${{ steps.set-outputs.outputs.VITE_INFURA_API_KEY }} | |
| VITE_ALCHEMY_API_KEY: ${{ steps.set-outputs.outputs.VITE_ALCHEMY_API_KEY }} | |
| VITE_QUICKNODE_API_KEY: ${{ steps.set-outputs.outputs.VITE_QUICKNODE_API_KEY }} | |
| VITE_WALLET_CONNECT_PROJECT_ID: ${{ steps.set-outputs.outputs.VITE_WALLET_CONNECT_PROJECT_ID }} | |
| VITE_COINGECKO_API_KEY: ${{ steps.set-outputs.outputs.VITE_COINGECKO_API_KEY }} | |
| VITE_PLAUSIBLE_ENABLED: ${{ steps.set-outputs.outputs.VITE_PLAUSIBLE_ENABLED }} | |
| VITE_EARNING_ENABLED: ${{ steps.set-outputs.outputs.VITE_EARNING_ENABLED }} | |
| VITE_AI_ASSISTANT_CONSOLE_ENABLED: ${{ steps.set-outputs.outputs.VITE_AI_ASSISTANT_CONSOLE_ENABLED }} | |
| VITE_UNIVERSAL_SCANNER_ENABLED: ${{ steps.set-outputs.outputs.VITE_UNIVERSAL_SCANNER_ENABLED }} | |
| VITE_OCP_PAY_WITH_BTC_ENABLED: ${{ steps.set-outputs.outputs.VITE_OCP_PAY_WITH_BTC_ENABLED }} | |
| VITE_ONRAMPER_API_KEY_DEV: ${{ steps.set-outputs.outputs.VITE_ONRAMPER_API_KEY_DEV }} | |
| VITE_ONRAMPER_API_KEY_PROD: ${{ steps.set-outputs.outputs.VITE_ONRAMPER_API_KEY_PROD }} | |
| VITE_AUTH_ALTERNATIVE_ORIGINS: ${{ steps.set-outputs.outputs.VITE_AUTH_ALTERNATIVE_ORIGINS }} | |
| DFX_DEPLOY_KEY: ${{ steps.set-outputs.outputs.DFX_DEPLOY_KEY }} | |
| - name: Deploy Backend to Environment | |
| run: | | |
| DFX_DEPLOY_FLAGS=() # Arguments to be added to the dfx deploy command. | |
| [[ "$FORCE_BACKEND" != "true" ]] || DFX_DEPLOY_FLAGS+=('--yes' '--upgrade-unchanged') # Corresponds to: dfx deploy --yes --upgrade-unchanged | |
| if [ "$deploy_backend" == "true" ] ; then | |
| if git diff --quiet "origin/$BASE_REF" HEAD -- Cargo.toml Cargo.lock rust-toolchain.toml src/backend/**/* src/shared/**/*; then | |
| if [ "$FORCE_BACKEND" != "true" ]; then | |
| echo "No changes in specified files/folders detected, skipping backend deployment." | |
| else | |
| ./scripts/setup cargo-binstall candid-extractor ic-wasm didc yq | |
| dfx deploy backend --network "$NETWORK" "${DFX_DEPLOY_FLAGS[@]}" | |
| fi | |
| else | |
| ./scripts/setup cargo-binstall candid-extractor ic-wasm didc yq | |
| dfx deploy backend --network "$NETWORK" "${DFX_DEPLOY_FLAGS[@]}" | |
| fi | |
| fi | |
| env: | |
| FORCE_BACKEND: ${{ github.event.inputs.force-backend }} | |
| DFX_DEPLOY_KEY: ${{ steps.set-outputs.outputs.DFX_DEPLOY_KEY }} | |
| BASE_REF: ${{ github.base_ref }} |