podman wip

This commit is contained in:
johba 2025-09-24 10:57:22 +02:00 committed by root
parent efecc5c348
commit 18d63e14d7
10 changed files with 482 additions and 0 deletions

15
containers/Caddyfile Normal file
View file

@ -0,0 +1,15 @@
:80 {
route /graphql* {
reverse_proxy ponder:42069
}
route /health* {
reverse_proxy ponder:42069
}
route /rpc/anvil* {
reverse_proxy anvil:8545
}
route /txn* {
reverse_proxy txn-bot:43069
}
reverse_proxy frontend:5173
}

14
containers/anvil-entrypoint.sh Executable file
View file

@ -0,0 +1,14 @@
#!/usr/bin/env bash
set -euo pipefail
MNEMONIC_FILE=/workspace/onchain/.secret.local
ANVIL_CMD=(anvil --fork-url "${FORK_URL:-https://sepolia.base.org}" --chain-id 31337 --block-time 1 --host 0.0.0.0 --port 8545)
if [[ -f "$MNEMONIC_FILE" ]]; then
MNEMONIC="$(tr -d '\n\r' <"$MNEMONIC_FILE")"
if [[ -n "$MNEMONIC" ]]; then
ANVIL_CMD+=(--mnemonic "$MNEMONIC")
fi
fi
exec "${ANVIL_CMD[@]}"

199
containers/bootstrap.sh Executable file
View file

@ -0,0 +1,199 @@
#!/usr/bin/env bash
set -euo pipefail
ROOT_DIR=/workspace
STATE_DIR=$ROOT_DIR/tmp/podman
LOG_DIR=$STATE_DIR/logs
SETUP_LOG=$LOG_DIR/setup.log
CONTRACT_ENV=$STATE_DIR/contracts.env
TXNBOT_ENV=$STATE_DIR/txnBot.env
MNEMONIC_FILE=$ROOT_DIR/onchain/.secret.local
mkdir -p "$LOG_DIR"
: >"$SETUP_LOG"
ANVIL_RPC=${ANVIL_RPC:-"http://anvil:8545"}
FEE_DEST=0xf6a3eef9088A255c32b6aD2025f83E57291D9011
WETH=0x4200000000000000000000000000000000000006
SWAP_ROUTER=0x94cC0AaC535CCDB3C01d6787D6413C739ae12bc4
MAX_UINT=0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
DEFAULT_DEPLOYER_PK=0xac0974bec39a17e36ba4a6b4d238ff944bacb478cbed5efcae784d7bf4f2ff80
DEFAULT_DEPLOYER_ADDR=0xf39Fd6e51aad88F6F4ce6aB8827279cffFb92266
DEPLOYER_PK=${DEPLOYER_PK:-$DEFAULT_DEPLOYER_PK}
DEPLOYER_ADDR=${DEPLOYER_ADDR:-$DEFAULT_DEPLOYER_ADDR}
DEFAULT_TXNBOT_PRIVATE_KEY=0x59c6995e998f97a5a0044966f0945389dc9e86dae88c7a8412f4603b6b78690d
DEFAULT_TXNBOT_ADDRESS=0x70997970C51812dc3A010C7d01b50e0d17dc79C8
TXNBOT_PRIVATE_KEY=${TXNBOT_PRIVATE_KEY:-$DEFAULT_TXNBOT_PRIVATE_KEY}
TXNBOT_ADDRESS=${TXNBOT_ADDRESS:-$DEFAULT_TXNBOT_ADDRESS}
TXNBOT_FUND_VALUE=${TXNBOT_FUND_VALUE:-1ether}
log() {
echo "[bootstrap] $*"
}
wait_for_rpc() {
for _ in {1..120}; do
if curl -s -o /dev/null -X POST "$ANVIL_RPC" \
-H "Content-Type: application/json" \
-d '{"jsonrpc":"2.0","id":1,"method":"eth_chainId","params":[]}'; then
return 0
fi
sleep 1
done
log "Timed out waiting for Anvil at $ANVIL_RPC"
return 1
}
maybe_set_deployer_from_mnemonic() {
if [[ -n "$DEPLOYER_PK" && -n "$DEPLOYER_ADDR" ]]; then
return
fi
if [[ -f "$MNEMONIC_FILE" ]]; then
local mnemonic pk addr
mnemonic="$(tr -d '\n\r' <"$MNEMONIC_FILE")"
if [[ -n "$mnemonic" ]]; then
pk="$(cast wallet private-key --mnemonic "$mnemonic" --mnemonic-derivation-path "m/44'/60'/0'/0/0")"
addr="$(cast wallet address --private-key "$pk")"
DEPLOYER_PK=${DEPLOYER_PK:-$pk}
DEPLOYER_ADDR=${DEPLOYER_ADDR:-$addr}
fi
fi
DEPLOYER_PK=${DEPLOYER_PK:-$DEFAULT_DEPLOYER_PK}
DEPLOYER_ADDR=${DEPLOYER_ADDR:-$DEFAULT_DEPLOYER_ADDR}
}
run_forge_script() {
log "Deploying contracts to fork"
pushd "$ROOT_DIR/onchain" >/dev/null
forge script script/DeployLocal.sol --fork-url "$ANVIL_RPC" --broadcast >>"$SETUP_LOG" 2>&1
popd >/dev/null
}
extract_addresses() {
local run_file
run_file="$(ls -t "$ROOT_DIR/onchain/broadcast/DeployLocal.sol"/*/run-latest.json 2>/dev/null | head -n1)"
if [[ -z "$run_file" ]]; then
log "Deployment artifact not found"
exit 1
fi
log "Using artifact ${run_file#$ROOT_DIR/}"
LIQUIDITY_MANAGER="$(jq -r '.transactions[] | select(.contractName=="LiquidityManager") | .contractAddress' "$run_file" | head -n1)"
KRAIKEN="$(jq -r '.transactions[] | select(.contractName=="Kraiken") | .contractAddress' "$run_file" | head -n1)"
STAKE="$(jq -r '.transactions[] | select(.contractName=="Stake") | .contractAddress' "$run_file" | head -n1)"
DEPLOY_BLOCK="$(jq -r '.receipts[0].blockNumber' "$run_file" | xargs printf "%d")"
if [[ -z "$LIQUIDITY_MANAGER" || "$LIQUIDITY_MANAGER" == "null" ]]; then
log "LiquidityManager address missing"
exit 1
fi
cat >"$CONTRACT_ENV" <<EOCONTRACTS
LIQUIDITY_MANAGER=$LIQUIDITY_MANAGER
KRAIKEN=$KRAIKEN
STAKE=$STAKE
EOCONTRACTS
}
fund_liquidity_manager() {
log "Funding LiquidityManager"
cast send --rpc-url "$ANVIL_RPC" --private-key "$DEPLOYER_PK" \
"$LIQUIDITY_MANAGER" --value 0.1ether >>"$SETUP_LOG" 2>&1
}
grant_recenter_access() {
log "Granting recenter access"
cast rpc --rpc-url "$ANVIL_RPC" anvil_impersonateAccount "$FEE_DEST" >>"$SETUP_LOG" 2>&1
cast send --rpc-url "$ANVIL_RPC" --from "$FEE_DEST" --unlocked \
"$LIQUIDITY_MANAGER" "setRecenterAccess(address)" "$DEPLOYER_ADDR" >>"$SETUP_LOG" 2>&1
cast rpc --rpc-url "$ANVIL_RPC" anvil_stopImpersonatingAccount "$FEE_DEST" >>"$SETUP_LOG" 2>&1
if [[ -n "$TXNBOT_ADDRESS" ]]; then
cast rpc --rpc-url "$ANVIL_RPC" anvil_impersonateAccount "$FEE_DEST" >>"$SETUP_LOG" 2>&1
cast send --rpc-url "$ANVIL_RPC" --from "$FEE_DEST" --unlocked \
"$LIQUIDITY_MANAGER" "setRecenterAccess(address)" "$TXNBOT_ADDRESS" >>"$SETUP_LOG" 2>&1
cast rpc --rpc-url "$ANVIL_RPC" anvil_stopImpersonatingAccount "$FEE_DEST" >>"$SETUP_LOG" 2>&1
fi
}
call_recenter() {
log "Calling recenter()"
cast send --rpc-url "$ANVIL_RPC" --private-key "$DEPLOYER_PK" \
"$LIQUIDITY_MANAGER" "recenter()" >>"$SETUP_LOG" 2>&1
}
seed_application_state() {
log "Wrapping ETH to WETH"
cast send --rpc-url "$ANVIL_RPC" --private-key "$DEPLOYER_PK" \
"$WETH" "deposit()" --value 0.02ether >>"$SETUP_LOG" 2>&1
log "Approving router"
cast send --rpc-url "$ANVIL_RPC" --private-key "$DEPLOYER_PK" \
"$WETH" "approve(address,uint256)" "$SWAP_ROUTER" "$MAX_UINT" >>"$SETUP_LOG" 2>&1
log "Executing initial KRK swap"
cast send --legacy --gas-limit 300000 --rpc-url "$ANVIL_RPC" --private-key "$DEPLOYER_PK" \
"$SWAP_ROUTER" "exactInputSingle((address,address,uint24,address,uint256,uint256,uint160))" \
"($WETH,$KRAIKEN,10000,$DEPLOYER_ADDR,10000000000000000,0,0)" >>"$SETUP_LOG" 2>&1
}
prime_chain() {
log "Pre-mining blocks"
for _ in {1..1200}; do
cast rpc --rpc-url "$ANVIL_RPC" evm_mine >/dev/null 2>&1 || true
done
}
write_ponder_env() {
cat >"$ROOT_DIR/services/ponder/.env.local" <<EOPONDER
PONDER_NETWORK=BASE_SEPOLIA_LOCAL_FORK
KRAIKEN_ADDRESS=$KRAIKEN
STAKE_ADDRESS=$STAKE
START_BLOCK=$DEPLOY_BLOCK
PONDER_RPC_URL_BASE_SEPOLIA_LOCAL_FORK=$ANVIL_RPC
EOPONDER
}
write_txn_bot_env() {
cat >"$TXNBOT_ENV" <<EOTXNBOT
ENVIRONMENT=BASE_SEPOLIA_LOCAL_FORK
PROVIDER_URL=$ANVIL_RPC
PRIVATE_KEY=$TXNBOT_PRIVATE_KEY
LM_CONTRACT_ADDRESS=$LIQUIDITY_MANAGER
STAKE_CONTRACT_ADDRESS=$STAKE
GRAPHQL_ENDPOINT=http://ponder:42069/graphql
WALLET_ADDRESS=$TXNBOT_ADDRESS
PORT=43069
EOTXNBOT
}
fund_txn_bot_wallet() {
if [[ -z "$TXNBOT_ADDRESS" ]]; then
return
fi
log "Funding txnBot wallet $TXNBOT_ADDRESS"
cast send --rpc-url "$ANVIL_RPC" --private-key "$DEPLOYER_PK" \
"$TXNBOT_ADDRESS" --value "$TXNBOT_FUND_VALUE" >>"$SETUP_LOG" 2>&1 || true
local wei hex
wei="$(cast --to-unit "$TXNBOT_FUND_VALUE" wei)"
hex="$(cast --to-hex "$wei")"
cast rpc --rpc-url "$ANVIL_RPC" anvil_setBalance "$TXNBOT_ADDRESS" "$hex" >>"$SETUP_LOG" 2>&1
}
main() {
log "Waiting for Anvil"
wait_for_rpc
maybe_set_deployer_from_mnemonic
run_forge_script
extract_addresses
fund_liquidity_manager
grant_recenter_access
call_recenter
seed_application_state
prime_chain
write_ponder_env
write_txn_bot_env
fund_txn_bot_wallet
log "Bootstrap complete"
log "Kraiken: $KRAIKEN"
log "Stake: $STAKE"
log "LiquidityManager: $LIQUIDITY_MANAGER"
}
main "$@"

View file

@ -0,0 +1,25 @@
FROM debian:bookworm-slim
RUN apt-get update \
&& apt-get install -y --no-install-recommends \
ca-certificates \
curl \
jq \
git \
build-essential \
pkg-config \
libssl-dev \
libclang-dev \
llvm \
unzip \
&& rm -rf /var/lib/apt/lists/*
RUN useradd -m -u 1000 foundry
USER foundry
WORKDIR /home/foundry
RUN curl -L https://foundry.paradigm.xyz | bash \
&& /home/foundry/.foundry/bin/foundryup
ENV PATH="/home/foundry/.foundry/bin:${PATH}"
WORKDIR /workspace

View file

@ -0,0 +1,32 @@
#!/usr/bin/env bash
set -euo pipefail
ROOT_DIR=/workspace
CONTRACT_ENV=$ROOT_DIR/tmp/podman/contracts.env
APP_DIR=$ROOT_DIR/web-app
SWAP_ROUTER=0x94cC0AaC535CCDB3C01d6787D6413C739ae12bc4
while [[ ! -f "$CONTRACT_ENV" ]]; do
echo "[frontend-entrypoint] waiting for contracts env"
sleep 2
done
# shellcheck disable=SC1090
source "$CONTRACT_ENV"
cd "$APP_DIR"
if [[ ! -d node_modules ]]; then
npm install
fi
export VITE_DEFAULT_CHAIN_ID=${VITE_DEFAULT_CHAIN_ID:-31337}
export VITE_LOCAL_RPC_URL=${VITE_LOCAL_RPC_URL:-/rpc/anvil}
export VITE_LOCAL_RPC_PROXY_TARGET=${VITE_LOCAL_RPC_PROXY_TARGET:-http://anvil:8545}
export VITE_KRAIKEN_ADDRESS=$KRAIKEN
export VITE_STAKE_ADDRESS=$STAKE
export VITE_SWAP_ROUTER=$SWAP_ROUTER
export VITE_PONDER_BASE_SEPOLIA_LOCAL_FORK=${VITE_PONDER_BASE_SEPOLIA_LOCAL_FORK:-/graphql}
export VITE_TXNBOT_BASE_SEPOLIA_LOCAL_FORK=${VITE_TXNBOT_BASE_SEPOLIA_LOCAL_FORK:-/txn}
export CHOKIDAR_USEPOLLING=${CHOKIDAR_USEPOLLING:-1}
exec npm run dev -- --host 0.0.0.0 --port 5173

View file

@ -0,0 +1,11 @@
FROM node:20-bookworm
RUN apt-get update \
&& apt-get install -y --no-install-recommends dumb-init \
&& rm -rf /var/lib/apt/lists/*
USER node
WORKDIR /workspace
ENV PATH="/workspace/node_modules/.bin:${PATH}"
ENTRYPOINT ["dumb-init", "--"]

View file

@ -0,0 +1,22 @@
#!/usr/bin/env bash
set -euo pipefail
ROOT_DIR=/workspace
CONTRACT_ENV=$ROOT_DIR/tmp/podman/contracts.env
PONDER_WORKDIR=$ROOT_DIR/services/ponder
while [[ ! -f "$CONTRACT_ENV" ]]; do
echo "[ponder-entrypoint] waiting for contracts env"
sleep 2
done
cd "$PONDER_WORKDIR"
if [[ ! -d node_modules ]]; then
npm install
fi
export CHOKIDAR_USEPOLLING=${CHOKIDAR_USEPOLLING:-1}
export HOST=0.0.0.0
export PORT=${PORT:-42069}
exec npm run dev

View file

@ -0,0 +1,19 @@
#!/usr/bin/env bash
set -euo pipefail
ROOT_DIR=/workspace
TXNBOT_ENV_FILE=$ROOT_DIR/tmp/podman/txnBot.env
BOT_DIR=$ROOT_DIR/services/txnBot
while [[ ! -f "$TXNBOT_ENV_FILE" ]]; do
echo "[txn-bot-entrypoint] waiting for env file"
sleep 2
done
cd "$BOT_DIR"
if [[ ! -d node_modules ]]; then
npm install
fi
export TXN_BOT_ENV_FILE="$TXNBOT_ENV_FILE"
exec npm run start