Important
This is a proof-of-concept, please reach out to the Tempo team if you are interested in using this library in production.
Web3.py extension for Tempo.
pip install -e .Or with uv:
uv add .from pytempo import patch_web3_for_tempo, create_tempo_transaction
from web3 import Web3
# Step 1: Patch web3.py to add Tempo support
patch_web3_for_tempo()
# Step 2: Use web3.py normally with Tempo features
w3 = Web3(Web3.HTTPProvider("https://rpc.testnet.tempo.xyz"))
account = w3.eth.account.from_key("0x...")
# Step 3: Create Tempo AA transaction (Type 0x76)
tx = create_tempo_transaction(
to="0xRecipient...",
value=0,
gas=100000,
max_fee_per_gas=w3.eth.gas_price * 2,
max_priority_fee_per_gas=w3.eth.gas_price,
nonce=w3.eth.get_transaction_count(account.address),
chain_id=w3.eth.chain_id,
fee_token="0x20c0000000000000000000000000000000000001", # AlphaUSD
)
# Step 4: Sign and send using standard web3.py
tx.sign(account.key.hex())
tx_hash = w3.eth.send_raw_transaction(tx.encode())
receipt = w3.eth.wait_for_transaction_receipt(tx_hash)from pytempo import create_tempo_transaction
tx = create_tempo_transaction(
to="0xRecipient...",
value=1000000000000000,
gas=100000,
max_fee_per_gas=2000000000,
max_priority_fee_per_gas=2000000000,
nonce=0,
chain_id=42429,
)
tx.sign("0xYourPrivateKey...")
encoded = tx.encode()tx = create_tempo_transaction(
to="0xRecipient...",
value=0,
fee_token="0xTokenAddress...", # Pay gas in this ERC-20 token
gas=100000,
max_fee_per_gas=2000000000,
max_priority_fee_per_gas=2000000000,
nonce=0,
chain_id=42429,
)# User creates and signs
tx = create_tempo_transaction(
to="0xRecipient...",
value=1000000000000000,
gas=100000,
max_fee_per_gas=2000000000,
max_priority_fee_per_gas=2000000000,
nonce=0,
chain_id=42429,
fee_token="0xTokenAddress...",
)
# Mark that fee payer will sign
tx._will_have_fee_payer = True
# User signs
tx.sign("0xUserPrivateKey...", for_fee_payer=False)
# Fee payer signs (pays gas)
tx.sign("0xFeePayerPrivateKey...", for_fee_payer=True)
# Send
w3.eth.send_raw_transaction(tx.encode())tx = create_tempo_transaction(
to="", # Not used
calls=[
{"to": "0xAddress1...", "value": 100000, "data": "0x"},
{"to": "0xAddress2...", "value": 200000, "data": "0xabcdef"},
],
gas=200000,
max_fee_per_gas=2000000000,
max_priority_fee_per_gas=2000000000,
nonce=0,
chain_id=42429,
)# Use different nonce keys for parallel execution
tx1 = create_tempo_transaction(
to="0xRecipient...",
nonce=0,
nonce_key=1, # First parallel key
# ... other params
)
tx2 = create_tempo_transaction(
to="0xRecipient...",
nonce=0,
nonce_key=2, # Second parallel key
# ... other params
)
# Both can be executed in parallelMonkey patches web3.py to recognize Tempo AA transactions. Must be called before using web3.
Creates a Tempo AA transaction.
Parameters:
to(str): Destination addressvalue(int): Value in wei (default: 0)gas(int): Gas limitmax_fee_per_gas(int): Maximum fee per gasmax_priority_fee_per_gas(int): Maximum priority fee per gasnonce(int): Transaction noncechain_id(int): Chain IDnonce_key(int): Nonce key for parallel execution (default: 0)fee_token(str, optional): ERC-20 token address for gas paymentcalls(list, optional): List of calls for batchingdata(str, optional): Transaction datavalid_before(int, optional): Timestamp before which tx is validvalid_after(int, optional): Timestamp after which tx becomes valid
Returns: TempoAATransaction
Main transaction class.
Methods:
sign(private_key, for_fee_payer=False)- Sign the transactionencode()- Encode to bytes for transmissionhash()- Get transaction hashget_signing_hash(for_fee_payer=False)- Get hash to signvrs()- Get v, r, s values (secp256k1 only)
See the examples/ directory:
simple_send.py- Simple value transferbasic_transaction.py- Transaction with fee tokenfee_payer_sponsored.py- Gas sponsorship and call batching
Our contributor guidelines can be found in CONTRIBUTING.md.
See SECURITY.md. Note: Tempo is still undergoing audit and does not have an active bug bounty. Submissions will not be eligible for a bounty until audits have concluded.
Licensed under either of Apache License, Version 2.0 or MIT License at your option.
Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in these crates by you, as defined in the Apache-2.0 license, shall be dual licensed as above, without any additional terms or conditions.