Skip to content

Commit 8f372b6

Browse files
committed
fix: take has_genesis_hash and has_genesis_id into account for transactions in an algod Block
1 parent 87b84b0 commit 8f372b6

File tree

3 files changed

+76
-1
lines changed

3 files changed

+76
-1
lines changed

api/oas-generator/src/oas_generator/renderer/templates/models/block.py.j2

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -335,7 +335,23 @@ class Block:
335335
decode=lambda raw: decode_model_sequence(lambda: SignedTxnInBlock, raw),
336336
),
337337
)
338-
338+
339+
def __post_init__(self) -> None:
340+
# populates genesis id and hash on transactions if required to ensure
341+
# tx id's are correct
342+
genesis_id = self.header.genesis_id
343+
genesis_hash = self.header.genesis_hash
344+
set_frozen_field = object.__setattr__
345+
for txn_in_block in self.payset or []:
346+
txn = txn_in_block.signed_transaction.signed_transaction.transaction
347+
348+
if txn_in_block.has_genesis_id and txn.genesis_id is None:
349+
set_frozen_field(txn, "genesis_id", genesis_id)
350+
351+
# the following assumes that Consensus.RequireGenesisHash is true
352+
# so assigns genesis hash unless explicitly set to False
353+
if txn_in_block.has_genesis_hash is not False and txn.genesis_hash is None:
354+
set_frozen_field(txn, "genesis_hash", genesis_hash)
339355

340356
@dataclass(slots=True)
341357
class BlockResponse:

src/algokit_algod_client/models/_block.py

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -337,6 +337,23 @@ class Block:
337337
),
338338
)
339339

340+
def __post_init__(self) -> None:
341+
# populates genesis id and hash on transactions if required to ensure
342+
# tx id's are correct
343+
genesis_id = self.header.genesis_id
344+
genesis_hash = self.header.genesis_hash
345+
set_frozen_field = object.__setattr__
346+
for txn_in_block in self.payset or []:
347+
txn = txn_in_block.signed_transaction.signed_transaction.txn
348+
349+
if txn_in_block.has_genesis_id and txn.genesis_id is None:
350+
set_frozen_field(txn, "genesis_id", genesis_id)
351+
352+
# the following assumes that Consensus.RequireGenesisHash is true
353+
# so assigns genesis hash unless explicitly set to False
354+
if txn_in_block.has_genesis_hash is not False and txn.genesis_hash is None:
355+
set_frozen_field(txn, "genesis_hash", genesis_hash)
356+
340357

341358
@dataclass(slots=True)
342359
class BlockResponse:
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
import base64
2+
import dataclasses
3+
4+
from algokit_transact import Transaction
5+
from algokit_utils import AlgorandClient, AlgoAmount, AssetCreateParams
6+
7+
8+
def test_block_tx_id_matches_submitted_id() -> None:
9+
localnet = AlgorandClient.default_localnet()
10+
algod = localnet.client.algod
11+
12+
sender = localnet.account.random()
13+
localnet.account.ensure_funded(sender, localnet.account.localnet_dispenser(), AlgoAmount(micro_algo=1_000_000))
14+
15+
txns = (
16+
localnet.new_group()
17+
.add_asset_create(
18+
AssetCreateParams(sender=sender.addr, static_fee=AlgoAmount(micro_algo=2000), total=100_000_000)
19+
)
20+
.send()
21+
)
22+
txn = txns.transactions[0]
23+
group_id = base64.b64decode(txns.group_id)
24+
tx_id = txns.tx_ids[0]
25+
confirmation = algod.pending_transaction_information(tx_id)
26+
confirmed_round = confirmation.confirmed_round
27+
assert confirmed_round is not None, "expected a confirmed round"
28+
assert confirmation.txn.txn.tx_id() == tx_id, "expected confirmation tx_id to match submitted tx_id"
29+
assert confirmation.txn.txn.group == group_id, "expected group_id to match"
30+
31+
block = algod.get_block(confirmed_round)
32+
assert block.block.payset is not None, "expected non null payset"
33+
(block_txn,) = block.block.payset
34+
txn_fields = {f.name: getattr(txn, f.name) for f in dataclasses.fields(Transaction)}
35+
block_txn_fields = {
36+
f.name: getattr(block_txn.signed_transaction.signed_transaction.txn, f.name)
37+
for f in dataclasses.fields(Transaction)
38+
}
39+
assert txn_fields == block_txn_fields
40+
41+
assert block_txn.signed_transaction.signed_transaction.txn.group == group_id, "expected group_id to match"
42+
assert block_txn.signed_transaction.signed_transaction.txn.tx_id() == tx_id, "expected block tx_id to match"

0 commit comments

Comments
 (0)