Skip to content

feat: Expose all missing protobuf fields in TransactionRecord #1781

Closed
gangulysiddhartha22-cmyk wants to merge 3 commits intohiero-ledger:mainfrom
gangulysiddhartha22-cmyk:feature/add-missing-fields-to-transactionrecord
Closed

feat: Expose all missing protobuf fields in TransactionRecord #1781
gangulysiddhartha22-cmyk wants to merge 3 commits intohiero-ledger:mainfrom
gangulysiddhartha22-cmyk:feature/add-missing-fields-to-transactionrecord

Conversation

@gangulysiddhartha22-cmyk
Copy link
Copy Markdown
Contributor

Description:
Expose all previously dropped fields from the TransactionRecord protobuf message in the Python SDK.

Related issue(s):

Fixes #1636

Notes for reviewer:
Restoration of dropped protobuf fields.

Checklist

  • Documented (Code comments, README, etc.)
  • Tested (unit, integration, etc.)

@github-actions
Copy link
Copy Markdown

Hi, this is MergeConflictBot.
Your pull request cannot be merged because it contains merge conflicts.

Please resolve these conflicts locally and push the changes.

Quick Fix for CHANGELOG.md Conflicts

If your conflict is only in CHANGELOG.md, you can resolve it easily using the GitHub web editor:

  1. Click on the "Resolve conflicts" button in the PR
  2. Accept both changes (keep both changelog entries)
  3. Click "Mark as resolved"
  4. Commit the merge

For all other merge conflicts, please read:

Thank you for contributing!

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented Feb 11, 2026

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review

Walkthrough

Adds a new public TokenAssociation dataclass and extends TransactionRecord with several protobuf-backed fields (timestamps, schedule ref, assessed custom fees, automatic token associations, parent timestamp, alias/ethereum/evm data, paid staking rewards, contract create result). Tests and an example script were added; proto (de)serialization and repr updated.

Changes

Cohort / File(s) Summary
TokenAssociation
src/hiero_sdk_python/tokens/token_association.py
Adds a public TokenAssociation dataclass with public fields token_id: Optional[TokenId], account_id: Optional[AccountId], classmethod _from_proto, instance _to_proto, and __str__. Represents automatic token associations from TransactionRecord.
TransactionRecord extension
src/hiero_sdk_python/transaction/transaction_record.py
Adds fields: consensus_timestamp, schedule_ref, assessed_custom_fees, automatic_token_associations, parent_consensus_timestamp, alias, ethereum_hash, paid_staking_rewards, evm_address, contract_create_result; updates _from_proto, _to_proto, imports, and __repr__. Adds mutual-exclusivity checks for contract create vs call and PRNG fields; ensures proper copying of nested and repeated proto fields.
Unit tests
tests/unit/token_association_test.py, tests/unit/transaction_record_test.py
Adds comprehensive tests for TokenAssociation and expanded TransactionRecord covering default/partial/full initialization, _from_proto/_to_proto round-trips, and repr/string assertions for new fields.
Example
examples/transaction/transaction_record.py
New example script create_mock_record() and helpers that construct a fully-populated TransactionRecord and print all fields; demonstrates new fields in a runnable script.
Changelog
CHANGELOG.md
Adds entry noting exposure of previously-missing TransactionRecord protobuf fields.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 71.83% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title accurately summarizes the main change: exposing missing protobuf fields in TransactionRecord, which matches the core objective.
Description check ✅ Passed The description clearly relates to the changeset, referencing restoration of dropped protobuf fields and fixes #1636, aligning with the changes made.
Linked Issues check ✅ Passed The pull request fully addresses all objectives from issue #1636: adds all 10 missing fields, implements bidirectional proto mapping, provides unit tests, adds supporting types (AssessedCustomFee, TokenAssociation), and maintains backward compatibility.
Out of Scope Changes check ✅ Passed All changes directly support the linked issue objectives: new fields, proto mappings, supporting classes, comprehensive tests, examples, and changelog entry are all in scope.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

📋 Issue Planner

Built with CodeRabbit's Coding Plans for faster development and fewer bugs.

View plan used: #1636

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
📝 Coding Plan
  • Generate coding plan for human review comments

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 4

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
src/hiero_sdk_python/transaction/transaction_record.py (1)

38-64: 🧹 Nitpick | 🔵 Trivial

Class docstring does not document the 10 new fields.

The Attributes section in the docstring still only lists the original fields. Users relying on docstrings or IDE tooltips won't discover consensus_timestamp, schedule_ref, assessed_custom_fees, etc.

Comment thread src/hiero_sdk_python/transaction/transaction_record.py Outdated
Comment thread tests/unit/token_association_test.py
Comment thread tests/unit/token_association_test.py Outdated
Comment thread tests/unit/transaction_record_test.py Outdated
@codecov
Copy link
Copy Markdown

codecov Bot commented Feb 11, 2026

Codecov Report

❌ Patch coverage is 98.78049% with 1 line in your changes missing coverage. Please review.

Impacted file tree graph

@@            Coverage Diff             @@
##             main    #1781      +/-   ##
==========================================
+ Coverage   93.56%   93.61%   +0.04%     
==========================================
  Files         141      142       +1     
  Lines        9215     9297      +82     
==========================================
+ Hits         8622     8703      +81     
- Misses        593      594       +1     
🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@gangulysiddhartha22-cmyk
Copy link
Copy Markdown
Contributor Author

@exploreriii Should I add some usage examples for these new TransactionRecord fields?

@gangulysiddhartha22-cmyk
Copy link
Copy Markdown
Contributor Author

@exploreriii @manishdait All review comments addressed: added docstring examples, improved coverage for new fields/repr/round-trips, fixed required fields.

Ready for review

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (2)
src/hiero_sdk_python/transaction/transaction_record.py (1)

366-376: 🧹 Nitpick | 🔵 Trivial

call_result and contract_create_result share a proto oneof — last-write-wins in _to_proto.

In the Hedera TransactionRecord protobuf, contractCallResult and contractCreateResult are in a oneof body. The constructor at line 371 sets contractCallResult, and line 431 may overwrite it with contractCreateResult via CopyFrom. If both fields are non-None on the dataclass, the call result is silently lost.

In practice the network never populates both, so this is low-risk, but adding a guard would prevent future confusion.

🛡️ Optional: add a defensive check
+        if self.call_result is not None and self.contract_create_result is not None:
+            raise ValueError(
+                "call_result and contract_create_result are mutually exclusive (proto oneof)"
+            )
+
         if self.contract_create_result is not None:
             record_proto.contractCreateResult.CopyFrom(self.contract_create_result._to_proto())

Also applies to: 431-432

tests/unit/transaction_record_test.py (1)

100-111: 🧹 Nitpick | 🔵 Trivial

Consider adding assertions for new Optional[bytes] fields when parsing a minimal proto.

test_from_proto validates the existing fields from proto_transaction_record but doesn't assert that the new bytes fields (alias, ethereum_hash, evm_address) are None after parsing a proto where they are unset. This would verify the proto.alias or None normalization path end-to-end.

Suggested additions
     assert record.prng_number == 100
     assert record.prng_bytes == b""
+    assert record.alias is None, "Unset proto alias should normalize to None"
+    assert record.ethereum_hash is None, "Unset proto ethereum_hash should normalize to None"
+    assert record.evm_address is None, "Unset proto evm_address should normalize to None"

As per coding guidelines, "Unit tests should be extensive - test even if we don't expect users to use it currently."

Comment thread src/hiero_sdk_python/transaction/transaction_record.py Outdated
Comment thread tests/unit/token_association_test.py Outdated
@gangulysiddhartha22-cmyk gangulysiddhartha22-cmyk force-pushed the feature/add-missing-fields-to-transactionrecord branch from 7d610b2 to af88ea9 Compare February 11, 2026 17:11
Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
src/hiero_sdk_python/transaction/transaction_record.py (1)

357-381: ⚠️ Potential issue | 🟠 Major

call_result is serialized twice — redundant CopyFrom on Line 376-377.

The constructor at Line 362-364 already sets contractCallResult via the keyword argument. The CopyFrom at Line 376-377 overwrites it with the same value. Remove one of the two to avoid calling _to_proto() twice.

♻️ Proposed fix — remove redundant CopyFrom and move guard before constructor
+        # Defensive guard for protobuf oneof
+        if self.call_result is not None and self.contract_create_result is not None:
+            raise ValueError(
+                "call_result and contract_create_result are mutually exclusive "
+                "(protobuf oneof) — only one may be set at a time"
+            )
+
         record_proto = transaction_record_pb2.TransactionRecord(
             transactionHash=self.transaction_hash,
             memo=self.transaction_memo,
             transactionFee=self.transaction_fee,
             receipt=self.receipt._to_proto() if self.receipt else None,
             contractCallResult=(
                 self.call_result._to_proto() if self.call_result else None
             ),
             prng_number=self.prng_number,
             prng_bytes=self.prng_bytes,
         )
-        
-        # Defensive guard for protobuf oneof
-        if self.call_result is not None and self.contract_create_result is not None:
-            raise ValueError(
-                "call_result and contract_create_result are mutually exclusive "
-                "(protobuf oneof) — only one may be set at a time"
-            )
-
-        if self.call_result is not None:
-            record_proto.contractCallResult.CopyFrom(self.call_result._to_proto())

         if self.contract_create_result is not None:
             record_proto.contractCreateResult.CopyFrom(self.contract_create_result._to_proto())

Comment thread src/hiero_sdk_python/transaction/transaction_record.py
Comment thread tests/unit/transaction_record_test.py Outdated
@gangulysiddhartha22-cmyk gangulysiddhartha22-cmyk force-pushed the feature/add-missing-fields-to-transactionrecord branch from af88ea9 to 2107434 Compare February 11, 2026 17:27
Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
src/hiero_sdk_python/transaction/transaction_record.py (1)

357-377: ⚠️ Potential issue | 🟠 Major

call_result is serialized twice — once in the constructor (Line 362-364) and again via CopyFrom (Line 376-377).

The constructor already sets contractCallResult from self.call_result._to_proto(), then lines 376-377 overwrite it with an identical CopyFrom. This calls _to_proto() on the same object twice for no benefit. Additionally, the mutual exclusivity check at lines 370-374 runs after the constructor already assigned contractCallResult, which is logically out of order.

🐛 Proposed fix — remove the duplicate and reorder the guard
+        # Defensive guard for protobuf oneof
+        if self.call_result is not None and self.contract_create_result is not None:
+            raise ValueError(
+                "call_result and contract_create_result are mutually exclusive "
+                "(protobuf oneof) — only one may be set at a time"
+            )
+
         record_proto = transaction_record_pb2.TransactionRecord(
             transactionHash=self.transaction_hash,
             memo=self.transaction_memo,
             transactionFee=self.transaction_fee,
             receipt=self.receipt._to_proto() if self.receipt else None,
-            contractCallResult=(
-                self.call_result._to_proto() if self.call_result else None
-            ),
             prng_number=self.prng_number,
             prng_bytes=self.prng_bytes,
         )
-        
-        # Defensive guard for protobuf oneof
-        if self.call_result is not None and self.contract_create_result is not None:
-            raise ValueError(
-                "call_result and contract_create_result are mutually exclusive "
-                "(protobuf oneof) — only one may be set at a time"
-            )
 
         if self.call_result is not None:
             record_proto.contractCallResult.CopyFrom(self.call_result._to_proto())

@gangulysiddhartha22-cmyk gangulysiddhartha22-cmyk force-pushed the feature/add-missing-fields-to-transactionrecord branch from 2107434 to ed7e895 Compare February 11, 2026 17:32
Comment thread tests/unit/token_association_test.py
Comment thread tests/unit/transaction_record_test.py Outdated
Copy link
Copy Markdown
Member

@AntonioCeppellini AntonioCeppellini left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is looking great! I agree with Manish about the docstrings🚀👀

Comment thread src/hiero_sdk_python/transaction/transaction_record.py Outdated
Comment thread src/hiero_sdk_python/tokens/token_association.py Outdated
Comment thread src/hiero_sdk_python/transaction/transaction_record.py Outdated
Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
tests/unit/transaction_record_test.py (1)

81-98: 🧹 Nitpick | 🔵 Trivial

Consider adding hasattr checks for new fields in the default initialization test.

The existing test_transaction_record_default_initialization validates pre-existing fields but doesn't assert the presence of new fields. While test_transaction_record_default_new_fields covers default values, adding hasattr checks here would protect the public API surface against accidental removal, consistent with the pattern used for duplicates at line 95.

As per coding guidelines, "Assert public attributes exist (e.g., assert hasattr(obj, 'account_id'))."

♻️ Proposed addition after line 98
     assert record.duplicates == []
+    # New field existence checks
+    assert hasattr(record, 'consensus_timestamp'), "Should have consensus_timestamp"
+    assert hasattr(record, 'parent_consensus_timestamp'), "Should have parent_consensus_timestamp"
+    assert hasattr(record, 'schedule_ref'), "Should have schedule_ref"
+    assert hasattr(record, 'assessed_custom_fees'), "Should have assessed_custom_fees"
+    assert hasattr(record, 'automatic_token_associations'), "Should have automatic_token_associations"
+    assert hasattr(record, 'alias'), "Should have alias"
+    assert hasattr(record, 'ethereum_hash'), "Should have ethereum_hash"
+    assert hasattr(record, 'evm_address'), "Should have evm_address"
+    assert hasattr(record, 'paid_staking_rewards'), "Should have paid_staking_rewards"
+    assert hasattr(record, 'contract_create_result'), "Should have contract_create_result"

@gangulysiddhartha22-cmyk
Copy link
Copy Markdown
Contributor Author

@manishdait

  • Docstrings have now been added to all test functions

@AntonioCeppellini

  • Updated all repeated protobuf fields

@exploreriii

  • Removed all inline >>> examples from the TokenAssociation docstring and added a pointer to the new dedicated example file: examples/tokens/token_association.py
  • Updated TransactionRecord.__repr__ to show actual content previews

Ready for another look!

Comment thread src/hiero_sdk_python/tokens/token_association.py Outdated
Comment thread src/hiero_sdk_python/tokens/token_association.py
Comment thread examples/tokens/token_association.py Outdated
Comment thread examples/tokens/token_association.py Outdated
Comment thread examples/tokens/token_association.py Outdated
Comment thread examples/tokens/token_association.py Outdated
@exploreriii exploreriii marked this pull request as draft February 12, 2026 10:49
@gangulysiddhartha22-cmyk gangulysiddhartha22-cmyk marked this pull request as ready for review February 12, 2026 15:57
@gangulysiddhartha22-cmyk
Copy link
Copy Markdown
Contributor Author

@exploreriii,
I updated the TokenAssociation example and docs based on your feedback. Ready for another look!

@gangulysiddhartha22-cmyk gangulysiddhartha22-cmyk force-pushed the feature/add-missing-fields-to-transactionrecord branch from 563bb6b to c8274a4 Compare February 13, 2026 15:11
@gangulysiddhartha22-cmyk
Copy link
Copy Markdown
Contributor Author

Hi @exploreriii,

First of all, really sorry for the delayed reply.

In the latest commit I have addressed all these review comments:

  • Fixed PRNG oneof handling in _to_proto()
  • Updated repeated field loops to use separate add() + CopyFrom() style (stronger / clearer per proto3 guide)
  • Expanded the existing examples/query/transaction_record_query.py to show many of the new TransactionRecord fields (added calls to print_advanced_record_fields() after each basic print, renamed loop var to avoid shadowing, cleaned type hint)
  • Added minimal integration tests for new fields: automatic_token_associations, contract_create_result, and paid_staking_rewards

Ready for another look!

Comment thread src/hiero_sdk_python/tokens/token_association.py
Comment thread tests/integration/transaction_record_query_e2e_test.py Outdated
@exploreriii
Copy link
Copy Markdown
Contributor

Hi @gangulysiddhartha22-cmyk note the outstanidng merge conflicts please!

@exploreriii
Copy link
Copy Markdown
Contributor

great please do click the ready to review button when it is :)

@gangulysiddhartha22-cmyk
Copy link
Copy Markdown
Contributor Author

@coderabbitai review

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented Mar 15, 2026

✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

@gangulysiddhartha22-cmyk
Copy link
Copy Markdown
Contributor Author

@coderabbitai resume

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

♻️ Duplicate comments (3)
src/hiero_sdk_python/transaction/transaction_record.py (2)

357-367: ⚠️ Potential issue | 🟠 Major

Add an explicit oneof guard for contractCallResult/contractCreateResult.

Line 362 and Line 425 can both be driven by object state without a pre-check. These are proto oneof body branches (contractCallResult field 7, contractCreateResult field 8), so the current flow can silently override one branch during serialization.

🐛 Suggested fix
+        if self.call_result is not None and self.contract_create_result is not None:
+            raise ValueError(
+                "contract_call_result and contract_create_result are mutually exclusive"
+            )
+
         record_proto = transaction_record_pb2.TransactionRecord(
             transactionHash=self.transaction_hash,
             memo=self.transaction_memo,
             transactionFee=self.transaction_fee,
             receipt=self.receipt._to_proto() if self.receipt else None,
-            contractCallResult=(
-                self.call_result._to_proto() if self.call_result else None
-            ),
             prng_number=self.prng_number,
             prng_bytes=self.prng_bytes,
         )
+
+        if self.call_result is not None:
+            record_proto.contractCallResult.CopyFrom(self.call_result._to_proto())
@@
         if self.contract_create_result is not None:
             record_proto.contractCreateResult.CopyFrom(self.contract_create_result._to_proto())
#!/bin/bash
# Verify oneof branches and absence/presence of mutual-exclusion guard in serializer
rg -n -C3 'contractCallResult|contractCreateResult|mutually exclusive|oneof' src/hiero_sdk_python/transaction/transaction_record.py

As per coding guidelines, "Verify that _to_proto does NOT set more than one field from the same oneof block simultaneously. If it does, a ValueError guard MUST be present before setting those fields."

Also applies to: 424-425


21-22: 🛠️ Refactor suggestion | 🟠 Major

New annotations should use X | None instead of Optional[X].

The newly added typing in this file uses Optional[...] (e.g., Line 99-Line 108), which conflicts with the repository typing rule for modified SDK code.

#!/bin/bash
# Verify Optional usage in modified annotations
rg -n 'Optional\[(Timestamp|ScheduleId|bytes|ContractFunctionResult)\]' src/hiero_sdk_python/transaction/transaction_record.py

As per coding guidelines, "The codebase uses X | None union syntax (Python 3.10+). Flag any use of Optional[X] from typing in newly added or modified code, as it is inconsistent with the established style."

Also applies to: 99-108

tests/unit/transaction_record_test.py (1)

281-286: ⚠️ Potential issue | 🟡 Minor

Add explicit SDK type assertions for parsed new-field entries.

These tests validate values, but not concrete parsed types (AssessedCustomFee, TokenAssociation). Type assertions would better protect API-shape compatibility.

🧪 Suggested additions
     record = TransactionRecord._from_proto(proto, transaction_id)
     assert len(record.assessed_custom_fees) == 1
     f = record.assessed_custom_fees[0]
+    assert isinstance(f, AssessedCustomFee)
     assert f.amount == 500000000
     assert f.fee_collector_account_id.num == 98
@@
     record = TransactionRecord._from_proto(proto, transaction_id)
     assert len(record.automatic_token_associations) == 1
     a = record.automatic_token_associations[0]
+    assert isinstance(a, TokenAssociation)
     assert a.token_id.num == 5678
     assert a.account_id.num == 1234

As per coding guidelines, "Assert return types where relevant (e.g., assert isinstance(result, AccountId))."

Also applies to: 299-304


ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 4a2ef771-236c-413f-bdf4-309fb2ec910b

📥 Commits

Reviewing files that changed from the base of the PR and between ae68178 and 158609f.

📒 Files selected for processing (5)
  • examples/transaction/transaction_record.py
  • src/hiero_sdk_python/tokens/token_association.py
  • src/hiero_sdk_python/transaction/transaction_record.py
  • tests/unit/token_association_test.py
  • tests/unit/transaction_record_test.py

Comment thread examples/transaction/transaction_record.py Outdated
Comment thread src/hiero_sdk_python/tokens/token_association.py
@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented Mar 15, 2026

✅ Actions performed

Reviews resumed.

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
src/hiero_sdk_python/transaction/transaction_record.py (1)

357-372: ⚠️ Potential issue | 🟠 Major

Add entropy oneof guard to prevent simultaneous setting of prng_number and prng_bytes.

The entropy oneof (proto fields 19, 20) is not guarded in _to_proto(). Line 370-371 sets both fields directly in the constructor, violating protobuf oneof semantics. Add a guard before the constructor call and conditional field assignment afterward, mirroring the contractCallResult/contractCreateResult pattern (lines 357–361, 429–430).

In _from_proto() (lines 245-246), use proto.WhichOneof("entropy") to detect which branch is populated instead of assigning both fields unconditionally.

Suggested fix
         return cls(
+            entropy_case = proto.WhichOneof("entropy")
+
+            return cls(
@@
-            prng_number=proto.prng_number,
-            prng_bytes=proto.prng_bytes,
+            prng_number=proto.prng_number if entropy_case == "prng_number" else None,
+            prng_bytes=proto.prng_bytes if entropy_case == "prng_bytes" else None,
@@
         if self.call_result is not None and self.contract_create_result is not None:
             raise ValueError(
                 "contractCallResult and contractCreateResult are mutually exclusive "
                 "proto oneof fields and cannot both be set simultaneously."
             )
+        if self.prng_number is not None and self.prng_bytes is not None:
+            raise ValueError(
+                "prng_number and prng_bytes are mutually exclusive "
+                "proto oneof fields and cannot both be set simultaneously."
+            )
         record_proto = transaction_record_pb2.TransactionRecord(
@@
-            prng_number=self.prng_number,
-            prng_bytes=self.prng_bytes,
         )
+        if self.prng_number is not None:
+            record_proto.prng_number = self.prng_number
+        if self.prng_bytes is not None:
+            record_proto.prng_bytes = self.prng_bytes
♻️ Duplicate comments (1)
src/hiero_sdk_python/tokens/token_association.py (1)

2-3: ⚠️ Potential issue | 🟡 Minor

Use X | None syntax for newly added type hints.

Line 2 and Lines 23/26 use Optional[...] in new code; project style requires X | None for modified SDK annotations.

♻️ Suggested change
-from typing import Optional
@@
-    token_id: Optional[TokenId] = None
+    token_id: TokenId | None = None
@@
-    account_id: Optional[AccountId] = None
+    account_id: AccountId | None = None
#!/bin/bash
# Verify Optional usage in this newly added SDK file.
rg -n 'Optional\[' src/hiero_sdk_python/tokens/token_association.py

As per coding guidelines, src/hiero_sdk_python/**/*.py: “The codebase uses X | None union syntax (Python 3.10+). Flag any use of Optional[X] in newly added or modified code.”

Also applies to: 23-26


ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 65ddf81b-9c00-4f5b-bd0f-e3949afac415

📥 Commits

Reviewing files that changed from the base of the PR and between 158609f and 1e83864.

📒 Files selected for processing (6)
  • CHANGELOG.md
  • examples/transaction/transaction_record.py
  • src/hiero_sdk_python/tokens/token_association.py
  • src/hiero_sdk_python/transaction/transaction_record.py
  • tests/unit/token_association_test.py
  • tests/unit/transaction_record_test.py

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 4


ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 5c974bb1-dc89-4f3a-91be-6b0d87524f0d

📥 Commits

Reviewing files that changed from the base of the PR and between 1e83864 and d2da101.

📒 Files selected for processing (6)
  • CHANGELOG.md
  • examples/transaction/transaction_record.py
  • src/hiero_sdk_python/tokens/token_association.py
  • src/hiero_sdk_python/transaction/transaction_record.py
  • tests/unit/token_association_test.py
  • tests/unit/transaction_record_test.py

Comment thread examples/transaction/transaction_record.py Outdated
Comment thread src/hiero_sdk_python/transaction/transaction_record.py Outdated
Comment thread tests/unit/transaction_record_test.py Outdated
Comment thread tests/unit/transaction_record_test.py
Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

♻️ Duplicate comments (2)
src/hiero_sdk_python/tokens/token_association.py (1)

2-3: ⚠️ Potential issue | 🟡 Minor

Use X | None annotations in newly added SDK code.

This new class uses Optional[...] in changed lines, but the repository guideline for new/modified code expects X | None.

♻️ Proposed fix
-from typing import Optional
@@
-    token_id: Optional[TokenId] = None
+    token_id: TokenId | None = None
@@
-    account_id: Optional[AccountId] = None
+    account_id: AccountId | None = None

As per coding guidelines, "X | None union syntax (Python 3.10+) is required in newly added or modified code; flag Optional[X]."

Also applies to: 23-26

src/hiero_sdk_python/transaction/transaction_record.py (1)

99-108: ⚠️ Potential issue | 🟡 Minor

Update type annotations to use X | None style per codebase standards.

The newly added fields at lines 99–108 use Optional[...] instead of the established X | None union syntax required for new/modified code. Update all eight field annotations to follow the codebase pattern.

♻️ Proposed fix
-    consensus_timestamp: Optional[Timestamp] = None
-    schedule_ref: Optional[ScheduleId] = None
+    consensus_timestamp: Timestamp | None = None
+    schedule_ref: ScheduleId | None = None
@@
-    parent_consensus_timestamp: Optional[Timestamp] = None
-    alias: Optional[bytes] = None
-    ethereum_hash: Optional[bytes] = None
+    parent_consensus_timestamp: Timestamp | None = None
+    alias: bytes | None = None
+    ethereum_hash: bytes | None = None
@@
-    evm_address: Optional[bytes] = None
-    contract_create_result: Optional[ContractFunctionResult] = None
+    evm_address: bytes | None = None
+    contract_create_result: ContractFunctionResult | None = None

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro

Run ID: 3a11cd79-2882-42a8-9678-132e7886eb38

📥 Commits

Reviewing files that changed from the base of the PR and between d2da101 and 3c6814d.

📒 Files selected for processing (6)
  • CHANGELOG.md
  • examples/transaction/transaction_record.py
  • src/hiero_sdk_python/tokens/token_association.py
  • src/hiero_sdk_python/transaction/transaction_record.py
  • tests/unit/token_association_test.py
  • tests/unit/transaction_record_test.py

Comment thread tests/unit/transaction_record_test.py
Comment thread CHANGELOG.md Outdated
manishdait
manishdait previously approved these changes Mar 19, 2026
Copy link
Copy Markdown
Contributor

@manishdait manishdait left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

seems good to me, need seconds opinion @exploreriii, @AntonioCeppellini

@github-actions
Copy link
Copy Markdown

Hi, this is WorkflowBot.
Your pull request cannot be merged as it is not passing all our workflow checks.
Please click on each check to review the logs and resolve issues so all checks pass.
To help you:

@manishdait
Copy link
Copy Markdown
Contributor

I think, based on the failing tests, it would be better to keep prng_number and alias as None when they are not present rather than defaulting them to values like 0 or b"". This more accurately and follow the same semantic as other sdks.

@manishdait
Copy link
Copy Markdown
Contributor

But this might, break the backward compatiblity like to hear your thoughts @exploreriii

@gangulysiddhartha22-cmyk
Copy link
Copy Markdown
Contributor Author

@manishdait Please could you run the workflows again?

@gangulysiddhartha22-cmyk
Copy link
Copy Markdown
Contributor Author

gangulysiddhartha22-cmyk commented Mar 19, 2026

@manishdait ,just fixed the PRNG tests by matching real network behavior (prng_number vs prng_bytes None cases) + cleaned up alias config.
All 3 failing tests are green now . Review required , @exploreriii

Copy link
Copy Markdown
Member

@AntonioCeppellini AntonioCeppellini left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@gangulysiddhartha22-cmyk @manishdait seems good to me, nice job :D

exploreriii
exploreriii previously approved these changes Mar 19, 2026
@exploreriii
Copy link
Copy Markdown
Contributor

@gangulysiddhartha22-cmyk could you add eg changelog addition being explicit on your changes to e.g. prng_number, prng_bytes, and alias returning None and this is good to go

Comment thread src/hiero_sdk_python/tokens/token_association.py
…h example

Signed-off-by: Siddhartha Ganguly <gangulysiddhartha22@gmail.com>
Signed-off-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
Signed-off-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
Signed-off-by: Siddhartha Ganguly <gangulysiddhartha22@gmail.com>
.
Signed-off-by: Siddhartha Ganguly <gangulysiddhartha22@gmail.com>
@manishdait
Copy link
Copy Markdown
Contributor

@gangulysiddhartha22-cmyk Thank you for the extensive effort you've put into this PR over the last few weeks. We recognize the importance of exposing these missing TransactionRecord fields.

However after 140 plus comments multiple pushes, and shifting logic and inconsistencies, this PR has become too fragmented to maintain or review effectively. The current state contains several inconsistencies

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

reviewer: maintainer PR needs a review from the maintainer team

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Add missing fields to TransactionRecord class

7 participants