From a749d83d40bc5b1911e3ace351114e4d0a944f87 Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 17:40:30 -0800 Subject: [PATCH 01/27] add new chain data classes --- bittensor/core/chain_data/chain_identity.py | 15 +++ bittensor/core/chain_data/metagrapg_info.py | 141 ++++++++++++++++++++ 2 files changed, 156 insertions(+) create mode 100644 bittensor/core/chain_data/chain_identity.py create mode 100644 bittensor/core/chain_data/metagrapg_info.py diff --git a/bittensor/core/chain_data/chain_identity.py b/bittensor/core/chain_data/chain_identity.py new file mode 100644 index 0000000000..f39daf0c87 --- /dev/null +++ b/bittensor/core/chain_data/chain_identity.py @@ -0,0 +1,15 @@ +from dataclasses import dataclass + + +@dataclass +class ChainIdentity: + """Dataclass for chain identity information.""" + + # In `bittensor.core.chain_data.utils.custom_rpc_type_registry` represents as `ChainIdentityOf` structure. + + name: str + url: str + image: str + discord: str + description: str + additional: list[str, int] diff --git a/bittensor/core/chain_data/metagrapg_info.py b/bittensor/core/chain_data/metagrapg_info.py new file mode 100644 index 0000000000..3e74d9b280 --- /dev/null +++ b/bittensor/core/chain_data/metagrapg_info.py @@ -0,0 +1,141 @@ +from dataclasses import dataclass +from typing import Optional + +from bittensor.core.chain_data.axon_info import AxonInfo +from bittensor.core.chain_data.chain_identity import ChainIdentity +from bittensor.core.chain_data.subnet_identity import SubnetIdentity +from bittensor.core.chain_data.utils import ( + ChainDataType, + from_scale_encoding, +) + + +@dataclass +class MetagraphInfo: + # Subnet index + netuid: int + + # Name and symbol + name: str + symbol: str + identity: Optional["SubnetIdentity"] + network_registered_at: int + + # Keys for owner. + owner_hotkey: str # hotkey + owner_coldkey: str # coldkey + + # Tempo terms. + block: int # block at call. + tempo: int # epoch tempo + last_step: int + blocks_since_last_step: int + + # Subnet emission terms + subnet_emission: int + alpha_in: int + alpha_out: int + tao_in: int # amount of tao injected per block + alpha_out_emission: int # amount injected in alpha reserves per block + alpha_in_emission: int # amount injected outstanding per block + tao_in_emission: int # amount of tao injected per block + pending_alpha_emission: int # pending alpha to be distributed + pending_root_emission: int # pending tao for root divs to be distributed + + # Hparams for epoch + rho: int # subnet rho param + kappa: int # subnet kappa param + + # Validator params + min_allowed_weights: int # min allowed weights per val + max_weights_limit: int # max allowed weights per val + weights_version: int # allowed weights version + weights_rate_limit: int # rate limit on weights. + activity_cutoff: int # validator weights cut off period in blocks + max_validators: int # max allowed validators. + + # Registration + num_uids: int + max_uids: int + burn: int # current burn cost. + difficulty: int # current difficulty. + registration_allowed: bool # allows registrations. + immunity_period: int # subnet miner immunity period + min_difficulty: int # min pow difficulty + max_difficulty: int # max pow difficulty + min_burn: int # min tao burn + max_burn: int # max tao burn + adjustment_alpha: int # adjustment speed for registration params. + adjustment_interval: int # pow and burn adjustment interval + target_regs_per_interval: int # target registrations per interval + max_regs_per_block: int # max registrations per block. + serving_rate_limit: int # axon serving rate limit + + # CR + commit_reveal_weights_enabled: bool # Is CR enabled. + commit_reveal_period: int # Commit reveal interval + + # Bonds + liquid_alpha_enabled: bool # Bonds liquid enabled. + alpha_high: int # Alpha param high + alpha_low: int # Alpha param low + bonds_moving_avg: int # Bonds moving avg + + # Metagraph info. + hotkeys: list[str] # hotkey per UID + coldkeys: list[str] # coldkey per UID + identities: list["ChainIdentity"] # coldkeys identities + axons: list["AxonInfo"] # UID axons. + active: list[bool] # Active per UID + validator_permit: list[bool] # Val permit per UID + pruning_score: list[int] # Pruning per UID + last_update: list[int] # Last update per UID + emission: list[int] # Emission per UID + dividends: list[int] # Dividends per UID + incentives: list[int] # Mining incentives per UID + consensus: list[int] # Consensus per UID + trust: list[int] # Trust per UID + rank: list[int] # Rank per UID + block_at_registration: list[int] # Reg block per UID + alpha_stake: list[int] # Alpha staked per UID + tao_stake: list[int] # TAO staked per UID + total_stake: list[int] # Total stake per UID + + # Dividend break down. + tao_dividends_per_hotkey: list[ + tuple[str, int] + ] # List of dividend payouts in tao via root. + alpha_dividends_per_hotkey: list[ + tuple[str, int] + ] # List of dividend payout in alpha via subnet. + + @classmethod + def from_vec_u8(cls, vec_u8: bytes) -> Optional["MetagraphInfo"]: + """Returns a Metagraph object from a encoded MetagraphInfo vector.""" + if len(vec_u8) == 0: + return None + decoded = from_scale_encoding(vec_u8, ChainDataType.MetagraphInfo) + if decoded is None: + return None + + return MetagraphInfo.fix_decoded_values(decoded) + + @classmethod + def list_from_vec_u8(cls, vec_u8: bytes) -> list["MetagraphInfo"]: + """Returns a list of Metagraph objects from a list of encoded MetagraphInfo vectors.""" + decoded = from_scale_encoding( + vec_u8, ChainDataType.MetagraphInfo, is_vec=True, is_option=True + ) + if decoded is None: + return [] + decoded = [MetagraphInfo.fix_decoded_values(d) for d in decoded] + return decoded + + @classmethod + def fix_decoded_values(cls, decoded: dict) -> "MetagraphInfo": + """Returns a Metagraph object from a decoded MetagraphInfo dictionary.""" + decoded.update({"identity": decoded.get("identity", {})}) + decoded.update({"identities": decoded.get("identities", {})}) + decoded.update({"axons": decoded.get("axons", {})}) + + return MetagraphInfo(**decoded) From cd2ee1ad82b8e3e848a563c053e6b53474b13f60 Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 17:41:26 -0800 Subject: [PATCH 02/27] update import --- bittensor/core/chain_data/__init__.py | 1 + 1 file changed, 1 insertion(+) diff --git a/bittensor/core/chain_data/__init__.py b/bittensor/core/chain_data/__init__.py index 8e697b2498..c3338c3ac4 100644 --- a/bittensor/core/chain_data/__init__.py +++ b/bittensor/core/chain_data/__init__.py @@ -9,6 +9,7 @@ from .delegate_info import DelegateInfo from .delegate_info_lite import DelegateInfoLite from .ip_info import IPInfo +from .metagrapg_info import MetagraphInfo from .neuron_info import NeuronInfo from .neuron_info_lite import NeuronInfoLite from .neuron_certificate import NeuronCertificate From 7d4080a5483c32f4bbcd7ff17686f78c6839a891 Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 17:41:45 -0800 Subject: [PATCH 03/27] update TYPE_REGISTRY --- bittensor/core/settings.py | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/bittensor/core/settings.py b/bittensor/core/settings.py index b2ac91848a..e21d60311a 100644 --- a/bittensor/core/settings.py +++ b/bittensor/core/settings.py @@ -245,6 +245,14 @@ "params": [{"name": "netuid", "type": "u16"}], "type": "Vec", }, + "get_metagraph": { + "params": [{"name": "netuid", "type": "u16"}], + "type": "Vec", + }, + "get_all_metagraphs": { + "params": [], + "type": "Vec", + }, } }, "SubnetRegistrationRuntimeApi": { From e855bffa6b924ab133efc10e5a2ce72e47e73b1e Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 17:42:08 -0800 Subject: [PATCH 04/27] update custom_rpc_type_registry and ChainDataType --- bittensor/core/chain_data/utils.py | 101 +++++++++++++++++++++++++++++ 1 file changed, 101 insertions(+) diff --git a/bittensor/core/chain_data/utils.py b/bittensor/core/chain_data/utils.py index 96a7592b9d..d15d74fb22 100644 --- a/bittensor/core/chain_data/utils.py +++ b/bittensor/core/chain_data/utils.py @@ -26,6 +26,9 @@ class ChainDataType(Enum): SubnetState = 12 DynamicInfo = 13 SubnetIdentity = 14 + MetagraphInfo = 15 + ChainIdentity = 16 + AxonInfo = 17 def from_scale_encoding( @@ -326,6 +329,104 @@ def from_scale_encoding_using_type_string( ["subnet_identity", "Option"], ], }, + "MetagraphInfo": { + "type": "struct", + "type_mapping": [ + ["netuid", "Compact"], + ["name", "Vec>"], + ["symbol", "Vec>"], + ["identity", "Option"], + ["network_registered_at", "Compact"], + ["owner_hotkey", "T::AccountId"], + ["owner_coldkey", "T::AccountId"], + ["block", "Compact"], + ["tempo", "Compact"], + ["last_step", "Compact"], + ["blocks_since_last_step", "Compact"], + ["subnet_emission", "Compact"], + ["alpha_in", "Compact"], + ["alpha_out", "Compact"], + ["tao_in", "Compact"], + ["alpha_out_emission", "Compact"], + ["alpha_in_emission", "Compact"], + ["tao_in_emission", "Compact"], + ["pending_alpha_emission", "Compact"], + ["pending_root_emission", "Compact"], + ["rho", "Compact"], + ["kappa", "Compact"], + ["min_allowed_weights", "Compact"], + ["max_weights_limit", "Compact"], + ["weights_version", "Compact"], + ["weights_rate_limit", "Compact"], + ["activity_cutoff", "Compact"], + ["max_validators", "Compact"], + ["num_uids", "Compact"], + ["max_uids", "Compact"], + ["burn", "Compact"], + ["difficulty", "Compact"], + ["registration_allowed", "bool"], + ["immunity_period", "Compact"], + ["min_difficulty", "Compact"], + ["max_difficulty", "Compact"], + ["min_burn", "Compact"], + ["max_burn", "Compact"], + ["adjustment_alpha", "Compact"], + ["adjustment_interval", "Compact"], + ["target_regs_per_interval", "Compact"], + ["max_regs_per_block", "Compact"], + ["serving_rate_limit", "Compact"], + ["commit_reveal_weights_enabled", "bool"], + ["commit_reveal_period", "Compact"], + ["liquid_alpha_enabled", "bool"], + ["alpha_high", "Compact"], + ["alpha_low", "Compact"], + ["bonds_moving_avg", "Compact"], + ["hotkeys", "Vec"], + ["coldkeys", "Vec"], + ["identities", "Vec"], + ["axons", "Vec"], + ["active", "Vec"], + ["validator_permit", "Vec"], + ["pruning_score", "Vec>"], + ["last_update", "Vec>"], + ["emission", "Vec>"], + ["dividends", "Vec>"], + ["incentives", "Vec>"], + ["consensus", "Vec>"], + ["trust", "Vec>"], + ["rank", "Vec>"], + ["block_at_registration", "Vec>"], + ["alpha_stake", "Vec>"], + ["tao_stake", "Vec>"], + ["total_stake", "Vec>"], + ["tao_dividends_per_hotkey", "Vec<(T::AccountId, Compact)>"], + ["alpha_dividends_per_hotkey", "Vec<(T::AccountId, Compact)>"], + ], + }, + "ChainIdentityOf": { + "type": "struct", + "type_mapping": [ + ["name", "Vec"], + ["url", "Vec"], + ["url", "Vec"], + ["discord", "Vec"], + ["description", "Vec"], + ["additional", "Vec"], + ], + }, + "AxonInfo": { + "type": "struct", + "type_mapping": [ + ["block", "u64"], + ["version", "u32"], + ["ip", "u128"], + ["port", "u16"], + ["ip_type", "u8"], + ["protocol", "u8"], + ["placeholder1", "u8"], + ["placeholder2", "u8"], + ], + }, } } From 093371e9658241268697e4e0886f65b9567396ec Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 17:42:26 -0800 Subject: [PATCH 05/27] add new sync methods --- bittensor/core/subtensor.py | 32 ++++++++++++++++++++++++++++++++ 1 file changed, 32 insertions(+) diff --git a/bittensor/core/subtensor.py b/bittensor/core/subtensor.py index d95fc9225c..7c9e91120d 100644 --- a/bittensor/core/subtensor.py +++ b/bittensor/core/subtensor.py @@ -26,6 +26,7 @@ from bittensor.core.chain_data import ( custom_rpc_type_registry, DelegateInfo, + MetagraphInfo, NeuronInfo, NeuronInfoLite, PrometheusInfo, @@ -704,6 +705,37 @@ def metagraph( return metagraph + def get_metagraph( + self, netuid: int, block: Optional[int] = None + ) -> Optional["MetagraphInfo"]: + if block is not None: + block_hash = self.get_block_hash(block) + else: + block_hash = None + + query = self.substrate.runtime_call( + "SubnetInfoRuntimeApi", + "get_metagraph", + params=[netuid], + block_hash=block_hash, + ) + metagraph_bytes = bytes.fromhex(query.decode()[2:]) + return MetagraphInfo.from_vec_u8(metagraph_bytes) + + def get_all_metagraphs(self, block: Optional[int] = None) -> list["MetagraphInfo"]: + if block is not None: + block_hash = self.get_block_hash(block) + else: + block_hash = None + + query = self.substrate.runtime_call( + "SubnetInfoRuntimeApi", + "get_all_metagraphs", + block_hash=block_hash, + ) + metagraphs_bytes = bytes.fromhex(query.decode()[2:]) + return MetagraphInfo.list_from_vec_u8(metagraphs_bytes) + @staticmethod def determine_chain_endpoint_and_network( network: str, From ed4352cf7e1fd092ef442a9e6fb3cc676e494e59 Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 17:45:57 -0800 Subject: [PATCH 06/27] add new async methods --- bittensor/core/async_subtensor.py | 34 +++++++++++++++++++++++++++++++ 1 file changed, 34 insertions(+) diff --git a/bittensor/core/async_subtensor.py b/bittensor/core/async_subtensor.py index f265f5dffa..cb4704d8df 100644 --- a/bittensor/core/async_subtensor.py +++ b/bittensor/core/async_subtensor.py @@ -23,6 +23,7 @@ DelegateInfo, custom_rpc_type_registry, StakeInfo, + MetagraphInfo, NeuronInfoLite, NeuronInfo, SubnetHyperparameters, @@ -350,6 +351,39 @@ async def metagraph( return metagraph + async def get_metagraph( + self, netuid: int, block: Optional[int] = None + ) -> Optional["MetagraphInfo"]: + if block is not None: + block_hash = await self.get_block_hash(block) + else: + block_hash = None + + query = await self.substrate.runtime_call( + "SubnetInfoRuntimeApi", + "get_metagraph", + params=[netuid], + block_hash=block_hash, + ) + metagraph_bytes = bytes.fromhex(query.decode()[2:]) + return MetagraphInfo.from_vec_u8(metagraph_bytes) + + async def get_all_metagraphs( + self, block: Optional[int] = None + ) -> list["MetagraphInfo"]: + if block is not None: + block_hash = await self.get_block_hash(block) + else: + block_hash = None + + query = await self.substrate.runtime_call( + "SubnetInfoRuntimeApi", + "get_all_metagraphs", + block_hash=block_hash, + ) + metagraphs_bytes = bytes.fromhex(query.decode()[2:]) + return MetagraphInfo.list_from_vec_u8(metagraphs_bytes) + async def get_current_block(self) -> int: """ Returns the current block number on the Bittensor blockchain. This function provides the latest block number, indicating the most recent state of the blockchain. From 82f9edb696ce88874814b28fd0f2aa6044b51f30 Mon Sep 17 00:00:00 2001 From: Roman <167799377+roman-opentensor@users.noreply.github.com> Date: Tue, 21 Jan 2025 18:07:52 -0800 Subject: [PATCH 07/27] Update bittensor/core/chain_data/utils.py Co-authored-by: Cameron Fairchild --- bittensor/core/chain_data/utils.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bittensor/core/chain_data/utils.py b/bittensor/core/chain_data/utils.py index d15d74fb22..c60718ad23 100644 --- a/bittensor/core/chain_data/utils.py +++ b/bittensor/core/chain_data/utils.py @@ -408,7 +408,7 @@ def from_scale_encoding_using_type_string( "type_mapping": [ ["name", "Vec"], ["url", "Vec"], - ["url", "Vec"], + ["image", "Vec"], ["discord", "Vec"], ["description", "Vec"], ["additional", "Vec"], From 1444ceb94be33919c7dc3ae01b50578939c3aefa Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 18:58:31 -0800 Subject: [PATCH 08/27] fix type annotation --- .../core/chain_data/{metagrapg_info.py => metagraph_info.py} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename bittensor/core/chain_data/{metagrapg_info.py => metagraph_info.py} (100%) diff --git a/bittensor/core/chain_data/metagrapg_info.py b/bittensor/core/chain_data/metagraph_info.py similarity index 100% rename from bittensor/core/chain_data/metagrapg_info.py rename to bittensor/core/chain_data/metagraph_info.py From 11e2c695cceb0f6c1b5b7b28169a9396fba84d33 Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 18:59:04 -0800 Subject: [PATCH 09/27] fix type annotation --- bittensor/core/chain_data/chain_identity.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bittensor/core/chain_data/chain_identity.py b/bittensor/core/chain_data/chain_identity.py index f39daf0c87..f66de75410 100644 --- a/bittensor/core/chain_data/chain_identity.py +++ b/bittensor/core/chain_data/chain_identity.py @@ -12,4 +12,4 @@ class ChainIdentity: image: str discord: str description: str - additional: list[str, int] + additional: str From acd464ead14906e1321016a92085c3f93c254599 Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 18:59:15 -0800 Subject: [PATCH 10/27] change the name of module --- bittensor/core/chain_data/__init__.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bittensor/core/chain_data/__init__.py b/bittensor/core/chain_data/__init__.py index c3338c3ac4..98a710862d 100644 --- a/bittensor/core/chain_data/__init__.py +++ b/bittensor/core/chain_data/__init__.py @@ -9,7 +9,7 @@ from .delegate_info import DelegateInfo from .delegate_info_lite import DelegateInfoLite from .ip_info import IPInfo -from .metagrapg_info import MetagraphInfo +from .metagraph_info import MetagraphInfo from .neuron_info import NeuronInfo from .neuron_info_lite import NeuronInfoLite from .neuron_certificate import NeuronCertificate From 897587accc51fb2f0a4112b2588b12a7b89d7322 Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 19:38:58 -0800 Subject: [PATCH 11/27] improve `bittensor.core.chain_data.metagraph_info.MetagraphInfo.fix_decoded_values` --- bittensor/core/chain_data/metagraph_info.py | 2 ++ 1 file changed, 2 insertions(+) diff --git a/bittensor/core/chain_data/metagraph_info.py b/bittensor/core/chain_data/metagraph_info.py index 3e74d9b280..7e376f3a8f 100644 --- a/bittensor/core/chain_data/metagraph_info.py +++ b/bittensor/core/chain_data/metagraph_info.py @@ -134,6 +134,8 @@ def list_from_vec_u8(cls, vec_u8: bytes) -> list["MetagraphInfo"]: @classmethod def fix_decoded_values(cls, decoded: dict) -> "MetagraphInfo": """Returns a Metagraph object from a decoded MetagraphInfo dictionary.""" + decoded.update({"name": bytes(decoded.get("name")).decode()}) + decoded.update({"symbol": bytes(decoded.get("symbol")).decode()}) decoded.update({"identity": decoded.get("identity", {})}) decoded.update({"identities": decoded.get("identities", {})}) decoded.update({"axons": decoded.get("axons", {})}) From 2559b13b1f5c91c004d2e53ca76a90102649ac3b Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 19:39:39 -0800 Subject: [PATCH 12/27] improve `bittensor.core.chain_data.metagraph_info.MetagraphInfo.fix_decoded_values` --- bittensor/core/chain_data/metagraph_info.py | 1 - 1 file changed, 1 deletion(-) diff --git a/bittensor/core/chain_data/metagraph_info.py b/bittensor/core/chain_data/metagraph_info.py index 7e376f3a8f..1ca7d5d3d0 100644 --- a/bittensor/core/chain_data/metagraph_info.py +++ b/bittensor/core/chain_data/metagraph_info.py @@ -139,5 +139,4 @@ def fix_decoded_values(cls, decoded: dict) -> "MetagraphInfo": decoded.update({"identity": decoded.get("identity", {})}) decoded.update({"identities": decoded.get("identities", {})}) decoded.update({"axons": decoded.get("axons", {})}) - return MetagraphInfo(**decoded) From 170867f4f5358b0303c387ef7b1654cda276a7d1 Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 20:09:23 -0800 Subject: [PATCH 13/27] improve `bittensor.core.chain_data.metagraph_info.MetagraphInfo.list_from_vec_u8` --- bittensor/core/chain_data/metagraph_info.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bittensor/core/chain_data/metagraph_info.py b/bittensor/core/chain_data/metagraph_info.py index 1ca7d5d3d0..4bf6215fbe 100644 --- a/bittensor/core/chain_data/metagraph_info.py +++ b/bittensor/core/chain_data/metagraph_info.py @@ -128,7 +128,7 @@ def list_from_vec_u8(cls, vec_u8: bytes) -> list["MetagraphInfo"]: ) if decoded is None: return [] - decoded = [MetagraphInfo.fix_decoded_values(d) for d in decoded] + decoded = [MetagraphInfo.fix_decoded_values(d) for d in decoded if d is not None] return decoded @classmethod From d6882fdb8c866be7d150c4f12be9936691e03ac1 Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 21 Jan 2025 20:15:56 -0800 Subject: [PATCH 14/27] ruff --- bittensor/core/chain_data/metagraph_info.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/bittensor/core/chain_data/metagraph_info.py b/bittensor/core/chain_data/metagraph_info.py index 4bf6215fbe..45436ad030 100644 --- a/bittensor/core/chain_data/metagraph_info.py +++ b/bittensor/core/chain_data/metagraph_info.py @@ -128,7 +128,9 @@ def list_from_vec_u8(cls, vec_u8: bytes) -> list["MetagraphInfo"]: ) if decoded is None: return [] - decoded = [MetagraphInfo.fix_decoded_values(d) for d in decoded if d is not None] + decoded = [ + MetagraphInfo.fix_decoded_values(d) for d in decoded if d is not None + ] return decoded @classmethod From 10a5d20bc94e5915b58c80cbecd9a0c8fbf803af Mon Sep 17 00:00:00 2001 From: Benjamin Himes Date: Wed, 22 Jan 2025 18:21:47 +0200 Subject: [PATCH 15/27] Added __all__ for imports, correctly handle block in asyncsubtensor --- bittensor/core/async_subtensor.py | 15 +++------------ bittensor/core/chain_data/__init__.py | 24 ++++++++++++++++++++++++ 2 files changed, 27 insertions(+), 12 deletions(-) diff --git a/bittensor/core/async_subtensor.py b/bittensor/core/async_subtensor.py index cb4704d8df..9bfcf3a9e1 100644 --- a/bittensor/core/async_subtensor.py +++ b/bittensor/core/async_subtensor.py @@ -354,10 +354,7 @@ async def metagraph( async def get_metagraph( self, netuid: int, block: Optional[int] = None ) -> Optional["MetagraphInfo"]: - if block is not None: - block_hash = await self.get_block_hash(block) - else: - block_hash = None + block_hash = await self.get_block_hash(block) query = await self.substrate.runtime_call( "SubnetInfoRuntimeApi", @@ -371,10 +368,7 @@ async def get_metagraph( async def get_all_metagraphs( self, block: Optional[int] = None ) -> list["MetagraphInfo"]: - if block is not None: - block_hash = await self.get_block_hash(block) - else: - block_hash = None + block_hash = await self.get_block_hash(block) query = await self.substrate.runtime_call( "SubnetInfoRuntimeApi", @@ -435,10 +429,7 @@ async def get_stake_for_coldkey( Optional[list[StakeInfo]]: A list of StakeInfo objects, or ``None`` if no stake information is found. """ encoded_coldkey = ss58_to_vec_u8(coldkey_ss58) - if block is not None: - block_hash = await self.get_block_hash(block) - else: - block_hash = None + block_hash = await self.get_block_hash(block) hex_bytes_result = await self.query_runtime_api( runtime_api="StakeInfoRuntimeApi", method="get_stake_info_for_coldkey", diff --git a/bittensor/core/chain_data/__init__.py b/bittensor/core/chain_data/__init__.py index 98a710862d..20ed1fa684 100644 --- a/bittensor/core/chain_data/__init__.py +++ b/bittensor/core/chain_data/__init__.py @@ -25,3 +25,27 @@ from .utils import custom_rpc_type_registry, decode_account_id, process_stake_data ProposalCallData = GenericCall + +__all__ = [ + AxonInfo, + DelegateInfo, + DelegateInfoLite, + IPInfo, + MetagraphInfo, + NeuronInfo, + NeuronInfoLite, + NeuronCertificate, + PrometheusInfo, + ProposalVoteData, + ScheduledColdkeySwapInfo, + SubnetState, + StakeInfo, + SubnetHyperparameters, + SubnetInfo, + DynamicInfo, + SubnetIdentity, + custom_rpc_type_registry, + decode_account_id, + process_stake_data, + ProposalCallData, +] From 15fea3607e8d2fc2fba1da3acbfee54d77cf0bdc Mon Sep 17 00:00:00 2001 From: Roman Date: Wed, 22 Jan 2025 18:55:48 -0800 Subject: [PATCH 16/27] add `pow_registration_allowed` field to MetagraphInfo --- bittensor/core/chain_data/metagraph_info.py | 5 ++++- bittensor/core/chain_data/utils.py | 1 + 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/bittensor/core/chain_data/metagraph_info.py b/bittensor/core/chain_data/metagraph_info.py index 45436ad030..f26789a03d 100644 --- a/bittensor/core/chain_data/metagraph_info.py +++ b/bittensor/core/chain_data/metagraph_info.py @@ -60,6 +60,7 @@ class MetagraphInfo: burn: int # current burn cost. difficulty: int # current difficulty. registration_allowed: bool # allows registrations. + pow_registration_allowed: bool # pow registration enabled. immunity_period: int # subnet miner immunity period min_difficulty: int # min pow difficulty max_difficulty: int # max pow difficulty @@ -129,7 +130,9 @@ def list_from_vec_u8(cls, vec_u8: bytes) -> list["MetagraphInfo"]: if decoded is None: return [] decoded = [ - MetagraphInfo.fix_decoded_values(d) for d in decoded if d is not None + MetagraphInfo.fix_decoded_values(meta) + for meta in decoded + if meta is not None ] return decoded diff --git a/bittensor/core/chain_data/utils.py b/bittensor/core/chain_data/utils.py index c60718ad23..5e66fc9d0c 100644 --- a/bittensor/core/chain_data/utils.py +++ b/bittensor/core/chain_data/utils.py @@ -365,6 +365,7 @@ def from_scale_encoding_using_type_string( ["burn", "Compact"], ["difficulty", "Compact"], ["registration_allowed", "bool"], + ["pow_registration_allowed", "bool"], ["immunity_period", "Compact"], ["min_difficulty", "Compact"], ["max_difficulty", "Compact"], From 41066224cc1ca48b5400eb0a4cb2847faaed5105 Mon Sep 17 00:00:00 2001 From: Roman Date: Fri, 24 Jan 2025 19:00:44 -0800 Subject: [PATCH 17/27] improve `bittensor.core.chain_data.metagraph_info.MetagraphInfo.fix_decoded_values` method --- bittensor/core/chain_data/metagraph_info.py | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/bittensor/core/chain_data/metagraph_info.py b/bittensor/core/chain_data/metagraph_info.py index f26789a03d..e335b012fd 100644 --- a/bittensor/core/chain_data/metagraph_info.py +++ b/bittensor/core/chain_data/metagraph_info.py @@ -139,9 +139,14 @@ def list_from_vec_u8(cls, vec_u8: bytes) -> list["MetagraphInfo"]: @classmethod def fix_decoded_values(cls, decoded: dict) -> "MetagraphInfo": """Returns a Metagraph object from a decoded MetagraphInfo dictionary.""" + identities = [ + {k: (v or None) for k, v in ident.items()} + for ident in decoded.get("identities", []) + ] + decoded.update({"name": bytes(decoded.get("name")).decode()}) decoded.update({"symbol": bytes(decoded.get("symbol")).decode()}) decoded.update({"identity": decoded.get("identity", {})}) - decoded.update({"identities": decoded.get("identities", {})}) + decoded.update({"identities": identities}) decoded.update({"axons": decoded.get("axons", {})}) return MetagraphInfo(**decoded) From 7824f9b6a559f234e3bc8b72cf908077a7afac23 Mon Sep 17 00:00:00 2001 From: Roman Date: Fri, 24 Jan 2025 19:24:14 -0800 Subject: [PATCH 18/27] improve `bittensor.core.chain_data.metagraph_info.MetagraphInfo.fix_decoded_values` method --- bittensor/core/chain_data/metagraph_info.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bittensor/core/chain_data/metagraph_info.py b/bittensor/core/chain_data/metagraph_info.py index e335b012fd..a012bf9aa2 100644 --- a/bittensor/core/chain_data/metagraph_info.py +++ b/bittensor/core/chain_data/metagraph_info.py @@ -148,5 +148,5 @@ def fix_decoded_values(cls, decoded: dict) -> "MetagraphInfo": decoded.update({"symbol": bytes(decoded.get("symbol")).decode()}) decoded.update({"identity": decoded.get("identity", {})}) decoded.update({"identities": identities}) - decoded.update({"axons": decoded.get("axons", {})}) + decoded.update({"axons": decoded.get("axons", [])}) return MetagraphInfo(**decoded) From b40fb7e501c6469885268d4b5019b57467333ee9 Mon Sep 17 00:00:00 2001 From: Roman Date: Mon, 27 Jan 2025 12:01:47 -0800 Subject: [PATCH 19/27] fix None logic --- bittensor/core/chain_data/metagraph_info.py | 4 +++- bittensor/core/chain_data/utils.py | 2 +- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/bittensor/core/chain_data/metagraph_info.py b/bittensor/core/chain_data/metagraph_info.py index a012bf9aa2..0dcc6b3df0 100644 --- a/bittensor/core/chain_data/metagraph_info.py +++ b/bittensor/core/chain_data/metagraph_info.py @@ -85,7 +85,7 @@ class MetagraphInfo: # Metagraph info. hotkeys: list[str] # hotkey per UID coldkeys: list[str] # coldkey per UID - identities: list["ChainIdentity"] # coldkeys identities + identities: list[Optional["ChainIdentity"]] # coldkeys identities axons: list["AxonInfo"] # UID axons. active: list[bool] # Active per UID validator_permit: list[bool] # Val permit per UID @@ -129,6 +129,7 @@ def list_from_vec_u8(cls, vec_u8: bytes) -> list["MetagraphInfo"]: ) if decoded is None: return [] + decoded = [ MetagraphInfo.fix_decoded_values(meta) for meta in decoded @@ -142,6 +143,7 @@ def fix_decoded_values(cls, decoded: dict) -> "MetagraphInfo": identities = [ {k: (v or None) for k, v in ident.items()} for ident in decoded.get("identities", []) + if ident is not None ] decoded.update({"name": bytes(decoded.get("name")).decode()}) diff --git a/bittensor/core/chain_data/utils.py b/bittensor/core/chain_data/utils.py index 5e66fc9d0c..c8b079c1fd 100644 --- a/bittensor/core/chain_data/utils.py +++ b/bittensor/core/chain_data/utils.py @@ -384,7 +384,7 @@ def from_scale_encoding_using_type_string( ["bonds_moving_avg", "Compact"], ["hotkeys", "Vec"], ["coldkeys", "Vec"], - ["identities", "Vec"], + ["identities", "Vec>"], ["axons", "Vec"], ["active", "Vec"], ["validator_permit", "Vec"], From 5af312c20b68e38d77a7dafa0d7030cea0e747a0 Mon Sep 17 00:00:00 2001 From: Roman Date: Mon, 27 Jan 2025 19:35:06 -0800 Subject: [PATCH 20/27] improve balance logic --- bittensor/utils/balance.py | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) diff --git a/bittensor/utils/balance.py b/bittensor/utils/balance.py index b8cca628be..3b1556224f 100644 --- a/bittensor/utils/balance.py +++ b/bittensor/utils/balance.py @@ -15,7 +15,7 @@ # OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER # DEALINGS IN THE SOFTWARE. -from typing import Union +from typing import Union, Optional from bittensor.core import settings @@ -228,44 +228,47 @@ def __abs__(self): return Balance.from_rao(abs(self.rao)) @staticmethod - def from_float(amount: float): + def from_float(amount: float, netuid: Optional[int] = 0): """ Given tao, return :func:`Balance` object with rao(``int``) and tao(``float``), where rao = int(tao*pow(10,9)) Args: amount (float): The amount in tao. + netuid (int): The subnet uid for set currency unit. Defaults to `0`. Returns: A Balance object representing the given amount. """ rao = int(amount * pow(10, 9)) - return Balance(rao) + return Balance(rao).set_unit(netuid) @staticmethod - def from_tao(amount: float): + def from_tao(amount: float, netuid: Optional[int] = 0): """ Given tao, return Balance object with rao(``int``) and tao(``float``), where rao = int(tao*pow(10,9)) Args: amount (float): The amount in tao. + netuid (int): The subnet uid for set currency unit. Defaults to `0`. Returns: A Balance object representing the given amount. """ rao = int(amount * pow(10, 9)) - return Balance(rao) + return Balance(rao).set_unit(netuid) @staticmethod - def from_rao(amount: int): + def from_rao(amount: int, netuid: Optional[int] = 0): """ Given rao, return Balance object with rao(``int``) and tao(``float``), where rao = int(tao*pow(10,9)) Args: amount (int): The amount in rao. + netuid (int): The subnet uid for set currency unit. Defaults to `0`. Returns: A Balance object representing the given amount. """ - return Balance(amount) + return Balance(amount).set_unit(netuid) @staticmethod def get_unit(netuid: int): From e87d1868f419559a58ea5d8dfa59beadd17d33a5 Mon Sep 17 00:00:00 2001 From: Roman Date: Mon, 27 Jan 2025 19:35:22 -0800 Subject: [PATCH 21/27] add TODO --- bittensor/core/settings.py | 1 + 1 file changed, 1 insertion(+) diff --git a/bittensor/core/settings.py b/bittensor/core/settings.py index e21d60311a..b7a79d0ba1 100644 --- a/bittensor/core/settings.py +++ b/bittensor/core/settings.py @@ -372,6 +372,7 @@ def __apply_nest_asyncio(): __apply_nest_asyncio() +# TODO: consider to move `units` to `bittensor.utils.balance` module. units = [ # Greek Alphabet (0-24) "\u03c4", # τ (tau, 0) From 41c3bc6e6e3f6ac9b150ed6adaa2d18d48ba9aba Mon Sep 17 00:00:00 2001 From: Roman Date: Mon, 27 Jan 2025 19:36:37 -0800 Subject: [PATCH 22/27] re-write MetagraphInfo.fix_decoded_values + update fields annotations --- bittensor/core/chain_data/metagraph_info.py | 155 ++++++++++++++------ 1 file changed, 113 insertions(+), 42 deletions(-) diff --git a/bittensor/core/chain_data/metagraph_info.py b/bittensor/core/chain_data/metagraph_info.py index 0dcc6b3df0..f3e1355c31 100644 --- a/bittensor/core/chain_data/metagraph_info.py +++ b/bittensor/core/chain_data/metagraph_info.py @@ -8,6 +8,15 @@ ChainDataType, from_scale_encoding, ) +from bittensor.utils import u64_normalized_float as u64tf, u16_normalized_float as u16tf +from bittensor.utils.balance import Balance +from scalecodec.utils.ss58 import ss58_encode + + +# to balance with unit (just shortcut) +def _tbwu(val: int, netuid: Optional[int] = 0) -> Balance: + """Returns a Balance object from a value and unit.""" + return Balance.from_tao(val).set_unit(netuid) @dataclass @@ -32,23 +41,23 @@ class MetagraphInfo: blocks_since_last_step: int # Subnet emission terms - subnet_emission: int - alpha_in: int - alpha_out: int - tao_in: int # amount of tao injected per block - alpha_out_emission: int # amount injected in alpha reserves per block - alpha_in_emission: int # amount injected outstanding per block - tao_in_emission: int # amount of tao injected per block - pending_alpha_emission: int # pending alpha to be distributed - pending_root_emission: int # pending tao for root divs to be distributed + subnet_emission: "Balance" # subnet emission via tao + alpha_in: "Balance" # amount of alpha in reserve + alpha_out: "Balance" # amount of alpha outstanding + tao_in: "Balance" # amount of tao injected per block + alpha_out_emission: "Balance" # amount injected in alpha reserves per block + alpha_in_emission: "Balance" # amount injected outstanding per block + tao_in_emission: "Balance" # amount of tao injected per block + pending_alpha_emission: "Balance" # pending alpha to be distributed + pending_root_emission: "Balance" # pending tao for root divs to be distributed # Hparams for epoch rho: int # subnet rho param - kappa: int # subnet kappa param + kappa: float # subnet kappa param # Validator params - min_allowed_weights: int # min allowed weights per val - max_weights_limit: int # max allowed weights per val + min_allowed_weights: float # min allowed weights per val + max_weights_limit: float # max allowed weights per val weights_version: int # allowed weights version weights_rate_limit: int # rate limit on weights. activity_cutoff: int # validator weights cut off period in blocks @@ -57,16 +66,16 @@ class MetagraphInfo: # Registration num_uids: int max_uids: int - burn: int # current burn cost. - difficulty: int # current difficulty. + burn: Balance # current burn cost. + difficulty: float # current difficulty. registration_allowed: bool # allows registrations. pow_registration_allowed: bool # pow registration enabled. immunity_period: int # subnet miner immunity period - min_difficulty: int # min pow difficulty - max_difficulty: int # max pow difficulty - min_burn: int # min tao burn - max_burn: int # max tao burn - adjustment_alpha: int # adjustment speed for registration params. + min_difficulty: float # min pow difficulty + max_difficulty: float # max pow difficulty + min_burn: Balance # min tao burn + max_burn: Balance # max tao burn + adjustment_alpha: float # adjustment speed for registration params. adjustment_interval: int # pow and burn adjustment interval target_regs_per_interval: int # target registrations per interval max_regs_per_block: int # max registrations per block. @@ -78,9 +87,9 @@ class MetagraphInfo: # Bonds liquid_alpha_enabled: bool # Bonds liquid enabled. - alpha_high: int # Alpha param high - alpha_low: int # Alpha param low - bonds_moving_avg: int # Bonds moving avg + alpha_high: float # Alpha param high + alpha_low: float # Alpha param low + bonds_moving_avg: float # Bonds moving avg # Metagraph info. hotkeys: list[str] # hotkey per UID @@ -89,30 +98,30 @@ class MetagraphInfo: axons: list["AxonInfo"] # UID axons. active: list[bool] # Active per UID validator_permit: list[bool] # Val permit per UID - pruning_score: list[int] # Pruning per UID + pruning_score: list[float] # Pruning per UID last_update: list[int] # Last update per UID - emission: list[int] # Emission per UID - dividends: list[int] # Dividends per UID - incentives: list[int] # Mining incentives per UID - consensus: list[int] # Consensus per UID - trust: list[int] # Trust per UID - rank: list[int] # Rank per UID + emission: list["Balance"] # Emission per UID + dividends: list[float] # Dividends per UID + incentives: list[float] # Mining incentives per UID + consensus: list[float] # Consensus per UID + trust: list[float] # Trust per UID + rank: list[float] # Rank per UID block_at_registration: list[int] # Reg block per UID - alpha_stake: list[int] # Alpha staked per UID - tao_stake: list[int] # TAO staked per UID - total_stake: list[int] # Total stake per UID + alpha_stake: list["Balance"] # Alpha staked per UID + tao_stake: list["Balance"] # TAO staked per UID + total_stake: list["Balance"] # Total stake per UID # Dividend break down. tao_dividends_per_hotkey: list[ - tuple[str, int] + tuple[str, "Balance"] ] # List of dividend payouts in tao via root. alpha_dividends_per_hotkey: list[ - tuple[str, int] + tuple[str, "Balance"] ] # List of dividend payout in alpha via subnet. @classmethod def from_vec_u8(cls, vec_u8: bytes) -> Optional["MetagraphInfo"]: - """Returns a Metagraph object from a encoded MetagraphInfo vector.""" + """Returns a Metagraph object from encoded MetagraphInfo vector.""" if len(vec_u8) == 0: return None decoded = from_scale_encoding(vec_u8, ChainDataType.MetagraphInfo) @@ -140,15 +149,77 @@ def list_from_vec_u8(cls, vec_u8: bytes) -> list["MetagraphInfo"]: @classmethod def fix_decoded_values(cls, decoded: dict) -> "MetagraphInfo": """Returns a Metagraph object from a decoded MetagraphInfo dictionary.""" - identities = [ - {k: (v or None) for k, v in ident.items()} - for ident in decoded.get("identities", []) - if ident is not None - ] + # Subnet index + _netuid = decoded["netuid"] + # Name and symbol decoded.update({"name": bytes(decoded.get("name")).decode()}) decoded.update({"symbol": bytes(decoded.get("symbol")).decode()}) decoded.update({"identity": decoded.get("identity", {})}) - decoded.update({"identities": identities}) - decoded.update({"axons": decoded.get("axons", [])}) + + # Keys for owner. + decoded["owner_hotkey"] = ss58_encode(decoded["owner_hotkey"]) + decoded["owner_coldkey"] = ss58_encode(decoded["owner_coldkey"]) + + # Subnet emission terms + decoded["subnet_emission"] = _tbwu(decoded["subnet_emission"]) + decoded["alpha_in"] = _tbwu(decoded["alpha_in"], _netuid) + decoded["alpha_out"] = _tbwu(decoded["alpha_out"], _netuid) + decoded["tao_in"] = _tbwu(decoded["tao_in"]) + decoded["alpha_out_emission"] = _tbwu(decoded["alpha_out_emission"], _netuid) + decoded["alpha_in_emission"] = _tbwu(decoded["alpha_in_emission"], _netuid) + decoded["tao_in_emission"] = _tbwu(decoded["tao_in_emission"]) + decoded["pending_alpha_emission"] = _tbwu( + decoded["pending_alpha_emission"], _netuid + ) + decoded["pending_root_emission"] = _tbwu(decoded["pending_root_emission"]) + + # Hparams for epoch + decoded["kappa"] = u16tf(decoded["kappa"]) + + # Validator params + decoded["min_allowed_weights"] = u16tf(decoded["min_allowed_weights"]) + decoded["max_weights_limit"] = u16tf(decoded["max_weights_limit"]) + + # Registration + decoded["burn"] = _tbwu(decoded["burn"]) + decoded["difficulty"] = u64tf(decoded["difficulty"]) + decoded["min_difficulty"] = u64tf(decoded["min_difficulty"]) + decoded["max_difficulty"] = u64tf(decoded["max_difficulty"]) + decoded["min_burn"] = _tbwu(decoded["min_burn"]) + decoded["max_burn"] = _tbwu(decoded["max_burn"]) + decoded["adjustment_alpha"] = u64tf(decoded["adjustment_alpha"]) + + # Bonds + decoded["alpha_high"] = u16tf(decoded["alpha_high"]) + decoded["alpha_low"] = u16tf(decoded["alpha_low"]) + decoded["bonds_moving_avg"] = u64tf(decoded["bonds_moving_avg"]) + + # Metagraph info. + decoded["hotkeys"] = [ss58_encode(ck) for ck in decoded.get("hotkeys", [])] + decoded["coldkeys"] = [ss58_encode(hk) for hk in decoded.get("coldkeys", [])] + decoded["axons"] = decoded.get("axons", []) + decoded["pruning_score"] = [ + u16tf(ps) for ps in decoded.get("pruning_score", []) + ] + decoded["emission"] = [_tbwu(em, _netuid) for em in decoded.get("emission", [])] + decoded["dividends"] = [u16tf(dv) for dv in decoded.get("dividends", [])] + decoded["incentives"] = [u16tf(ic) for ic in decoded.get("incentives", [])] + decoded["consensus"] = [u16tf(cs) for cs in decoded.get("consensus", [])] + decoded["trust"] = [u16tf(tr) for tr in decoded.get("trust", [])] + decoded["rank"] = [u16tf(rk) for rk in decoded.get("trust", [])] + decoded["alpha_stake"] = [_tbwu(ast, _netuid) for ast in decoded["alpha_stake"]] + decoded["tao_stake"] = [_tbwu(ts) for ts in decoded["tao_stake"]] + decoded["total_stake"] = [_tbwu(ts, _netuid) for ts in decoded["total_stake"]] + + # Dividend break down + decoded["tao_dividends_per_hotkey"] = [ + (ss58_encode(alpha[0]), _tbwu(alpha[1])) + for alpha in decoded["tao_dividends_per_hotkey"] + ] + decoded["alpha_dividends_per_hotkey"] = [ + (ss58_encode(adphk[0]), _tbwu(adphk[1], _netuid)) + for adphk in decoded["alpha_dividends_per_hotkey"] + ] + return MetagraphInfo(**decoded) From 4a2c7b21d5a4950c389d833f7f65a88d77cee1c8 Mon Sep 17 00:00:00 2001 From: Roman Date: Mon, 27 Jan 2025 19:40:02 -0800 Subject: [PATCH 23/27] update helper `_tbwu` --- bittensor/core/chain_data/metagraph_info.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bittensor/core/chain_data/metagraph_info.py b/bittensor/core/chain_data/metagraph_info.py index f3e1355c31..ac2637fdb7 100644 --- a/bittensor/core/chain_data/metagraph_info.py +++ b/bittensor/core/chain_data/metagraph_info.py @@ -16,7 +16,7 @@ # to balance with unit (just shortcut) def _tbwu(val: int, netuid: Optional[int] = 0) -> Balance: """Returns a Balance object from a value and unit.""" - return Balance.from_tao(val).set_unit(netuid) + return Balance.from_tao(val, netuid) @dataclass From 98eb7c23d29a10984c324a4e0b889583d1df202e Mon Sep 17 00:00:00 2001 From: Roman Date: Mon, 27 Jan 2025 20:41:36 -0800 Subject: [PATCH 24/27] add cast for mypy passing --- bittensor/core/subtensor.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/bittensor/core/subtensor.py b/bittensor/core/subtensor.py index 796d9899b9..e189e3aa6c 100644 --- a/bittensor/core/subtensor.py +++ b/bittensor/core/subtensor.py @@ -7,7 +7,7 @@ import copy import ssl import time -from typing import Union, Optional, TypedDict, Any +from typing import Union, Optional, TypedDict, Any, cast import warnings import numpy as np import scalecodec @@ -2704,7 +2704,7 @@ def transfer_stake( StakeError: If the transfer fails due to insufficient stake or other reasons. """ if isinstance(amount, (float, int)): - amount = Balance.from_tao(amount) + amount = cast(Balance, Balance.from_tao(amount)) hotkey_owner = self.get_hotkey_owner(hotkey_ss58) if hotkey_owner != wallet.coldkeypub.ss58_address: @@ -2786,7 +2786,7 @@ def swap_stake( """ # Convert amount to Balance if needed if isinstance(amount, (float, int)): - amount = Balance.from_tao(amount) + amount = cast(Balance, Balance.from_tao(amount)) hotkey_owner = self.get_hotkey_owner(hotkey_ss58) if hotkey_owner != wallet.coldkeypub.ss58_address: @@ -2873,7 +2873,7 @@ def move_stake( StakeError: If the movement fails due to insufficient stake or other reasons. """ if isinstance(amount, (float, int)): - amount = Balance.from_tao(amount) + amount = cast(Balance, Balance.from_tao(amount)) stake_in_origin = self.get_stake( hotkey_ss58=origin_hotkey, From 3309699a5702efcbb473151d3335b0b8d22111f2 Mon Sep 17 00:00:00 2001 From: Roman Date: Mon, 27 Jan 2025 20:41:50 -0800 Subject: [PATCH 25/27] fix test --- tests/unit_tests/test_subtensor.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/unit_tests/test_subtensor.py b/tests/unit_tests/test_subtensor.py index a2ec87b330..ca86384047 100644 --- a/tests/unit_tests/test_subtensor.py +++ b/tests/unit_tests/test_subtensor.py @@ -2064,7 +2064,7 @@ def test_recycle_success(subtensor, mocker): ) mocked_balance.assert_called_once_with(int(mocked_get_hyperparameter.return_value)) - assert result == mocked_balance.return_value + assert result == mocked_balance.return_value.set_unit.return_value def test_recycle_none(subtensor, mocker): From 0710c7d74f230681b3937b51894f34d2b0182d40 Mon Sep 17 00:00:00 2001 From: Benjamin Himes Date: Tue, 28 Jan 2025 18:48:18 +0200 Subject: [PATCH 26/27] Simplified typing. --- bittensor/core/async_subtensor.py | 4 +-- bittensor/core/chain_data/metagraph_info.py | 36 ++++++++++----------- bittensor/core/subtensor.py | 4 +-- 3 files changed, 22 insertions(+), 22 deletions(-) diff --git a/bittensor/core/async_subtensor.py b/bittensor/core/async_subtensor.py index 50b01ed895..17c4658130 100644 --- a/bittensor/core/async_subtensor.py +++ b/bittensor/core/async_subtensor.py @@ -356,7 +356,7 @@ async def metagraph( async def get_metagraph( self, netuid: int, block: Optional[int] = None - ) -> Optional["MetagraphInfo"]: + ) -> Optional[MetagraphInfo]: block_hash = await self.get_block_hash(block) query = await self.substrate.runtime_call( @@ -370,7 +370,7 @@ async def get_metagraph( async def get_all_metagraphs( self, block: Optional[int] = None - ) -> list["MetagraphInfo"]: + ) -> list[MetagraphInfo]: block_hash = await self.get_block_hash(block) query = await self.substrate.runtime_call( diff --git a/bittensor/core/chain_data/metagraph_info.py b/bittensor/core/chain_data/metagraph_info.py index ac2637fdb7..19399fb65c 100644 --- a/bittensor/core/chain_data/metagraph_info.py +++ b/bittensor/core/chain_data/metagraph_info.py @@ -27,7 +27,7 @@ class MetagraphInfo: # Name and symbol name: str symbol: str - identity: Optional["SubnetIdentity"] + identity: Optional[SubnetIdentity] network_registered_at: int # Keys for owner. @@ -41,15 +41,15 @@ class MetagraphInfo: blocks_since_last_step: int # Subnet emission terms - subnet_emission: "Balance" # subnet emission via tao - alpha_in: "Balance" # amount of alpha in reserve - alpha_out: "Balance" # amount of alpha outstanding - tao_in: "Balance" # amount of tao injected per block - alpha_out_emission: "Balance" # amount injected in alpha reserves per block - alpha_in_emission: "Balance" # amount injected outstanding per block - tao_in_emission: "Balance" # amount of tao injected per block - pending_alpha_emission: "Balance" # pending alpha to be distributed - pending_root_emission: "Balance" # pending tao for root divs to be distributed + subnet_emission: Balance # subnet emission via tao + alpha_in: Balance # amount of alpha in reserve + alpha_out: Balance # amount of alpha outstanding + tao_in: Balance # amount of tao injected per block + alpha_out_emission: Balance # amount injected in alpha reserves per block + alpha_in_emission: Balance # amount injected outstanding per block + tao_in_emission: Balance # amount of tao injected per block + pending_alpha_emission: Balance # pending alpha to be distributed + pending_root_emission: Balance # pending tao for root divs to be distributed # Hparams for epoch rho: int # subnet rho param @@ -94,29 +94,29 @@ class MetagraphInfo: # Metagraph info. hotkeys: list[str] # hotkey per UID coldkeys: list[str] # coldkey per UID - identities: list[Optional["ChainIdentity"]] # coldkeys identities - axons: list["AxonInfo"] # UID axons. + identities: list[Optional[ChainIdentity]] # coldkeys identities + axons: list[AxonInfo] # UID axons. active: list[bool] # Active per UID validator_permit: list[bool] # Val permit per UID pruning_score: list[float] # Pruning per UID last_update: list[int] # Last update per UID - emission: list["Balance"] # Emission per UID + emission: list[Balance] # Emission per UID dividends: list[float] # Dividends per UID incentives: list[float] # Mining incentives per UID consensus: list[float] # Consensus per UID trust: list[float] # Trust per UID rank: list[float] # Rank per UID block_at_registration: list[int] # Reg block per UID - alpha_stake: list["Balance"] # Alpha staked per UID - tao_stake: list["Balance"] # TAO staked per UID - total_stake: list["Balance"] # Total stake per UID + alpha_stake: list[Balance] # Alpha staked per UID + tao_stake: list[Balance] # TAO staked per UID + total_stake: list[Balance] # Total stake per UID # Dividend break down. tao_dividends_per_hotkey: list[ - tuple[str, "Balance"] + tuple[str, Balance] ] # List of dividend payouts in tao via root. alpha_dividends_per_hotkey: list[ - tuple[str, "Balance"] + tuple[str, Balance] ] # List of dividend payout in alpha via subnet. @classmethod diff --git a/bittensor/core/subtensor.py b/bittensor/core/subtensor.py index e189e3aa6c..2871153d04 100644 --- a/bittensor/core/subtensor.py +++ b/bittensor/core/subtensor.py @@ -705,7 +705,7 @@ def metagraph( def get_metagraph( self, netuid: int, block: Optional[int] = None - ) -> Optional["MetagraphInfo"]: + ) -> Optional[MetagraphInfo]: if block is not None: block_hash = self.get_block_hash(block) else: @@ -720,7 +720,7 @@ def get_metagraph( metagraph_bytes = bytes.fromhex(query.decode()[2:]) return MetagraphInfo.from_vec_u8(metagraph_bytes) - def get_all_metagraphs(self, block: Optional[int] = None) -> list["MetagraphInfo"]: + def get_all_metagraphs(self, block: Optional[int] = None) -> list[MetagraphInfo]: if block is not None: block_hash = self.get_block_hash(block) else: From 25f9c31354027521f1af10b781867b32b3d231cf Mon Sep 17 00:00:00 2001 From: Roman Date: Tue, 28 Jan 2025 09:06:45 -0800 Subject: [PATCH 27/27] rename methods --- bittensor/core/subtensor.py | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/bittensor/core/subtensor.py b/bittensor/core/subtensor.py index 2871153d04..724d18d11c 100644 --- a/bittensor/core/subtensor.py +++ b/bittensor/core/subtensor.py @@ -703,7 +703,7 @@ def metagraph( return metagraph - def get_metagraph( + def get_metagraph_info( self, netuid: int, block: Optional[int] = None ) -> Optional[MetagraphInfo]: if block is not None: @@ -720,7 +720,9 @@ def get_metagraph( metagraph_bytes = bytes.fromhex(query.decode()[2:]) return MetagraphInfo.from_vec_u8(metagraph_bytes) - def get_all_metagraphs(self, block: Optional[int] = None) -> list[MetagraphInfo]: + def get_all_metagraphs_info( + self, block: Optional[int] = None + ) -> list[MetagraphInfo]: if block is not None: block_hash = self.get_block_hash(block) else: