bittensor-cli 8.4.3__py3-none-any.whl → 9.0.0rc2__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.
Files changed (30) hide show
  1. bittensor_cli/__init__.py +2 -2
  2. bittensor_cli/cli.py +1508 -1385
  3. bittensor_cli/src/__init__.py +627 -197
  4. bittensor_cli/src/bittensor/balances.py +41 -8
  5. bittensor_cli/src/bittensor/chain_data.py +557 -428
  6. bittensor_cli/src/bittensor/extrinsics/registration.py +161 -47
  7. bittensor_cli/src/bittensor/extrinsics/root.py +14 -8
  8. bittensor_cli/src/bittensor/extrinsics/transfer.py +14 -21
  9. bittensor_cli/src/bittensor/minigraph.py +46 -8
  10. bittensor_cli/src/bittensor/subtensor_interface.py +572 -253
  11. bittensor_cli/src/bittensor/utils.py +326 -75
  12. bittensor_cli/src/commands/stake/__init__.py +154 -0
  13. bittensor_cli/src/commands/stake/children_hotkeys.py +121 -87
  14. bittensor_cli/src/commands/stake/move.py +1000 -0
  15. bittensor_cli/src/commands/stake/stake.py +1637 -1264
  16. bittensor_cli/src/commands/subnets/__init__.py +0 -0
  17. bittensor_cli/src/commands/subnets/price.py +867 -0
  18. bittensor_cli/src/commands/subnets/subnets.py +2055 -0
  19. bittensor_cli/src/commands/sudo.py +529 -26
  20. bittensor_cli/src/commands/wallets.py +234 -544
  21. bittensor_cli/src/commands/weights.py +15 -11
  22. {bittensor_cli-8.4.3.dist-info → bittensor_cli-9.0.0rc2.dist-info}/METADATA +7 -4
  23. bittensor_cli-9.0.0rc2.dist-info/RECORD +32 -0
  24. bittensor_cli/src/bittensor/async_substrate_interface.py +0 -2748
  25. bittensor_cli/src/commands/root.py +0 -1752
  26. bittensor_cli/src/commands/subnets.py +0 -897
  27. bittensor_cli-8.4.3.dist-info/RECORD +0 -31
  28. {bittensor_cli-8.4.3.dist-info → bittensor_cli-9.0.0rc2.dist-info}/WHEEL +0 -0
  29. {bittensor_cli-8.4.3.dist-info → bittensor_cli-9.0.0rc2.dist-info}/entry_points.txt +0 -0
  30. {bittensor_cli-8.4.3.dist-info → bittensor_cli-9.0.0rc2.dist-info}/top_level.txt +0 -0
@@ -1,25 +1,59 @@
1
+ from abc import abstractmethod
1
2
  from dataclasses import dataclass
2
- from typing import Optional
3
+ from enum import Enum
4
+ from typing import Optional, Any, Union
3
5
 
4
- import bt_decode
5
6
  import netaddr
6
7
  from scalecodec.utils.ss58 import ss58_encode
7
8
 
8
9
  from bittensor_cli.src.bittensor.balances import Balance
9
10
  from bittensor_cli.src.bittensor.networking import int_to_ip
10
- from bittensor_cli.src.bittensor.utils import SS58_FORMAT, u16_normalized_float
11
-
12
-
13
- def decode_account_id(account_id_bytes: tuple):
14
- # Convert the AccountId bytes to a Base64 string
15
- return ss58_encode(bytes(account_id_bytes).hex(), SS58_FORMAT)
16
-
17
-
18
- def process_stake_data(stake_data):
11
+ from bittensor_cli.src.bittensor.utils import (
12
+ SS58_FORMAT,
13
+ u16_normalized_float,
14
+ decode_account_id,
15
+ )
16
+
17
+
18
+ class ChainDataType(Enum):
19
+ NeuronInfo = 1
20
+ DelegateInfo = 2
21
+ NeuronInfoLite = 3
22
+ StakeInfo = 4
23
+ SubnetHyperparameters = 5
24
+ DelegateInfoLite = 6
25
+ DynamicInfo = 7
26
+ ScheduledColdkeySwapInfo = 8
27
+ SubnetInfo = 9
28
+ SubnetState = 10
29
+ SubnetIdentity = 11
30
+
31
+
32
+ def decode_hex_identity(info_dictionary):
33
+ decoded_info = {}
34
+ for k, v in info_dictionary.items():
35
+ if isinstance(v, dict):
36
+ item = next(iter(v.values()))
37
+ else:
38
+ item = v
39
+
40
+ if isinstance(item, tuple):
41
+ try:
42
+ decoded_info[k] = bytes(item).decode()
43
+ except UnicodeDecodeError:
44
+ print(f"Could not decode: {k}: {item}")
45
+ else:
46
+ decoded_info[k] = item
47
+ return decoded_info
48
+
49
+
50
+ def process_stake_data(stake_data, netuid):
19
51
  decoded_stake_data = {}
20
52
  for account_id_bytes, stake_ in stake_data:
21
53
  account_id = decode_account_id(account_id_bytes)
22
- decoded_stake_data.update({account_id: Balance.from_rao(stake_)})
54
+ decoded_stake_data.update(
55
+ {account_id: Balance.from_rao(stake_).set_unit(netuid)}
56
+ )
23
57
  return decoded_stake_data
24
58
 
25
59
 
@@ -62,14 +96,39 @@ class AxonInfo:
62
96
 
63
97
 
64
98
  @dataclass
65
- class SubnetHyperparameters:
99
+ class InfoBase:
100
+ """Base dataclass for info objects."""
101
+
102
+ @abstractmethod
103
+ def _fix_decoded(self, decoded: Any) -> "InfoBase":
104
+ raise NotImplementedError(
105
+ "This is an abstract method and must be implemented in a subclass."
106
+ )
107
+
108
+ @classmethod
109
+ def from_any(cls, data: Any) -> "InfoBase":
110
+ return cls._fix_decoded(data)
111
+
112
+ @classmethod
113
+ def list_from_any(cls, data_list: list[Any]) -> list["InfoBase"]:
114
+ return [cls.from_any(data) for data in data_list]
115
+
116
+ def __getitem__(self, item):
117
+ return getattr(self, item)
118
+
119
+ def get(self, item, default=None):
120
+ return getattr(self, item, default)
121
+
122
+
123
+ @dataclass
124
+ class SubnetHyperparameters(InfoBase):
66
125
  """Dataclass for subnet hyperparameters."""
67
126
 
68
127
  rho: int
69
128
  kappa: int
70
129
  immunity_period: int
71
130
  min_allowed_weights: int
72
- max_weight_limit: float
131
+ max_weights_limit: float
73
132
  tempo: int
74
133
  min_difficulty: int
75
134
  max_difficulty: int
@@ -87,90 +146,78 @@ class SubnetHyperparameters:
87
146
  max_validators: int
88
147
  adjustment_alpha: int
89
148
  difficulty: int
90
- commit_reveal_weights_interval: int
149
+ commit_reveal_period: int
91
150
  commit_reveal_weights_enabled: bool
92
151
  alpha_high: int
93
152
  alpha_low: int
94
153
  liquid_alpha_enabled: bool
95
154
 
96
155
  @classmethod
97
- def from_vec_u8(cls, vec_u8: bytes) -> Optional["SubnetHyperparameters"]:
98
- decoded = bt_decode.SubnetHyperparameters.decode(vec_u8)
156
+ def _fix_decoded(
157
+ cls, decoded: Union[dict, "SubnetHyperparameters"]
158
+ ) -> "SubnetHyperparameters":
99
159
  return SubnetHyperparameters(
100
- rho=decoded.rho,
101
- kappa=decoded.kappa,
102
- immunity_period=decoded.immunity_period,
103
- min_allowed_weights=decoded.min_allowed_weights,
104
- max_weight_limit=decoded.max_weights_limit,
105
- tempo=decoded.tempo,
106
- min_difficulty=decoded.min_difficulty,
107
- max_difficulty=decoded.max_difficulty,
108
- weights_version=decoded.weights_version,
109
- weights_rate_limit=decoded.weights_rate_limit,
110
- adjustment_interval=decoded.adjustment_interval,
111
- activity_cutoff=decoded.activity_cutoff,
112
- registration_allowed=decoded.registration_allowed,
113
- target_regs_per_interval=decoded.target_regs_per_interval,
114
- min_burn=decoded.min_burn,
115
- max_burn=decoded.max_burn,
116
- bonds_moving_avg=decoded.bonds_moving_avg,
117
- max_regs_per_block=decoded.max_regs_per_block,
118
- serving_rate_limit=decoded.serving_rate_limit,
119
- max_validators=decoded.max_validators,
120
- adjustment_alpha=decoded.adjustment_alpha,
121
- difficulty=decoded.difficulty,
122
- commit_reveal_weights_interval=decoded.commit_reveal_weights_interval,
123
- commit_reveal_weights_enabled=decoded.commit_reveal_weights_enabled,
124
- alpha_high=decoded.alpha_high,
125
- alpha_low=decoded.alpha_low,
126
- liquid_alpha_enabled=decoded.liquid_alpha_enabled,
160
+ rho=decoded.get("rho"),
161
+ kappa=decoded.get("kappa"),
162
+ immunity_period=decoded.get("immunity_period"),
163
+ min_allowed_weights=decoded.get("min_allowed_weights"),
164
+ max_weights_limit=decoded.get("max_weights_limit"),
165
+ tempo=decoded.get("tempo"),
166
+ min_difficulty=decoded.get("min_difficulty"),
167
+ max_difficulty=decoded.get("max_difficulty"),
168
+ weights_version=decoded.get("weights_version"),
169
+ weights_rate_limit=decoded.get("weights_rate_limit"),
170
+ adjustment_interval=decoded.get("adjustment_interval"),
171
+ activity_cutoff=decoded.get("activity_cutoff"),
172
+ registration_allowed=decoded.get("registration_allowed"),
173
+ target_regs_per_interval=decoded.get("target_regs_per_interval"),
174
+ min_burn=decoded.get("min_burn"),
175
+ max_burn=decoded.get("max_burn"),
176
+ bonds_moving_avg=decoded.get("bonds_moving_avg"),
177
+ max_regs_per_block=decoded.get("max_regs_per_block"),
178
+ serving_rate_limit=decoded.get("serving_rate_limit"),
179
+ max_validators=decoded.get("max_validators"),
180
+ adjustment_alpha=decoded.get("adjustment_alpha"),
181
+ difficulty=decoded.get("difficulty"),
182
+ commit_reveal_period=decoded.get("commit_reveal_period"),
183
+ commit_reveal_weights_enabled=decoded.get("commit_reveal_weights_enabled"),
184
+ alpha_high=decoded.get("alpha_high"),
185
+ alpha_low=decoded.get("alpha_low"),
186
+ liquid_alpha_enabled=decoded.get("liquid_alpha_enabled"),
127
187
  )
128
188
 
129
189
 
130
190
  @dataclass
131
- class StakeInfo:
191
+ class StakeInfo(InfoBase):
132
192
  """Dataclass for stake info."""
133
193
 
134
194
  hotkey_ss58: str # Hotkey address
135
195
  coldkey_ss58: str # Coldkey address
196
+ netuid: int
136
197
  stake: Balance # Stake for the hotkey-coldkey pair
198
+ locked: Balance # Stake which is locked.
199
+ emission: Balance # Emission for the hotkey-coldkey pair
200
+ drain: int
201
+ is_registered: bool
137
202
 
138
203
  @classmethod
139
- def list_from_vec_u8(cls, vec_u8: bytes) -> list["StakeInfo"]:
140
- """
141
- Returns a list of StakeInfo objects from a `vec_u8`.
142
- """
143
- decoded = bt_decode.StakeInfo.decode_vec(vec_u8)
144
- results = []
145
- for d in decoded:
146
- hotkey = decode_account_id(d.hotkey)
147
- coldkey = decode_account_id(d.coldkey)
148
- stake = Balance.from_rao(d.stake)
149
- results.append(StakeInfo(hotkey, coldkey, stake))
150
-
151
- return results
152
-
153
-
154
- @dataclass
155
- class PrometheusInfo:
156
- """Dataclass for prometheus info."""
157
-
158
- block: int
159
- version: int
160
- ip: str
161
- port: int
162
- ip_type: int
163
-
164
- @classmethod
165
- def fix_decoded_values(cls, prometheus_info_decoded: dict) -> "PrometheusInfo":
166
- """Returns a PrometheusInfo object from a prometheus_info_decoded dictionary."""
167
- prometheus_info_decoded["ip"] = int_to_ip(int(prometheus_info_decoded["ip"]))
168
-
169
- return cls(**prometheus_info_decoded)
204
+ def _fix_decoded(cls, decoded: Any) -> "StakeInfo":
205
+ hotkey = decode_account_id(decoded.get("hotkey"))
206
+ coldkey = decode_account_id(decoded.get("coldkey"))
207
+ netuid = int(decoded.get("netuid"))
208
+ stake = Balance.from_rao(decoded.get("stake")).set_unit(netuid)
209
+ locked = Balance.from_rao(decoded.get("locked")).set_unit(netuid)
210
+ emission = Balance.from_rao(decoded.get("emission")).set_unit(netuid)
211
+ drain = int(decoded.get("drain"))
212
+ is_registered = bool(decoded.get("is_registered"))
213
+
214
+ return StakeInfo(
215
+ hotkey, coldkey, netuid, stake, locked, emission, drain, is_registered
216
+ )
170
217
 
171
218
 
172
219
  @dataclass
173
- class NeuronInfo:
220
+ class NeuronInfo(InfoBase):
174
221
  """Dataclass for neuron metadata."""
175
222
 
176
223
  hotkey: str
@@ -194,7 +241,6 @@ class NeuronInfo:
194
241
  weights: list[list[int]]
195
242
  bonds: list[list[int]]
196
243
  pruning_score: int
197
- prometheus_info: Optional["PrometheusInfo"] = None
198
244
  axon_info: Optional[AxonInfo] = None
199
245
  is_null: bool = False
200
246
 
@@ -231,7 +277,6 @@ class NeuronInfo:
231
277
  validator_permit=False,
232
278
  weights=[],
233
279
  bonds=[],
234
- prometheus_info=None,
235
280
  axon_info=None,
236
281
  is_null=True,
237
282
  coldkey="000000000000000000000000000000000000000000000000",
@@ -241,49 +286,42 @@ class NeuronInfo:
241
286
  return neuron
242
287
 
243
288
  @classmethod
244
- def from_vec_u8(cls, vec_u8: bytes) -> "NeuronInfo":
245
- n = bt_decode.NeuronInfo.decode(vec_u8)
246
- stake_dict = process_stake_data(n.stake)
289
+ def _fix_decoded(cls, decoded: Any) -> "NeuronInfo":
290
+ netuid = decoded.get("netuid")
291
+ stake_dict = process_stake_data(decoded.get("stake"), netuid=netuid)
247
292
  total_stake = sum(stake_dict.values()) if stake_dict else Balance(0)
248
- axon_info = n.axon_info
249
- coldkey = decode_account_id(n.coldkey)
250
- hotkey = decode_account_id(n.hotkey)
293
+ axon_info = decoded.get("axon_info", {})
294
+ coldkey = decode_account_id(decoded.get("coldkey"))
295
+ hotkey = decode_account_id(decoded.get("hotkey"))
251
296
  return NeuronInfo(
252
297
  hotkey=hotkey,
253
298
  coldkey=coldkey,
254
- uid=n.uid,
255
- netuid=n.netuid,
256
- active=n.active,
299
+ uid=decoded.get("uid"),
300
+ netuid=netuid,
301
+ active=decoded.get("active"),
257
302
  stake=total_stake,
258
303
  stake_dict=stake_dict,
259
304
  total_stake=total_stake,
260
- rank=u16_normalized_float(n.rank),
261
- emission=n.emission / 1e9,
262
- incentive=u16_normalized_float(n.incentive),
263
- consensus=u16_normalized_float(n.consensus),
264
- trust=u16_normalized_float(n.trust),
265
- validator_trust=u16_normalized_float(n.validator_trust),
266
- dividends=u16_normalized_float(n.dividends),
267
- last_update=n.last_update,
268
- validator_permit=n.validator_permit,
269
- weights=[[e[0], e[1]] for e in n.weights],
270
- bonds=[[e[0], e[1]] for e in n.bonds],
271
- pruning_score=n.pruning_score,
272
- prometheus_info=PrometheusInfo(
273
- block=n.prometheus_info.block,
274
- version=n.prometheus_info.version,
275
- ip=str(netaddr.IPAddress(n.prometheus_info.ip)),
276
- port=n.prometheus_info.port,
277
- ip_type=n.prometheus_info.ip_type,
278
- ),
305
+ rank=u16_normalized_float(decoded.get("rank")),
306
+ emission=decoded.get("emission") / 1e9,
307
+ incentive=u16_normalized_float(decoded.get("incentive")),
308
+ consensus=u16_normalized_float(decoded.get("consensus")),
309
+ trust=u16_normalized_float(decoded.get("trust")),
310
+ validator_trust=u16_normalized_float(decoded.get("validator_trust")),
311
+ dividends=u16_normalized_float(decoded.get("dividends")),
312
+ last_update=decoded.get("last_update"),
313
+ validator_permit=decoded.get("validator_permit"),
314
+ weights=[[e[0], e[1]] for e in decoded.get("weights")],
315
+ bonds=[[e[0], e[1]] for e in decoded.get("bonds")],
316
+ pruning_score=decoded.get("pruning_score"),
279
317
  axon_info=AxonInfo(
280
- version=axon_info.version,
281
- ip=str(netaddr.IPAddress(axon_info.ip)),
282
- port=axon_info.port,
283
- ip_type=axon_info.ip_type,
284
- placeholder1=axon_info.placeholder1,
285
- placeholder2=axon_info.placeholder2,
286
- protocol=axon_info.protocol,
318
+ version=axon_info.get("version"),
319
+ ip=str(netaddr.IPAddress(axon_info.get("ip"))),
320
+ port=axon_info.get("port"),
321
+ ip_type=axon_info.get("ip_type"),
322
+ placeholder1=axon_info.get("placeholder1"),
323
+ placeholder2=axon_info.get("placeholder2"),
324
+ protocol=axon_info.get("protocol"),
287
325
  hotkey=hotkey,
288
326
  coldkey=coldkey,
289
327
  ),
@@ -292,7 +330,7 @@ class NeuronInfo:
292
330
 
293
331
 
294
332
  @dataclass
295
- class NeuronInfoLite:
333
+ class NeuronInfoLite(InfoBase):
296
334
  """Dataclass for neuron metadata, but without the weights and bonds."""
297
335
 
298
336
  hotkey: str
@@ -313,7 +351,6 @@ class NeuronInfoLite:
313
351
  dividends: float
314
352
  last_update: int
315
353
  validator_permit: bool
316
- prometheus_info: Optional["PrometheusInfo"]
317
354
  axon_info: AxonInfo
318
355
  pruning_score: int
319
356
  is_null: bool = False
@@ -336,7 +373,6 @@ class NeuronInfoLite:
336
373
  dividends=0,
337
374
  last_update=0,
338
375
  validator_permit=False,
339
- prometheus_info=None,
340
376
  axon_info=None,
341
377
  is_null=True,
342
378
  coldkey="000000000000000000000000000000000000000000000000",
@@ -346,74 +382,63 @@ class NeuronInfoLite:
346
382
  return neuron
347
383
 
348
384
  @classmethod
349
- def list_from_vec_u8(cls, vec_u8: bytes) -> list["NeuronInfoLite"]:
350
- decoded = bt_decode.NeuronInfoLite.decode_vec(vec_u8)
351
- results = []
352
- for item in decoded:
353
- active = item.active
354
- axon_info = item.axon_info
355
- coldkey = decode_account_id(item.coldkey)
356
- consensus = item.consensus
357
- dividends = item.dividends
358
- emission = item.emission
359
- hotkey = decode_account_id(item.hotkey)
360
- incentive = item.incentive
361
- last_update = item.last_update
362
- netuid = item.netuid
363
- prometheus_info = item.prometheus_info
364
- pruning_score = item.pruning_score
365
- rank = item.rank
366
- stake_dict = process_stake_data(item.stake)
367
- stake = sum(stake_dict.values()) if stake_dict else Balance(0)
368
- trust = item.trust
369
- uid = item.uid
370
- validator_permit = item.validator_permit
371
- validator_trust = item.validator_trust
372
- results.append(
373
- NeuronInfoLite(
374
- active=active,
375
- axon_info=AxonInfo(
376
- version=axon_info.version,
377
- ip=str(netaddr.IPAddress(axon_info.ip)),
378
- port=axon_info.port,
379
- ip_type=axon_info.ip_type,
380
- placeholder1=axon_info.placeholder1,
381
- placeholder2=axon_info.placeholder2,
382
- protocol=axon_info.protocol,
383
- hotkey=hotkey,
384
- coldkey=coldkey,
385
- ),
386
- coldkey=coldkey,
387
- consensus=u16_normalized_float(consensus),
388
- dividends=u16_normalized_float(dividends),
389
- emission=emission / 1e9,
390
- hotkey=hotkey,
391
- incentive=u16_normalized_float(incentive),
392
- last_update=last_update,
393
- netuid=netuid,
394
- prometheus_info=PrometheusInfo(
395
- version=prometheus_info.version,
396
- ip=str(netaddr.IPAddress(prometheus_info.ip)),
397
- port=prometheus_info.port,
398
- ip_type=prometheus_info.ip_type,
399
- block=prometheus_info.block,
400
- ),
401
- pruning_score=pruning_score,
402
- rank=u16_normalized_float(rank),
403
- stake_dict=stake_dict,
404
- stake=stake,
405
- total_stake=stake,
406
- trust=u16_normalized_float(trust),
407
- uid=uid,
408
- validator_permit=validator_permit,
409
- validator_trust=u16_normalized_float(validator_trust),
410
- )
411
- )
412
- return results
385
+ def _fix_decoded(cls, decoded: Union[dict, "NeuronInfoLite"]) -> "NeuronInfoLite":
386
+ active = decoded.get("active")
387
+ axon_info = decoded.get("axon_info", {})
388
+ coldkey = decode_account_id(decoded.get("coldkey"))
389
+ consensus = decoded.get("consensus")
390
+ dividends = decoded.get("dividends")
391
+ emission = decoded.get("emission")
392
+ hotkey = decode_account_id(decoded.get("hotkey"))
393
+ incentive = decoded.get("incentive")
394
+ last_update = decoded.get("last_update")
395
+ netuid = decoded.get("netuid")
396
+ pruning_score = decoded.get("pruning_score")
397
+ rank = decoded.get("rank")
398
+ stake_dict = process_stake_data(decoded.get("stake"), netuid)
399
+ stake = sum(stake_dict.values()) if stake_dict else Balance(0)
400
+ trust = decoded.get("trust")
401
+ uid = decoded.get("uid")
402
+ validator_permit = decoded.get("validator_permit")
403
+ validator_trust = decoded.get("validator_trust")
404
+
405
+ neuron = cls(
406
+ active=active,
407
+ axon_info=AxonInfo(
408
+ version=axon_info.get("version"),
409
+ ip=str(netaddr.IPAddress(axon_info.get("ip"))),
410
+ port=axon_info.get("port"),
411
+ ip_type=axon_info.get("ip_type"),
412
+ placeholder1=axon_info.get("placeholder1"),
413
+ placeholder2=axon_info.get("placeholder2"),
414
+ protocol=axon_info.get("protocol"),
415
+ hotkey=hotkey,
416
+ coldkey=coldkey,
417
+ ),
418
+ coldkey=coldkey,
419
+ consensus=u16_normalized_float(consensus),
420
+ dividends=u16_normalized_float(dividends),
421
+ emission=emission / 1e9,
422
+ hotkey=hotkey,
423
+ incentive=u16_normalized_float(incentive),
424
+ last_update=last_update,
425
+ netuid=netuid,
426
+ pruning_score=pruning_score,
427
+ rank=u16_normalized_float(rank),
428
+ stake_dict=stake_dict,
429
+ stake=stake,
430
+ total_stake=stake,
431
+ trust=u16_normalized_float(trust),
432
+ uid=uid,
433
+ validator_permit=validator_permit,
434
+ validator_trust=u16_normalized_float(validator_trust),
435
+ )
436
+
437
+ return neuron
413
438
 
414
439
 
415
440
  @dataclass
416
- class DelegateInfo:
441
+ class DelegateInfo(InfoBase):
417
442
  """
418
443
  Dataclass for delegate information. For a lighter version of this class, see :func:`DelegateInfoLite`.
419
444
 
@@ -444,80 +469,69 @@ class DelegateInfo:
444
469
  total_daily_return: Balance # Total daily return of the delegate
445
470
 
446
471
  @classmethod
447
- def from_vec_u8(cls, vec_u8: bytes) -> Optional["DelegateInfo"]:
448
- decoded = bt_decode.DelegateInfo.decode(vec_u8)
449
- hotkey = decode_account_id(decoded.delegate_ss58)
450
- owner = decode_account_id(decoded.owner_ss58)
472
+ def _fix_decoded(cls, decoded: "DelegateInfo") -> "DelegateInfo":
473
+ hotkey = decode_account_id(decoded.get("hotkey_ss58"))
474
+ owner = decode_account_id(decoded.get("owner_ss58"))
451
475
  nominators = [
452
- (decode_account_id(x), Balance.from_rao(y)) for x, y in decoded.nominators
476
+ (decode_account_id(x), Balance.from_rao(y))
477
+ for x, y in decoded.get("nominators")
453
478
  ]
454
479
  total_stake = sum((x[1] for x in nominators)) if nominators else Balance(0)
455
- return DelegateInfo(
480
+ return cls(
456
481
  hotkey_ss58=hotkey,
457
482
  total_stake=total_stake,
458
483
  nominators=nominators,
459
484
  owner_ss58=owner,
460
- take=u16_normalized_float(decoded.take),
461
- validator_permits=decoded.validator_permits,
462
- registrations=decoded.registrations,
463
- return_per_1000=Balance.from_rao(decoded.return_per_1000),
464
- total_daily_return=Balance.from_rao(decoded.total_daily_return),
485
+ take=u16_normalized_float(decoded.get("take")),
486
+ validator_permits=decoded.get("validator_permits"),
487
+ registrations=decoded.get("registrations"),
488
+ return_per_1000=Balance.from_rao(decoded.get("return_per_1000")),
489
+ total_daily_return=Balance.from_rao(decoded.get("total_daily_return")),
465
490
  )
466
491
 
467
- @classmethod
468
- def list_from_vec_u8(cls, vec_u8: bytes) -> list["DelegateInfo"]:
469
- decoded = bt_decode.DelegateInfo.decode_vec(vec_u8)
470
- results = []
471
- for d in decoded:
472
- hotkey = decode_account_id(d.delegate_ss58)
473
- owner = decode_account_id(d.owner_ss58)
474
- nominators = [
475
- (decode_account_id(x), Balance.from_rao(y)) for x, y in d.nominators
476
- ]
477
- total_stake = sum((x[1] for x in nominators)) if nominators else Balance(0)
478
- results.append(
479
- DelegateInfo(
480
- hotkey_ss58=hotkey,
481
- total_stake=total_stake,
482
- nominators=nominators,
483
- owner_ss58=owner,
484
- take=u16_normalized_float(d.take),
485
- validator_permits=d.validator_permits,
486
- registrations=d.registrations,
487
- return_per_1000=Balance.from_rao(d.return_per_1000),
488
- total_daily_return=Balance.from_rao(d.total_daily_return),
489
- )
490
- )
491
- return results
492
+
493
+ @dataclass
494
+ class DelegateInfoLite(InfoBase):
495
+ """
496
+ Dataclass for light delegate information.
497
+
498
+ Args:
499
+ hotkey_ss58 (str): Hotkey of the delegate for which the information is being fetched.
500
+ owner_ss58 (str): Coldkey of the owner.
501
+ total_stake (int): Total stake of the delegate.
502
+ owner_stake (int): Own stake of the delegate.
503
+ take (float): Take of the delegate as a percentage. None if custom
504
+ """
505
+
506
+ hotkey_ss58: str # Hotkey of delegate
507
+ owner_ss58: str # Coldkey of owner
508
+ take: Optional[float]
509
+ total_stake: Balance # Total stake of the delegate
510
+ previous_total_stake: Optional[Balance] # Total stake of the delegate
511
+ owner_stake: Balance # Own stake of the delegate
492
512
 
493
513
  @classmethod
494
- def delegated_list_from_vec_u8(
495
- cls, vec_u8: bytes
496
- ) -> list[tuple["DelegateInfo", Balance]]:
497
- decoded = bt_decode.DelegateInfo.decode_delegated(vec_u8)
498
- results = []
499
- for d, b in decoded:
500
- nominators = [
501
- (decode_account_id(x), Balance.from_rao(y)) for x, y in d.nominators
502
- ]
503
- total_stake = sum((x[1] for x in nominators)) if nominators else Balance(0)
504
- delegate = DelegateInfo(
505
- hotkey_ss58=decode_account_id(d.delegate_ss58),
506
- total_stake=total_stake,
507
- nominators=nominators,
508
- owner_ss58=decode_account_id(d.owner_ss58),
509
- take=u16_normalized_float(d.take),
510
- validator_permits=d.validator_permits,
511
- registrations=d.registrations,
512
- return_per_1000=Balance.from_rao(d.return_per_1000),
513
- total_daily_return=Balance.from_rao(d.total_daily_return),
514
- )
515
- results.append((delegate, Balance.from_rao(b)))
516
- return results
514
+ def _fix_decoded(cls, decoded: Any) -> "DelegateInfoLite":
515
+ """Fixes the decoded values."""
516
+ decoded_take = decoded.get("take")
517
+
518
+ if decoded_take == 65535:
519
+ fixed_take = None
520
+ else:
521
+ fixed_take = u16_normalized_float(decoded_take)
522
+
523
+ return cls(
524
+ hotkey_ss58=ss58_encode(decoded.get("delegate_ss58"), SS58_FORMAT),
525
+ owner_ss58=ss58_encode(decoded.get("owner_ss58"), SS58_FORMAT),
526
+ take=fixed_take,
527
+ total_stake=Balance.from_rao(decoded.get("total_stake")),
528
+ owner_stake=Balance.from_rao(decoded.get("owner_stake")),
529
+ previous_total_stake=None,
530
+ )
517
531
 
518
532
 
519
533
  @dataclass
520
- class SubnetInfo:
534
+ class SubnetInfo(InfoBase):
521
535
  """Dataclass for subnet info."""
522
536
 
523
537
  netuid: int
@@ -527,7 +541,7 @@ class SubnetInfo:
527
541
  immunity_period: int
528
542
  max_allowed_validators: int
529
543
  min_allowed_weights: int
530
- max_weight_limit: float
544
+ max_weights_limit: float
531
545
  scaling_law_power: float
532
546
  subnetwork_n: int
533
547
  max_n: int
@@ -540,193 +554,308 @@ class SubnetInfo:
540
554
  owner_ss58: str
541
555
 
542
556
  @classmethod
543
- def list_from_vec_u8(cls, vec_u8: bytes) -> list["SubnetInfo"]:
544
- decoded = bt_decode.SubnetInfo.decode_vec_option(vec_u8)
545
- result = []
546
- for d in decoded:
547
- result.append(
548
- SubnetInfo(
549
- netuid=d.netuid,
550
- rho=d.rho,
551
- kappa=d.kappa,
552
- difficulty=d.difficulty,
553
- immunity_period=d.immunity_period,
554
- max_allowed_validators=d.max_allowed_validators,
555
- min_allowed_weights=d.min_allowed_weights,
556
- max_weight_limit=d.max_weights_limit,
557
- scaling_law_power=d.scaling_law_power,
558
- subnetwork_n=d.subnetwork_n,
559
- max_n=d.max_allowed_uids,
560
- blocks_since_epoch=d.blocks_since_last_step,
561
- tempo=d.tempo,
562
- modality=d.network_modality,
563
- connection_requirements={
564
- str(int(netuid)): u16_normalized_float(int(req))
565
- for (netuid, req) in d.network_connect
566
- },
567
- emission_value=d.emission_values,
568
- burn=Balance.from_rao(d.burn),
569
- owner_ss58=decode_account_id(d.owner),
570
- )
571
- )
572
- return result
573
-
574
-
575
- custom_rpc_type_registry = {
576
- "types": {
577
- "SubnetInfo": {
578
- "type": "struct",
579
- "type_mapping": [
580
- ["netuid", "Compact<u16>"],
581
- ["rho", "Compact<u16>"],
582
- ["kappa", "Compact<u16>"],
583
- ["difficulty", "Compact<u64>"],
584
- ["immunity_period", "Compact<u16>"],
585
- ["max_allowed_validators", "Compact<u16>"],
586
- ["min_allowed_weights", "Compact<u16>"],
587
- ["max_weights_limit", "Compact<u16>"],
588
- ["scaling_law_power", "Compact<u16>"],
589
- ["subnetwork_n", "Compact<u16>"],
590
- ["max_allowed_uids", "Compact<u16>"],
591
- ["blocks_since_last_step", "Compact<u64>"],
592
- ["tempo", "Compact<u16>"],
593
- ["network_modality", "Compact<u16>"],
594
- ["network_connect", "Vec<[u16; 2]>"],
595
- ["emission_values", "Compact<u64>"],
596
- ["burn", "Compact<u64>"],
597
- ["owner", "AccountId"],
598
- ],
599
- },
600
- "DelegateInfo": {
601
- "type": "struct",
602
- "type_mapping": [
603
- ["delegate_ss58", "AccountId"],
604
- ["take", "Compact<u16>"],
605
- ["nominators", "Vec<(AccountId, Compact<u64>)>"],
606
- ["owner_ss58", "AccountId"],
607
- ["registrations", "Vec<Compact<u16>>"],
608
- ["validator_permits", "Vec<Compact<u16>>"],
609
- ["return_per_1000", "Compact<u64>"],
610
- ["total_daily_return", "Compact<u64>"],
611
- ],
612
- },
613
- "NeuronInfo": {
614
- "type": "struct",
615
- "type_mapping": [
616
- ["hotkey", "AccountId"],
617
- ["coldkey", "AccountId"],
618
- ["uid", "Compact<u16>"],
619
- ["netuid", "Compact<u16>"],
620
- ["active", "bool"],
621
- ["axon_info", "axon_info"],
622
- ["prometheus_info", "PrometheusInfo"],
623
- ["stake", "Vec<(AccountId, Compact<u64>)>"],
624
- ["rank", "Compact<u16>"],
625
- ["emission", "Compact<u64>"],
626
- ["incentive", "Compact<u16>"],
627
- ["consensus", "Compact<u16>"],
628
- ["trust", "Compact<u16>"],
629
- ["validator_trust", "Compact<u16>"],
630
- ["dividends", "Compact<u16>"],
631
- ["last_update", "Compact<u64>"],
632
- ["validator_permit", "bool"],
633
- ["weights", "Vec<(Compact<u16>, Compact<u16>)>"],
634
- ["bonds", "Vec<(Compact<u16>, Compact<u16>)>"],
635
- ["pruning_score", "Compact<u16>"],
636
- ],
637
- },
638
- "NeuronInfoLite": {
639
- "type": "struct",
640
- "type_mapping": [
641
- ["hotkey", "AccountId"],
642
- ["coldkey", "AccountId"],
643
- ["uid", "Compact<u16>"],
644
- ["netuid", "Compact<u16>"],
645
- ["active", "bool"],
646
- ["axon_info", "axon_info"],
647
- ["prometheus_info", "PrometheusInfo"],
648
- ["stake", "Vec<(AccountId, Compact<u64>)>"],
649
- ["rank", "Compact<u16>"],
650
- ["emission", "Compact<u64>"],
651
- ["incentive", "Compact<u16>"],
652
- ["consensus", "Compact<u16>"],
653
- ["trust", "Compact<u16>"],
654
- ["validator_trust", "Compact<u16>"],
655
- ["dividends", "Compact<u16>"],
656
- ["last_update", "Compact<u64>"],
657
- ["validator_permit", "bool"],
658
- ["pruning_score", "Compact<u16>"],
659
- ],
660
- },
661
- "axon_info": {
662
- "type": "struct",
663
- "type_mapping": [
664
- ["block", "u64"],
665
- ["version", "u32"],
666
- ["ip", "u128"],
667
- ["port", "u16"],
668
- ["ip_type", "u8"],
669
- ["protocol", "u8"],
670
- ["placeholder1", "u8"],
671
- ["placeholder2", "u8"],
557
+ def _fix_decoded(cls, decoded: "SubnetInfo") -> "SubnetInfo":
558
+ return SubnetInfo(
559
+ netuid=decoded.get("netuid"),
560
+ rho=decoded.get("rho"),
561
+ kappa=decoded.get("kappa"),
562
+ difficulty=decoded.get("difficulty"),
563
+ immunity_period=decoded.get("immunity_period"),
564
+ max_allowed_validators=decoded.get("max_allowed_validators"),
565
+ min_allowed_weights=decoded.get("min_allowed_weights"),
566
+ max_weights_limit=decoded.get("max_weights_limit"),
567
+ scaling_law_power=decoded.get("scaling_law_power"),
568
+ subnetwork_n=decoded.get("subnetwork_n"),
569
+ max_n=decoded.get("max_allowed_uids"),
570
+ blocks_since_epoch=decoded.get("blocks_since_last_step"),
571
+ tempo=decoded.get("tempo"),
572
+ modality=decoded.get("network_modality"),
573
+ connection_requirements={
574
+ str(int(netuid)): u16_normalized_float(int(req))
575
+ for (netuid, req) in decoded.get("network_connect")
576
+ },
577
+ emission_value=decoded.get("emission_value"),
578
+ burn=Balance.from_rao(decoded.get("burn")),
579
+ owner_ss58=decode_account_id(decoded.get("owner")),
580
+ )
581
+
582
+
583
+ @dataclass
584
+ class SubnetIdentity(InfoBase):
585
+ """Dataclass for subnet identity information."""
586
+
587
+ subnet_name: str
588
+ github_repo: str
589
+ subnet_contact: str
590
+ subnet_url: str
591
+ discord: str
592
+ description: str
593
+ additional: str
594
+
595
+ @classmethod
596
+ def _fix_decoded(cls, decoded: dict) -> "SubnetIdentity":
597
+ return SubnetIdentity(
598
+ subnet_name=bytes(decoded["subnet_name"]).decode(),
599
+ github_repo=bytes(decoded["github_repo"]).decode(),
600
+ subnet_contact=bytes(decoded["subnet_contact"]).decode(),
601
+ subnet_url=bytes(decoded["subnet_url"]).decode(),
602
+ discord=bytes(decoded["discord"]).decode(),
603
+ description=bytes(decoded["description"]).decode(),
604
+ additional=bytes(decoded["additional"]).decode(),
605
+ )
606
+
607
+
608
+ @dataclass
609
+ class DynamicInfo(InfoBase):
610
+ netuid: int
611
+ owner_hotkey: str
612
+ owner_coldkey: str
613
+ subnet_name: str
614
+ symbol: str
615
+ tempo: int
616
+ last_step: int
617
+ blocks_since_last_step: int
618
+ emission: Balance
619
+ alpha_in: Balance
620
+ alpha_out: Balance
621
+ tao_in: Balance
622
+ price: Balance
623
+ k: float
624
+ is_dynamic: bool
625
+ alpha_out_emission: Balance
626
+ alpha_in_emission: Balance
627
+ tao_in_emission: Balance
628
+ pending_alpha_emission: Balance
629
+ pending_root_emission: Balance
630
+ network_registered_at: int
631
+ subnet_identity: Optional[SubnetIdentity]
632
+ subnet_volume: Balance
633
+
634
+ @classmethod
635
+ def _fix_decoded(cls, decoded: Any) -> "DynamicInfo":
636
+ """Returns a DynamicInfo object from a decoded DynamicInfo dictionary."""
637
+
638
+ netuid = int(decoded.get("netuid"))
639
+ symbol = bytes([int(b) for b in decoded.get("token_symbol")]).decode()
640
+ subnet_name = bytes([int(b) for b in decoded.get("subnet_name")]).decode()
641
+ is_dynamic = True if netuid > 0 else False # Patching for netuid 0
642
+
643
+ owner_hotkey = decode_account_id(decoded.get("owner_hotkey"))
644
+ owner_coldkey = decode_account_id(decoded.get("owner_coldkey"))
645
+
646
+ emission = Balance.from_rao(decoded.get("emission")).set_unit(0)
647
+ alpha_in = Balance.from_rao(decoded.get("alpha_in")).set_unit(netuid)
648
+ alpha_out = Balance.from_rao(decoded.get("alpha_out")).set_unit(netuid)
649
+ tao_in = Balance.from_rao(decoded.get("tao_in")).set_unit(0)
650
+ alpha_out_emission = Balance.from_rao(
651
+ decoded.get("alpha_out_emission")
652
+ ).set_unit(netuid)
653
+ alpha_in_emission = Balance.from_rao(decoded.get("alpha_in_emission")).set_unit(
654
+ netuid
655
+ )
656
+ subnet_volume = Balance.from_rao(decoded.get("subnet_volume")).set_unit(netuid)
657
+ tao_in_emission = Balance.from_rao(decoded.get("tao_in_emission")).set_unit(0)
658
+ pending_alpha_emission = Balance.from_rao(
659
+ decoded.get("pending_alpha_emission")
660
+ ).set_unit(netuid)
661
+ pending_root_emission = Balance.from_rao(
662
+ decoded.get("pending_root_emission")
663
+ ).set_unit(0)
664
+ price = (
665
+ Balance.from_tao(1.0)
666
+ if netuid == 0
667
+ else Balance.from_tao(tao_in.tao / alpha_in.tao)
668
+ if alpha_in.tao > 0
669
+ else Balance.from_tao(1)
670
+ ) # TODO: Patching this temporarily for netuid 0
671
+
672
+ if decoded.get("subnet_identity"):
673
+ subnet_identity = SubnetIdentity.from_any(decoded.get("subnet_identity"))
674
+ else:
675
+ subnet_identity = None
676
+
677
+ return cls(
678
+ netuid=netuid,
679
+ owner_hotkey=owner_hotkey,
680
+ owner_coldkey=owner_coldkey,
681
+ subnet_name=subnet_name,
682
+ symbol=symbol,
683
+ tempo=int(decoded.get("tempo")),
684
+ last_step=int(decoded.get("last_step")),
685
+ blocks_since_last_step=int(decoded.get("blocks_since_last_step")),
686
+ emission=emission,
687
+ alpha_in=alpha_in,
688
+ alpha_out=alpha_out,
689
+ tao_in=tao_in,
690
+ k=tao_in.rao * alpha_in.rao,
691
+ is_dynamic=is_dynamic,
692
+ price=price,
693
+ alpha_out_emission=alpha_out_emission,
694
+ alpha_in_emission=alpha_in_emission,
695
+ tao_in_emission=tao_in_emission,
696
+ pending_alpha_emission=pending_alpha_emission,
697
+ pending_root_emission=pending_root_emission,
698
+ network_registered_at=int(decoded.get("network_registered_at")),
699
+ subnet_identity=subnet_identity,
700
+ subnet_volume=subnet_volume,
701
+ )
702
+
703
+ def tao_to_alpha(self, tao: Balance) -> Balance:
704
+ if self.price.tao != 0:
705
+ return Balance.from_tao(tao.tao / self.price.tao).set_unit(self.netuid)
706
+ else:
707
+ return Balance.from_tao(0)
708
+
709
+ def alpha_to_tao(self, alpha: Balance) -> Balance:
710
+ return Balance.from_tao(alpha.tao * self.price.tao)
711
+
712
+ def tao_to_alpha_with_slippage(self, tao: Balance) -> tuple[Balance, Balance]:
713
+ """
714
+ Returns an estimate of how much Alpha would a staker receive if they stake their tao using the current pool state.
715
+ Args:
716
+ tao: Amount of TAO to stake.
717
+ Returns:
718
+ Tuple of balances where the first part is the amount of Alpha received, and the
719
+ second part (slippage) is the difference between the estimated amount and ideal
720
+ amount as if there was no slippage
721
+ """
722
+ if self.is_dynamic:
723
+ new_tao_in = self.tao_in + tao
724
+ if new_tao_in == 0:
725
+ return tao, Balance.from_rao(0)
726
+ new_alpha_in = self.k / new_tao_in
727
+
728
+ # Amount of alpha given to the staker
729
+ alpha_returned = Balance.from_rao(
730
+ self.alpha_in.rao - new_alpha_in.rao
731
+ ).set_unit(self.netuid)
732
+
733
+ # Ideal conversion as if there is no slippage, just price
734
+ alpha_ideal = self.tao_to_alpha(tao)
735
+
736
+ if alpha_ideal.tao > alpha_returned.tao:
737
+ slippage = Balance.from_tao(
738
+ alpha_ideal.tao - alpha_returned.tao
739
+ ).set_unit(self.netuid)
740
+ else:
741
+ slippage = Balance.from_tao(0)
742
+ else:
743
+ alpha_returned = tao.set_unit(self.netuid)
744
+ slippage = Balance.from_tao(0)
745
+
746
+ slippage_pct_float = (
747
+ 100 * float(slippage) / float(slippage + alpha_returned)
748
+ if slippage + alpha_returned != 0
749
+ else 0
750
+ )
751
+ return alpha_returned, slippage, slippage_pct_float
752
+
753
+ def alpha_to_tao_with_slippage(self, alpha: Balance) -> tuple[Balance, Balance]:
754
+ """
755
+ Returns an estimate of how much TAO would a staker receive if they unstake their alpha using the current pool state.
756
+ Args:
757
+ alpha: Amount of Alpha to stake.
758
+ Returns:
759
+ Tuple of balances where the first part is the amount of TAO received, and the
760
+ second part (slippage) is the difference between the estimated amount and ideal
761
+ amount as if there was no slippage
762
+ """
763
+ if self.is_dynamic:
764
+ new_alpha_in = self.alpha_in + alpha
765
+ new_tao_reserve = self.k / new_alpha_in
766
+ # Amount of TAO given to the unstaker
767
+ tao_returned = Balance.from_rao(self.tao_in - new_tao_reserve)
768
+
769
+ # Ideal conversion as if there is no slippage, just price
770
+ tao_ideal = self.alpha_to_tao(alpha)
771
+
772
+ if tao_ideal > tao_returned:
773
+ slippage = Balance.from_tao(tao_ideal.tao - tao_returned.tao)
774
+ else:
775
+ slippage = Balance.from_tao(0)
776
+ else:
777
+ tao_returned = alpha.set_unit(0)
778
+ slippage = Balance.from_tao(0)
779
+ slippage_pct_float = (
780
+ 100 * float(slippage) / float(slippage + tao_returned)
781
+ if slippage + tao_returned != 0
782
+ else 0
783
+ )
784
+ return tao_returned, slippage, slippage_pct_float
785
+
786
+
787
+ @dataclass
788
+ class ScheduledColdkeySwapInfo(InfoBase):
789
+ """Dataclass for scheduled coldkey swap information."""
790
+
791
+ old_coldkey: str
792
+ new_coldkey: str
793
+ arbitration_block: int
794
+
795
+ @classmethod
796
+ def _fix_decoded(cls, decoded: Any) -> "ScheduledColdkeySwapInfo":
797
+ """Fixes the decoded values."""
798
+ return cls(
799
+ old_coldkey=decode_account_id(decoded.get("old_coldkey")),
800
+ new_coldkey=decode_account_id(decoded.get("new_coldkey")),
801
+ arbitration_block=decoded.get("arbitration_block"),
802
+ )
803
+
804
+
805
+ @dataclass
806
+ class SubnetState(InfoBase):
807
+ netuid: int
808
+ hotkeys: list[str]
809
+ coldkeys: list[str]
810
+ active: list[bool]
811
+ validator_permit: list[bool]
812
+ pruning_score: list[float]
813
+ last_update: list[int]
814
+ emission: list[Balance]
815
+ dividends: list[float]
816
+ incentives: list[float]
817
+ consensus: list[float]
818
+ trust: list[float]
819
+ rank: list[float]
820
+ block_at_registration: list[int]
821
+ alpha_stake: list[Balance]
822
+ tao_stake: list[Balance]
823
+ total_stake: list[Balance]
824
+ emission_history: list[list[int]]
825
+
826
+ @classmethod
827
+ def _fix_decoded(cls, decoded: Any) -> "SubnetState":
828
+ netuid = decoded.get("netuid")
829
+ return SubnetState(
830
+ netuid=netuid,
831
+ hotkeys=[decode_account_id(val) for val in decoded.get("hotkeys")],
832
+ coldkeys=[decode_account_id(val) for val in decoded.get("coldkeys")],
833
+ active=decoded.get("active"),
834
+ validator_permit=decoded.get("validator_permit"),
835
+ pruning_score=[
836
+ u16_normalized_float(val) for val in decoded.get("pruning_score")
672
837
  ],
673
- },
674
- "PrometheusInfo": {
675
- "type": "struct",
676
- "type_mapping": [
677
- ["block", "u64"],
678
- ["version", "u32"],
679
- ["ip", "u128"],
680
- ["port", "u16"],
681
- ["ip_type", "u8"],
838
+ last_update=decoded.get("last_update"),
839
+ emission=[
840
+ Balance.from_rao(val).set_unit(netuid)
841
+ for val in decoded.get("emission")
682
842
  ],
683
- },
684
- "IPInfo": {
685
- "type": "struct",
686
- "type_mapping": [
687
- ["ip", "Compact<u128>"],
688
- ["ip_type_and_protocol", "Compact<u8>"],
843
+ dividends=[u16_normalized_float(val) for val in decoded.get("dividends")],
844
+ incentives=[u16_normalized_float(val) for val in decoded.get("incentives")],
845
+ consensus=[u16_normalized_float(val) for val in decoded.get("consensus")],
846
+ trust=[u16_normalized_float(val) for val in decoded.get("trust")],
847
+ rank=[u16_normalized_float(val) for val in decoded.get("rank")],
848
+ block_at_registration=decoded.get("block_at_registration"),
849
+ alpha_stake=[
850
+ Balance.from_rao(val).set_unit(netuid)
851
+ for val in decoded.get("alpha_stake")
689
852
  ],
690
- },
691
- "StakeInfo": {
692
- "type": "struct",
693
- "type_mapping": [
694
- ["hotkey", "AccountId"],
695
- ["coldkey", "AccountId"],
696
- ["stake", "Compact<u64>"],
853
+ tao_stake=[
854
+ Balance.from_rao(val).set_unit(0) for val in decoded.get("tao_stake")
697
855
  ],
698
- },
699
- "SubnetHyperparameters": {
700
- "type": "struct",
701
- "type_mapping": [
702
- ["rho", "Compact<u16>"],
703
- ["kappa", "Compact<u16>"],
704
- ["immunity_period", "Compact<u16>"],
705
- ["min_allowed_weights", "Compact<u16>"],
706
- ["max_weights_limit", "Compact<u16>"],
707
- ["tempo", "Compact<u16>"],
708
- ["min_difficulty", "Compact<u64>"],
709
- ["max_difficulty", "Compact<u64>"],
710
- ["weights_version", "Compact<u64>"],
711
- ["weights_rate_limit", "Compact<u64>"],
712
- ["adjustment_interval", "Compact<u16>"],
713
- ["activity_cutoff", "Compact<u16>"],
714
- ["registration_allowed", "bool"],
715
- ["target_regs_per_interval", "Compact<u16>"],
716
- ["min_burn", "Compact<u64>"],
717
- ["max_burn", "Compact<u64>"],
718
- ["bonds_moving_avg", "Compact<u64>"],
719
- ["max_regs_per_block", "Compact<u16>"],
720
- ["serving_rate_limit", "Compact<u64>"],
721
- ["max_validators", "Compact<u16>"],
722
- ["adjustment_alpha", "Compact<u64>"],
723
- ["difficulty", "Compact<u64>"],
724
- ["commit_reveal_weights_interval", "Compact<u64>"],
725
- ["commit_reveal_weights_enabled", "bool"],
726
- ["alpha_high", "Compact<u16>"],
727
- ["alpha_low", "Compact<u16>"],
728
- ["liquid_alpha_enabled", "bool"],
856
+ total_stake=[
857
+ Balance.from_rao(val).set_unit(netuid)
858
+ for val in decoded.get("total_stake")
729
859
  ],
730
- },
731
- }
732
- }
860
+ emission_history=decoded.get("emission_history"),
861
+ )