bittensor-cli 8.2.0rc14__py3-none-any.whl → 8.2.0rc15__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
bittensor_cli/__init__.py CHANGED
@@ -18,6 +18,6 @@
18
18
  from .cli import CLIManager
19
19
 
20
20
 
21
- __version__ = "8.2.0rc14"
21
+ __version__ = "8.2.0rc15"
22
22
 
23
23
  __all__ = ["CLIManager", "__version__"]
bittensor_cli/cli.py CHANGED
@@ -64,7 +64,7 @@ except ImportError:
64
64
  pass
65
65
 
66
66
 
67
- __version__ = "8.2.0rc14"
67
+ __version__ = "8.2.0rc15"
68
68
 
69
69
 
70
70
  _core_version = re.match(r"^\d+\.\d+\.\d+", __version__).group(0)
@@ -2478,6 +2478,7 @@ class CLIManager:
2478
2478
  live: bool = Options.live,
2479
2479
  quiet: bool = Options.quiet,
2480
2480
  verbose: bool = Options.verbose,
2481
+ no_prompt: bool = Options.prompt,
2481
2482
  # TODO add: all-wallets, reuse_last, html_output
2482
2483
  ):
2483
2484
  """List all stake accounts for wallet."""
@@ -2506,7 +2507,7 @@ class CLIManager:
2506
2507
 
2507
2508
  return self._run_command(
2508
2509
  stake.stake_list(
2509
- wallet, coldkey_ss58, self.initialize_chain(network), live, verbose
2510
+ wallet, coldkey_ss58, self.initialize_chain(network), live, verbose, no_prompt
2510
2511
  )
2511
2512
  )
2512
2513
 
@@ -4041,8 +4042,10 @@ class CLIManager:
4041
4042
  wallet_hotkey,
4042
4043
  ask_for=[
4043
4044
  WO.NAME,
4045
+ WO.HOTKEY,
4046
+ WO.PATH,
4044
4047
  ],
4045
- validate=WV.WALLET,
4048
+ validate=WV.WALLET_AND_HOTKEY,
4046
4049
  )
4047
4050
  identity = prompt_for_subnet_identity(
4048
4051
  subnet_name=subnet_name,
@@ -900,6 +900,7 @@ class DynamicInfo:
900
900
  pending_root_emission: Balance
901
901
  network_registered_at: int
902
902
  subnet_identity: Optional[SubnetIdentity]
903
+ subnet_volume: float
903
904
 
904
905
  @classmethod
905
906
  def from_vec_u8(cls, vec_u8: list[int]) -> Optional["DynamicInfo"]:
@@ -938,6 +939,7 @@ class DynamicInfo:
938
939
  alpha_in = Balance.from_rao(decoded["alpha_in"]).set_unit(netuid)
939
940
  alpha_out = Balance.from_rao(decoded["alpha_out"]).set_unit(netuid)
940
941
  tao_in = Balance.from_rao(decoded["tao_in"]).set_unit(0)
942
+ subnet_volume = Balance.from_rao(decoded["subnet_volume"]).set_unit(netuid)
941
943
  alpha_out_emission = Balance.from_rao(decoded["alpha_out_emission"]).set_unit(
942
944
  netuid
943
945
  )
@@ -991,6 +993,7 @@ class DynamicInfo:
991
993
  pending_root_emission=pending_root_emission,
992
994
  network_registered_at=int(decoded["network_registered_at"]),
993
995
  subnet_identity=subnet_identity,
996
+ subnet_volume=subnet_volume,
994
997
  )
995
998
 
996
999
  def tao_to_alpha(self, tao: Balance) -> Balance:
@@ -1601,6 +1604,7 @@ custom_rpc_type_registry = {
1601
1604
  ["pending_alpha_emission", "Compact<u64>"],
1602
1605
  ["pending_root_emission", "Compact<u64>"],
1603
1606
  ["network_registered_at", "Compact<u64>"],
1607
+ ["subnet_volume", "Compact<u128>"],
1604
1608
  ["subnet_identity", "Option<SubnetIdentity>"],
1605
1609
  ],
1606
1610
  },
@@ -27,6 +27,7 @@ from bittensor_cli.src.bittensor.chain_data import (
27
27
  decode_hex_identity,
28
28
  DelegateInfoLite,
29
29
  DynamicInfo,
30
+ SubnetState,
30
31
  )
31
32
  from bittensor_cli.src import DelegatesDetails
32
33
  from bittensor_cli.src.bittensor.balances import Balance, FixedPoint, fixed_to_float
@@ -588,6 +589,36 @@ class SubtensorInterface:
588
589
  )
589
590
  return result
590
591
 
592
+ async def get_subnet_state(
593
+ self, netuid: int, block_hash: Optional[str] = None
594
+ ) -> Optional["SubnetState"]:
595
+ """
596
+ Retrieves the state of a specific subnet within the Bittensor network.
597
+
598
+ Args:
599
+ netuid: The network UID of the subnet to query.
600
+ block_hash: The hash of the blockchain block number for the query.
601
+
602
+ Returns:
603
+ SubnetState object containing the subnet's state information, or None if the subnet doesn't exist.
604
+ """
605
+ hex_bytes_result = await self.query_runtime_api(
606
+ runtime_api="SubnetInfoRuntimeApi",
607
+ method="get_subnet_state",
608
+ params=[netuid],
609
+ block_hash=block_hash,
610
+ )
611
+
612
+ if hex_bytes_result is None:
613
+ return None
614
+
615
+ try:
616
+ bytes_result = bytes.fromhex(hex_bytes_result[2:])
617
+ except ValueError:
618
+ bytes_result = bytes.fromhex(hex_bytes_result)
619
+
620
+ return SubnetState.from_vec_u8(bytes_result)
621
+
591
622
  async def get_hyperparameter(
592
623
  self,
593
624
  param_name: str,
@@ -1185,6 +1185,7 @@ async def stake_list(
1185
1185
  subtensor: "SubtensorInterface",
1186
1186
  live: bool = False,
1187
1187
  verbose: bool = False,
1188
+ prompt: bool = False,
1188
1189
  ):
1189
1190
  coldkey_address = coldkey_ss58 if coldkey_ss58 else wallet.coldkeypub.ss58_address
1190
1191
 
@@ -1217,8 +1218,9 @@ async def stake_list(
1217
1218
  live: bool = False,
1218
1219
  ):
1219
1220
  title = f"\n[{COLOR_PALETTE['GENERAL']['HEADER']}]Hotkey: {hotkey_name}\nNetwork: {subtensor.network}\n\n"
1220
- if not live:
1221
- title += f"[{COLOR_PALETTE['GENERAL']['HINT']}]See below for an explanation of the columns\n"
1221
+ # TODO: Add hint back in after adding columns descriptions
1222
+ # if not live:
1223
+ # title += f"[{COLOR_PALETTE['GENERAL']['HINT']}]See below for an explanation of the columns\n"
1222
1224
  table = Table(
1223
1225
  title=title,
1224
1226
  show_footer=True,
@@ -1729,7 +1731,7 @@ async def stake_list(
1729
1731
  all_hotkeys_total_global_tao += stake
1730
1732
  all_hotkeys_total_tao_value += value
1731
1733
 
1732
- if num_hotkeys > 1 and counter < num_hotkeys:
1734
+ if num_hotkeys > 1 and counter < num_hotkeys and prompt:
1733
1735
  console.print("\nPress Enter to continue to the next hotkey...")
1734
1736
  input()
1735
1737
 
@@ -806,24 +806,16 @@ async def show(
806
806
  print_error("The root subnet does not exist")
807
807
  raise typer.Exit()
808
808
 
809
- hex_bytes_result, identities, old_identities = await asyncio.gather(
810
- subtensor.query_runtime_api(
811
- runtime_api="SubnetInfoRuntimeApi",
812
- method="get_subnet_state",
813
- params=[0],
814
- ),
809
+ root_state, identities, old_identities = await asyncio.gather(
810
+ subtensor.get_subnet_state(netuid=0),
815
811
  subtensor.query_all_identities(),
816
812
  subtensor.get_delegate_identities(),
817
813
  )
818
814
 
819
- if (bytes_result := hex_bytes_result) is None:
815
+ if root_state is None:
820
816
  err_console.print("The root subnet does not exist")
821
817
  return
822
818
 
823
- if bytes_result.startswith("0x"):
824
- bytes_result = bytes.fromhex(bytes_result[2:])
825
-
826
- root_state: "SubnetState" = SubnetState.from_vec_u8(bytes_result)
827
819
  if len(root_state.hotkeys) == 0:
828
820
  err_console.print(
829
821
  "The root-subnet is currently empty with 0 UIDs registered."
@@ -991,33 +983,39 @@ async def show(
991
983
  """
992
984
  )
993
985
  if delegate_selection:
986
+ valid_uids = [str(row[0]) for row in sorted_rows[:max_rows]]
994
987
  while True:
995
988
  selection = Prompt.ask(
996
- "\nEnter the position of the delegate you want to stake to [dim](or press Enter to cancel)[/dim]",
989
+ "\nEnter the Position of the delegate you want to stake to [dim](or press Enter to cancel)[/dim]",
997
990
  default="",
991
+ choices=[""] + valid_uids,
992
+ show_choices=False,
993
+ show_default=False,
998
994
  )
999
995
 
1000
996
  if selection == "":
1001
997
  return None
1002
998
 
1003
- try:
1004
- idx = int(selection)
1005
- if 1 <= idx <= max_rows:
1006
- selected_hotkey = sorted_hks_delegation[idx - 1]
1007
- row_data = sorted_rows[idx - 1]
1008
- identity = "" if row_data[5] == "~" else row_data[5]
1009
- identity_str = f" ({identity})" if identity else ""
1010
- console.print(
1011
- f"\nSelected delegate: [{COLOR_PALETTE['GENERAL']['SUBHEADING']}]{selected_hotkey}{identity_str}"
1012
- )
999
+ position = int(selection)
1000
+ idx = position - 1
1001
+ original_idx = sorted_hotkeys[idx][0]
1002
+ selected_hotkey = root_state.hotkeys[original_idx]
1003
+
1004
+ coldkey_identity = identities.get(
1005
+ root_state.coldkeys[original_idx], {}
1006
+ ).get("name", "")
1007
+ hotkey_identity = old_identities.get(selected_hotkey)
1008
+ validator_identity = (
1009
+ coldkey_identity
1010
+ if coldkey_identity
1011
+ else (hotkey_identity.display if hotkey_identity else "")
1012
+ )
1013
+ identity_str = f" ({validator_identity})" if validator_identity else ""
1013
1014
 
1014
- return selected_hotkey
1015
- else:
1016
- console.print(
1017
- f"[red]Invalid selection. Please enter a number between 1 and {max_rows}[/red]"
1018
- )
1019
- except ValueError:
1020
- console.print("[red]Please enter a valid number[/red]")
1015
+ console.print(
1016
+ f"\nSelected delegate: [{COLOR_PALETTE['GENERAL']['SUBHEADING']}]{selected_hotkey}{identity_str}"
1017
+ )
1018
+ return selected_hotkey
1021
1019
 
1022
1020
  async def show_subnet(netuid_: int):
1023
1021
  if not await subtensor.subnet_exists(netuid=netuid):
@@ -1025,35 +1023,24 @@ async def show(
1025
1023
  raise typer.Exit()
1026
1024
  (
1027
1025
  subnet_info,
1028
- hex_bytes_result,
1026
+ subnet_state,
1029
1027
  identities,
1030
1028
  old_identities,
1031
1029
  ) = await asyncio.gather(
1032
1030
  subtensor.subnet(netuid=netuid_),
1033
- subtensor.query_runtime_api(
1034
- runtime_api="SubnetInfoRuntimeApi",
1035
- method="get_subnet_state",
1036
- params=[netuid_],
1037
- ),
1031
+ subtensor.get_subnet_state(netuid=netuid_),
1038
1032
  subtensor.query_all_identities(),
1039
1033
  subtensor.get_delegate_identities(),
1040
1034
  )
1041
- if subnet_info is None:
1035
+ if subnet_state is None:
1042
1036
  print_error(f"Subnet {netuid_} does not exist")
1043
1037
  raise typer.Exit()
1044
1038
 
1045
- if (bytes_result := hex_bytes_result) is None:
1046
- print_error(f"Subnet {netuid_} does not exist")
1047
- raise typer.Exit()
1048
-
1049
- if bytes_result.startswith("0x"):
1050
- bytes_result = bytes.fromhex(bytes_result[2:])
1051
-
1052
- subnet_state: "SubnetState" = SubnetState.from_vec_u8(bytes_result)
1053
1039
  if subnet_info is None:
1054
1040
  print_error(f"Subnet {netuid_} does not exist")
1055
1041
  raise typer.Exit()
1056
- elif len(subnet_state.hotkeys) == 0:
1042
+
1043
+ if len(subnet_state.hotkeys) == 0:
1057
1044
  print_error(f"Subnet {netuid_} is currently empty with 0 UIDs registered.")
1058
1045
  raise typer.Exit()
1059
1046
 
@@ -1072,10 +1059,6 @@ async def show(
1072
1059
  pad_edge=True,
1073
1060
  )
1074
1061
 
1075
- # Add index for selection if selecting delegates
1076
- if delegate_selection:
1077
- table.add_column("#", style="cyan", justify="right")
1078
-
1079
1062
  # For hotkey_block_emission calculation
1080
1063
  emission_sum = sum(
1081
1064
  [
@@ -1266,8 +1249,6 @@ async def show(
1266
1249
  )
1267
1250
  for pos, row in enumerate(rows, 1):
1268
1251
  table_row = []
1269
- if delegate_selection:
1270
- table_row.append(str(pos))
1271
1252
  table_row.extend(row)
1272
1253
  table.add_row(*table_row)
1273
1254
  if delegate_selection and pos == max_rows:
@@ -1320,20 +1301,24 @@ async def show(
1320
1301
 
1321
1302
  if delegate_selection:
1322
1303
  while True:
1304
+ valid_uids = [str(row[0]) for row in rows[:max_rows]]
1323
1305
  selection = Prompt.ask(
1324
- "\nEnter the number of the delegate you want to stake to [dim](or press Enter to cancel)[/dim]",
1306
+ "\nEnter the UID of the delegate you want to stake to [dim](or press Enter to cancel)[/dim]",
1325
1307
  default="",
1308
+ choices=[""] + valid_uids,
1309
+ show_choices=False,
1310
+ show_default=False,
1326
1311
  )
1327
1312
 
1328
1313
  if selection == "":
1329
1314
  return None
1330
1315
 
1331
1316
  try:
1332
- idx = int(selection)
1333
- if 1 <= idx <= max_rows:
1334
- uid = int(rows[idx - 1][0])
1317
+ uid = int(selection)
1318
+ # Check if the UID exists in the subnet
1319
+ if uid in [int(row[0]) for row in rows]:
1320
+ row_data = next(row for row in rows if int(row[0]) == uid)
1335
1321
  hotkey = subnet_state.hotkeys[uid]
1336
- row_data = rows[idx - 1]
1337
1322
  identity = "" if row_data[9] == "~" else row_data[9]
1338
1323
  identity_str = f" ({identity})" if identity else ""
1339
1324
  console.print(
@@ -1342,7 +1327,7 @@ async def show(
1342
1327
  return hotkey
1343
1328
  else:
1344
1329
  console.print(
1345
- f"[red]Invalid selection. Please enter a number between 1 and {max_rows}[/red]"
1330
+ f"[red]Invalid UID. Please enter a valid UID from the table above[/red]"
1346
1331
  )
1347
1332
  except ValueError:
1348
1333
  console.print("[red]Please enter a valid number[/red]")
@@ -1585,7 +1570,13 @@ async def metagraph_cmd(
1585
1570
  print_error(f"Subnet with netuid: {netuid} does not exist", status)
1586
1571
  return False
1587
1572
 
1588
- neurons, difficulty_, total_issuance_, block = await asyncio.gather(
1573
+ (
1574
+ neurons,
1575
+ difficulty_,
1576
+ total_issuance_,
1577
+ block,
1578
+ subnet_state,
1579
+ ) = await asyncio.gather(
1589
1580
  subtensor.neurons(netuid, block_hash=block_hash),
1590
1581
  subtensor.get_hyperparameter(
1591
1582
  param_name="Difficulty", netuid=netuid, block_hash=block_hash
@@ -1597,22 +1588,9 @@ async def metagraph_cmd(
1597
1588
  block_hash=block_hash,
1598
1589
  ),
1599
1590
  subtensor.substrate.get_block_number(block_hash=block_hash),
1591
+ subtensor.get_subnet_state(netuid=netuid),
1600
1592
  )
1601
1593
 
1602
- hex_bytes_result = await subtensor.query_runtime_api(
1603
- runtime_api="SubnetInfoRuntimeApi",
1604
- method="get_subnet_state",
1605
- params=[netuid],
1606
- )
1607
- if not (bytes_result := hex_bytes_result):
1608
- err_console.print(f"Subnet {netuid} does not exist")
1609
- return
1610
-
1611
- if bytes_result.startswith("0x"):
1612
- bytes_result = bytes.fromhex(bytes_result[2:])
1613
-
1614
- subnet_state: "SubnetState" = SubnetState.from_vec_u8(bytes_result)
1615
-
1616
1594
  difficulty = int(difficulty_)
1617
1595
  total_issuance = Balance.from_rao(total_issuance_)
1618
1596
  metagraph = MiniGraph(
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: bittensor-cli
3
- Version: 8.2.0rc14
3
+ Version: 8.2.0rc15
4
4
  Summary: Bittensor CLI
5
5
  Home-page: https://github.com/opentensor/btcli
6
6
  Author: bittensor.com
@@ -1,14 +1,14 @@
1
- bittensor_cli/__init__.py,sha256=Loe--RajOIR8vCTua14sZsUSnSHLdBA2Mb0hFBSoECQ,1221
2
- bittensor_cli/cli.py,sha256=WsPsMHOWNdqUKgNbXDyr-fgQeO8shn8-xlndWgzNBJ4,170158
1
+ bittensor_cli/__init__.py,sha256=ZYU7KUzCNWfB7qHzWaA9DQN0qXv3gAQ689sTTWJv9RM,1221
2
+ bittensor_cli/cli.py,sha256=Fnz8znP8gSEW81PQDp3krWMad30YKFX3GnXz7czem1Q,170276
3
3
  bittensor_cli/doc_generation_helper.py,sha256=GexqjEIKulWg84hpNBEchJ840oOgOi7DWpt447nsdNI,91
4
4
  bittensor_cli/src/__init__.py,sha256=KprSr1MmKKyh15PYcnA57mbX1svihIXyrtwnUIaUvbk,32042
5
5
  bittensor_cli/src/bittensor/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
6
6
  bittensor_cli/src/bittensor/async_substrate_interface.py,sha256=qetCcD5qlAxeedhQ0cwfHo6QSjohCljJarqyzKpcHFQ,103240
7
7
  bittensor_cli/src/bittensor/balances.py,sha256=1ch3c4Gc3IRgIn8MMfbavQm71n3N_fUH7j9EGM6oH6M,11436
8
- bittensor_cli/src/bittensor/chain_data.py,sha256=zRQdZXERrRxqWXcdS3XgST1bgwcuEn4aGYtK6SbqtVk,59832
8
+ bittensor_cli/src/bittensor/chain_data.py,sha256=WPMzvS8YgIJzMRC1AOba1p3HDTR7zK_l-OoSi6o1cbI,60034
9
9
  bittensor_cli/src/bittensor/minigraph.py,sha256=MCiuLRn9lhGoO1aKrM7YOiQAmANxFRkknwHCcjpn8uw,10499
10
10
  bittensor_cli/src/bittensor/networking.py,sha256=pZLMs8YXpZzDMLXWMBb_Bj6TVkm_q9khyY-lnbwVMuE,462
11
- bittensor_cli/src/bittensor/subtensor_interface.py,sha256=ceB6nwEIDShFEKkHwZ6vGOEC8bNFxBfy3XzkH7izvZs,56357
11
+ bittensor_cli/src/bittensor/subtensor_interface.py,sha256=bF1-ziyWr7Xg8oVRyql9qmpG6TvYqRi_HJHcgSE476k,57384
12
12
  bittensor_cli/src/bittensor/utils.py,sha256=-t51UAbvs2WA6bFe6DxrAN_eINfaMXCud3bnABAjzZE,41421
13
13
  bittensor_cli/src/bittensor/extrinsics/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
14
14
  bittensor_cli/src/bittensor/extrinsics/registration.py,sha256=p_ARqDiniDNL-ZPuswfk_DJW5kl5rMNxL_uRbfVTkTA,64599
@@ -22,12 +22,12 @@ bittensor_cli/src/commands/weights.py,sha256=3BCqVB1-W6BG0U_iOtuUZmFOQ9QngsnXAkB
22
22
  bittensor_cli/src/commands/stake/__init__.py,sha256=kcQE86CfemAw2LoNBHA_FIwixf4VyJ26FT10f0peJEU,6569
23
23
  bittensor_cli/src/commands/stake/children_hotkeys.py,sha256=WTFR0oprtOzMc5x0MXtWm595Bd4yK9iZCymwc3whr0U,28215
24
24
  bittensor_cli/src/commands/stake/move.py,sha256=c0YsQxKcFYJ8Bf6Gg_8_t99QV5RBx_KiuKCkHLc2fZ4,37199
25
- bittensor_cli/src/commands/stake/stake.py,sha256=hCJzZScVeJ4bpGnCnzZcPq7gPpZ3U_qOUKloB7rZfuU,78705
25
+ bittensor_cli/src/commands/stake/stake.py,sha256=L-xi1O82lL2jeLBN3GCjiKnZjDYzZwCvUlp8P7faOAM,78813
26
26
  bittensor_cli/src/commands/subnets/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
27
27
  bittensor_cli/src/commands/subnets/price.py,sha256=TWcRXUFeS_Q-pfyv0YIluAL8SE7d2gzTODK-9M2J5pw,29878
28
- bittensor_cli/src/commands/subnets/subnets.py,sha256=9nMoAjMe7l6gUsd3snk8IU-rwwtFM9Ntw_HWS9uxlkk,80784
29
- bittensor_cli-8.2.0rc14.dist-info/METADATA,sha256=MKLDM6O03vN2ClHMxHEBRyZDlAj0DClN2J2mnuqv0-U,6885
30
- bittensor_cli-8.2.0rc14.dist-info/WHEEL,sha256=tZoeGjtWxWRfdplE7E3d45VPlLNQnvbKiYnx7gwAy8A,92
31
- bittensor_cli-8.2.0rc14.dist-info/entry_points.txt,sha256=hBTLGLbVxmAKy69XSKaUZvjTCmyEzDGZKq4S8UOto8I,49
32
- bittensor_cli-8.2.0rc14.dist-info/top_level.txt,sha256=DvgvXpmTtI_Q1BbDZMlK90LFcGFCreN1daViEPV2iFw,14
33
- bittensor_cli-8.2.0rc14.dist-info/RECORD,,
28
+ bittensor_cli/src/commands/subnets/subnets.py,sha256=g5fsmJlrZFmABMReBg6whu0A4QplBxx5bMsM1himpfo,79808
29
+ bittensor_cli-8.2.0rc15.dist-info/METADATA,sha256=Z8ehWeQw4iUaZbo6-IhFf_SLFMaRayWWB9PKOfHhy5A,6885
30
+ bittensor_cli-8.2.0rc15.dist-info/WHEEL,sha256=tZoeGjtWxWRfdplE7E3d45VPlLNQnvbKiYnx7gwAy8A,92
31
+ bittensor_cli-8.2.0rc15.dist-info/entry_points.txt,sha256=hBTLGLbVxmAKy69XSKaUZvjTCmyEzDGZKq4S8UOto8I,49
32
+ bittensor_cli-8.2.0rc15.dist-info/top_level.txt,sha256=DvgvXpmTtI_Q1BbDZMlK90LFcGFCreN1daViEPV2iFw,14
33
+ bittensor_cli-8.2.0rc15.dist-info/RECORD,,