Merge pull request 'feature-podman' (#21) from feature-podman into master
Reviewed-on: https://codeberg.org/johba/harb/pulls/21
This commit is contained in:
commit
7da7b12b6b
16 changed files with 4708 additions and 8 deletions
20
containers/Caddyfile
Normal file
20
containers/Caddyfile
Normal file
|
|
@ -0,0 +1,20 @@
|
|||
:80 {
|
||||
route /app* {
|
||||
reverse_proxy webapp:5173
|
||||
}
|
||||
route /graphql* {
|
||||
reverse_proxy ponder:42069
|
||||
}
|
||||
route /health* {
|
||||
reverse_proxy ponder:42069
|
||||
}
|
||||
route /rpc/anvil* {
|
||||
uri strip_prefix /rpc/anvil
|
||||
reverse_proxy anvil:8545
|
||||
}
|
||||
route /txn* {
|
||||
uri strip_prefix /txn
|
||||
reverse_proxy txn-bot:43069
|
||||
}
|
||||
reverse_proxy landing:5174
|
||||
}
|
||||
14
containers/anvil-entrypoint.sh
Executable file
14
containers/anvil-entrypoint.sh
Executable 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[@]}"
|
||||
205
containers/bootstrap.sh
Executable file
205
containers/bootstrap.sh
Executable file
|
|
@ -0,0 +1,205 @@
|
|||
#!/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() {
|
||||
local recenter_pk="$DEPLOYER_PK"
|
||||
local recenter_addr="$DEPLOYER_ADDR"
|
||||
if [[ -n "$TXNBOT_ADDRESS" ]]; then
|
||||
recenter_pk="$TXNBOT_PRIVATE_KEY"
|
||||
recenter_addr="$TXNBOT_ADDRESS"
|
||||
fi
|
||||
log "Calling recenter() via $recenter_addr"
|
||||
cast send --rpc-url "$ANVIL_RPC" --private-key "$recenter_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 "$@"
|
||||
28
containers/foundry.Containerfile
Normal file
28
containers/foundry.Containerfile
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
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
|
||||
ENV SHELL=/bin/bash
|
||||
ENV LANG=C.UTF-8
|
||||
ENV LC_ALL=C.UTF-8
|
||||
|
||||
RUN curl -L https://foundry.paradigm.xyz | bash \
|
||||
&& /home/foundry/.foundry/bin/foundryup
|
||||
|
||||
ENV PATH="/home/foundry/.foundry/bin:${PATH}"
|
||||
WORKDIR /workspace
|
||||
18
containers/landing-dev-entrypoint.sh
Executable file
18
containers/landing-dev-entrypoint.sh
Executable file
|
|
@ -0,0 +1,18 @@
|
|||
#!/usr/bin/env bash
|
||||
set -euo pipefail
|
||||
|
||||
ROOT_DIR=/workspace
|
||||
LANDING_DIR=$ROOT_DIR/landing
|
||||
|
||||
cd "$LANDING_DIR"
|
||||
echo "[landing-entrypoint] Installing dependencies..."
|
||||
npm install --no-save --loglevel error 2>&1 || {
|
||||
echo "[landing-entrypoint] npm install failed, trying with --force"
|
||||
npm install --force --no-save --loglevel error
|
||||
}
|
||||
|
||||
export CHOKIDAR_USEPOLLING=${CHOKIDAR_USEPOLLING:-1}
|
||||
export HOST=0.0.0.0
|
||||
export PORT=${PORT:-5174}
|
||||
|
||||
exec npm run dev -- --host 0.0.0.0 --port 5174
|
||||
13
containers/node-dev.Containerfile
Normal file
13
containers/node-dev.Containerfile
Normal file
|
|
@ -0,0 +1,13 @@
|
|||
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 LANG=C.UTF-8
|
||||
ENV LC_ALL=C.UTF-8
|
||||
|
||||
ENV PATH="/workspace/node_modules/.bin:${PATH}"
|
||||
ENTRYPOINT ["dumb-init", "--"]
|
||||
24
containers/ponder-dev-entrypoint.sh
Executable file
24
containers/ponder-dev-entrypoint.sh
Executable file
|
|
@ -0,0 +1,24 @@
|
|||
#!/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"
|
||||
echo "[ponder-entrypoint] Installing dependencies..."
|
||||
npm install --no-save --loglevel error 2>&1 || {
|
||||
echo "[ponder-entrypoint] npm install failed, trying with --force"
|
||||
npm install --force --no-save --loglevel error
|
||||
}
|
||||
|
||||
export CHOKIDAR_USEPOLLING=${CHOKIDAR_USEPOLLING:-1}
|
||||
export HOST=0.0.0.0
|
||||
export PORT=${PORT:-42069}
|
||||
|
||||
exec npm run dev
|
||||
62
containers/txn-bot-entrypoint.sh
Executable file
62
containers/txn-bot-entrypoint.sh
Executable file
|
|
@ -0,0 +1,62 @@
|
|||
#!/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
|
||||
KRAIKEN_LIB_DIR=$ROOT_DIR/kraiken-lib
|
||||
|
||||
while [[ ! -f "$TXNBOT_ENV_FILE" ]]; do
|
||||
echo "[txn-bot-entrypoint] waiting for env file"
|
||||
sleep 2
|
||||
done
|
||||
|
||||
# Build kraiken-lib first
|
||||
echo "[txn-bot-entrypoint] Building kraiken-lib..."
|
||||
cd "$KRAIKEN_LIB_DIR"
|
||||
|
||||
# Install dependencies if needed
|
||||
if [[ ! -d node_modules ]]; then
|
||||
echo "[txn-bot-entrypoint] Installing kraiken-lib dependencies..."
|
||||
npm install --loglevel error
|
||||
fi
|
||||
|
||||
# Install TypeScript if not present
|
||||
if [[ ! -f node_modules/.bin/tsc ]]; then
|
||||
echo "[txn-bot-entrypoint] Installing TypeScript..."
|
||||
npm install --loglevel error typescript
|
||||
fi
|
||||
|
||||
# Build TypeScript files (dist is now a volume, writable by node user)
|
||||
echo "[txn-bot-entrypoint] Compiling TypeScript..."
|
||||
if [[ ! -f dist/index.js ]]; then
|
||||
echo "[txn-bot-entrypoint] Running tsc to compile kraiken-lib..."
|
||||
./node_modules/.bin/tsc \
|
||||
--outDir dist \
|
||||
--declaration \
|
||||
--module commonjs \
|
||||
--target es2020 \
|
||||
--skipLibCheck \
|
||||
--esModuleInterop \
|
||||
--allowSyntheticDefaultImports \
|
||||
--resolveJsonModule \
|
||||
src/index.ts src/helpers.ts src/subgraph.ts src/__generated__/graphql.ts 2>&1 | head -20 || {
|
||||
echo "[txn-bot-entrypoint] TypeScript compilation had some issues, checking if files were created..."
|
||||
}
|
||||
|
||||
# Verify the main file exists
|
||||
if [[ ! -f dist/index.js ]]; then
|
||||
echo "[txn-bot-entrypoint] ERROR: Failed to compile kraiken-lib"
|
||||
exit 1
|
||||
fi
|
||||
fi
|
||||
|
||||
cd "$BOT_DIR"
|
||||
echo "[txn-bot-entrypoint] Installing txn-bot dependencies..."
|
||||
npm install --no-save --loglevel error 2>&1 || {
|
||||
echo "[txn-bot-entrypoint] npm install failed, trying with --force"
|
||||
npm install --force --no-save --loglevel error
|
||||
}
|
||||
|
||||
export TXN_BOT_ENV_FILE="$TXNBOT_ENV_FILE"
|
||||
exec npm run start
|
||||
34
containers/webapp-dev-entrypoint.sh
Executable file
34
containers/webapp-dev-entrypoint.sh
Executable file
|
|
@ -0,0 +1,34 @@
|
|||
#!/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"
|
||||
echo "[frontend-entrypoint] Installing dependencies..."
|
||||
npm install --no-save --loglevel error 2>&1 || {
|
||||
echo "[frontend-entrypoint] npm install failed, trying with --force"
|
||||
npm install --force --no-save --loglevel error
|
||||
}
|
||||
|
||||
export VITE_DEFAULT_CHAIN_ID=${VITE_DEFAULT_CHAIN_ID:-31337}
|
||||
export VITE_LOCAL_RPC_URL=${VITE_LOCAL_RPC_URL:-/app/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:-/app/graphql}
|
||||
export VITE_TXNBOT_BASE_SEPOLIA_LOCAL_FORK=${VITE_TXNBOT_BASE_SEPOLIA_LOCAL_FORK:-/app/txn}
|
||||
export CHOKIDAR_USEPOLLING=${CHOKIDAR_USEPOLLING:-1}
|
||||
|
||||
exec npm run dev -- --host 0.0.0.0 --port 5173 --base /app/
|
||||
44
docs/podman.md
Normal file
44
docs/podman.md
Normal file
|
|
@ -0,0 +1,44 @@
|
|||
# Podman Staging Environment
|
||||
|
||||
The Podman stack mirrors `scripts/local_env.sh` using long-lived containers. Every boot spins up a fresh Base Sepolia fork, redeploys contracts, seeds liquidity, and launches the live-reload services behind Caddy on port 80.
|
||||
|
||||
## Service Topology
|
||||
- `anvil` – Base Sepolia fork with optional mnemonic from `onchain/.secret.local`
|
||||
- `bootstrap` – one-shot job running `DeployLocal.sol`, seeding liquidity, priming blocks, and writing shared env files
|
||||
- `ponder` – `npm run dev` for the indexer (port 42069 inside the pod)
|
||||
- `frontend` – Vite dev server for `web-app` (port 5173 inside the pod)
|
||||
- `txn-bot` – automation loop plus Express status API (port 43069 inside the pod)
|
||||
- `caddy` – front door at `http://<host>:80`, routing `/graphql`, `/health`, `/rpc/anvil`, and `/txn` to the internal services
|
||||
|
||||
All containers mount the repository so code edits hot-reload exactly as the local script. Named volumes keep `node_modules` caches between restarts.
|
||||
|
||||
## Prerequisites
|
||||
- Podman 4.x (rootless recommended)
|
||||
- `podman-compose`
|
||||
|
||||
## Launching
|
||||
```bash
|
||||
podman-compose -f podman-compose.yml build
|
||||
podman-compose -f podman-compose.yml up
|
||||
```
|
||||
- First run takes several minutes while Foundry installs deps, deploys contracts, and runs the seeding transactions.
|
||||
- Use `podman-compose down` to stop. Bring-up always redeploys and rewrites `services/ponder/.env.local` plus `tmp/podman/txnBot.env`.
|
||||
|
||||
### Access Points (via Caddy)
|
||||
- Frontend: `http://<host>/`
|
||||
- GraphQL: `http://<host>/graphql`
|
||||
- RPC passthrough: `http://<host>/rpc/anvil`
|
||||
- Txn bot status: `http://<host>/txn/status`
|
||||
|
||||
## Configuration Knobs
|
||||
Set environment variables before `podman-compose up`:
|
||||
- `FORK_URL` – Anvil upstream RPC (defaults to `https://sepolia.base.org`)
|
||||
- `DEPLOYER_PK`, `DEPLOYER_ADDR` – override deployer wallet; otherwise derived from `.secret.local` or Foundry defaults
|
||||
- `TXNBOT_PRIVATE_KEY`, `TXNBOT_ADDRESS`, `TXNBOT_FUND_VALUE` – customise bot signer and funding
|
||||
|
||||
Edit `containers/Caddyfile` if you need different routes or ports.
|
||||
|
||||
## Known Limitations
|
||||
- State is ephemeral; every restart wipes the fork and redeploys contracts.
|
||||
- Processes run in dev/watch mode (`npm run dev`), so staging traffic is not production hardened.
|
||||
- Secrets live in env files inside the repo mount because no external secret store is wired in.
|
||||
|
|
@ -3,9 +3,14 @@
|
|||
"module": "commonjs",
|
||||
"target": "es2020",
|
||||
"declaration": true,
|
||||
"outDir": "./dist"
|
||||
"outDir": "./dist",
|
||||
"skipLibCheck": true,
|
||||
"types": []
|
||||
},
|
||||
"include": [
|
||||
"src/**/*"
|
||||
],
|
||||
"exclude": [
|
||||
"src/tests/**/*"
|
||||
]
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -2387,11 +2387,6 @@ fs.realpath@^1.0.0:
|
|||
resolved "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz"
|
||||
integrity sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==
|
||||
|
||||
fsevents@^2.3.2:
|
||||
version "2.3.3"
|
||||
resolved "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz"
|
||||
integrity sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==
|
||||
|
||||
function-bind@^1.1.2:
|
||||
version "1.1.2"
|
||||
resolved "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz"
|
||||
|
|
|
|||
4109
package-lock.json
generated
Normal file
4109
package-lock.json
generated
Normal file
File diff suppressed because it is too large
Load diff
6
package.json
Normal file
6
package.json
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
{
|
||||
"devDependencies": {
|
||||
"@playwright/test": "^1.55.1",
|
||||
"playwright-mcp": "^0.0.12"
|
||||
}
|
||||
}
|
||||
123
podman-compose.yml
Normal file
123
podman-compose.yml
Normal file
|
|
@ -0,0 +1,123 @@
|
|||
version: "3.8"
|
||||
|
||||
services:
|
||||
anvil:
|
||||
build:
|
||||
context: .
|
||||
dockerfile: containers/foundry.Containerfile
|
||||
command: ["/workspace/containers/anvil-entrypoint.sh"]
|
||||
volumes:
|
||||
- .:/workspace:Z
|
||||
expose:
|
||||
- "8545"
|
||||
restart: unless-stopped
|
||||
|
||||
bootstrap:
|
||||
build:
|
||||
context: .
|
||||
dockerfile: containers/foundry.Containerfile
|
||||
command: ["/workspace/containers/bootstrap.sh"]
|
||||
volumes:
|
||||
- .:/workspace:Z
|
||||
environment:
|
||||
- ANVIL_RPC=http://anvil:8545
|
||||
depends_on:
|
||||
anvil:
|
||||
condition: service_started
|
||||
restart: "no"
|
||||
|
||||
ponder:
|
||||
build:
|
||||
context: .
|
||||
dockerfile: containers/node-dev.Containerfile
|
||||
entrypoint: ["/workspace/containers/ponder-dev-entrypoint.sh"]
|
||||
volumes:
|
||||
- .:/workspace:z
|
||||
- ponder-node-modules:/workspace/services/ponder/node_modules
|
||||
working_dir: /workspace
|
||||
environment:
|
||||
- CHOKIDAR_USEPOLLING=1
|
||||
depends_on:
|
||||
- anvil
|
||||
expose:
|
||||
- "42069"
|
||||
restart: unless-stopped
|
||||
|
||||
webapp:
|
||||
build:
|
||||
context: .
|
||||
dockerfile: containers/node-dev.Containerfile
|
||||
entrypoint: ["/workspace/containers/webapp-dev-entrypoint.sh"]
|
||||
volumes:
|
||||
- .:/workspace:z
|
||||
- webapp-node-modules:/workspace/web-app/node_modules
|
||||
working_dir: /workspace
|
||||
environment:
|
||||
- CHOKIDAR_USEPOLLING=1
|
||||
depends_on:
|
||||
- anvil
|
||||
expose:
|
||||
- "5173"
|
||||
restart: unless-stopped
|
||||
|
||||
landing:
|
||||
build:
|
||||
context: .
|
||||
dockerfile: containers/node-dev.Containerfile
|
||||
entrypoint: ["/workspace/containers/landing-dev-entrypoint.sh"]
|
||||
volumes:
|
||||
- .:/workspace:z
|
||||
- landing-node-modules:/workspace/landing/node_modules
|
||||
working_dir: /workspace
|
||||
environment:
|
||||
- CHOKIDAR_USEPOLLING=1
|
||||
depends_on:
|
||||
- anvil
|
||||
expose:
|
||||
- "5174"
|
||||
restart: unless-stopped
|
||||
|
||||
txn-bot:
|
||||
build:
|
||||
context: .
|
||||
dockerfile: containers/node-dev.Containerfile
|
||||
entrypoint: ["/workspace/containers/txn-bot-entrypoint.sh"]
|
||||
volumes:
|
||||
- .:/workspace:z
|
||||
- txn-node-modules:/workspace/services/txnBot/node_modules
|
||||
- kraiken-node-modules:/workspace/kraiken-lib/node_modules
|
||||
- kraiken-dist:/workspace/kraiken-lib/dist
|
||||
working_dir: /workspace
|
||||
depends_on:
|
||||
- anvil
|
||||
- ponder
|
||||
expose:
|
||||
- "43069"
|
||||
restart: unless-stopped
|
||||
|
||||
caddy:
|
||||
image: docker.io/library/caddy:2.8
|
||||
volumes:
|
||||
- ./containers/Caddyfile:/etc/caddy/Caddyfile:Z
|
||||
ports:
|
||||
- "0.0.0.0:8081:80"
|
||||
depends_on:
|
||||
anvil:
|
||||
condition: service_started
|
||||
ponder:
|
||||
condition: service_started
|
||||
webapp:
|
||||
condition: service_started
|
||||
landing:
|
||||
condition: service_started
|
||||
txn-bot:
|
||||
condition: service_started
|
||||
restart: unless-stopped
|
||||
|
||||
volumes:
|
||||
webapp-node-modules:
|
||||
landing-node-modules:
|
||||
ponder-node-modules:
|
||||
txn-node-modules:
|
||||
kraiken-node-modules:
|
||||
kraiken-dist:
|
||||
|
|
@ -17,7 +17,7 @@
|
|||
<RouterLink v-for="navbarRoute in navbarRoutes" :key="navbarRoute.name" :to="navbarRoute.path">
|
||||
{{ navbarRoute.title }}
|
||||
</RouterLink>
|
||||
<a href="https://emberspirit007.github.io/KraikenLanding/#/docs/Introduction" target="_blank">Docs</a>
|
||||
<a href="/#/docs">Docs</a>
|
||||
</nav>
|
||||
<template v-if="!isMobile">
|
||||
<div class="vertical-line"></div>
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue