Skip to content

Python decoder regression test for signed int24 events #57

@Pratham6392

Description

@Pratham6392

End-to-end Python decoder correctness test for a real Uniswap V3 Mint event with signed int24 indexed fields.

The test verifies that:

  • the Python client fetches the expected log,
  • hypersync.Decoder.decode_logs_sync(...) successfully decodes it,
  • signed indexed values are preserved correctly at the Python layer (tickLower == -1, tickUpper == 1).

Upstream Rust already covers decoder internals, but this repository’s responsibility is the Python-facing contract: decoded values must continue to arrive in Python with the correct semantics after PyO3 conversion, wrapper changes, or dependency upgrades. This test focuses on a real signed-integer event case that is easy to regress silently at the binding layer.

This was the test which I used :

"""Integration-style correctness tests for decoded Python values.

These tests exercise the real compiled extension against actual HyperSync
responses so they protect the Python-visible behavior of the Rust decoder
bindings.
"""

import os

import pytest

import hypersync

_BASE_URL = "https://base.hypersync.xyz"

_MINT_SIGNATURE = (
    "event Mint(address sender, address indexed owner, "
    "int24 indexed tickLower, int24 indexed tickUpper, "
    "uint128 amount, uint256 amount0, uint256 amount1)"
)
_MINT_TOPIC0 = "0x7a53080ba414158be7ec69b987b5fb7d07dee101fe85488f0853ae16239d0bde"
_POOL_ADDRESS = "0x98c7A2338336d2d354663246F64676009c7bDa97"
_OWNER_TOPIC = "0x000000000000000000000000827922686190790b37229fd06084350e74485b72"
_TICK_LOWER_TOPIC = (
    "0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff"
)
_TICK_UPPER_TOPIC = (
    "0x0000000000000000000000000000000000000000000000000000000000000001"
)


def _token() -> str | None:
    return os.getenv("ENVIO_API_TOKEN") 


def _client() -> hypersync.HypersyncClient:
    return hypersync.HypersyncClient(
        hypersync.ClientConfig(
            url=_BASE_URL,
            api_token=_token(),
        )
    )


def _mint_query() -> hypersync.Query:
    return hypersync.Query(
        from_block=13_899_663,
        to_block=13_899_664,
        logs=[
            hypersync.LogSelection(
                address=[_POOL_ADDRESS],
                topics=[
                    [_MINT_TOPIC0],
                    [_OWNER_TOPIC],
                    [_TICK_LOWER_TOPIC],
                    [_TICK_UPPER_TOPIC],
                ],
            )
        ],
        field_selection=hypersync.FieldSelection(
            log=[
                hypersync.LogField.BLOCK_NUMBER,
                hypersync.LogField.LOG_INDEX,
                hypersync.LogField.TRANSACTION_INDEX,
                hypersync.LogField.ADDRESS,
                hypersync.LogField.DATA,
                hypersync.LogField.TOPIC0,
                hypersync.LogField.TOPIC1,
                hypersync.LogField.TOPIC2,
                hypersync.LogField.TOPIC3,
            ]
        ),
    )


@pytest.mark.asyncio
async def test_decoder_decodes_signed_int24_values_correctly():
    """Signed indexed values should arrive in Python as real negative ints."""
    token = _token()
    print(f"ENVIO_API_TOKEN present: {bool(token)}")
    if not token:
        print("Skipping decoder correctness test because ENVIO_API_TOKEN is not set.")
        pytest.skip("set ENVIO_API_TOKEN to run integration decoder tests")

    print(f"Creating client for {_BASE_URL}")
    client = _client()
    print(
        "Running query:",
        {
            "from_block": 13_899_663,
            "to_block": 13_899_664,
            "address": _POOL_ADDRESS,
            "topic0": _MINT_TOPIC0,
        },
    )
    response = await client.get(_mint_query())
    print(f"Fetched {len(response.data.logs)} matching log(s)")
    assert len(response.data.logs) == 1, "expected exactly one matching Mint log"

    log = response.data.logs[0]
    print(
        "Fetched log:",
        {
            "block_number": log.block_number,
            "log_index": log.log_index,
            "address": log.address,
            "topics": log.topics,
            "data": log.data,
        },
    )

    decoder = hypersync.Decoder([_MINT_SIGNATURE])
    print("Decoding log through hypersync.Decoder.decode_logs_sync(...)")
    result = decoder.decode_logs_sync(response.data.logs)

    assert len(result) == 1, "expected exactly one decoded result"
    decoded = result[0]
    assert decoded is not None, "expected Mint log to decode successfully"

    owner = decoded.indexed[0].val
    tick_lower = decoded.indexed[1].val
    tick_upper = decoded.indexed[2].val
    amount = decoded.body[1].val

    print(
        "Decoded values:",
        {
            "owner": owner,
            "tick_lower": tick_lower,
            "tick_upper": tick_upper,
            "amount": amount,
        },
    )

    assert owner == "0x827922686190790b37229fd06084350e74485b72"
    assert tick_lower == -1
    assert tick_upper == 1
    assert amount == 196849270

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions