Coverage for silkaj/tools.py: 100%

38 statements  

« prev     ^ index     » next       coverage.py v7.8.0, created at 2025-04-22 12:04 +0000

1# Copyright 2016-2025 Maël Azimi <m.a@moul.re> 

2# 

3# Silkaj is free software: you can redistribute it and/or modify 

4# it under the terms of the GNU Affero General Public License as published by 

5# the Free Software Foundation, either version 3 of the License, or 

6# (at your option) any later version. 

7# 

8# Silkaj is distributed in the hope that it will be useful, 

9# but WITHOUT ANY WARRANTY; without even the implied warranty of 

10# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 

11# GNU Affero General Public License for more details. 

12# 

13# You should have received a copy of the GNU Affero General Public License 

14# along with Silkaj. If not, see <https://www.gnu.org/licenses/>. 

15 

16import functools 

17import sys 

18from typing import Any, Union 

19 

20import rich_click as click 

21 

22from silkaj.blockchain.tools import get_blockchain_parameters 

23from silkaj.constants import FAILURE_EXIT_STATUS, G1_SYMBOL, GTEST_SYMBOL 

24 

25 

26@functools.lru_cache(maxsize=1) 

27def get_currency_symbol() -> str: 

28 params = get_blockchain_parameters() 

29 if params["currency"] == "g1": 

30 return G1_SYMBOL 

31 return GTEST_SYMBOL 

32 

33 

34@click.pass_context 

35def has_account_defined( 

36 ctx: click.Context, 

37 exit_error: bool = True, 

38) -> Union[bool, str]: 

39 if not (account_name := ctx.obj["ACCOUNT_NAME"]): 

40 if exit_error: 

41 click_fail("--account general option should be specified") 

42 return False 

43 return account_name 

44 

45 

46def message_exit(message: str) -> None: 

47 print(message) 

48 sys.exit(FAILURE_EXIT_STATUS) 

49 

50 

51@click.pass_context 

52def click_fail(context: click.Context, message: str) -> None: 

53 context.fail(message) 

54 

55 

56class MutuallyExclusiveOption(click.Option): 

57 def __init__(self, *args: Any, **kwargs: Any) -> None: 

58 self.mutually_exclusive = set(kwargs.pop("mutually_exclusive", [])) 

59 _help = kwargs.get("help", "") 

60 if self.mutually_exclusive: 

61 ex_str = ", ".join(self.mutually_exclusive) 

62 kwargs["help"] = ( 

63 f"{_help} NOTE: This argument is mutually exclusive with arguments: [{ex_str}]." 

64 ) 

65 super().__init__(*args, **kwargs) 

66 

67 def handle_parse_result(self, ctx: click.Context, opts: Any, args: Any) -> Any: 

68 if self.mutually_exclusive.intersection(opts) and self.name in opts: 

69 arguments = ", ".join(self.mutually_exclusive) 

70 raise click.UsageError( 

71 message=f"Usage: `{self.name}` is mutually exclusive with arguments `{arguments}`.", 

72 ) 

73 

74 return super().handle_parse_result(ctx, opts, args)