Skip to content

Commit 02a09e1

Browse files
authored
feat(account): add __str__ and __repr__ to AccountInfo (#1129)
Signed-off-by: Akshat Kumar <[email protected]> Signed-off-by: Akshat8510 <[email protected]>
1 parent e73693c commit 02a09e1

File tree

4 files changed

+74
-9
lines changed

4 files changed

+74
-9
lines changed

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ This changelog is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.
99

1010

1111
### Added
12+
- Added `__str__` and `__repr__` methods to `AccountInfo` class for improved logging and debugging experience (#1098)
1213
- Added Good First Issue (GFI) management and frequency documentation to clarify maintainer expectations and SDK-level GFI governance.
1314
- Added SDK-level Good First Issue (GFI) guidelines for maintainers to clarify what qualifies as a good first issue.
1415
- Codecov workflow

examples/account/account_info.py

Lines changed: 3 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -53,19 +53,13 @@ def build_mock_account_info() -> AccountInfo:
5353

5454
def print_account_info(info: AccountInfo) -> None:
5555
"""Pretty-print key AccountInfo fields."""
56-
print("📜 AccountInfo Example (Mock Data)")
57-
print(f"Account ID: {info.account_id}")
58-
print(f"Key: {info.key}")
59-
print(f"Balance: {info.balance}")
60-
print(f"Expiration Time: {info.expiration_time}")
61-
print(f"Auto Renew Period: {info.auto_renew_period}")
62-
print(f"Token Relationships: {info.token_relationships}")
63-
print(f"Memo: {info.account_memo}")
56+
print("📜 AccountInfo String Representation:")
57+
print(info)
6458

6559
def main():
6660
"""Run the AccountInfo example."""
6761
info = build_mock_account_info()
6862
print_account_info(info)
6963

7064
if __name__ == "__main__":
71-
main()
65+
main()

src/hiero_sdk_python/account/account_info.py

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -153,3 +153,56 @@ def _to_proto(self) -> CryptoGetInfoResponse.AccountInfo:
153153
decline_reward=self.decline_staking_reward
154154
),
155155
)
156+
157+
def __str__(self) -> str:
158+
"""Returns a user-friendly string representation of the AccountInfo."""
159+
# Define simple fields to print if they exist
160+
# Format: (value_to_check, label)
161+
simple_fields = [
162+
(self.account_id, "Account ID"),
163+
(self.contract_account_id, "Contract Account ID"),
164+
(self.balance, "Balance"),
165+
(self.key, "Key"),
166+
(self.account_memo, "Memo"),
167+
(self.owned_nfts, "Owned NFTs"),
168+
(self.max_automatic_token_associations, "Max Automatic Token Associations"),
169+
(self.staked_account_id, "Staked Account ID"),
170+
(self.staked_node_id, "Staked Node ID"),
171+
(self.proxy_received, "Proxy Received"),
172+
(self.expiration_time, "Expiration Time"),
173+
(self.auto_renew_period, "Auto Renew Period"),
174+
]
175+
176+
# Use a list comprehension to process simple fields (reduces complexity score)
177+
lines = [f"{label}: {val}" for val, label in simple_fields if val is not None]
178+
179+
# 2. Handle booleans and special cases explicitly
180+
if self.is_deleted is not None:
181+
lines.append(f"Deleted: {self.is_deleted}")
182+
183+
if self.receiver_signature_required is not None:
184+
lines.append(f"Receiver Signature Required: {self.receiver_signature_required}")
185+
186+
if self.decline_staking_reward is not None:
187+
lines.append(f"Decline Staking Reward: {self.decline_staking_reward}")
188+
189+
if self.token_relationships:
190+
lines.append(f"Token Relationships: {len(self.token_relationships)}")
191+
192+
return "\n".join(lines)
193+
194+
def __repr__(self) -> str:
195+
"""Returns a string representation of the AccountInfo object for debugging."""
196+
return (
197+
f"AccountInfo("
198+
f"account_id={self.account_id!r}, "
199+
f"contract_account_id={self.contract_account_id!r}, "
200+
f"is_deleted={self.is_deleted!r}, "
201+
f"balance={self.balance!r}, "
202+
f"receiver_signature_required={self.receiver_signature_required!r}, "
203+
f"owned_nfts={self.owned_nfts!r}, "
204+
f"account_memo={self.account_memo!r}, "
205+
f"staked_node_id={self.staked_node_id!r}, "
206+
f"staked_account_id={self.staked_account_id!r}"
207+
f")"
208+
)

tests/unit/account_info_test.py

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -169,3 +169,20 @@ def test_proto_conversion(account_info):
169169
assert converted_account_info.token_relationships == account_info.token_relationships
170170
assert converted_account_info.account_memo == account_info.account_memo
171171
assert converted_account_info.owned_nfts == account_info.owned_nfts
172+
173+
def test_str_and_repr(account_info):
174+
"""Test the __str__ and __repr__ methods"""
175+
info_str = str(account_info)
176+
info_repr = repr(account_info)
177+
178+
# __str__ checks (User-friendly output)
179+
assert "Account ID: 0.0.100" in info_str
180+
assert "Contract Account ID: 0.0.100" in info_str
181+
assert "Balance: 0.05000000 ℏ" in info_str
182+
assert "Memo: Test account memo" in info_str
183+
184+
# __repr__ checks (Debug output)
185+
assert info_repr.startswith("AccountInfo(")
186+
assert "account_id=AccountId(shard=0, realm=0, num=100" in info_repr
187+
assert "contract_account_id='0.0.100'" in info_repr
188+
assert "account_memo='Test account memo'" in info_repr

0 commit comments

Comments
 (0)