From 7afd13e9be0bf21c2ed3c8b394ec21e8a85da694 Mon Sep 17 00:00:00 2001 From: Piotr Roslaniec Date: Wed, 26 Nov 2025 15:19:41 +0100 Subject: [PATCH 1/2] ci: add Cloudflare Pages deployment with noindex headers --- .../cloudflare-legacy-deployment.yml | 133 ++++++++++++++++++ docs/cloudflare-deploy-runbook.md | 45 ++++++ public/_headers | 2 + public/robots.txt | 3 +- 4 files changed, 182 insertions(+), 1 deletion(-) create mode 100644 .github/workflows/cloudflare-legacy-deployment.yml create mode 100644 docs/cloudflare-deploy-runbook.md create mode 100644 public/_headers diff --git a/.github/workflows/cloudflare-legacy-deployment.yml b/.github/workflows/cloudflare-legacy-deployment.yml new file mode 100644 index 000000000..b57ce98f0 --- /dev/null +++ b/.github/workflows/cloudflare-legacy-deployment.yml @@ -0,0 +1,133 @@ +name: Cloudflare Pages Deploy (production) + +on: + workflow_dispatch: + inputs: + branch: + description: "Git ref/branch to deploy" + required: false + default: "main" + env_prefix: + description: "Optional path prefix (e.g., preview/)" + required: false + default: "" + +jobs: + build: + name: Build + runs-on: ubuntu-latest + permissions: + contents: read + env: + NODE_VERSION: "20" + PUBLIC_URL: / + CANONICAL_HOSTNAME: old-app.threshold.network + CHAIN_ID: 1 + ALCHEMY_API_KEY: ${{ secrets.ALCHEMY_API_KEY }} + ELECTRUM_PROTOCOL: ${{ secrets.MAINNET_ELECTRUMX_PROTOCOL }} + ELECTRUM_HOST: ${{ secrets.MAINNET_ELECTRUMX_HOST }} + ELECTRUM_PORT: ${{ secrets.MAINNET_ELECTRUMX_PORT }} + SENTRY_DSN: ${{ secrets.MAINNET_SENTRY_DSN }} + TRM_SUPPORT: ${{ secrets.TRM_SUPPORT }} + WALLET_CONNECT_PROJECT_ID: ${{ secrets.WALLET_CONNECT_PROJECT_ID }} + TBTC_SUBGRAPH_API_KEY: ${{ secrets.TBTC_SUBGRAPH_API_KEY }} + GOOGLE_TAG_MANAGER_ID: ${{ secrets.GOOGLE_TAG_MANAGER_ID }} + GOOGLE_TAG_MANAGER_SUPPORT: true + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + ref: ${{ github.event.inputs.branch || 'main' }} + + - uses: actions/setup-node@v3 + with: + node-version: "20" + cache: yarn + + - name: Force git to use https + run: git config --global url."https://".insteadOf git:// + + - name: Install dependencies + run: yarn install --ignore-scripts --frozen-lockfile + + - name: Postinstall + run: yarn run postinstall + + - name: Build + run: | + PUBLIC_URL=${PUBLIC_URL} \ + CANONICAL_HOSTNAME=${CANONICAL_HOSTNAME} \ + CHAIN_ID=${CHAIN_ID} \ + ALCHEMY_API_KEY=${ALCHEMY_API_KEY} \ + ELECTRUM_PROTOCOL=${ELECTRUM_PROTOCOL} \ + ELECTRUM_HOST=${ELECTRUM_HOST} \ + ELECTRUM_PORT=${ELECTRUM_PORT} \ + SENTRY_DSN=${SENTRY_DSN} \ + TRM_SUPPORT=${TRM_SUPPORT} \ + WALLET_CONNECT_PROJECT_ID=${WALLET_CONNECT_PROJECT_ID} \ + TBTC_SUBGRAPH_API_KEY=${TBTC_SUBGRAPH_API_KEY} \ + GOOGLE_TAG_MANAGER_SUPPORT=${GOOGLE_TAG_MANAGER_SUPPORT} \ + GOOGLE_TAG_MANAGER_ID=${GOOGLE_TAG_MANAGER_ID} \ + yarn build + + - uses: actions/upload-artifact@v4 + with: + name: build + path: build + + deploy: + name: Deploy to Cloudflare Pages + needs: build + runs-on: ubuntu-latest + environment: + name: cloudflare-production + url: https://token-dashboard-legacy.pages.dev + permissions: + contents: read + env: + CF_PAGES_PROJECT: token-dashboard-legacy + CLOUDFLARE_API_TOKEN: ${{ secrets.CF_PAGES_API_TOKEN }} + CLOUDFLARE_ACCOUNT_ID: ${{ secrets.CLOUDFLARE_ACCOUNT_ID || secrets.CF_ACCOUNT_ID }} + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + ref: ${{ github.event.inputs.branch || 'main' }} + + - uses: actions/download-artifact@v4 + with: + name: build + path: build + + - name: Install wrangler + run: npm install -g wrangler@4.50.0 + + - name: Deploy + env: + CF_DEPLOY_BRANCH: ${{ github.event.inputs.branch || 'main' }} + CF_DEPLOY_ENV_PREFIX: ${{ github.event.inputs.env_prefix }} + run: | + set -euo pipefail + export CLOUDFLARE_API_TOKEN + export CF_API_TOKEN="$CLOUDFLARE_API_TOKEN" + export CLOUDFLARE_ACCOUNT_ID + if [ -z "$CLOUDFLARE_ACCOUNT_ID" ]; then + echo "CLOUDFLARE_ACCOUNT_ID missing" >&2 + exit 1 + fi + if [ -z "$CF_DEPLOY_ENV_PREFIX" ]; then + BRANCH_NAME="$CF_DEPLOY_BRANCH" + else + BRANCH_NAME="$CF_DEPLOY_ENV_PREFIX" + fi + wrangler pages deploy build \ + --project-name ${CF_PAGES_PROJECT} \ + --branch ${BRANCH_NAME} + + - name: Smoke check (post-deploy) + env: + SMOKE_URL: https://old-app.threshold.network/overview/network + run: | + set -euo pipefail + echo "Smoke checking ${SMOKE_URL}" + curl -I --fail "$SMOKE_URL" diff --git a/docs/cloudflare-deploy-runbook.md b/docs/cloudflare-deploy-runbook.md new file mode 100644 index 000000000..74da3d1e4 --- /dev/null +++ b/docs/cloudflare-deploy-runbook.md @@ -0,0 +1,45 @@ +# Cloudflare Pages Deploy (token-dashboard-legacy) + +## Workflow + +- File: `.github/workflows/cloudflare-legacy-deployment.yml` +- Trigger: `workflow_dispatch` with inputs + - `branch` (default `main`) + - `env_prefix` (optional path/alias override) +- Jobs: `Build` (yarn build, artifact upload) → `Deploy` (wrangler pages deploy) + → smoke check. +- Environment gate: `cloudflare-production` (approve in Actions UI). + +## Required secrets + +- `CF_PAGES_API_TOKEN` (Pages:Edit scope) +- `CLOUDFLARE_ACCOUNT_ID` +- Build secrets: `ALCHEMY_API_KEY`, `MAINNET_ELECTRUMX_PROTOCOL`, + `MAINNET_ELECTRUMX_HOST`, `MAINNET_ELECTRUMX_PORT`, `MAINNET_SENTRY_DSN`, + `TRM_SUPPORT`, `WALLET_CONNECT_PROJECT_ID`, `TBTC_SUBGRAPH_API_KEY`, + `GOOGLE_TAG_MANAGER_ID`, `GOOGLE_TAG_MANAGER_SUPPORT` (true/false in workflow + env). + +## How to deploy + +```bash +# from any machine with gh auth +gh workflow run cloudflare-legacy-deployment.yml -f branch=main +# approve the environment prompt in GitHub Actions +``` + +- Production URL: https://token-dashboard-legacy.pages.dev +- Custom domain: https://old-app.threshold.network +- Post-deploy smoke: curls + `https://old-app.threshold.network/overview/network` (fails the job on + non-200/301). + +## Notes + +- Wrangler pinned to 4.50.0. +- If you need a preview alias, pass `env_prefix=preview/` so Pages uses + that alias. +- Redirects/headers can be added via `_redirects` / `_headers` in the repo. +- Current legacy deployment is intentionally non-indexable: `_headers` sets + `X-Robots-Tag: noindex, nofollow` and `robots.txt` disallows all. Remove these + when you want search indexing back. diff --git a/public/_headers b/public/_headers new file mode 100644 index 000000000..c01bc2027 --- /dev/null +++ b/public/_headers @@ -0,0 +1,2 @@ +/* + X-Robots-Tag: noindex, nofollow diff --git a/public/robots.txt b/public/robots.txt index e9e57dc4d..9c76deb24 100644 --- a/public/robots.txt +++ b/public/robots.txt @@ -1,3 +1,4 @@ # https://www.robotstxt.org/robotstxt.html +# Block all crawlers for legacy Cloudflare deployment User-agent: * -Disallow: +Disallow: / From 5af8e93a23346d301f2ad4cce684e2f1900b37af Mon Sep 17 00:00:00 2001 From: Piotr Roslaniec Date: Sun, 30 Nov 2025 11:24:27 +0100 Subject: [PATCH 2/2] ci(testnet): add cloudflare legacy pages deploy --- .../cloudflare-legacy-testnet-deployment.yml | 131 ++++++++++++++++++ docs/cloudflare-deploy-runbook.md | 29 ++++ 2 files changed, 160 insertions(+) create mode 100644 .github/workflows/cloudflare-legacy-testnet-deployment.yml diff --git a/.github/workflows/cloudflare-legacy-testnet-deployment.yml b/.github/workflows/cloudflare-legacy-testnet-deployment.yml new file mode 100644 index 000000000..a4895870a --- /dev/null +++ b/.github/workflows/cloudflare-legacy-testnet-deployment.yml @@ -0,0 +1,131 @@ +name: Cloudflare Pages Deploy (testnet legacy) + +on: + workflow_dispatch: + inputs: + branch: + description: "Git ref/branch to deploy" + required: false + default: "main" + env_prefix: + description: "Optional path prefix (e.g., preview/)" + required: false + default: "" + +jobs: + build: + name: Build + runs-on: ubuntu-latest + permissions: + contents: read + env: + NODE_VERSION: "20" + PUBLIC_URL: / + CANONICAL_HOSTNAME: testnet-token-dashboard-legacy.pages.dev + CHAIN_ID: 11155111 + ALCHEMY_API_KEY: ${{ secrets.ALCHEMY_API_KEY }} + ELECTRUM_PROTOCOL: ${{ secrets.TESTNET_ELECTRUMX_PROTOCOL }} + ELECTRUM_HOST: ${{ secrets.TESTNET_ELECTRUMX_HOST }} + ELECTRUM_PORT: ${{ secrets.TESTNET_ELECTRUMX_PORT }} + SENTRY_SUPPORT: true + SENTRY_DSN: ${{ secrets.TESTNET_SENTRY_DSN }} + WALLET_CONNECT_PROJECT_ID: ${{ secrets.WALLET_CONNECT_PROJECT_ID }} + TBTC_SUBGRAPH_API_KEY: ${{ secrets.TBTC_SUBGRAPH_API_KEY }} + DAPP_DEVELOPMENT_TESTNET_CONTRACTS: false + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + ref: ${{ github.event.inputs.branch || 'main' }} + + - uses: actions/setup-node@v3 + with: + node-version: "20" + cache: yarn + + - name: Force git to use https + run: git config --global url."https://".insteadOf git:// + + - name: Install dependencies + run: yarn install --ignore-scripts --frozen-lockfile + + - name: Postinstall + run: yarn run postinstall + + - name: Build + run: | + PUBLIC_URL=${PUBLIC_URL} \ + CANONICAL_HOSTNAME=${CANONICAL_HOSTNAME} \ + CHAIN_ID=${CHAIN_ID} \ + ALCHEMY_API_KEY=${ALCHEMY_API_KEY} \ + ELECTRUM_PROTOCOL=${ELECTRUM_PROTOCOL} \ + ELECTRUM_HOST=${ELECTRUM_HOST} \ + ELECTRUM_PORT=${ELECTRUM_PORT} \ + SENTRY_SUPPORT=${SENTRY_SUPPORT} \ + SENTRY_DSN=${SENTRY_DSN} \ + WALLET_CONNECT_PROJECT_ID=${WALLET_CONNECT_PROJECT_ID} \ + TBTC_SUBGRAPH_API_KEY=${TBTC_SUBGRAPH_API_KEY} \ + DAPP_DEVELOPMENT_TESTNET_CONTRACTS=${DAPP_DEVELOPMENT_TESTNET_CONTRACTS} \ + yarn build + + - uses: actions/upload-artifact@v4 + with: + name: build + path: build + + deploy: + name: Deploy to Cloudflare Pages + needs: build + runs-on: ubuntu-latest + environment: + name: cloudflare-testnet + url: https://testnet-token-dashboard-legacy.pages.dev + permissions: + contents: read + env: + CF_PAGES_PROJECT: testnet-token-dashboard-legacy + CLOUDFLARE_API_TOKEN: ${{ secrets.CF_PAGES_API_TOKEN }} + CLOUDFLARE_ACCOUNT_ID: ${{ secrets.CLOUDFLARE_ACCOUNT_ID || secrets.CF_ACCOUNT_ID }} + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + ref: ${{ github.event.inputs.branch || 'main' }} + + - uses: actions/download-artifact@v4 + with: + name: build + path: build + + - name: Install wrangler + run: npm install -g wrangler@4.50.0 + + - name: Deploy + env: + CF_DEPLOY_BRANCH: ${{ github.event.inputs.branch || 'main' }} + CF_DEPLOY_ENV_PREFIX: ${{ github.event.inputs.env_prefix }} + run: | + set -euo pipefail + export CLOUDFLARE_API_TOKEN + export CF_API_TOKEN="$CLOUDFLARE_API_TOKEN" + export CLOUDFLARE_ACCOUNT_ID + if [ -z "$CLOUDFLARE_ACCOUNT_ID" ]; then + echo "CLOUDFLARE_ACCOUNT_ID missing" >&2 + exit 1 + fi + if [ -z "$CF_DEPLOY_ENV_PREFIX" ]; then + BRANCH_NAME="$CF_DEPLOY_BRANCH" + else + BRANCH_NAME="$CF_DEPLOY_ENV_PREFIX" + fi + wrangler pages deploy build \ + --project-name ${CF_PAGES_PROJECT} \ + --branch ${BRANCH_NAME} + + - name: Smoke check (post-deploy) + env: + SMOKE_URL: https://testnet-token-dashboard-legacy.pages.dev/ + run: | + set -euo pipefail + echo "Smoke checking ${SMOKE_URL}" + curl -I --fail "$SMOKE_URL" diff --git a/docs/cloudflare-deploy-runbook.md b/docs/cloudflare-deploy-runbook.md index 74da3d1e4..062962994 100644 --- a/docs/cloudflare-deploy-runbook.md +++ b/docs/cloudflare-deploy-runbook.md @@ -43,3 +43,32 @@ gh workflow run cloudflare-legacy-deployment.yml -f branch=main - Current legacy deployment is intentionally non-indexable: `_headers` sets `X-Robots-Tag: noindex, nofollow` and `robots.txt` disallows all. Remove these when you want search indexing back. + +## Testnet workflow (legacy) + +- File: `.github/workflows/cloudflare-legacy-testnet-deployment.yml` +- Trigger: `workflow_dispatch` with inputs + - `branch` (default `main`) + - `env_prefix` (optional path/alias override) +- Jobs: `Build` (yarn build, artifact upload) → `Deploy` (wrangler pages deploy) + → smoke check. +- Environment gate: `cloudflare-testnet` (approve in Actions UI). +- Pages project: `testnet-token-dashboard-legacy` +- Default domain: https://testnet-token-dashboard-legacy.pages.dev +- Smoke check: HEAD `https://testnet-token-dashboard-legacy.pages.dev/` + +### Required secrets (testnet) + +- `CF_PAGES_API_TOKEN` +- `CLOUDFLARE_ACCOUNT_ID` +- Build secrets: `ALCHEMY_API_KEY`, `TESTNET_ELECTRUMX_PROTOCOL`, + `TESTNET_ELECTRUMX_HOST`, `TESTNET_ELECTRUMX_PORT`, `TESTNET_SENTRY_DSN`, + `WALLET_CONNECT_PROJECT_ID`, `TBTC_SUBGRAPH_API_KEY` + +### How to deploy (testnet) + +```bash +# from any machine with gh auth +gh workflow run cloudflare-legacy-testnet-deployment.yml -f branch=main +# approve the environment prompt in GitHub Actions +```