Skip to content

Commit 6042e64

Browse files
authored
Merge pull request #799 from opentensor/feat/warnings-mev-safe-staking
Feat: Add protection warnings
2 parents 2673cde + 575a3a2 commit 6042e64

File tree

2 files changed

+72
-6
lines changed

2 files changed

+72
-6
lines changed

bittensor_cli/cli.py

Lines changed: 36 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,7 @@
7474
ProxyAddressBook,
7575
ProxyAnnouncements,
7676
confirm_action,
77+
print_protection_warnings,
7778
)
7879
from bittensor_cli.src.commands import sudo, wallets, view
7980
from bittensor_cli.src.commands import weights as weights_cmds
@@ -4699,7 +4700,12 @@ def stake_add(
46994700
if safe_staking:
47004701
rate_tolerance = self.ask_rate_tolerance(rate_tolerance)
47014702
allow_partial_stake = self.ask_partial_stake(allow_partial_stake)
4702-
console.print("\n")
4703+
4704+
print_protection_warnings(
4705+
mev_protection=mev_protection,
4706+
safe_staking=safe_staking,
4707+
command_name="stake add",
4708+
)
47034709

47044710
if netuids:
47054711
netuids = parse_to_list(
@@ -5016,8 +5022,12 @@ def stake_remove(
50165022
if safe_staking:
50175023
rate_tolerance = self.ask_rate_tolerance(rate_tolerance)
50185024
allow_partial_stake = self.ask_partial_stake(allow_partial_stake)
5019-
console.print("\n")
50205025

5026+
print_protection_warnings(
5027+
mev_protection=mev_protection,
5028+
safe_staking=safe_staking,
5029+
command_name="stake remove",
5030+
)
50215031
if interactive and any(
50225032
[hotkey_ss58_address, include_hotkeys, exclude_hotkeys, all_hotkeys]
50235033
):
@@ -5353,6 +5363,11 @@ def stake_move(
53535363
"""
53545364
self.verbosity_handler(quiet, verbose, json_output, prompt, decline)
53555365
proxy = self.is_valid_proxy_name_or_ss58(proxy, announce_only)
5366+
print_protection_warnings(
5367+
mev_protection=mev_protection,
5368+
safe_staking=None,
5369+
command_name="stake move",
5370+
)
53565371
if prompt:
53575372
if not confirm_action(
53585373
"This transaction will [bold]move stake[/bold] to another hotkey while keeping the same "
@@ -5574,6 +5589,11 @@ def stake_transfer(
55745589
"""
55755590
self.verbosity_handler(quiet, verbose, json_output, prompt, decline)
55765591
proxy = self.is_valid_proxy_name_or_ss58(proxy, announce_only)
5592+
print_protection_warnings(
5593+
mev_protection=mev_protection,
5594+
safe_staking=None,
5595+
command_name="stake transfer",
5596+
)
55775597
if prompt:
55785598
if not confirm_action(
55795599
"This transaction will [bold]transfer ownership[/bold] from one coldkey to another, in subnets "
@@ -5780,6 +5800,15 @@ def stake_swap(
57805800
"[dim]This command moves stake from one subnet to another subnet while keeping "
57815801
"the same coldkey-hotkey pair.[/dim]"
57825802
)
5803+
safe_staking = self.ask_safe_staking(safe_staking)
5804+
if safe_staking:
5805+
rate_tolerance = self.ask_rate_tolerance(rate_tolerance)
5806+
allow_partial_stake = self.ask_partial_stake(allow_partial_stake)
5807+
print_protection_warnings(
5808+
mev_protection=mev_protection,
5809+
safe_staking=safe_staking,
5810+
command_name="stake swap",
5811+
)
57835812

57845813
wallet = self.wallet_ask(
57855814
wallet_name,
@@ -5803,10 +5832,6 @@ def stake_swap(
58035832
)
58045833
if not amount and not swap_all:
58055834
amount = FloatPrompt.ask("Enter the [blue]amount[/blue] to swap")
5806-
safe_staking = self.ask_safe_staking(safe_staking)
5807-
if safe_staking:
5808-
rate_tolerance = self.ask_rate_tolerance(rate_tolerance)
5809-
allow_partial_stake = self.ask_partial_stake(allow_partial_stake)
58105835

58115836
logger.debug(
58125837
"args:\n"
@@ -7598,6 +7623,11 @@ def subnets_create(
75987623
"""
75997624
self.verbosity_handler(quiet, verbose, json_output, prompt)
76007625
proxy = self.is_valid_proxy_name_or_ss58(proxy, announce_only)
7626+
print_protection_warnings(
7627+
mev_protection=mev_protection,
7628+
safe_staking=None,
7629+
command_name="subnets create",
7630+
)
76017631
wallet = self.wallet_ask(
76027632
wallet_name,
76037633
wallet_path,

bittensor_cli/src/bittensor/utils.py

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -167,6 +167,42 @@ def print_success(message: str, status=None):
167167
print_console(success_message, "green", console)
168168

169169

170+
def print_protection_warnings(
171+
mev_protection: bool,
172+
safe_staking: Optional[bool] = None,
173+
command_name: str = "",
174+
) -> None:
175+
"""
176+
Print warnings about missing MEV protection and/or limit price protection.
177+
178+
Args:
179+
mev_protection: Whether MEV protection is enabled.
180+
safe_staking: Whether safe staking (limit price protection) is enabled.
181+
None if limit price protection is not available for this command.
182+
command_name: Name of the command (e.g., "stake add") for context.
183+
"""
184+
warnings = []
185+
186+
if not mev_protection:
187+
warnings.append(
188+
"⚠️ [dim][yellow]Warning:[/yellow] MEV protection is disabled. "
189+
"This transaction may be exposed to MEV attacks.[/dim]"
190+
)
191+
192+
if safe_staking is not None and not safe_staking:
193+
warnings.append(
194+
"⚠️ [dim][yellow]Warning:[/yellow] Limit price protection (safe staking) is disabled. "
195+
"This transaction may be subject to slippage.[/dim]"
196+
)
197+
198+
if warnings:
199+
if command_name:
200+
console.print(f"\n[dim]Protection status for '{command_name}':[/dim]")
201+
for warning in warnings:
202+
console.print(warning)
203+
console.print()
204+
205+
170206
RAO_PER_TAO = 1e9
171207
U16_MAX = 65535
172208
U64_MAX = 18446744073709551615

0 commit comments

Comments
 (0)