chore: sync all changes to Gitea
Some checks failed
Deploy to Phoenix / deploy (push) Has been cancelled

- Config, docs, scripts, and backup manifests
- Submodule refs unchanged (m = modified content in submodules)

Made-with: Cursor
This commit is contained in:
defiQUG
2026-03-02 11:37:34 -08:00
parent ed85135249
commit b3a8fe4496
883 changed files with 73580 additions and 4796 deletions

View File

@@ -0,0 +1,113 @@
#!/usr/bin/env bash
# Check deployer wallet balances on ChainID 138 (native ETH + ERC-20: WETH, WETH10, LINK, cUSDT, cUSDC).
# Output half of each balance as the funding plan for the three PMM liquidity pools.
#
# Usage:
# RPC_URL_138=https://rpc-core.d-bis.org ./scripts/deployment/check-deployer-balance-chain138-and-funding-plan.sh
# # Or from smom-dbis-138: source .env then run from repo root with RPC_URL_138 set
#
# Requires: cast (foundry), jq (optional). RPC_URL_138 must be set and reachable.
set -euo pipefail
DEPLOYER="${DEPLOYER_ADDRESS:-0x4A666F96fC8764181194447A7dFdb7d471b301C8}"
RPC="${RPC_URL_138:-}"
if [ -z "$RPC" ]; then
echo "ERROR: Set RPC_URL_138 (e.g. https://rpc-core.d-bis.org or http://192.168.11.211:8545)"
exit 1
fi
CHAIN_ID=138
# Chain 138 token addresses (from CHAIN138_TOKEN_ADDRESSES / ADDRESS_MATRIX)
WETH="0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2"
WETH10="0xf4BB2e28688e89fCcE3c0580D37d36A7672E8A9f"
LINK="0xb7721dD53A8c629d9f1Ba31a5819AFe250002b03"
CUSDT="0x93E66202A11B1772E55407B32B44e5Cd8eda7f22"
CUSDC="0xf22258f57794CC8E06237084b353Ab30fFfa640b"
USDT_OFFICIAL="0x15DF1D5BFDD8Aa4b380445D4e3E9B38d34283619"
# PMM pool addresses (from LIQUIDITY_POOLS_MASTER_MAP / ADDRESS_MATRIX)
POOL_CUSDTCUSDC="0x9fcB06Aa1FD5215DC0E91Fd098aeff4B62fEa5C8"
POOL_CUSDTUSDT="0xa3Ee6091696B28e5497b6F491fA1e99047250c59"
POOL_CUSDCUSDC="0x90bd9Bf18Daa26Af3e814ea224032d015db58Ea5"
get_balance() {
local addr="$1"
cast call "$addr" "balanceOf(address)(uint256)" "$DEPLOYER" --rpc-url "$RPC" 2>/dev/null || echo "0"
}
get_decimals() {
local addr="$1"
cast call "$addr" "decimals()(uint8)" --rpc-url "$RPC" 2>/dev/null | cast --to-dec 2>/dev/null || echo "18"
}
# Native balance
native_wei=$(cast balance "$DEPLOYER" --rpc-url "$RPC" 2>/dev/null || echo "0")
native_eth=$(awk "BEGIN { printf \"%.6f\", $native_wei / 1e18 }" 2>/dev/null || echo "0")
half_native_wei=$((native_wei / 2))
echo "============================================"
echo "Deployer wallet — ChainID 138"
echo "Deployer: $DEPLOYER"
echo "RPC: $RPC"
echo "============================================"
echo ""
echo "--- Current balances ---"
echo " Native ETH: $native_eth ETH (raw: $native_wei wei)"
echo ""
RAW_WETH=0; RAW_WETH10=0; RAW_LINK=0; RAW_CUSDT=0; RAW_CUSDC=0
HALF_WETH=0; HALF_WETH10=0; HALF_LINK=0; HALF_CUSDT=0; HALF_CUSDC=0
for entry in "WETH:$WETH:18" "WETH10:$WETH10:18" "LINK:$LINK:18" "cUSDT:$CUSDT:6" "cUSDC:$CUSDC:6"; do
sym="${entry%%:*}"; rest="${entry#*:}"; addr="${rest%%:*}"; dec="${rest#*:}"
raw=$(get_balance "$addr")
half=$((raw / 2))
case "$sym" in
WETH) RAW_WETH=$raw; HALF_WETH=$half ;;
WETH10) RAW_WETH10=$raw; HALF_WETH10=$half ;;
LINK) RAW_LINK=$raw; HALF_LINK=$half ;;
cUSDT) RAW_CUSDT=$raw; HALF_CUSDT=$half ;;
cUSDC) RAW_CUSDC=$raw; HALF_CUSDC=$half ;;
esac
if [ "$dec" = "18" ]; then
disp=$(awk "BEGIN { printf \"%.6f\", $raw / 1e18 }" 2>/dev/null || echo "0")
half_disp=$(awk "BEGIN { printf \"%.6f\", $half / 1e18 }" 2>/dev/null || echo "0")
else
disp=$(awk "BEGIN { printf \"%.2f\", $raw / 1e$dec }" 2>/dev/null || echo "0")
half_disp=$(awk "BEGIN { printf \"%.2f\", $half / 1e$dec }" 2>/dev/null || echo "0")
fi
echo " $sym: $disp (raw: $raw) → half for LP: $half_disp (raw: $half)"
done
echo ""
echo "--- Funding plan: use HALF of each balance for PMM liquidity ---"
echo ""
echo "Pool 1: cUSDT/cUSDC ($POOL_CUSDTCUSDC)"
echo " Base (cUSDT): $HALF_CUSDT (decimals 6)"
echo " Quote (cUSDC): $HALF_CUSDC (decimals 6)"
echo ""
echo "Pool 2: cUSDT/USDT ($POOL_CUSDTUSDT)"
echo " Base (cUSDT): $HALF_CUSDT (decimals 6)"
echo " Quote (USDT): use same amount in USDT (official) — check deployer USDT balance separately if needed"
echo ""
echo "Pool 3: cUSDC/USDC ($POOL_CUSDCUSDC)"
echo " Base (cUSDC): $HALF_CUSDC (decimals 6)"
echo " Quote (USDC): use same amount in USDC (official) — check deployer USDC balance separately if needed"
echo ""
echo "--- Env vars for AddLiquidityPMMPoolsChain138 (half of cUSDT/cUSDC) ---"
echo "# Add to smom-dbis-138/.env and run: forge script script/dex/AddLiquidityPMMPoolsChain138.s.sol:AddLiquidityPMMPoolsChain138 --rpc-url \$RPC_URL_138 --broadcast --private-key \$PRIVATE_KEY"
echo "POOL_CUSDTCUSDC=$POOL_CUSDTCUSDC"
echo "POOL_CUSDTUSDT=$POOL_CUSDTUSDT"
echo "POOL_CUSDCUSDC=$POOL_CUSDCUSDC"
echo "ADD_LIQUIDITY_BASE_AMOUNT=$HALF_CUSDT"
echo "ADD_LIQUIDITY_QUOTE_AMOUNT=$HALF_CUSDC"
echo "# For pool cUSDT/cUSDC only (base=cUSDT, quote=cUSDC). For cUSDT/USDT and cUSDC/USDC use per-pool vars:"
echo "# ADD_LIQUIDITY_CUSDTUSDT_BASE=$HALF_CUSDT ADD_LIQUIDITY_CUSDTUSDT_QUOTE=<deployer USDT balance / 2>"
echo "# ADD_LIQUIDITY_CUSDCUSDC_BASE=$HALF_CUSDC ADD_LIQUIDITY_CUSDCUSDC_QUOTE=<deployer USDC balance / 2>"
echo ""
echo "--- Reserve ---"
echo " Keep half of native ETH for gas. Half for LP (if wrapping to WETH for a pool): $((half_native_wei / 2)) wei."
echo " WETH/LINK: half amounts above can be reserved for other use or future pools."
echo "============================================"

View File

@@ -0,0 +1,50 @@
#!/usr/bin/env bash
# Check deployer nonce and balance on Mainnet, Cronos, and Arbitrum.
# Use to diagnose "nonce too high" / "invalid nonce" and "insufficient funds" before retrying cW* deploy.
# Usage: ./scripts/deployment/check-deployer-nonce-and-balance.sh
# Requires: smom-dbis-138/.env with PRIVATE_KEY, ETHEREUM_MAINNET_RPC, CRONOS_RPC_URL, ARBITRUM_MAINNET_RPC
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
SMOM="${PROJECT_ROOT}/smom-dbis-138"
[[ -f "$SMOM/.env" ]] || { echo "Missing $SMOM/.env" >&2; exit 1; }
set -a
source "$SMOM/.env"
set +a
DEPLOYER=""
if [[ -n "${PRIVATE_KEY:-}" ]]; then
DEPLOYER=$(cast wallet address "$PRIVATE_KEY" 2>/dev/null || true)
fi
[[ -z "$DEPLOYER" ]] && { echo "Could not derive deployer address (set PRIVATE_KEY in $SMOM/.env)" >&2; exit 1; }
echo "Deployer address: $DEPLOYER"
echo ""
for label in "Mainnet (1)" "Cronos (25)" "Arbitrum (42161)"; do
case "$label" in
"Mainnet (1)") RPC="${ETHEREUM_MAINNET_RPC:-$ETH_MAINNET_RPC_URL}"; CHAIN=1 ;;
"Cronos (25)") RPC="${CRONOS_RPC_URL:-$CRONOS_RPC}"; CHAIN=25 ;;
"Arbitrum (42161)") RPC="${ARBITRUM_MAINNET_RPC:-$ARBITRUM_MAINNET_RPC_URL}"; CHAIN=42161 ;;
esac
[[ -z "$RPC" ]] && { echo "$label: no RPC set, skip"; continue; }
NONCE=$(cast nonce "$DEPLOYER" --rpc-url "$RPC" 2>/dev/null || echo "?")
BALANCE=$(cast balance "$DEPLOYER" --rpc-url "$RPC" 2>/dev/null || echo "?")
echo "$label"
echo " RPC: ${RPC%%\?*}"
echo " Nonce (next tx): $NONCE"
echo " Balance (wei): $BALANCE"
if [[ "$CHAIN" == "42161" && "$BALANCE" != "?" ]]; then
# ~0.44 ETH needed at 35 gwei for 10 contracts
NEEDED=440872740000000000
if [[ "$BALANCE" -lt "$NEEDED" ]]; then
echo " → Insufficient for cW* deploy (~0.44 ETH at 35 gwei). Send ETH to deployer."
else
echo " → Balance OK for deploy."
fi
fi
echo ""
done
echo "Mainnet/Cronos nonce: If 'nonce too high' or 'invalid nonce', either wait for pending txs to confirm or replace/cancel them (e.g. same nonce, higher gas, 0 value to self)."
echo "Arbitrum: Fund deployer with ~0.5 ETH on Arbitrum One, then run deploy with ARBITRUM_GAS_PRICE=35000000000."

View File

@@ -0,0 +1,63 @@
#!/usr/bin/env bash
# Create all three DODO PMM pools on Chain 138: cUSDT/cUSDC, cUSDT/USDT, cUSDC/USDC.
# Requires: DODOPMMIntegration deployed, deployer with POOL_MANAGER_ROLE, PRIVATE_KEY and RPC_URL_138 in smom-dbis-138/.env.
#
# Usage: ./scripts/deployment/create-all-pmm-pools-chain138.sh [--dry-run]
# --dry-run Print commands only; do not broadcast.
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
SMOM="${PROJECT_ROOT}/smom-dbis-138"
DRY_RUN=""
for a in "$@"; do
[[ "$a" == "--dry-run" ]] && DRY_RUN=1
done
if [[ ! -f "$SMOM/.env" ]]; then
echo "Missing $SMOM/.env. Abort." >&2
exit 1
fi
set -a
source "$SMOM/.env"
set +a
RPC="${RPC_URL_138:-http://192.168.11.211:8545}"
GAS_PRICE="${GAS_PRICE_138:-${GAS_PRICE:-1000000000}}"
export DODO_PMM_INTEGRATION="${DODO_PMM_INTEGRATION_ADDRESS:-${DODO_PMM_INTEGRATION:-0x79cdbaFBaA0FdF9F55D26F360F54cddE5c743F7D}}"
export RPC_URL_138="$RPC"
cd "$SMOM"
POOLS=(
"script/dex/CreateCUSDTCUSDCPool.s.sol:CreateCUSDTCUSDCPool"
"script/dex/CreateCUSDTUSDTPool.s.sol:CreateCUSDTUSDTPool"
"script/dex/CreateCUSDCUSDCPool.s.sol:CreateCUSDCUSDCPool"
)
if [[ -n "$DRY_RUN" ]]; then
echo "[dry-run] Would run the following (from $SMOM):"
for spec in "${POOLS[@]}"; do
echo " forge script $spec --rpc-url \"$RPC\" --broadcast --private-key \"\$PRIVATE_KEY\" --with-gas-price $GAS_PRICE"
done
exit 0
fi
for spec in "${POOLS[@]}"; do
echo "=== Creating pool: $spec ==="
out=$(forge script $spec --rpc-url "$RPC" --broadcast --private-key "$PRIVATE_KEY" --with-gas-price "$GAS_PRICE" 2>&1) || true
echo "$out"
if echo "$out" | grep -qE "pool exists|Pool already exists"; then
echo "Pool already exists; skipping."
elif echo "$out" | grep -q "Error:" && ! echo "$out" | grep -qE "pool exists|Pool already exists"; then
echo "Pool creation failed (see above)." >&2
exit 1
else
echo "Pool created successfully."
fi
sleep 2
done
echo "Done. Run ./scripts/verify/check-contracts-on-chain-138.sh \"$RPC\" to verify."

View File

@@ -119,7 +119,7 @@ deploy_inside() {
log "Creating startup script and systemd service..."
run_ct "bash -c '
cat > /srv/gov-portals/start-portals.sh << \"SCRIPT\"
#!/bin/bash
#!/usr/bin/env bash
cd /srv/gov-portals
export NODE_ENV=production
PORT=3001 node DBIS/node_modules/next/dist/bin/next start -p 3001 &

View File

@@ -2,12 +2,19 @@
# Deploy TransactionMirror and create DODO cUSDT/cUSDC PMM pool on Chain 138.
# Run after clearing RPC tx pool (./scripts/clear-all-transaction-pools.sh) so deployer nonce is not stuck.
#
# Uses: smom-dbis-138/.env (PRIVATE_KEY, RPC_URL_138, RPC_URL_138_PUBLIC, DODO_PMM_INTEGRATION, GAS_PRICE)
# and config/ip-addresses.conf for RPC fallbacks. Always checks nonce, RPC active, and gas.
# RPC: Contract deployments use ONLY Core RPC (RPC_URL_138 = 192.168.11.211:8545, VMID 2101).
# No Public RPC fallback. If Core is down or read-only, fix it first (see docs/03-deployment/RPC_2101_READONLY_FIX.md).
#
# Usage: ./scripts/deployment/deploy-transaction-mirror-and-pmm-pool-after-txpool-clear.sh [--dry-run] [--force]
# --dry-run Check env, RPC, nonce only; no deploy.
# --force Skip RPC reachability check (not recommended).
# Uses: smom-dbis-138/.env (PRIVATE_KEY, RPC_URL_138, DODO_PMM_INTEGRATION, GAS_PRICE)
#
# Usage: ./scripts/deployment/deploy-transaction-mirror-and-pmm-pool-after-txpool-clear.sh [--dry-run] [--force] [--skip-mirror]
# --dry-run Check env, RPC, nonce only; no deploy.
# --force Skip RPC reachability check (not recommended).
# --skip-mirror Skip TransactionMirror deploy; only create PMM pool (set TRANSACTION_MIRROR_ADDRESS in .env if mirror already deployed).
#
# Before first deploy: fix Core if read-only, then run health check:
# ./scripts/maintenance/make-rpc-vmids-writable-via-ssh.sh
# ./scripts/maintenance/health-check-rpc-2101.sh
set -euo pipefail
@@ -17,9 +24,11 @@ SMOM="${PROJECT_ROOT}/smom-dbis-138"
DRY_RUN=""
FORCE=""
SKIP_MIRROR=""
for a in "$@"; do
[[ "$a" == "--dry-run" ]] && DRY_RUN=1
[[ "$a" == "--force" ]] && FORCE=1
[[ "$a" == "--skip-mirror" ]] && SKIP_MIRROR=1
done
# 1) Load dotenv: project config (RPCs) then smom-dbis-138/.env (PRIVATE_KEY, overrides)
@@ -32,44 +41,32 @@ set -a
source "$SMOM/.env"
set +a
# 2) RPC: prefer .env, fallback to config
# 2) RPC: Core (2101) only — no Public fallback for deployments
RPC="${RPC_URL_138:-http://192.168.11.211:8545}"
PUBLIC_RPC="${RPC_URL_138_PUBLIC:-http://192.168.11.221:8545}"
[[ -z "${PRIVATE_KEY:-}" ]] && echo "PRIVATE_KEY not set in $SMOM/.env. Abort." >&2 && exit 1
# Chain 138 gas: min 1 gwei; use GAS_PRICE from .env or default
GAS_PRICE="${GAS_PRICE_138:-${GAS_PRICE:-1000000000}}"
echo "=== TransactionMirror + PMM pool (Chain 138) ==="
echo "RPC: $RPC"
echo "RPC (Core for deploy): $RPC"
echo "Gas price: $GAS_PRICE wei"
echo ""
# 3) Ensure RPC is active (chainId 138)
rpc_ok=""
# 3) Ensure Core RPC is active (chainId 138). No Public fallback.
if [[ -z "$FORCE" ]]; then
chain_id_hex=$(curl -s -m 10 -X POST "$RPC" -H "Content-Type: application/json" \
-d '{"jsonrpc":"2.0","method":"eth_chainId","params":[],"id":1}' 2>/dev/null | sed -n 's/.*"result":"\([^"]*\)".*/\1/p') || true
if [[ "$chain_id_hex" == "0x8a" ]]; then
rpc_ok=1
else
if [[ "$chain_id_hex" != "0x8a" ]]; then
if [[ -n "$chain_id_hex" ]]; then
echo "RPC returned chainId $chain_id_hex (expected 0x8a for Chain 138)." >&2
echo "Core RPC returned chainId $chain_id_hex (expected 0x8a for Chain 138)." >&2
else
echo "RPC unreachable or invalid response: $RPC" >&2
fi
if [[ "$RPC" == *"192.168.11.211"* ]] && [[ "$PUBLIC_RPC" != *"192.168.11.211"* ]]; then
pub_hex=$(curl -s -m 5 -X POST "$PUBLIC_RPC" -H "Content-Type: application/json" \
-d '{"jsonrpc":"2.0","method":"eth_chainId","params":[],"id":1}' 2>/dev/null | sed -n 's/.*"result":"\([^"]*\)".*/\1/p') || true
if [[ "$pub_hex" == "0x8a" ]]; then
echo "Using Public RPC: $PUBLIC_RPC" >&2
RPC="$PUBLIC_RPC"
rpc_ok=1
fi
fi
if [[ -z "$rpc_ok" ]]; then
echo "Set RPC_URL_138 (and optionally RPC_URL_138_PUBLIC) in $SMOM/.env to a reachable Chain 138 RPC." >&2
exit 1
echo "Core RPC unreachable or invalid response: $RPC" >&2
fi
echo "Contract deployments use Core RPC only (VMID 2101, 192.168.11.211:8545). Fix read-only/storage then re-run:" >&2
echo " 1. ./scripts/maintenance/make-rpc-vmids-writable-via-ssh.sh" >&2
echo " 2. ./scripts/maintenance/health-check-rpc-2101.sh" >&2
echo " See docs/03-deployment/RPC_2101_READONLY_FIX.md" >&2
exit 1
fi
else
echo "(--force: skipping RPC check)" >&2
@@ -102,12 +99,36 @@ cd "$SMOM"
export RPC_URL_138="$RPC"
export DODO_PMM_INTEGRATION="${DODO_PMM_INTEGRATION_ADDRESS:-${DODO_PMM_INTEGRATION:-0x79cdbaFBaA0FdF9F55D26F360F54cddE5c743F7D}}"
echo "Deploying TransactionMirror (NEXT_NONCE=$NEXT_NONCE, gas $GAS_PRICE)..."
forge script script/DeployTransactionMirror.s.sol:DeployTransactionMirror \
--rpc-url "$RPC" --broadcast --private-key "$PRIVATE_KEY" --with-gas-price "$GAS_PRICE"
# Skip TransactionMirror deploy if already deployed at TRANSACTION_MIRROR_ADDRESS or if --skip-mirror
MIRROR_ADDR="${TRANSACTION_MIRROR_ADDRESS:-}"
if [[ -n "$SKIP_MIRROR" ]]; then
echo "Skipping TransactionMirror deploy (--skip-mirror)."
if [[ -z "$MIRROR_ADDR" ]]; then
echo "Set TRANSACTION_MIRROR_ADDRESS in $SMOM/.env to the existing mirror address, then re-run for pool-only." >&2
exit 1
fi
elif [[ -n "$MIRROR_ADDR" ]]; then
CODE_LEN=$(cast code "$MIRROR_ADDR" --rpc-url "$RPC" 2>/dev/null | wc -c)
if [[ -n "$CODE_LEN" && "$CODE_LEN" -gt 10 ]]; then
echo "TransactionMirror already deployed at $MIRROR_ADDR (has code). Skipping mirror deploy."
SKIP_MIRROR=1
fi
fi
# Re-query pending nonce for pool deploy; wait briefly so first tx can be mined (reduces "Replacement transaction underpriced")
sleep 3
if [[ -z "$SKIP_MIRROR" ]]; then
echo "Deploying TransactionMirror (NEXT_NONCE=$NEXT_NONCE, gas $GAS_PRICE)..."
if ! forge script script/DeployTransactionMirror.s.sol:DeployTransactionMirror \
--rpc-url "$RPC" --broadcast --private-key "$PRIVATE_KEY" --with-gas-price "$GAS_PRICE"; then
echo ""
echo "If the failure was CreateCollision (contract already at expected address), set in $SMOM/.env:" >&2
echo " TRANSACTION_MIRROR_ADDRESS=0xC7f2Cf4845C6db0e1a1e91ED41Bcd0FcC1b0E141" >&2
echo "Then re-run this script to create only the PMM pool, or run with --skip-mirror." >&2
exit 1
fi
sleep 3
fi
# Re-query pending nonce for pool deploy
NONCE_USED_FIRST=$NEXT_NONCE
NEXT_NONCE=$(cast nonce "$DEPLOYER" --rpc-url "$RPC" --block pending 2>/dev/null) || true
[[ -z "${NEXT_NONCE//[0-9a-fA-Fx]/}" && -n "$NEXT_NONCE" ]] || NEXT_NONCE=$((NONCE_USED_FIRST + 1))
@@ -138,6 +159,10 @@ while true; do
if echo "$POOL_OUTPUT" | grep -q "Script ran successfully"; then
break
fi
if echo "$POOL_OUTPUT" | grep -qE "pool exists|DODOPMMIntegration: pool exists"; then
echo "Pool already exists; continuing."
break
fi
echo "Pool deploy failed. Check output above." >&2
exit 1
done

View File

@@ -0,0 +1,33 @@
#!/usr/bin/env bash
# Deploy TransactionMirror to Chain 138 using next nonce (skip stuck tx).
# Usage: ./scripts/deployment/deploy-transaction-mirror-chain138-nonce-fix.sh [NONCE]
# Default NONCE = 13370 (when current is 13369 stuck). Requires: .env with PRIVATE_KEY; RPC reachable (Public 2201 OK).
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
SMOM="${PROJECT_ROOT}/smom-dbis-138"
NONCE="${1:-13370}"
[[ -f "${SMOM}/.env" ]] && set -a && source "${SMOM}/.env" 2>/dev/null && set +a
RPC="${RPC_URL_138:-${RPC_URL_138_PUBLIC:-http://192.168.11.221:8545}}"
[[ -z "${PRIVATE_KEY:-}" ]] && echo "PRIVATE_KEY not set." >&2 && exit 1
[[ "${PRIVATE_KEY#0x}" == "$PRIVATE_KEY" ]] && export PRIVATE_KEY="0x$PRIVATE_KEY"
ADMIN="${MIRROR_ADMIN:-$(cast wallet address --private-key "$PRIVATE_KEY" 2>/dev/null)}"
echo "Deploying TransactionMirror (nonce=$NONCE) to $RPC"
cd "$SMOM"
out=$(forge create contracts/mirror/TransactionMirror.sol:TransactionMirror \
--constructor-args "$ADMIN" \
--rpc-url "$RPC" \
--private-key "$PRIVATE_KEY" \
--gas-price 1000000000 \
--nonce "$NONCE" 2>&1) || { echo "$out"; exit 1; }
echo "$out"
addr=$(echo "$out" | grep -oE 'Deployed to: (0x[a-fA-F0-9]{40})' | sed 's/Deployed to: //')
[[ -z "$addr" ]] && addr=$(echo "$out" | grep -oE '0x[a-fA-F0-9]{40}' | head -1)
[[ -z "$addr" ]] && { echo "Could not parse deployed address"; exit 1; }
echo ""
echo "TransactionMirror deployed at: $addr"
echo "Update scripts/verify/check-contracts-on-chain-138.sh and docs to use $addr instead of 0xe363a69273C3471ECaf313f8Ca45bc7C538c5e78"

View File

@@ -0,0 +1,93 @@
#!/usr/bin/env bash
# Pre-flight checks before Chain 138 deployment: correct RPC, dotenv, nonce (no stuck txs).
# Optionally run gas/cost estimate for deployment cost.
#
# Usage: ./scripts/deployment/preflight-chain138-deploy.sh [--cost]
# --cost Also run cost estimate (smom-dbis-138/scripts/deployment/calculate-costs-consolidated.sh).
#
# Requires: run from repo root. Uses smom-dbis-138/.env only (PRIVATE_KEY, RPC_URL_138).
# See: docs/03-deployment/DEPLOYMENT_ORDER_OF_OPERATIONS.md § Deployment safety
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
SMOM="${PROJECT_ROOT}/smom-dbis-138"
RUN_COST=""
for a in "$@"; do [[ "$a" == "--cost" ]] && RUN_COST=1; done
echo "=== Chain 138 deployment pre-flight ==="
echo ""
# 1) Dotenv: must exist and be the canonical one
if [[ ! -f "$SMOM/.env" ]]; then
echo "FAIL: $SMOM/.env not found. Use smom-dbis-138/.env only for deployment secrets." >&2
exit 1
fi
echo "OK Dotenv: $SMOM/.env exists (canonical for Chain 138 deploy)."
# 2) Env check script (keys only, no values)
if [[ -f "$SMOM/scripts/deployment/check-env-required.sh" ]]; then
echo ""
bash "$SMOM/scripts/deployment/check-env-required.sh" || { echo "FAIL: env check failed. Fix MISS entries in $SMOM/.env." >&2; exit 1; }
else
echo "WARN: $SMOM/scripts/deployment/check-env-required.sh not found; skipping env key check." >&2
fi
# 3) Load env for RPC and nonce checks (no secrets printed)
[[ -f "${PROJECT_ROOT}/config/ip-addresses.conf" ]] && source "${PROJECT_ROOT}/config/ip-addresses.conf" 2>/dev/null || true
set -a
source "$SMOM/.env"
set +a
RPC="${RPC_URL_138:-http://192.168.11.211:8545}"
if [[ -z "${PRIVATE_KEY:-}" ]]; then
echo "FAIL: PRIVATE_KEY not set in $SMOM/.env." >&2
exit 1
fi
# 4) RPC: must be Core (chainId 138 = 0x8a)
echo ""
chain_id_hex=$(curl -s -m 10 -X POST "$RPC" -H "Content-Type: application/json" \
-d '{"jsonrpc":"2.0","method":"eth_chainId","params":[],"id":1}' 2>/dev/null | sed -n 's/.*"result":"\([^"]*\)".*/\1/p') || true
if [[ "$chain_id_hex" != "0x8a" ]]; then
if [[ -n "$chain_id_hex" ]]; then
echo "FAIL: RPC returned chainId $chain_id_hex (expected 0x8a for Chain 138). Use Core RPC only (RPC_URL_138 = VMID 2101, e.g. http://192.168.11.211:8545)." >&2
else
echo "FAIL: RPC unreachable: $RPC. Fix Core RPC or network." >&2
fi
echo " See docs/04-configuration/RPC_ENDPOINTS_MASTER.md." >&2
exit 1
fi
echo "OK RPC (Core): $RPC (chainId 138)."
# 5) Nonce: warn if pending > latest (stuck txs)
DEPLOYER=$(cast wallet address --private-key "$PRIVATE_KEY" 2>/dev/null) || { echo "FAIL: cast wallet address failed. Check PRIVATE_KEY in .env." >&2; exit 1; }
NONCE_PENDING=$(cast nonce "$DEPLOYER" --rpc-url "$RPC" --block pending 2>/dev/null) || true
NONCE_LATEST=$(cast nonce "$DEPLOYER" --rpc-url "$RPC" --block latest 2>/dev/null) || true
# Normalize to decimal (cast may return hex 0xN or decimal N)
[[ -z "${NONCE_LATEST//[0-9a-fA-Fx]/}" && -n "$NONCE_LATEST" ]] || NONCE_LATEST=0
[[ -z "${NONCE_PENDING//[0-9a-fA-Fx]/}" && -n "$NONCE_PENDING" ]] || NONCE_PENDING="$NONCE_LATEST"
NONCE_PENDING=$((NONCE_PENDING))
NONCE_LATEST=$((NONCE_LATEST))
echo " Deployer: $DEPLOYER"
echo " Nonce (pending): $NONCE_PENDING (latest: $NONCE_LATEST)"
if [[ $NONCE_PENDING -gt $NONCE_LATEST ]]; then
echo ""
echo "WARN: Pending nonce ($NONCE_PENDING) > latest ($NONCE_LATEST) — possible stuck transaction(s)." >&2
echo " Do NOT deploy until resolved: run ./scripts/clear-all-transaction-pools.sh then wait ~60s." >&2
echo " See docs/03-deployment/DEPLOYMENT_ORDER_OF_OPERATIONS.md § Do not deploy when stuck." >&2
exit 1
fi
echo "OK No stuck transactions (nonce consistent)."
# 6) Optional: cost estimate
if [[ -n "$RUN_COST" ]] && [[ -f "$SMOM/scripts/deployment/calculate-costs-consolidated.sh" ]]; then
echo ""
echo "=== Cost estimate (--cost) ==="
(cd "$SMOM" && bash scripts/deployment/calculate-costs-consolidated.sh) || true
fi
echo ""
echo "Pre-flight passed. Proceed with deployment using scripts that source $SMOM/.env and use RPC_URL_138 (Core only)."

View File

@@ -0,0 +1,100 @@
#!/usr/bin/env bash
# Run all deployment next steps for Chain 138 in order: preflight → mirror+pool (or pool-only) → register c* as GRU → verify.
#
# Usage: ./scripts/deployment/run-all-next-steps-chain138.sh [--dry-run] [--skip-mirror] [--skip-register-gru] [--skip-verify]
# --dry-run Print steps only; do not run deploy/scripts.
# --skip-mirror Do not deploy TransactionMirror (pool-only; requires TRANSACTION_MIRROR_ADDRESS in smom-dbis-138/.env).
# --skip-register-gru Skip RegisterGRUCompliantTokens (e.g. if already registered).
# --skip-verify Skip final on-chain verification.
#
# Requires: repo root; smom-dbis-138/.env with PRIVATE_KEY, RPC_URL_138; for register-gru: UNIVERSAL_ASSET_REGISTRY, CUSDT_ADDRESS_138, CUSDC_ADDRESS_138 (and optional c* vars).
# See: docs/03-deployment/DEPLOYMENT_ORDER_OF_OPERATIONS.md
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
SMOM="$PROJECT_ROOT/smom-dbis-138"
DRY_RUN=""
SKIP_MIRROR=""
SKIP_REGISTER_GRU=""
SKIP_VERIFY=""
for a in "$@"; do
[[ "$a" == "--dry-run" ]] && DRY_RUN=1
[[ "$a" == "--skip-mirror" ]] && SKIP_MIRROR=1
[[ "$a" == "--skip-register-gru" ]] && SKIP_REGISTER_GRU=1
[[ "$a" == "--skip-verify" ]] && SKIP_VERIFY=1
done
echo "=== Chain 138 — run all next steps ==="
echo " dry-run: $DRY_RUN skip-mirror: $SKIP_MIRROR skip-register-gru: $SKIP_REGISTER_GRU skip-verify: $SKIP_VERIFY"
echo ""
# 1) Preflight
echo "--- Step 1: Preflight ---"
if [[ -n "$DRY_RUN" ]]; then
echo "[DRY-RUN] $PROJECT_ROOT/scripts/deployment/preflight-chain138-deploy.sh"
else
"$SCRIPT_DIR/preflight-chain138-deploy.sh" || { echo "Preflight failed." >&2; exit 1; }
fi
echo ""
# 2) TransactionMirror + PMM pool (or pool-only)
echo "--- Step 2: TransactionMirror + PMM pool ---"
if [[ -n "$DRY_RUN" ]]; then
if [[ -n "$SKIP_MIRROR" ]]; then
echo "[DRY-RUN] $PROJECT_ROOT/scripts/deployment/deploy-transaction-mirror-and-pmm-pool-after-txpool-clear.sh --skip-mirror"
else
echo "[DRY-RUN] $PROJECT_ROOT/scripts/deployment/deploy-transaction-mirror-and-pmm-pool-after-txpool-clear.sh"
fi
else
if [[ -n "$SKIP_MIRROR" ]]; then
"$PROJECT_ROOT/scripts/deployment/deploy-transaction-mirror-and-pmm-pool-after-txpool-clear.sh" --skip-mirror || { echo "Deploy (pool-only) failed." >&2; exit 1; }
else
"$PROJECT_ROOT/scripts/deployment/deploy-transaction-mirror-and-pmm-pool-after-txpool-clear.sh" || { echo "Deploy failed." >&2; exit 1; }
fi
fi
echo ""
# 3) Register c* as GRU (optional)
if [[ -z "$SKIP_REGISTER_GRU" ]]; then
echo "--- Step 3: Register c* as GRU (UniversalAssetRegistry) ---"
if [[ -n "$DRY_RUN" ]]; then
echo "[DRY-RUN] cd $SMOM && forge script script/deploy/RegisterGRUCompliantTokens.s.sol --rpc-url \$RPC_URL_138 --broadcast --private-key \$PRIVATE_KEY --with-gas-price 1000000000"
else
if [[ -f "$SMOM/.env" ]]; then
set -a; source "$SMOM/.env"; set +a
# Fallback: Register script expects CUSDT_ADDRESS_138/CUSDC_ADDRESS_138; use COMPLIANT_USDT/COMPLIANT_USDC if set
[[ -z "${CUSDT_ADDRESS_138:-}" && -n "${COMPLIANT_USDT:-}" ]] && export CUSDT_ADDRESS_138="$COMPLIANT_USDT"
[[ -z "${CUSDC_ADDRESS_138:-}" && -n "${COMPLIANT_USDC:-}" ]] && export CUSDC_ADDRESS_138="$COMPLIANT_USDC"
if [[ -n "${UNIVERSAL_ASSET_REGISTRY:-}" && ( -n "${CUSDT_ADDRESS_138:-}" || -n "${CUSDC_ADDRESS_138:-}" ) ]]; then
(cd "$SMOM" && forge script script/deploy/RegisterGRUCompliantTokens.s.sol --rpc-url "${RPC_URL_138:-http://192.168.11.211:8545}" --broadcast --private-key "$PRIVATE_KEY" --with-gas-price 1000000000) || echo "RegisterGRUCompliantTokens failed or skipped (check UNIVERSAL_ASSET_REGISTRY and CUSDT_ADDRESS_138/CUSDC_ADDRESS_138)."
else
echo "Skip: set UNIVERSAL_ASSET_REGISTRY and CUSDT_ADDRESS_138 (and optional c* vars) in $SMOM/.env to register c* as GRU."
fi
else
echo "Skip: $SMOM/.env not found."
fi
fi
echo ""
else
echo "--- Step 3: Register c* as GRU (skipped) ---"
echo ""
fi
# 4) Verify
if [[ -z "$SKIP_VERIFY" ]]; then
echo "--- Step 4: On-chain verification ---"
if [[ -n "$DRY_RUN" ]]; then
echo "[DRY-RUN] $PROJECT_ROOT/scripts/verify/check-contracts-on-chain-138.sh"
else
[[ -f "$SMOM/.env" ]] && set -a && source "$SMOM/.env" && set +a
"$PROJECT_ROOT/scripts/verify/check-contracts-on-chain-138.sh" "${RPC_URL_138:-}" || true
fi
echo ""
else
echo "--- Step 4: Verify (skipped) ---"
echo ""
fi
echo "=== Next steps run complete. ==="

View File

@@ -0,0 +1,85 @@
#!/usr/bin/env bash
# Run all checkable "before deploy" items from RECOMMENDATIONS_AND_FIXES_BEFORE_DEPLOY.md.
# Usage: ./scripts/deployment/run-before-deploy-checks.sh [--cost] [--alltra] [--on-chain] [--skip-build]
# --cost Run preflight with --cost (gas estimate).
# --alltra Include alltra-lifi-settlement in contract tests (slower).
# --on-chain Run check-contracts-on-chain-138.sh (requires RPC).
# --skip-build Skip forge build; use existing artifacts (step 3 and test script both skip build).
#
# Requires: run from repo root; forge in PATH.
# See: docs/03-deployment/RECOMMENDATIONS_AND_FIXES_BEFORE_DEPLOY.md
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
RUN_COST=""
RUN_ALLTRA=""
RUN_ONCHAIN=""
SKIP_BUILD=""
FAILED=0
for a in "$@"; do
case "$a" in
--cost) RUN_COST=1 ;;
--alltra) RUN_ALLTRA=1 ;;
--on-chain) RUN_ONCHAIN=1 ;;
--skip-build) SKIP_BUILD=1 ;;
esac
done
echo "=== Before-deploy checks (recommendations and fixes) ==="
echo ""
# 1) Preflight
echo "--- 1. Preflight (RPC, dotenv, nonce) ---"
if [[ -n "$RUN_COST" ]]; then
if "$SCRIPT_DIR/preflight-chain138-deploy.sh" --cost; then echo " PASS"; else echo " FAIL"; FAILED=$((FAILED+1)); fi
else
if "$SCRIPT_DIR/preflight-chain138-deploy.sh"; then echo " PASS"; else echo " FAIL"; FAILED=$((FAILED+1)); fi
fi
echo ""
# 2) Env check (smom-dbis-138)
echo "--- 2. Env check (smom-dbis-138) ---"
if (cd "$PROJECT_ROOT/smom-dbis-138" && ./scripts/deployment/check-env-required.sh) >/dev/null 2>&1; then echo " PASS"; else echo " FAIL"; FAILED=$((FAILED+1)); fi
echo ""
# 3) Forge build (skip if --skip-build)
echo "--- 3. Forge build (smom-dbis-138) ---"
if [[ -n "$SKIP_BUILD" ]]; then
echo " SKIP (--skip-build)"
else
if (cd "$PROJECT_ROOT/smom-dbis-138" && forge build) >/dev/null 2>&1; then echo " PASS"; else echo " FAIL"; FAILED=$((FAILED+1)); fi
fi
echo ""
# 4) Contract tests (skip build here; use step 3 build or existing artifacts)
echo "--- 4. Contract tests (unit; use --alltra for e2e) ---"
if [[ -n "$RUN_ALLTRA" ]]; then
if "$SCRIPT_DIR/test-all-contracts-before-deploy.sh" --alltra --skip-build 2>/dev/null; then echo " PASS"; else echo " FAIL"; FAILED=$((FAILED+1)); fi
else
if "$SCRIPT_DIR/test-all-contracts-before-deploy.sh" --no-match "Fork|Mainnet|Integration|e2e" --skip-build 2>/dev/null; then echo " PASS"; else echo " FAIL"; FAILED=$((FAILED+1)); fi
fi
echo ""
# 5) Config validation
echo "--- 5. Config validation ---"
if (cd "$PROJECT_ROOT" && bash scripts/validation/validate-config-files.sh) >/dev/null 2>&1; then echo " PASS"; else echo " FAIL"; FAILED=$((FAILED+1)); fi
echo ""
# 6) On-chain verification (optional)
if [[ -n "$RUN_ONCHAIN" ]]; then
echo "--- 6. On-chain verification (Chain 138) ---"
if (cd "$PROJECT_ROOT" && ./scripts/verify/check-contracts-on-chain-138.sh) >/dev/null 2>&1; then echo " PASS"; else echo " FAIL"; FAILED=$((FAILED+1)); fi
echo ""
fi
echo "=== Summary ==="
if [[ $FAILED -eq 0 ]]; then
echo "All checkable items passed. Complete remaining operator items (gas, POOL_MANAGER_ROLE, RPC writable if needed) per RECOMMENDATIONS_AND_FIXES_BEFORE_DEPLOY.md."
exit 0
else
echo "$FAILED check(s) failed. Fix and re-run."
exit 1
fi

View File

@@ -0,0 +1,138 @@
#!/usr/bin/env bash
# Run remaining cW* steps: deploy (or dry-run), update token-mapping from .env, optional verify.
# See docs/07-ccip/CW_DEPLOY_AND_WIRE_RUNBOOK.md and docs/00-meta/CW_BRIDGE_TASK_LIST.md.
#
# Usage:
# ./scripts/deployment/run-cw-remaining-steps.sh [--dry-run] [--deploy] [--update-mapping] [--verify]
# --dry-run Run deploy-cw in dry-run mode (print commands only).
# --deploy Run deploy-cw on all chains (requires RPC/PRIVATE_KEY in smom-dbis-138/.env).
# --update-mapping Update config/token-mapping-multichain.json from CWUSDT_*/CWUSDC_* in .env.
# --verify For each chain with CWUSDT_* set, check MINTER_ROLE/BURNER_ROLE on cW* for CW_BRIDGE_*.
# With no options, runs --dry-run then --update-mapping (if any CWUSDT_* in .env).
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
SMOM="${PROJECT_ROOT}/smom-dbis-138"
CONFIG="${PROJECT_ROOT}/config/token-mapping-multichain.json"
DRY_RUN=false
DO_DEPLOY=false
DO_UPDATE_MAPPING=false
DO_VERIFY=false
for a in "$@"; do
case "$a" in
--dry-run) DRY_RUN=true ;;
--deploy) DO_DEPLOY=true ;;
--update-mapping) DO_UPDATE_MAPPING=true ;;
--verify) DO_VERIFY=true ;;
esac
done
if ! $DRY_RUN && ! $DO_DEPLOY && ! $DO_UPDATE_MAPPING && ! $DO_VERIFY; then
DRY_RUN=true
DO_UPDATE_MAPPING=true
fi
if [[ ! -f "$SMOM/.env" ]]; then
echo "Missing $SMOM/.env" >&2
exit 1
fi
set -a
source "$SMOM/.env"
set +a
# Chain name (env suffix) -> chainId for 138 -> chain pairs
declare -A CHAIN_NAME_TO_ID=(
[MAINNET]=1 [CRONOS]=25 [BSC]=56 [POLYGON]=137 [GNOSIS]=100
[AVALANCHE]=43114 [BASE]=8453 [ARBITRUM]=42161 [OPTIMISM]=10 [ALL]=651940
)
if $DO_DEPLOY; then
echo "=== Deploy cW* (DeployCWTokens) on all chains ==="
(cd "$SMOM" && ./scripts/deployment/deploy-tokens-and-weth-all-chains-skip-canonical.sh --deploy-cw)
echo "→ Set CWUSDT_<CHAIN> and CWUSDC_<CHAIN> in $SMOM/.env from script output; then run with --update-mapping"
fi
if $DRY_RUN; then
echo "=== Dry-run: deploy cW* (commands only) ==="
(cd "$SMOM" && ./scripts/deployment/deploy-tokens-and-weth-all-chains-skip-canonical.sh --deploy-cw --dry-run)
fi
update_mapping() {
local env_file="$SMOM/.env"
local config_file="$CONFIG"
[[ -f "$config_file" ]] || { echo "Missing $config_file" >&2; return 1; }
node -e "
const fs = require('fs');
const path = require('path');
function loadEnv(f) {
const c = fs.readFileSync(f, 'utf8');
const out = {};
c.split('\n').forEach(line => {
const m = line.match(/^([A-Za-z_0-9]+)=(.*)$/);
if (m) out[m[1]] = m[2].replace(/^[\"']|[\"']\$/g, '').trim();
});
return out;
}
const env = loadEnv('$env_file');
const chainToId = { MAINNET: 1, CRONOS: 25, BSC: 56, POLYGON: 137, GNOSIS: 100, AVALANCHE: 43114, BASE: 8453, ARBITRUM: 42161, OPTIMISM: 10, ALL: 651940 };
const keyToEnv = { Compliant_USDT_cW: 'CWUSDT', Compliant_USDC_cW: 'CWUSDC', Compliant_EURC_cW: 'CWEURC', Compliant_EURT_cW: 'CWEURT', Compliant_GBPC_cW: 'CWGBPC', Compliant_GBPT_cW: 'CWGBPT', Compliant_AUDC_cW: 'CWAUDC', Compliant_JPYC_cW: 'CWJPYC', Compliant_CHFC_cW: 'CWCHFC', Compliant_CADC_cW: 'CWCADC', Compliant_XAUC_cW: 'CWXAUC', Compliant_XAUT_cW: 'CWXAUT' };
const j = JSON.parse(fs.readFileSync('$config_file', 'utf8'));
let updated = 0;
for (const [name, chainId] of Object.entries(chainToId)) {
const pair = j.pairs.find(p => p.fromChainId === 138 && p.toChainId === chainId);
if (!pair) continue;
for (const t of pair.tokens) {
const envKey = keyToEnv[t.key];
if (!envKey) continue;
const addr = env[envKey + '_' + name];
if (addr && t.addressTo !== addr) { t.addressTo = addr; updated++; }
}
}
if (updated) {
fs.writeFileSync('$config_file', JSON.stringify(j, null, 2) + '\n');
console.log('Updated', updated, 'addressTo entries in token-mapping-multichain.json');
} else {
console.log('No cW* addresses set in .env for mapped chains, or already up to date');
}
"
}
if $DO_UPDATE_MAPPING; then
echo "=== Update token-mapping from .env ==="
update_mapping
fi
if $DO_VERIFY; then
echo "=== Verify MINTER/BURNER roles on cW* for each chain ==="
MINTER_ROLE=$(cast keccak "MINTER_ROLE" 2>/dev/null || echo "0x")
BURNER_ROLE=$(cast keccak "BURNER_ROLE" 2>/dev/null || echo "0x")
for name in MAINNET CRONOS BSC POLYGON GNOSIS AVALANCHE BASE ARBITRUM OPTIMISM; do
cwusdt_var="CWUSDT_${name}"
bridge_var="CW_BRIDGE_${name}"
cwusdt="${!cwusdt_var:-}"
bridge="${!bridge_var:-}"
rpc_var="${name}_RPC_URL"
[[ -z "$rpc_var" ]] && rpc_var="${name}_RPC"
rpc="${!rpc_var:-}"
if [[ -z "$cwusdt" || -z "$bridge" ]]; then continue; fi
if [[ -z "$rpc" ]]; then
case "$name" in
MAINNET) rpc="${ETH_MAINNET_RPC_URL:-${ETHEREUM_MAINNET_RPC:-}}";;
CRONOS) rpc="${CRONOS_RPC_URL:-${CRONOS_RPC:-}}";;
BSC) rpc="${BSC_RPC_URL:-}";;
POLYGON) rpc="${POLYGON_MAINNET_RPC:-${POLYGON_RPC_URL:-}}";;
GNOSIS) rpc="${GNOSIS_RPC:-}";;
AVALANCHE) rpc="${AVALANCHE_RPC_URL:-}";;
BASE) rpc="${BASE_MAINNET_RPC:-}";;
ARBITRUM) rpc="${ARBITRUM_MAINNET_RPC:-}";;
OPTIMISM) rpc="${OPTIMISM_MAINNET_RPC:-}";;
esac
fi
if [[ -z "$rpc" ]]; then echo " Skip $name: no RPC"; continue; fi
m=$(cast call "$cwusdt" "hasRole(bytes32,address)(bool)" "$MINTER_ROLE" "$bridge" --rpc-url "$rpc" 2>/dev/null || echo "false")
b=$(cast call "$cwusdt" "hasRole(bytes32,address)(bool)" "$BURNER_ROLE" "$bridge" --rpc-url "$rpc" 2>/dev/null || echo "false")
echo " $name: MINTER=$m BURNER=$b (cWUSDT=$cwusdt bridge=$bridge)"
done
fi
echo "Done. See docs/07-ccip/CW_DEPLOY_AND_WIRE_RUNBOOK.md for Phase E (relay and E2E)."

View File

@@ -0,0 +1,88 @@
#!/usr/bin/env bash
# Set COMPLIANT_USDT/COMPLIANT_USDC (all c*) and other Chain 138 token addresses in smom-dbis-138/.env,
# then run RegisterGRUCompliantTokens to register all c* as GRU in UniversalAssetRegistry.
#
# Addresses are from docs/11-references/CONTRACT_ADDRESSES_REFERENCE.md and TOKENS_AND_NETWORKS_MINTABLE_TO_DEPLOYER.md.
# Usage: ./scripts/deployment/set-dotenv-c-tokens-and-register-gru.sh [--no-register]
# --no-register Only update .env; do not run RegisterGRUCompliantTokens.
#
# Note: RegisterGRUCompliantTokens requires (1) broadcast account has REGISTRAR_ROLE, and (2) the
# UniversalAssetRegistry *implementation* (not just proxy) exposes registerGRUCompliantAsset.
# Grant REGISTRAR_ROLE (role hash = keccak256("REGISTRAR_ROLE")):
# REGISTRAR_ROLE=0xedcc084d3dcd65a1f7f23c65c46722faca6953d28e43150a467cf43e5c309238
# cast send $UNIVERSAL_ASSET_REGISTRY "grantRole(bytes32,address)" $REGISTRAR_ROLE $DEPLOYER --rpc-url $RPC_URL_138 --private-key $PRIVATE_KEY --gas-limit 100000
# If registration still reverts (empty revert data), the proxy's implementation may be an older
# version without registerGRUCompliantAsset — upgrade the implementation then re-run.
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
SMOM="$PROJECT_ROOT/smom-dbis-138"
ENV_FILE="$SMOM/.env"
RUN_REGISTER=1
for a in "$@"; do [[ "$a" == "--no-register" ]] && RUN_REGISTER=0; done
if [[ ! -f "$ENV_FILE" ]]; then
echo "Missing $ENV_FILE. Create it first (e.g. copy from .env.example)." >&2
exit 1
fi
# Set or update a single variable in .env (value must not contain newline or unescaped specials)
set_env_var() {
local var="$1" val="$2"
if grep -q "^${var}=" "$ENV_FILE" 2>/dev/null; then
sed -i "s|^${var}=.*|${var}=${val}|" "$ENV_FILE"
else
echo "${var}=${val}" >> "$ENV_FILE"
fi
}
echo "=== Setting c* and token addresses in $ENV_FILE (canonical Chain 138) ==="
# Canonical compliant tokens (c*) — CONTRACT_ADDRESSES_REFERENCE + TOKENS_AND_NETWORKS
set_env_var "COMPLIANT_USDT" "0x93E66202A11B1772E55407B32B44e5Cd8eda7f22"
set_env_var "COMPLIANT_USDC" "0xf22258f57794CC8E06237084b353Ab30fFfa640b"
set_env_var "CUSDT_ADDRESS_138" "0x93E66202A11B1772E55407B32B44e5Cd8eda7f22"
set_env_var "CUSDC_ADDRESS_138" "0xf22258f57794CC8E06237084b353Ab30fFfa640b"
# cEURC (TOKENS_AND_NETWORKS_MINTABLE_TO_DEPLOYER)
set_env_var "CEURC_ADDRESS_138" "0x8085961F9cF02b4d800A3c6d386D31da4B34266a"
# Remaining c* (Chain 138) — from DeployCompliantFiatTokens / ENV_EXAMPLE_CONTENT.md; register as GRU
set_env_var "CEURT_ADDRESS_138" "0xdf4b71c61E5912712C1Bdd451416B9aC26949d72"
set_env_var "CGBPC_ADDRESS_138" "0x003960f16D9d34F2e98d62723B6721Fb92074aD2"
set_env_var "CGBPT_ADDRESS_138" "0x350f54e4D23795f86A9c03988c7135357CCaD97c"
set_env_var "CAUDC_ADDRESS_138" "0xD51482e567c03899eecE3CAe8a058161FD56069D"
set_env_var "CJPYC_ADDRESS_138" "0xEe269e1226a334182aace90056EE4ee5Cc8A6770"
set_env_var "CCHFC_ADDRESS_138" "0x873990849DDa5117d7C644f0aF24370797C03885"
set_env_var "CCADC_ADDRESS_138" "0x54dBd40cF05e15906A2C21f600937e96787f5679"
set_env_var "CXAUC_ADDRESS_138" "0x290E52a8819A4fbD0714E517225429aA2B70EC6b"
set_env_var "CXAUT_ADDRESS_138" "0x94e408E26c6FD8F4ee00b54dF19082FDA07dC96E"
# UniversalAssetRegistry (required for GRU registration)
set_env_var "UNIVERSAL_ASSET_REGISTRY" "0xAEE4b7fBe82E1F8295951584CBc772b8BBD68575"
# Other key tokens (Chain 138) — CONTRACT_ADDRESSES_REFERENCE canonical
set_env_var "WETH9" "0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2"
set_env_var "WETH10" "0xf4BB2e28688e89fCcE3c0580D37d36A7672E8A9f"
set_env_var "LINK_TOKEN" "0xb7721dD53A8c629d9f1Ba31a5819AFe250002b03"
set_env_var "CCIP_FEE_TOKEN" "0xb7721dD53A8c629d9f1Ba31a5819AFe250002b03"
echo "Done. Set: COMPLIANT_USDT, COMPLIANT_USDC, all C*_ADDRESS_138 (cUSDT, cUSDC, cEURC, cEURT, cGBPC, cGBPT, cAUDC, cJPYC, cCHFC, cCADC, cXAUC, cXAUT), UNIVERSAL_ASSET_REGISTRY, WETH9, WETH10, LINK_TOKEN, CCIP_FEE_TOKEN."
echo "All c* on explorer.d-bis.org/tokens must be GRU-registered. See docs/04-configuration/EXPLORER_TOKENS_GRU_POLICY.md."
if [[ "$RUN_REGISTER" -eq 0 ]]; then
echo "Skipping GRU registration (--no-register)."
exit 0
fi
echo ""
echo "=== Registering all c* as GRU (RegisterGRUCompliantTokens) ==="
set -a
source "$ENV_FILE"
set +a
RPC="${RPC_URL_138:-http://192.168.11.211:8545}"
export RPC_URL_138="$RPC"
(cd "$SMOM" && forge script script/deploy/RegisterGRUCompliantTokens.s.sol \
--rpc-url "$RPC_URL_138" --broadcast --private-key "$PRIVATE_KEY" --with-gas-price 1000000000)
echo "=== Done. ==="

View File

@@ -0,0 +1,37 @@
#!/usr/bin/env bash
# Append missing Chain 138 / DODO PMM env vars to smom-dbis-138/.env (no overwrite, no secrets).
# Usage: ./scripts/deployment/set-missing-dotenv-chain138.sh
# From smom-dbis-138: ../scripts/deployment/set-missing-dotenv-chain138.sh (if called from there, adjust path)
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
ENV_FILE="${SMOM_ENV_FILE:-$PROJECT_ROOT/smom-dbis-138/.env}"
if [[ ! -f "$ENV_FILE" ]]; then
echo "Error: $ENV_FILE not found. Create it from env.additions.example or copy from .env.example." >&2
exit 1
fi
append_if_missing() {
local key="$1"
local value="$2"
if ! grep -qE "^${key}=" "$ENV_FILE" 2>/dev/null; then
echo "${key}=${value}" >> "$ENV_FILE"
echo " Added: $key"
fi
}
echo "=== Set missing dotenv (Chain 138 / DODO PMM) ==="
echo " Target: $ENV_FILE"
echo ""
append_if_missing "DODO_PMM_PROVIDER_ADDRESS" "0x8EF6657D2a86c569F6ffc337EE6b4260Bd2e59d0"
append_if_missing "DODO_PMM_INTEGRATION_ADDRESS" "0x79cdbaFBaA0FdF9F55D26F360F54cddE5c743F7D"
append_if_missing "POOL_CUSDTCUSDC" "0x9fcB06Aa1FD5215DC0E91Fd098aeff4B62fEa5C8"
append_if_missing "POOL_CUSDTUSDT" "0xa3Ee6091696B28e5497b6F491fA1e99047250c59"
append_if_missing "POOL_CUSDCUSDC" "0x90bd9Bf18Daa26Af3e814ea224032d015db58Ea5"
echo ""
echo "Done. Verify: grep -E 'DODO_PMM|POOL_' $ENV_FILE"

View File

@@ -0,0 +1,87 @@
#!/usr/bin/env bash
# Run all contract tests before deploying (Phase 0.8).
# Usage: ./scripts/deployment/test-all-contracts-before-deploy.sh [--dry-run] [--alltra] [--no-match PATTERN] [--skip-build]
#
# --dry-run Print commands only; do not run forge build/test.
# --alltra Also run forge test and npm run test:e2e in alltra-lifi-settlement.
# --no-match Exclude tests matching PATTERN (e.g. "Fork|Mainnet|Integration|e2e" for unit-only).
# --skip-build Skip forge build; use existing artifacts (forge test still compiles changed files incrementally).
#
# Requires: run from repo root; forge in PATH.
# See: docs/03-deployment/DEPLOYMENT_ORDER_OF_OPERATIONS.md § Phase 0.8
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
DRY_RUN=""
ALLTRA=""
NO_MATCH=""
SKIP_BUILD=""
while [[ $# -gt 0 ]]; do
case "$1" in
--dry-run) DRY_RUN=1; shift ;;
--skip-build) SKIP_BUILD=1; shift ;;
--alltra) ALLTRA=1; shift ;;
--no-match)
if [[ -n "${2:-}" && "${2:0:1}" != "-" ]]; then
NO_MATCH="$2"; shift 2
else
NO_MATCH="Fork|Mainnet|Integration|e2e"; shift
fi
;;
*) shift ;;
esac
done
echo "=== Test all contracts before deploy ==="
echo ""
# 1) smom-dbis-138: forge build (skip if --skip-build or already built)
if [[ -n "$SKIP_BUILD" ]]; then
echo "--- smom-dbis-138: forge build (skipped, using existing artifacts) ---"
elif [[ -n "$DRY_RUN" ]]; then
echo "--- smom-dbis-138: forge build ---"
echo "[DRY-RUN] cd $PROJECT_ROOT/smom-dbis-138 && forge build"
else
echo "--- smom-dbis-138: forge build ---"
(cd "$PROJECT_ROOT/smom-dbis-138" && forge build) || { echo "FAIL: forge build (smom-dbis-138)" >&2; exit 1; }
fi
echo ""
# 2) smom-dbis-138: forge test (includes GRU c* integration: GRUCompliantTokensRegistryTest)
echo "--- smom-dbis-138: forge test ---"
if [[ -n "$NO_MATCH" ]]; then
if [[ -n "$DRY_RUN" ]]; then
echo "[DRY-RUN] cd $PROJECT_ROOT/smom-dbis-138 && forge test --no-match-test \"$NO_MATCH\""
else
(cd "$PROJECT_ROOT/smom-dbis-138" && forge test --no-match-test "$NO_MATCH") || { echo "FAIL: forge test (smom-dbis-138)" >&2; exit 1; }
fi
else
if [[ -n "$DRY_RUN" ]]; then
echo "[DRY-RUN] cd $PROJECT_ROOT/smom-dbis-138 && forge test"
else
(cd "$PROJECT_ROOT/smom-dbis-138" && forge test) || { echo "FAIL: forge test (smom-dbis-138)" >&2; exit 1; }
fi
fi
echo ""
# 3) Optional: alltra-lifi-settlement
if [[ -n "$ALLTRA" ]]; then
echo "--- alltra-lifi-settlement: forge test ---"
if [[ -n "$DRY_RUN" ]]; then
echo "[DRY-RUN] cd $PROJECT_ROOT/alltra-lifi-settlement && forge test"
echo "[DRY-RUN] cd $PROJECT_ROOT/alltra-lifi-settlement && npm run test:e2e"
else
(cd "$PROJECT_ROOT/alltra-lifi-settlement" && forge test) || { echo "FAIL: forge test (alltra-lifi-settlement)" >&2; exit 1; }
(cd "$PROJECT_ROOT/alltra-lifi-settlement" && npm run test:e2e) || { echo "FAIL: npm run test:e2e (alltra-lifi-settlement)" >&2; exit 1; }
fi
echo ""
fi
if [[ -n "$DRY_RUN" ]]; then
echo "Dry-run complete. Run without --dry-run to execute."
else
echo "All contract tests passed. Proceed with deployment (Phase 1+)."
fi