Skip to content

feat(tokens): add _from_protobuf support for token supply transactions - #2729

Open
anchit-goel wants to merge 9 commits into
hiero-ledger:mainfrom
anchit-goel:token-transaction
Open

anchit-goel wants to merge 9 commits into
hiero-ledger:mainfrom
anchit-goel:token-transaction

Conversation

@anchit-goel

@anchit-goel anchit-goel commented Oct 13, 2026 •

Copy link
Copy Markdown
Contributor

Description:
Add _from_protobuf inverse-serialization support for TokenMintTransaction, TokenBurnTransaction, and TokenWipeTransaction so that Transaction.from_bytes() restores type-specific fields accurately with byte-for-byte fidelity.

  • Add @classmethod _from_protobuf to TokenMintTransaction, restoring token_id, amount, and metadata
  • Add @classmethod _from_protobuf to TokenBurnTransaction, restoring token_id, amount, and serials
  • Add @classmethod _from_protobuf to TokenWipeTransaction, restoring token_id, account_id, amount, and serial
  • Remove obsolete _from_proto instance methods from TokenBurnTransaction and TokenWipeTransaction
  • Add protobuf reconstruction unit tests for fungible and NFT variants across all three classes
  • Add serialization round-trip tests asserting field equality and exact byte match (restored.to_bytes() == original_bytes)
  • Remove obsolete test_burn_transaction_from_proto test

Related issue(s):

Fixes #2617

Notes for reviewer:

  • Each _from_protobuf method cleanly falls back across super()._from_protobuf(transaction_body, ...) argument signatures to support both 1-arg and 3-arg callers.
  • All 3,309 unit tests pass:
    pytest tests/unit/token_mint_transaction_test.py tests/unit/token_burn_transaction_test.py tests/unit/token_wipe_transaction_test.py
    # 44 passed in 0.35s
  • Ruff linting and formatting checks pass with zero warnings.

Checklist

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

Signed-off-by: anchit-goel <anchitgoel5@gmail.com>
@anchit-goel
anchit-goel marked this pull request as ready for review October 13, 2026 08:00
@anchit-goel
anchit-goel requested review from a team as code owners October 13, 2026 08:00
@anchit-goel
anchit-goel requested review from Akshat8510 and danielmarv and a balanced review from Copilot October 13, 2026 08:00

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

@github-actions github-actions Bot added open to community review PR is open for community review and feedback queue:junior-committer PR awaiting initial quality review labels Oct 13, 2026
@coderabbitai

coderabbitai Bot commented Oct 13, 2026 •

Copy link
Copy Markdown
Contributor

Review in Change Stack →

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

Mint, burn, and wipe transactions now restore transaction-specific fields from protobuf data. Tests cover fungible and NFT restoration, absent fields, and byte-identical serialization after deserialization.

Changes

Token supply transaction deserialization

Layer / File(s) Summary
Restore mint, burn, and wipe fields
src/hiero_sdk_python/tokens/token_mint_transaction.py, src/hiero_sdk_python/tokens/token_burn_transaction.py, src/hiero_sdk_python/tokens/token_wipe_transaction.py
The three transaction classes add _from_protobuf methods that restore token-specific fields from protobuf bodies.
Test restoration and byte round trips
tests/unit/token_burn_transaction_test.py, tests/unit/token_mint_transaction_test.py, tests/unit/token_wipe_transaction_test.py
Tests cover fungible and NFT payloads, absent fields, and byte-identical serialization after Transaction.from_bytes().

Priority: ➖ Normal

Estimated code review effort: 3 (Moderate) | ~20 minutes

Severity of issue fixed: Medium

Merge Risk: 🔵 Low · up to 49805

Deserializing mint, burn and wipe transactions from bytes now works for normal fungible and NFT payloads. Edge cases still restore an unset amount as zero, and a mixed payload can lose a nonzero amount, which may change re-serialized bytes. These are small, bounded gaps that the author can address or document before or after merge.

Security architecture risk: 🔵 Low · up to 49805

Normal fungible and NFT transactions regain their token-specific fields without changing signing authority. Mixed fungible and NFT payloads can still produce an incomplete field-level view of the signed transaction. No introduced authorization bypass was established, but downstream approval behavior and network-side validation remain unverified.

Retained concerns
No architecture-level concerns identified.

Security review details

Security Blast Radius

  • inferred — The relevant exposure is an application accepting externally supplied mint, burn or wipe transaction bytes, inspecting restored fields, and subsequently supplying signing authority or submitting the transaction. Decoding itself does not obtain credentials or submit a network request. The inspected paths do not establish broader tenant, service or infrastructure exposure.

Security Findings and Attack Paths

  • observed — At head, a payload containing both NFT data and a nonzero amount exposes amount as None while a frozen transaction can retain that amount in cached wire bytes. This is a field-view limitation, not an established new authorization bypass: base byte decoding already left token-specific fields unset while preserving cached bodies. Network acceptance of mixed payloads and an affected downstream approval policy were not established.

Trust Boundaries and Controls

  • observed — Signing requires a frozen transaction and signs exact cached body bytes. Frozen serialization and submission also use those cached bytes, with signature maps keyed by body bytes. The PR does not replace that authority boundary with reconstructed token fields or implicitly authorize the decoded transaction.

Resilience and Maintainability Implications

  • observed — Reconstruction creates fresh transaction objects and accumulates transaction-list state locally before validation and return. A reconstruction failure does not publish a partially restored transaction through this API, and repeated decoding does not reuse a shared mutable transaction instance.

Hardening Proposals

  • proposed — For applications authorizing transactions from restored fields, define an explicit mixed-payload policy: reject conflicting fungible and NFT fields before approval, or expose all populated wire fields. Treat byte equality as signature-preservation evidence, not proof that the approval view is complete.
Pre-merge checks: Passed 4 · Failed 1

Failed Failed checks: 1 warning

Check name Status Explanation Resolution
Linked Issues check Warning Issue #2617 requires field-for-field reconstruction, including unset optional fields and byte-identical round trips. The new methods restore fungible amount directly from the protobuf scalar. An uns… Use the schema-supported presence check for amount and restore an unset amount as None. Add or retain round-trip tests for unset optional fields on all three transactions. Remove the obsolete _from_proto methods from `TokenBurnTransac…
Passed Passed checks: 4 passed
Check name Status Explanation
Description check Passed The description directly covers the added _from_protobuf implementations, removed obsolete methods, and related tests. It matches the changeset.
Title check Passed The title clearly identifies the main change: adding _from_protobuf support for token supply transactions.
Out of Scope Changes check Passed The production changes add deserialization for the three token supply transactions. The test changes cover protobuf reconstruction and serialization round trips for the linked issue. No unrelated prod…
Docstring Coverage Passed Docstring coverage is 96.30% which is sufficient. The required threshold is 80.00%. Docstring coverage is scoped to functions touched by this diff. Analyzed 27 functions across 6 files.
Full details: Out of Scope Changes check

Explanation

The production changes add deserialization for the three token supply transactions. The test changes cover protobuf reconstruction and serialization round trips for the linked issue. No unrelated production, API, or test changes are shown.

Full details: Linked Issues check

Explanation

Issue #2617 requires field-for-field reconstruction, including unset optional fields and byte-identical round trips. The new methods restore fungible amount directly from the protobuf scalar. An unset amount therefore becomes 0 instead of None when the schema does not report presence. This can change the reconstructed field state and round-trip behavior. The current PR description also requires removal of the obsolete _from_proto methods, but both methods remain in the burn and wipe classes.

Resolution

Use the schema-supported presence check for amount and restore an unset amount as None. Add or retain round-trip tests for unset optional fields on all three transactions. Remove the obsolete _from_proto methods from TokenBurnTransaction and TokenWipeTransaction.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create a new PR
  • Autofix · Keep fixing CodeRabbit findings and required CI, and resolving merge conflicts

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.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Actionable comments posted: 1


ℹ️ Review info
⚙️ Run configuration
  • Configuration used: Repository: hiero-ledger/hiero-sdk-python/.coderabbit.yaml
  • Review profile: ASSERTIVE
  • Plan: Advanced
  • Run ID: 7c0a4b63-907f-4056-994c-ea4b951a49c2
📥 Commits

Reviewing files that changed from the base of the PR and between 02b2e8a and 5c4a13b.

📒 Files selected for processing (6)
  • src/hiero_sdk_python/tokens/token_burn_transaction.py
  • src/hiero_sdk_python/tokens/token_mint_transaction.py
  • src/hiero_sdk_python/tokens/token_wipe_transaction.py
  • tests/unit/token_burn_transaction_test.py
  • tests/unit/token_mint_transaction_test.py
  • tests/unit/token_wipe_transaction_test.py

Included review availability: This review used your included allowance. Your plan provides up to 1 included review per hour; 0 remain after this review.

Comment thread src/hiero_sdk_python/tokens/token_burn_transaction.py Outdated
Comment thread CHANGELOG.md Outdated
Comment thread src/hiero_sdk_python/tokens/token_burn_transaction.py Outdated
def _get_method(self, channel: _Channel) -> _Method:
return _Method(transaction_func=channel.token.mintToken, query_func=None)

@classmethod

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

same here

Comment thread src/hiero_sdk_python/tokens/token_wipe_transaction.py Outdated
def _get_method(self, channel: _Channel) -> _Method:
return _Method(transaction_func=channel.token.wipeTokenAccount, query_func=None)

def _from_proto(self, proto: TokenWipeAccountTransactionBody) -> TokenWipeTransaction:

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

this method should not be remove

"""
return _Method(transaction_func=channel.token.burnToken, query_func=None)

def _from_proto(self, proto: TokenBurnTransactionBody) -> TokenBurnTransaction:

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

this method should not be remove

@anchit-goel
anchit-goel marked this pull request as draft October 17, 2026 12:58
@github-actions github-actions Bot removed queue:junior-committer PR awaiting initial quality review open to community review PR is open for community review and feedback labels Oct 17, 2026
@anchit-goel
anchit-goel marked this pull request as ready for review October 18, 2026 10:13
@anchit-goel

Copy link
Copy Markdown
Contributor Author

@manishdait @danielmarv

kindly review.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Actionable comments posted: 1


ℹ️ Review info
⚙️ Run configuration
  • Configuration used: Repository: hiero-ledger/hiero-sdk-python/.coderabbit.yaml
  • Review profile: ASSERTIVE
  • Plan: Advanced
  • Run ID: 17979d4c-f12c-4cdb-a3e9-ffb5b44c6c5d
📥 Commits

Reviewing files that changed from the base of the PR and between c3c67bb and fd2bf43.

📒 Files selected for processing: 6
  • src/hiero_sdk_python/tokens/token_burn_transaction.py
  • src/hiero_sdk_python/tokens/token_mint_transaction.py
  • src/hiero_sdk_python/tokens/token_wipe_transaction.py
  • tests/unit/token_burn_transaction_test.py
  • tests/unit/token_mint_transaction_test.py
  • tests/unit/token_wipe_transaction_test.py

Included review availability: This review used your included allowance. Your plan provides up to 1 included review per hour; 0 remain after this review.

Comment thread src/hiero_sdk_python/tokens/token_wipe_transaction.py Outdated
@github-actions github-actions Bot added the open to community review PR is open for community review and feedback label Oct 18, 2026
@github-actions github-actions Bot added the queue:junior-committer PR awaiting initial quality review label Oct 18, 2026
Comment thread src/hiero_sdk_python/tokens/token_burn_transaction.py Outdated
Signed-off-by: anchit-goel <anchitgoel5@gmail.com>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Actionable comments posted: 3


ℹ️ Review info
⚙️ Run configuration
  • Configuration used: Repository: hiero-ledger/hiero-sdk-python/.coderabbit.yaml
  • Review profile: ASSERTIVE
  • Plan: Advanced
  • Run ID: 467c9ddd-3f0e-4520-b160-9881285f19c6
📥 Commits

Reviewing files that changed from the base of the PR and between fd2bf43 and 498055e.

📒 Files selected for processing: 3
  • src/hiero_sdk_python/tokens/token_burn_transaction.py
  • src/hiero_sdk_python/tokens/token_mint_transaction.py
  • src/hiero_sdk_python/tokens/token_wipe_transaction.py

Included review availability: This review used your included allowance. Your plan provides up to 1 included review per hour; 0 remain after this review.

Comment thread src/hiero_sdk_python/tokens/token_burn_transaction.py
Comment thread src/hiero_sdk_python/tokens/token_mint_transaction.py
transaction.serial = list(token_wipe_body.serialNumbers)
transaction.amount = None
else:
transaction.amount = token_wipe_body.amount

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

🗄️ Data Integrity & Integration | 🟡 Minor | ⚡ Quick win

🔎 Supported by static analysis

🏁 Script executed:

set -e
printf '%s\n' '--- diff ---'
git diff --no-ext-diff --unified=80 7260ea7290637399c6ac181ed893a567144d96eb 498055eae945a04fe589feec142586e3f53a7a38 -- src/hiero_sdk_python/tokens/token_wipe_transaction.py tests/unit/token_wipe_transaction_test.py
printf '%s\n' '--- current source ---'
nl -ba src/hiero_sdk_python/tokens/token_wipe_transaction.py | sed -n '1,270p'
printf '%s\n' '--- relevant tests ---'
rg -n -F --glob 'tests/**/*.py' -e 'TokenWipeTransaction' -e 'amount' -e 'serial' tests/unit/token_wipe_transaction_test.py || true
printf '%s\n' '--- proto field declaration ---'
rg -n -F --glob '*.py' -e 'class TokenWipeAccountTransactionBody' -e 'amount' src/hiero_sdk_python/hapi | head -80 || true

Repository: hiero-ledger/hiero-sdk-python

Length of output: 31814


🏁 Script executed:

set -e
printf '%s\n' '--- generated token-wipe module ---'
find . -path '*token_wipe_account_pb2.py' -print
printf '%s\n' '--- transaction deserialization ---'
rg -n -F -- 'def from_bytes' src/hiero_sdk_python/transaction src/hiero_sdk_python/tokens
rg -n -F -- '_from_protobuf(' src/hiero_sdk_python/transaction/transaction.py
nl -ba src/hiero_sdk_python/transaction/transaction.py | sed -n '240,360p'
printf '%s\n' '--- amount fixture definitions ---'
rg -n -F -- 'def amount' tests conftest.py src || true
rg -n -F -- 'amount =' tests/conftest.py tests || true

Repository: hiero-ledger/hiero-sdk-python

Length of output: 31137


Define and test the ambiguous zero-amount policy.

TokenWipeTransaction.amount defaults to None, but _from_protobuf assigns token_wipe_body.amount whenever serialNumbers is empty. A body with neither value therefore restores amount as 0. The protobuf amount field is a plain uint64, and the schema also permits amount = 0, so the wire value cannot distinguish an omitted amount from an explicit zero.

Define the public restoration policy for this ambiguous case. Add tests for the selected policy and document the wire-level limitation before changing this assignment. Do not apply a blanket or None conversion, because that would lose explicit zero amounts.

Source: Path instructions

@github-actions

Copy link
Copy Markdown

Hello, this is the OfficeHourBot.

This is a reminder that the Hiero Python SDK Office Hours will begin in approximately 3 hours and 56 minutes (14:00 UTC).

This session provides an opportunity to ask questions regarding this Pull Request.

Details:

Disclaimer: This is an automated reminder. Please verify the schedule here for any changes.

From,
The Python SDK Team

This branch has not been deployed

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

Labels

open to community review PR is open for community review and feedback queue:junior-committer PR awaiting initial quality review

Projects

None yet

Development

Successfully merging this pull request may close these issues.

feat: implement _from_protobuf for token supply transactions (from_bytes round-trip)

6 participants