Python SDK

In order to simplify the implementation of Bebop solvers, you can use the JAM Python SDK. It includes:

  • Managed websocket connection to JAM

  • Simple base class to implement for providing solutions

  • Cache management and validation

  • Fully typed request and responses

  • Jam contract deployments and ABIs

The SDK can also be a helpful guide for implementing a solver in your language of choice.

pip install jam_sdk

Creating your solver

To implement these functions, simply implement the BaseSolver class with get_quote and execute functions.

get_quote

Receives a quote request and expects a response with the output token amounts.

execute_order

Given a execution request, execute the given quote on chain and return the transaction hash.

You may access the quote request and response for this execution using the quote_cache parameter.

Utilities

build_settle - Simulate and build the settlement call to JAM.

encode_order - Create an order object that is compatible with the onchain settlement call.

Example

import asyncio

from jam_sdk.solver.base import BaseSolver
from jam_sdk.solver.types import (
    CachedQuote,
    ExecuteError,
    ExecuteRequest,
    ExecuteResponse,
    InteractionData,
    QuoteError,
    QuoteRequest,
    QuoteResponse,
    SolverConnection,
    TokenAmountResponse,
)


class MySolver(BaseSolver):
    async def get_quote(self, chain_id: int, request: QuoteRequest) -> QuoteResponse | QuoteError:
        return QuoteResponse(
            quote_id=request.quote_id,
            amounts=[TokenAmountResponse("0x2791Bca1f2de4661ED88A30C99A7a9449Aa84174", 100000)],  # Output token amount
            fee=50000000000000000,  # Fee in wei
        )

    async def execute(self, request: ExecuteRequest, quote_cache: CachedQuote) -> ExecuteResponse | ExecuteError:
        interactions = [  # A set of calls to make on chain in order to fulfil the quote
            InteractionData(
                result=True, to="0x0000", value=0, data="0x00000000000"  # Whether the interaction must succeed
            )
        ]
        account = self.web3.eth.account.from_key("<a private key>")
        settle_tx = await self.build_settle(
            quote_cache.request,
            quote_cache.response,
            interactions,
            request,
            self.jam_contract.address,  # The recipient of user sell tokens. Can be your own solver contract
            {"from": account.address},
        )
        signed_transaction = account.sign_transaction(settle_tx)
        tx = await self.web3.eth.send_raw_transaction(signed_transaction.rawTransaction)
        tx_hash = tx.hex()
        return ExecuteResponse(request.quote_id, tx_hash)


if __name__ == "__main__":
    connection = SolverConnection(
        "my-solver", "mypassword123", "wss://api.bebop.xyz"
    )  # Obtain from Bebop
    solver = MySolver(chain_id=137, rpc_url="https://polygon-rpc.com", connection=connection)
    asyncio.run(solver.start())

Last updated