1010
1111import aiohttp .client_exceptions
1212
13- from electrum import segwit_addr
13+ from electrum import segwit_addr , util
1414from electrum .segwit_addr import bech32_decode , Encoding , convertbits , bech32_encode
1515from electrum .lnaddr import LnDecodeException , LnEncodeException
1616from electrum .network import Network
1717from electrum .logging import get_logger
18+ from electrum .i18n import _
1819
1920
2021_logger = get_logger (__name__ )
2122
2223
23- class LNURLError (Exception ):
24- def __init__ (self , message = "" , * args ):
25- # error messages are returned by the LNURL server, some services could try to trick
26- # users into doing something by sending a malicious error message
27- modified_message = f"[DO NOT TRUST THIS MESSAGE]:\n { message } "
28- super ().__init__ (modified_message , * args )
24+ class LNURLError (Exception ): pass
25+
26+ class UntrustedLNURLError (LNURLError ):
27+ def __init__ (self , message = "" ):
28+ # use if error messages are returned by the LNURL server,
29+ # some services could try to trick users into doing something
30+ # by sending a malicious error message
31+ if message :
32+ message = (
33+ f"{ _ ('[DO NOT TRUST THIS MESSAGE]:' )} \n "
34+ f"{ util .error_text_str_to_safe_str (message )} "
35+ )
36+ super ().__init__ (message )
2937
3038
3139def decode_lnurl (lnurl : str ) -> str :
@@ -124,7 +132,7 @@ async def _request_lnurl(url: str) -> dict:
124132
125133 status = response .get ("status" )
126134 if status and status == "ERROR" :
127- raise LNURLError (f"LNURL request encountered an error: { response .get ('reason' , '<missing reason>' )} " )
135+ raise UntrustedLNURLError (f"LNURL request encountered an error: { response .get ('reason' , '<missing reason>' )} " )
128136 return response
129137
130138
@@ -168,7 +176,7 @@ def _parse_lnurl3_response(lnurl_response: dict) -> LNURL3Data:
168176 """Parses the server response received when requesting a LNURL-withdraw (lud3) request"""
169177 callback_url = _parse_lnurl_response_callback_url (lnurl_response )
170178 if not (k1 := lnurl_response .get ('k1' )):
171- raise LNURLError (f"Missing k1 value in LNURL3 response: { lnurl_response = } " )
179+ raise UntrustedLNURLError (f"Missing k1 value in LNURL3 response: { lnurl_response = } " )
172180 default_description = lnurl_response .get ('defaultDescription' , '' )
173181 try :
174182 min_withdrawable_sat = int (lnurl_response ['minWithdrawable' ]) // 1000
@@ -194,7 +202,7 @@ async def request_lnurl(url: str) -> LNURLData:
194202 return _parse_lnurl6_response (lnurl_dict )
195203 elif tag == 'withdrawRequest' :
196204 return _parse_lnurl3_response (lnurl_dict )
197- raise LNURLError (f"Unknown subtype of lnurl. tag={ tag } " )
205+ raise UntrustedLNURLError (f"Unknown subtype of lnurl. tag={ tag } " )
198206
199207
200208async def try_resolve_lnurlpay (lnurl : Optional [str ]) -> Optional [LNURL6Data ]:
@@ -236,7 +244,7 @@ async def callback_lnurl(url: str, params: dict) -> dict:
236244
237245 status = response .get ("status" )
238246 if status and status == "ERROR" :
239- raise LNURLError (f"LNURL request encountered an error: { response .get ('reason' , '<missing reason>' )} " )
247+ raise UntrustedLNURLError (f"LNURL request encountered an error: { response .get ('reason' , '<missing reason>' )} " )
240248 # TODO: handling of specific errors (validate fields, e.g. for lnurl6)
241249 return response
242250
0 commit comments