diff --git a/.github/workflows/ci.yaml b/.github/workflows/ci.yaml index 7fcaa08a0..e56a458b3 100644 --- a/.github/workflows/ci.yaml +++ b/.github/workflows/ci.yaml @@ -89,7 +89,7 @@ jobs: sleep 5 fi - if go test -short -p 1 -timeout=15m -count=1 -tags=kwiltest ./...; then + if go test -failfast -short -p 1 -timeout=15m -count=1 -tags=kwiltest ./...; then echo "✅ Tests passed on attempt $attempt" break else diff --git a/.github/workflows/publish-node-image.yaml b/.github/workflows/publish-node-image.yaml index 5ad6e0817..d36e5d6c4 100644 --- a/.github/workflows/publish-node-image.yaml +++ b/.github/workflows/publish-node-image.yaml @@ -16,7 +16,7 @@ permissions: packages: write env: - IMAGE_NAME: ghcr.io/${{ github.repository_owner }}/tn-db + IMAGE_NAME: ghcr.io/${{ github.repository_owner }}/node jobs: build-and-push: diff --git a/Taskfile.yml b/Taskfile.yml index 7c6e6b488..c6dfdbafd 100644 --- a/Taskfile.yml +++ b/Taskfile.yml @@ -79,7 +79,7 @@ tasks: docker:build:local: desc: Build Docker image for local development (no version args needed) cmds: - - docker build -f deployments/Dockerfile -t tn-db:local . + - docker build -f deployments/Dockerfile -t ghcr.io/trufnetwork/node:local . # ─── host ───────────────────────────────────────────────────────────────────── @@ -121,6 +121,8 @@ tasks: desc: Set environment variables for devnet internal: true env: + SETUP_DB_OWNER: "{{.DEV_DB_OWNER}}" + SETUP_CHAIN_ID: "{{.DEV_CHAIN_ID}}" DB_OWNER: "{{.DEV_DB_OWNER}}" CHAIN_ID: "{{.DEV_CHAIN_ID}}" requires: { vars: [ DEV_DB_OWNER, DEV_CHAIN_ID ] } @@ -129,6 +131,8 @@ tasks: desc: Run docker-compose locally (single node stack) deps: [ single:env, build:binaries ] env: + SETUP_DB_OWNER: "{{.DEV_DB_OWNER}}" + SETUP_CHAIN_ID: "{{.DEV_CHAIN_ID}}" DB_OWNER: "{{.DEV_DB_OWNER}}" CHAIN_ID: "{{.DEV_CHAIN_ID}}" cmds: @@ -148,14 +152,23 @@ tasks: internal: true env: BACKENDS: "{{.DEV_NODE_1_ADDRESS}},{{.DEV_NODE_2_ADDRESS}}" - CHAIN_ID: "{{.DEV_CHAIN_ID}}" NODE_RPC_ENDPOINT: "{{.DEV_NODE_1_RPC_ENDPOINT}}" + SETUP_CHAIN_ID: "{{.DEV_CHAIN_ID}}" + SETUP_DB_OWNER: "{{.DEV_DB_OWNER}}" + CHAIN_ID: "{{.DEV_CHAIN_ID}}" DB_OWNER: "{{.DEV_DB_OWNER}}" requires: { vars: [ DEV_NODE_1_ADDRESS, DEV_NODE_2_ADDRESS, DEV_CHAIN_ID, DEV_DB_OWNER ] } # Added requires guard for all used vars devnet:start: desc: Run docker-compose locally with dev configuration, 2 nodes, gateway, and indexer services deps: [ devnet:env, build:binaries ] + env: + SETUP_DB_OWNER: "{{.DEV_DB_OWNER}}" + SETUP_CHAIN_ID: "{{.DEV_CHAIN_ID}}" + DB_OWNER: "{{.DEV_DB_OWNER}}" + CHAIN_ID: "{{.DEV_CHAIN_ID}}" + BACKENDS: "{{.DEV_NODE_1_ADDRESS}},{{.DEV_NODE_2_ADDRESS}}" + NODE_RPC_ENDPOINT: "{{.DEV_NODE_1_RPC_ENDPOINT}}" cmds: - task: _compose vars: @@ -165,6 +178,13 @@ tasks: devnet:stop: desc: Shutdown dev 2 nodes, gateway, and indexer services deps: [ devnet:env ] + env: + SETUP_DB_OWNER: "{{.DEV_DB_OWNER}}" + SETUP_CHAIN_ID: "{{.DEV_CHAIN_ID}}" + DB_OWNER: "{{.DEV_DB_OWNER}}" + CHAIN_ID: "{{.DEV_CHAIN_ID}}" + BACKENDS: "{{.DEV_NODE_1_ADDRESS}},{{.DEV_NODE_2_ADDRESS}}" + NODE_RPC_ENDPOINT: "{{.DEV_NODE_1_RPC_ENDPOINT}}" cmds: - task: _compose vars: @@ -325,4 +345,4 @@ tasks: PRIVATE_KEY: "{{.PRIVATE_KEY}}" PROVIDER: "{{.PROVIDER}}" ADMIN_WALLET: "{{.DEV_DB_OWNER}}" - - kwil-cli exec-action grant_roles text:system text:network_writer text[]:{{.DEV_DB_OWNER}} --private-key {{.PRIVATE_KEY}} --provider {{.PROVIDER}} --sync \ No newline at end of file + - kwil-cli exec-action grant_roles text:system text:network_writer text[]:{{.DEV_DB_OWNER}} --private-key {{.PRIVATE_KEY}} --provider {{.PROVIDER}} --sync diff --git a/compose.yaml b/compose.yaml index 6938c6895..f7bfa1023 100644 --- a/compose.yaml +++ b/compose.yaml @@ -28,19 +28,18 @@ services: tn-db: container_name: tn-db hostname: tn-db - image: "tn-db:local" + image: "ghcr.io/trufnetwork/node:local" restart: unless-stopped build: context: . dockerfile: ./deployments/Dockerfile - args: - - CHAIN_ID=${CHAIN_ID:-trufnetwork-dev} environment: CONFIG_PATH: /root/.kwild # app.pg-db-host KWILD_DB_HOST: kwil-postgres - # DB_OWNER must be provided at runtime - DB_OWNER: ${DB_OWNER:-} + # Optionally supply SETUP_DB_OWNER to override the owner derived from the generated node key + SETUP_DB_OWNER: ${SETUP_DB_OWNER:-} + SETUP_CHAIN_ID: ${SETUP_CHAIN_ID:-trufnetwork-dev} ports: - "50051:50051" - "${TN_RPC_PORT:-8484}:8484" @@ -58,6 +57,8 @@ services: - ${TN_VOLUME:-data-tn-db}:/root/.kwild networks: - tn-network + extra_hosts: + - "host.docker.internal:host-gateway" logging: driver: "json-file" options: @@ -72,5 +73,4 @@ networks: volumes: data-kwil-postgres: - data-tn-db: diff --git a/deployments/Dockerfile b/deployments/Dockerfile index c8e23f9a2..d7b8906c8 100644 --- a/deployments/Dockerfile +++ b/deployments/Dockerfile @@ -24,7 +24,7 @@ FROM alpine:latest ENV SETUP_CHAIN_ID=truflation-dev ENV SETUP_DB_OWNER= -# DB_OWNER will be provided as an environment variable at runtime +# Provide SETUP_DB_OWNER at runtime to override the derived owner; otherwise kwild derives one from the generated node key ENV CONFIG_PATH=/root/.kwild WORKDIR /app diff --git a/deployments/dev-net/devnet-compose.yaml b/deployments/dev-net/devnet-compose.yaml index 98f2d940a..7eaa2892f 100644 --- a/deployments/dev-net/devnet-compose.yaml +++ b/deployments/dev-net/devnet-compose.yaml @@ -76,7 +76,8 @@ services: - KWILD_DB_HOST=kwil-postgres-1 - KWILD_APP_HOSTNAME=tn-db-1 - KWILD_CHAIN_P2P_EXTERNAL_ADDRESS=http://tn-db-1:26656 - - DB_OWNER=${DB_OWNER:-0x4710A8D8F0D845da110086812a32De6d90d7ff5C} + - SETUP_DB_OWNER=${SETUP_DB_OWNER:-0x4710A8D8F0D845da110086812a32De6d90d7ff5C} + - SETUP_CHAIN_ID=${SETUP_CHAIN_ID:-trufnetwork-dev} ports: - "50051:50051" - "8080:8080" @@ -106,7 +107,8 @@ services: - KWILD_DB_HOST=kwil-postgres-2 - KWILD_APP_HOSTNAME=tn-db-2 - KWILD_CHAIN_P2P_EXTERNAL_ADDRESS=http://tn-db-2:26656 - - DB_OWNER=${DB_OWNER:-0x4710A8D8F0D845da110086812a32De6d90d7ff5C} + - SETUP_DB_OWNER=${SETUP_DB_OWNER:-0x4710A8D8F0D845da110086812a32De6d90d7ff5C} + - SETUP_CHAIN_ID=${SETUP_CHAIN_ID:-trufnetwork-dev} ports: - "8485:8484" - "26658:26657" @@ -132,4 +134,4 @@ networks: volumes: data-kwil-postgres-1: data-kwil-postgres-2: - tn-conf: \ No newline at end of file + tn-conf: diff --git a/deployments/infra/scripts/renderer/templates/tn_db_startup.sh.tmpl b/deployments/infra/scripts/renderer/templates/tn_db_startup.sh.tmpl index 09af538ac..aa384e535 100644 --- a/deployments/infra/scripts/renderer/templates/tn_db_startup.sh.tmpl +++ b/deployments/infra/scripts/renderer/templates/tn_db_startup.sh.tmpl @@ -37,8 +37,8 @@ for i in {1..5}; do if aws ecr get-login-password --region {{ .Region }} | docker login --username AWS --password-stdin {{ .RepoURI }} && \ docker pull {{ .ImageURI }}; then echo "ECR login and pull successful." - # Tag the image as tn-db:local, as the docker-compose file expects that - docker tag {{ .ImageURI }} tn-db:local + # Tag the image as ghcr.io/trufnetwork/node:local, as the docker-compose file expects that + docker tag {{ .ImageURI }} ghcr.io/trufnetwork/node:local break fi if [ $i -eq 5 ]; then diff --git a/deployments/infra/scripts/renderer/testdata/TestGoldenTnScript.golden b/deployments/infra/scripts/renderer/testdata/TestGoldenTnScript.golden index f0ca74243..c84711085 100644 --- a/deployments/infra/scripts/renderer/testdata/TestGoldenTnScript.golden +++ b/deployments/infra/scripts/renderer/testdata/TestGoldenTnScript.golden @@ -14,8 +14,8 @@ for i in {1..5}; do if aws ecr get-login-password --region us-west-2 | docker login --username AWS --password-stdin 123456789012.dkr.ecr.us-west-2.amazonaws.com/mock-repo && \ docker pull 123456789012.dkr.ecr.us-west-2.amazonaws.com/mock-repo:latest; then echo "ECR login and pull successful." - # Tag the image as tn-db:local, as the docker-compose file expects that - docker tag 123456789012.dkr.ecr.us-west-2.amazonaws.com/mock-repo:latest tn-db:local + # Tag the image as ghcr.io/trufnetwork/node:local, as the docker-compose file expects that + docker tag 123456789012.dkr.ecr.us-west-2.amazonaws.com/mock-repo:latest ghcr.io/trufnetwork/node:local break fi if [ $i -eq 5 ]; then diff --git a/docs/container-image-guide.md b/docs/container-image-guide.md new file mode 100644 index 000000000..15ed740f4 --- /dev/null +++ b/docs/container-image-guide.md @@ -0,0 +1,118 @@ +# TN Node Container Quickstart + +Run the TRUF.NETWORK node container with Docker Compose while keeping the standard operator layout for data and configuration. + +> **Heads up** +> The default quickstart relies on the container’s auto-initialization, which generates a brand-new genesis and starts an isolated network. Follow the optional pre-population section (or mount existing config) before the first run if you need to join an established network instead of bootstrapping a fresh one. + +## Prerequisites +- Docker Engine 24+ with the `docker compose` plugin. +- Pull access to `ghcr.io/trufnetwork/node` and `kwildb/postgres`. +- Optional: the [`kwild` CLI](https://github.com/trufnetwork/node/releases) if you want to pre-populate configuration files instead of using the container’s auto-initialization path. + +## 1. Prepare the workspace +```bash +mkdir -p ~/truf-node/tn_data +cd ~/truf-node +``` +The `tn_data` directory becomes the bind mount that stores keys, logs, and the blockstore on the host so they persist across container rebuilds. + +## 2. Save the Compose stack +Create `docker-compose.yml` in `~/truf-node` using the minimal stack below. + +
+Minimal docker-compose.yml + +```yaml +services: + postgres: + image: kwildb/postgres:16.8-1 + restart: unless-stopped + environment: + POSTGRES_HOST_AUTH_METHOD: trust + volumes: + # this creates a host directory named pg-data in the current workspace + - ./pg-data:/var/lib/postgresql/data + healthcheck: + test: ["CMD-SHELL", "pg_isready -U postgres"] + interval: 5s + timeout: 5s + retries: 5 + + tn-node: + image: ghcr.io/trufnetwork/node:${TN_NODE_TAG:-latest} + restart: unless-stopped + depends_on: + postgres: + condition: service_healthy + environment: + KWILD_DB_HOST: postgres + KWILD_DB_PORT: 5432 + SETUP_CHAIN_ID: ${SETUP_CHAIN_ID:-truflation-dev} + SETUP_DB_OWNER: ${SETUP_DB_OWNER:-} + volumes: + # this creates a host directory named tn_data in the current workspace, or reuses your pre-generated config if it exists + - ./tn_data:/root/.kwild + ports: + - "8484:8484" # JSON-RPC + - "6600:6600" # P2P +``` + +
+ +Compose automatically loads variables from a `.env` file in the same directory. At a minimum set the node image tag you want to run (for example the latest release) and optionally pre-fill auto-setup values: + +```dotenv +TN_NODE_TAG=v0.15.0 +SETUP_CHAIN_ID=truflation-dev +# Leave empty to let the container derive the owner from the generated node key +SETUP_DB_OWNER= +``` + +## 3. Launch the services +```bash +docker compose up -d +docker compose ps +``` +The node waits for Postgres to pass its health check before it starts. Use the bind mount (`~/truf-node/tn_data`) to inspect the generated config, keys, and logs. + +### Verify the node +```bash +curl http://localhost:8484/api/v1/health +docker compose logs -f tn-node +``` + +## Optional: Pre-populate the configuration +If you need this container to join an existing network (mainnet/testnet/devnet), generate `config.toml`, `genesis.json`, and keys ahead of time so the container skips auto-initialization. + +1. Clone the operator repository (once): + ```bash + git clone https://github.com/trufnetwork/truf-node-operator.git ~/truf-node-operator + ``` +2. Install or download the matching `kwild` release binary and add it to your `PATH`. +3. Generate the config with the official genesis (adjust flags as needed for your environment, just like the [Node Operator Guide](node-operator-guide.md)): + ```bash + kwild setup init \ + --genesis ~/truf-node-operator/configs/network/v2/genesis.json \ + --root ~/truf-node/tn_data \ + --p2p.bootnodes "4e0b5c952be7f26698dc1898ff3696ac30e990f25891aeaf88b0285eab4663e1#ed25519@node-1.mainnet.truf.network:26656,0c830b69790eaa09315826403c2008edc65b5c7132be9d4b7b4da825c2a166ae#ed25519@node-2.mainnet.truf.network:26656" \ + --state-sync.enable \ + --state-sync.trusted-providers "0c830b69790eaa09315826403c2008edc65b5c7132be9d4b7b4da825c2a166ae#ed25519@node-2.mainnet.truf.network:26656" \ + --rpc.private + ``` +4. Update the generated database host so it matches the Compose service name. Open `~/truf-node/tn_data/config.toml` and set: + ```toml + [db] + host = 'postgres' + ``` + (This ensures the node reaches the Postgres container without relying on environment overrides.) + +The next `docker compose up -d` start reuses this configuration instead of triggering auto-setup. + +### Relying on auto-generation +For throwaway networks you can skip the steps above. Leave `SETUP_DB_OWNER` blank to let the container derive an identifier from the generated node key. Override `SETUP_CHAIN_ID` and `SETUP_DB_OWNER` in `.env` only when you want deterministic values for the generated genesis. + +## Maintenance tips +- Back up the `~/truf-node/tn_data` directory; it contains the node identity, admin certificates, and blockstore. +- To rotate configuration, stop the stack, edit files under `~/truf-node/tn_data`, then start the stack again. The entrypoint leaves existing files untouched. +- Testing a new image? Set `TN_NODE_TAG` to the candidate tag and point the compose stack at a fresh host directory so you can diff auto-generated config before promoting it to production. diff --git a/go.mod b/go.mod index 2d02b586c..b25485eb4 100644 --- a/go.mod +++ b/go.mod @@ -19,8 +19,8 @@ require ( github.com/spf13/cobra v1.9.1 github.com/stretchr/testify v1.10.0 github.com/testcontainers/testcontainers-go v0.37.0 - github.com/trufnetwork/kwil-db v0.10.3-0.20250915124855-c60f28b113d1 - github.com/trufnetwork/kwil-db/core v0.4.3-0.20250915124855-c60f28b113d1 + github.com/trufnetwork/kwil-db v0.10.3-0.20250916115210-a6b854684a3e + github.com/trufnetwork/kwil-db/core v0.4.3-0.20250916115210-a6b854684a3e github.com/trufnetwork/sdk-go v0.3.2-0.20250630062504-841b40cdb709 go.uber.org/zap v1.27.0 golang.org/x/exp v0.0.0-20250218142911-aa4b98e5adaa diff --git a/go.sum b/go.sum index ce258a2eb..09dff45fe 100644 --- a/go.sum +++ b/go.sum @@ -1214,8 +1214,12 @@ github.com/tklauser/numcpus v0.9.0 h1:lmyCHtANi8aRUgkckBgoDk1nHCux3n2cgkJLXdQGPD github.com/tklauser/numcpus v0.9.0/go.mod h1:SN6Nq1O3VychhC1npsWostA+oW+VOQTxZrS604NSRyI= github.com/trufnetwork/kwil-db v0.10.3-0.20250915124855-c60f28b113d1 h1:NQ1HD0kf61QtNhcaCJ0jDqTaMw7WipBEZzn7lb0Mios= github.com/trufnetwork/kwil-db v0.10.3-0.20250915124855-c60f28b113d1/go.mod h1:LiBAC48uZl2B0IiLtD2hpOce7RNfpuDdghVAOc3u1Qo= +github.com/trufnetwork/kwil-db v0.10.3-0.20250916115210-a6b854684a3e h1:1J0GDHNtJqoTLbFyTjGDzSn9u1h3JeeV3E2GL8uUm9k= +github.com/trufnetwork/kwil-db v0.10.3-0.20250916115210-a6b854684a3e/go.mod h1:LiBAC48uZl2B0IiLtD2hpOce7RNfpuDdghVAOc3u1Qo= github.com/trufnetwork/kwil-db/core v0.4.3-0.20250915124855-c60f28b113d1 h1:FJ/dHHviqqx4wyH5ucA2z2JRmo4+k1eOCy6d9ye5djA= github.com/trufnetwork/kwil-db/core v0.4.3-0.20250915124855-c60f28b113d1/go.mod h1:HnOsh9+BN13LJCjiH0+XKaJzyjWKf+H9AofFFp90KwQ= +github.com/trufnetwork/kwil-db/core v0.4.3-0.20250916115210-a6b854684a3e h1:IHsL26fvglbJ8t2CVbwPWv1nFD5mIJofwq80tS4Quus= +github.com/trufnetwork/kwil-db/core v0.4.3-0.20250916115210-a6b854684a3e/go.mod h1:HnOsh9+BN13LJCjiH0+XKaJzyjWKf+H9AofFFp90KwQ= github.com/trufnetwork/openzeppelin-merkle-tree-go v0.0.2 h1:DCq8MzbWH0wZmICNmMVsSzUHUPl+2vqRhluEABjxl88= github.com/trufnetwork/openzeppelin-merkle-tree-go v0.0.2/go.mod h1:Y0MJpPp9QXU5vC6Gpoilql2NkgmGNcbHm9HYC2v2N8s= github.com/trufnetwork/sdk-go v0.3.2-0.20250630062504-841b40cdb709 h1:d9EqPXIjbq/atzEncK5dM3Z9oStx1BxCGuL/sjefeCw= diff --git a/internal/migrations/test_only/bootstrap_erc20.sql b/internal/migrations/0_test_only/bootstrap_erc20.sql similarity index 100% rename from internal/migrations/test_only/bootstrap_erc20.sql rename to internal/migrations/0_test_only/bootstrap_erc20.sql diff --git a/internal/migrations/erc20-bridge/000-extension.sql b/internal/migrations/erc20-bridge/000-extension.sql index b70d50627..4344e03f0 100644 --- a/internal/migrations/erc20-bridge/000-extension.sql +++ b/internal/migrations/erc20-bridge/000-extension.sql @@ -1,4 +1,4 @@ --- Only necessary to run on leader and validator nodes. +-- This is not meant to be run on tests as the contract address is valid for mainnet only. USE erc20 { chain: 'sepolia', diff --git a/internal/migrations/migration.go b/internal/migrations/migration.go index e54f8d9f7..1226ea590 100644 --- a/internal/migrations/migration.go +++ b/internal/migrations/migration.go @@ -2,60 +2,47 @@ package migrations import ( "embed" + "io/fs" "path/filepath" "runtime" + "sort" "strings" ) -//go:embed *.sql test_only/*.sql erc20-bridge/*.sql +//go:embed *.sql 0_test_only/*.sql erc20-bridge/*.sql var seedFiles embed.FS func GetSeedScriptPaths() []string { - var seedsFiles []string + var seedFilesPaths []string // Get the absolute path to the directory where this file (migration.go) is located _, filename, _, _ := runtime.Caller(0) dir := filepath.Dir(filename) - // Read embedded seed files from root directory - entries, err := seedFiles.ReadDir(".") - if err != nil { - panic(err) - } - - // Process root directory SQL files - for _, entry := range entries { - if !entry.IsDir() && strings.HasSuffix(entry.Name(), ".sql") { - // Create absolute path by joining the directory path with the file name - seedsFiles = append(seedsFiles, filepath.Join(dir, entry.Name())) + err := fs.WalkDir(seedFiles, ".", func(path string, d fs.DirEntry, err error) error { + if err != nil { + return err } - } - - // process test_only directory - entries, err = seedFiles.ReadDir("test_only") - if err != nil { - panic(err) - } - for _, entry := range entries { - if !entry.IsDir() && strings.HasSuffix(entry.Name(), ".sql") { - seedsFiles = append(seedsFiles, filepath.Join(dir, "test_only", entry.Name())) + if d.IsDir() { + return nil } - } - - // process erc20-bridge directory - entries, err = seedFiles.ReadDir("erc20-bridge") + if !strings.HasSuffix(path, ".sql") { + return nil + } + if strings.HasSuffix(path, ".prod.sql") { + return nil + } + seedFilesPaths = append(seedFilesPaths, filepath.Join(dir, filepath.FromSlash(path))) + return nil + }) if err != nil { panic(err) } - for _, entry := range entries { - if !entry.IsDir() && strings.HasSuffix(entry.Name(), ".sql") { - seedsFiles = append(seedsFiles, filepath.Join(dir, "erc20-bridge", entry.Name())) - } - } - if len(seedsFiles) == 0 { + if len(seedFilesPaths) == 0 { panic("no seeds files found in embedded directory") } - return seedsFiles + sort.Strings(seedFilesPaths) + return seedFilesPaths } diff --git a/scripts/ci-cleanup.sh b/scripts/ci-cleanup.sh index e891e9029..ff5b19187 100644 --- a/scripts/ci-cleanup.sh +++ b/scripts/ci-cleanup.sh @@ -11,7 +11,7 @@ fi # Common container names/images names=("tn-db" "kwil-postgres" "kwild" "postgres") -images=("kwildb/postgres" "tn-db:local" "kwildb/postgres:latest" "kwildb/postgres:16.8-1") +images=("kwildb/postgres" "ghcr.io/trufnetwork/node:local" "kwildb/postgres:latest" "kwildb/postgres:16.8-1") echo "[ci-cleanup] Stopping/removing lingering containers by name..." for n in "${names[@]}"; do @@ -49,5 +49,3 @@ echo "[ci-cleanup] Cleanup complete." if command -v pkill >/dev/null 2>&1; then pkill -9 -f "\bkwild\b" 2>/dev/null || true fi - - diff --git a/tests/extensions/erc20/common_test.go b/tests/extensions/erc20/common_test.go index ba34f1333..53cc9697d 100644 --- a/tests/extensions/erc20/common_test.go +++ b/tests/extensions/erc20/common_test.go @@ -11,8 +11,6 @@ import ( kwilTesting "github.com/trufnetwork/kwil-db/testing" "github.com/trufnetwork/node/internal/migrations" testutils "github.com/trufnetwork/node/tests/streams/utils" - - erc20shim "github.com/trufnetwork/kwil-db/node/exts/erc20-bridge/erc20" ) // Common deterministic values used across ERC20 bridge tests @@ -34,13 +32,7 @@ func seedAndRun(t TestingT, name string, fn kwilTesting.TestFunc) { // Wrap the test function to add singleton reset and cleanup wrappedFn := func(ctx context.Context, platform *kwilTesting.Platform) error { - // STEP 1: Register cleanup (runs after transaction rollback) - t.Cleanup(func() { - erc20shim.ForTestingClearAllInstances(ctx, platform) - erc20shim.ForTestingResetSingleton() - }) - - // STEP 2: Run the actual test inside a transaction for rollback isolation + // Run the actual test inside a transaction for rollback isolation tx, err := platform.DB.BeginTx(ctx) if err != nil { return fmt.Errorf("begin tx: %w", err) diff --git a/tests/extensions/erc20/erc20_bridge_transfer_actions_test.go b/tests/extensions/erc20/erc20_bridge_transfer_actions_test.go index effc96409..08009b997 100644 --- a/tests/extensions/erc20/erc20_bridge_transfer_actions_test.go +++ b/tests/extensions/erc20/erc20_bridge_transfer_actions_test.go @@ -21,8 +21,8 @@ import ( // without needing to use the extension methods directly. func TestSepoliaTransferActions(t *testing.T) { seedAndRun(t, "sepolia_transfer_actions", func(ctx context.Context, platform *kwilTesting.Platform) error { - // Initialize the extension to load the sepolia_bridge instance - err := erc20shim.ForTestingInitializeExtension(ctx, platform) + // Enable instance with alias in one step + err := erc20shim.ForTestingSeedAndActivateInstance(ctx, platform, TestChain, TestEscrowA, TestERC20, 18, 60, TestExtensionAlias) require.NoError(t, err) // Get the configured escrow address from bridge info @@ -31,7 +31,7 @@ func TestSepoliaTransferActions(t *testing.T) { // Credit initial balance to TestUserA using configured escrow err = testerc20.InjectERC20Transfer(ctx, platform, - TestChain, configuredEscrow, TestERC20, configuredEscrow, TestUserA, TestAmount2, 10, nil) + TestChain, configuredEscrow, TestERC20, TestUserA, configuredEscrow, TestAmount2, 10, nil) require.NoError(t, err) // Verify initial balance via sepolia_wallet_balance action @@ -64,8 +64,8 @@ func TestSepoliaTransferActions(t *testing.T) { // TestTransferActionValidation tests the validation logic in the new transfer actions. func TestTransferActionValidation(t *testing.T) { seedAndRun(t, "transfer_action_validation", func(ctx context.Context, platform *kwilTesting.Platform) error { - // Initialize the extension to load the sepolia_bridge instance - err := erc20shim.ForTestingInitializeExtension(ctx, platform) + // Enable instance with alias in one step + err := erc20shim.ForTestingSeedAndActivateInstance(ctx, platform, TestChain, TestEscrowA, TestERC20, 18, 60, TestExtensionAlias) require.NoError(t, err) // Get the configured escrow address from bridge info @@ -122,7 +122,7 @@ func TestTransferActionValidation(t *testing.T) { // Give TestUserA a small balance (half of what they'll try to transfer) smallAmount := "500000000000000000" // 0.5 tokens (half of TestAmount1 which is 1.0) err = testerc20.InjectERC20Transfer(ctx, platform, - TestChain, configuredEscrow, TestERC20, configuredEscrow, TestUserA, smallAmount, 10, nil) + TestChain, configuredEscrow, TestERC20, TestUserA, configuredEscrow, smallAmount, 10, nil) require.NoError(t, err) // Verify they have the small balance @@ -155,8 +155,8 @@ func TestTransferActionValidation(t *testing.T) { // TestMultipleTransferActions tests multiple sequential transfers using the new actions. func TestMultipleTransferActions(t *testing.T) { seedAndRun(t, "multiple_transfer_actions", func(ctx context.Context, platform *kwilTesting.Platform) error { - // Initialize the extension to load the sepolia_bridge instance - err := erc20shim.ForTestingInitializeExtension(ctx, platform) + // Enable instance with alias in one step + err := erc20shim.ForTestingSeedAndActivateInstance(ctx, platform, TestChain, TestEscrowA, TestERC20, 18, 60, TestExtensionAlias) require.NoError(t, err) // Get the configured escrow address from bridge info @@ -171,7 +171,7 @@ func TestMultipleTransferActions(t *testing.T) { // Credit large initial balance to userA initialAmount := "10000000000000000000" // 10.0 tokens err = testerc20.InjectERC20Transfer(ctx, platform, - TestChain, configuredEscrow, TestERC20, configuredEscrow, userA, initialAmount, 10, nil) + TestChain, configuredEscrow, TestERC20, userA, configuredEscrow, initialAmount, 10, nil) require.NoError(t, err) // Transfer A -> B (3 tokens) diff --git a/tests/extensions/tn_cache_metrics/docker-compose.yml b/tests/extensions/tn_cache_metrics/docker-compose.yml index 76147893a..39f6cdcf1 100644 --- a/tests/extensions/tn_cache_metrics/docker-compose.yml +++ b/tests/extensions/tn_cache_metrics/docker-compose.yml @@ -16,7 +16,7 @@ services: - metrics-net kwild: - image: tn-db:metrics-test + image: ghcr.io/trufnetwork/node:metrics-test depends_on: postgres: condition: service_healthy @@ -25,8 +25,8 @@ services: KWILD_DB_HOST: postgres KWILD_DB_PORT: 5432 # Node configuration - CHAIN_ID: tn-metrics-test - DB_OWNER: "0x7E5F4552091A69125d5DfCb7b8C2659029395Bdf" + SETUP_CHAIN_ID: tn-metrics-test + SETUP_DB_OWNER: "0x7E5F4552091A69125d5DfCb7b8C2659029395Bdf" # Network configuration KWILD_APP_JSONRPC_LISTEN_ADDR: "0.0.0.0:8484" KWILD_APP_P2P_LISTEN_ADDR: "0.0.0.0:6600" @@ -142,4 +142,4 @@ networks: volumes: prometheus-data: - grafana-data: \ No newline at end of file + grafana-data: diff --git a/tests/extensions/tn_cache_metrics/test_tn_cache_metrics.sh b/tests/extensions/tn_cache_metrics/test_tn_cache_metrics.sh index 8441fb17a..6dea4fc83 100755 --- a/tests/extensions/tn_cache_metrics/test_tn_cache_metrics.sh +++ b/tests/extensions/tn_cache_metrics/test_tn_cache_metrics.sh @@ -12,7 +12,7 @@ YELLOW='\033[1;33m' NC='\033[0m' # No Color # Configuration -DOCKER_IMAGE="tn-db:metrics-test" +DOCKER_IMAGE="ghcr.io/trufnetwork/node:metrics-test" COMPOSE_PROJECT="tn-cache-metrics" # Function to print colored output @@ -196,4 +196,4 @@ main() { } # Run main function -main "$@" \ No newline at end of file +main "$@" diff --git a/tests/extensions/tn_digest/configs/custom-entrypoint.sh b/tests/extensions/tn_digest/configs/custom-entrypoint.sh index 51345cc58..8cfda0bcd 100755 --- a/tests/extensions/tn_digest/configs/custom-entrypoint.sh +++ b/tests/extensions/tn_digest/configs/custom-entrypoint.sh @@ -6,7 +6,7 @@ echo "Starting custom entrypoint for tn_digest E2E test..." # Initialize configuration if it doesn't exist if [ ! -f /root/.kwild/config.toml ]; then echo "Initializing kwild configuration..." - ./kwild setup init --chain-id ${CHAIN_ID:-tn-digest-test} --db-owner ${DB_OWNER} -r /root/.kwild/ + ./kwild setup init --chain-id ${SETUP_CHAIN_ID:-tn-digest-test} --db-owner ${SETUP_DB_OWNER} -r /root/.kwild/ echo "Configuration initialized successfully" # Add tn_digest extension configuration with fast reload for testing diff --git a/tests/extensions/tn_digest/docker-compose.yml b/tests/extensions/tn_digest/docker-compose.yml index e3238d8ed..3a9f17820 100644 --- a/tests/extensions/tn_digest/docker-compose.yml +++ b/tests/extensions/tn_digest/docker-compose.yml @@ -16,7 +16,7 @@ services: - digest-net kwild: - image: tn-db:digest-test + image: ghcr.io/trufnetwork/node:digest-test depends_on: postgres: condition: service_healthy @@ -25,8 +25,8 @@ services: KWILD_DB_HOST: postgres KWILD_DB_PORT: 5432 # Node configuration - CHAIN_ID: tn-digest-test - DB_OWNER: "0x7E5F4552091A69125d5DfCb7b8C2659029395Bdf" + SETUP_CHAIN_ID: tn-digest-test + SETUP_DB_OWNER: "0x7E5F4552091A69125d5DfCb7b8C2659029395Bdf" # Network configuration KWILD_APP_JSONRPC_LISTEN_ADDR: "0.0.0.0:8484" KWILD_APP_P2P_LISTEN_ADDR: "0.0.0.0:6600" @@ -51,4 +51,4 @@ services: networks: digest-net: - driver: bridge \ No newline at end of file + driver: bridge diff --git a/tests/extensions/tn_digest/test_tn_digest.sh b/tests/extensions/tn_digest/test_tn_digest.sh index dd5ea1424..7ad1a6bd4 100755 --- a/tests/extensions/tn_digest/test_tn_digest.sh +++ b/tests/extensions/tn_digest/test_tn_digest.sh @@ -12,7 +12,7 @@ YELLOW='\033[1;33m' NC='\033[0m' # No Color # Configuration -DOCKER_IMAGE="tn-db:digest-test" +DOCKER_IMAGE="ghcr.io/trufnetwork/node:digest-test" COMPOSE_PROJECT="tn-digest-e2e" # Function to print colored output @@ -186,4 +186,4 @@ main() { } # Run main function -main "$@" \ No newline at end of file +main "$@" diff --git a/tests/setup/simple_node.go b/tests/setup/simple_node.go index 71c8b3a34..bc3a4f0dc 100644 --- a/tests/setup/simple_node.go +++ b/tests/setup/simple_node.go @@ -160,8 +160,8 @@ func (f *SimpleNodeFixture) startKwild(ctx context.Context, image string, config "KWILD_DB_PASS": "kwil", "KWILD_DB_NAME": "kwil", // Required for config.sh initialization - "CHAIN_ID": config.ChainID, - "DB_OWNER": dbOwnerIdentifier, + "SETUP_CHAIN_ID": config.ChainID, + "SETUP_DB_OWNER": dbOwnerIdentifier, // Additional configuration overrides "KWILD_APP_JSONRPC_LISTEN_ADDR": "0.0.0.0:8484", "KWILD_APP_P2P_LISTEN_ADDR": "0.0.0.0:6600", diff --git a/tests/streams/query/metadata_test.go b/tests/streams/query/metadata_test.go index af2897e15..745ab0a04 100644 --- a/tests/streams/query/metadata_test.go +++ b/tests/streams/query/metadata_test.go @@ -3,6 +3,7 @@ package tests import ( "context" "fmt" + "strconv" "strings" "testing" @@ -177,18 +178,22 @@ func testListMetadataByHeight(t *testing.T, contractInfo setup.StreamInfo) kwilT Value string ValType string }{ + {metadataKey, "2", "int"}, {metadataKey, "1", "int"}, - {metadataKey, "0", "int"}, } for _, item := range metadataItems { - err := procedure.InsertMetadata(ctx, procedure.InsertMetadataInput{ + height, err := strconv.Atoi(item.Value) + if err != nil { + return errors.Wrapf(err, "error converting value to int") + } + err = procedure.InsertMetadata(ctx, procedure.InsertMetadataInput{ Platform: platform, Locator: contractInfo.Locator, Key: item.Key, Value: item.Value, ValType: item.ValType, - Height: 1, + Height: int64(height), }) if err != nil { return errors.Wrapf(err, "error inserting metadata with key %s", item.Key) @@ -198,7 +203,7 @@ func testListMetadataByHeight(t *testing.T, contractInfo setup.StreamInfo) kwilT result, err := procedure.ListMetadataByHeight(ctx, procedure.ListMetadataByHeightInput{ Platform: platform, Key: metadataKey, - Height: 1, + Height: int64(len(metadataItems)), }) if err != nil { return errors.Wrapf(err, "error listing metadata") @@ -207,8 +212,8 @@ func testListMetadataByHeight(t *testing.T, contractInfo setup.StreamInfo) kwilT expected := ` | value_i | value_f | value_b | value_s | value_ref | created_at | |---------|---------|---------|---------|-----------|------------| - | 0 | | | | | 1 | - | 1 | | | | | 1 |` + | 1 | | | | | 1 | + | 2 | | | | | 2 |` table.AssertResultRowsEqualMarkdownTable(t, table.AssertResultRowsEqualMarkdownTableInput{ Actual: result, diff --git a/tests/streams/utils/runner.go b/tests/streams/utils/runner.go index 1efbf5864..5350eb6ad 100644 --- a/tests/streams/utils/runner.go +++ b/tests/streams/utils/runner.go @@ -17,6 +17,7 @@ import ( "github.com/trufnetwork/node/tests/streams/utils/erc20" "github.com/trufnetwork/node/tests/streams/utils/service" + erc20shim "github.com/trufnetwork/kwil-db/node/exts/erc20-bridge/erc20" orderedsync "github.com/trufnetwork/kwil-db/node/exts/ordered-sync" ) @@ -88,6 +89,8 @@ func RunSchemaTest(t TestingT, s kwilTesting.SchemaTest, options *Options) { if len(wrappedTests) <= 1 { // Single function: simple path orderedsync.ForTestingReset() + erc20shim.ForTestingResetSingleton() + erc20shim.ForTestingClearAllInstances(context.Background(), nil) kwilTesting.RunSchemaTest(testT, kwilTesting.SchemaTest{ Name: s.Name, SeedScripts: s.SeedScripts, @@ -100,6 +103,8 @@ func RunSchemaTest(t TestingT, s kwilTesting.SchemaTest, options *Options) { for _, fn := range wrappedTests { orderedsync.ForTestingReset() + erc20shim.ForTestingResetSingleton() + erc20shim.ForTestingClearAllInstances(context.Background(), nil) kwilTesting.RunSchemaTest(testT, kwilTesting.SchemaTest{ Name: s.Name, SeedScripts: s.SeedScripts,