|
31 | 31 | from datetime import datetime, timezone, timedelta
|
32 | 32 | import decimal
|
33 | 33 | from decimal import Decimal
|
34 |
| -import urllib |
| 34 | +from urllib.parse import urlparse |
35 | 35 | import threading
|
36 | 36 | import hmac
|
37 | 37 | import hashlib
|
38 | 38 | import stat
|
39 | 39 | import locale
|
40 | 40 | import asyncio
|
41 |
| -import urllib.request, urllib.parse, urllib.error |
42 | 41 | import builtins
|
43 | 42 | import json
|
44 | 43 | import time
|
@@ -699,6 +698,27 @@ def is_valid_email(s):
|
699 | 698 | regexp = r"[^@]+@[^@]+\.[^@]+"
|
700 | 699 | return re.match(regexp, s) is not None
|
701 | 700 |
|
| 701 | +def is_valid_websocket_url(url: str) -> bool: |
| 702 | + """ |
| 703 | + uses this django url validation regex: |
| 704 | + https://github.com/django/django/blob/2c6906a0c4673a7685817156576724aba13ad893/django/core/validators.py#L45C1-L52C43 |
| 705 | + Note: this is not perfect, urls and their parsing can get very complex (see recent django code). |
| 706 | + however its sufficient for catching weird user input in the gui dialog |
| 707 | + """ |
| 708 | + # stores the compiled regex in the function object itself to avoid recompiling it every call |
| 709 | + if not hasattr(is_valid_websocket_url, "regex"): |
| 710 | + is_valid_websocket_url.regex = re.compile( |
| 711 | + r'^(?:ws|wss)://' # ws:// or wss:// |
| 712 | + r'(?:(?:[A-Z0-9](?:[A-Z0-9-]{0,61}[A-Z0-9])?\.)+(?:[A-Z]{2,6}\.?|[A-Z0-9-]{2,}\.?)|' # domain... |
| 713 | + r'localhost|' # localhost... |
| 714 | + r'\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}|' # ...or ipv4 |
| 715 | + r'\[?[A-F0-9]*:[A-F0-9:]+\]?)' # ...or ipv6 |
| 716 | + r'(?::\d+)?' # optional port |
| 717 | + r'(?:/?|[/?]\S+)$', re.IGNORECASE) |
| 718 | + try: |
| 719 | + return re.match(is_valid_websocket_url.regex, url) is not None |
| 720 | + except Exception: |
| 721 | + return False |
702 | 722 |
|
703 | 723 | def is_hash256_str(text: Any) -> bool:
|
704 | 724 | if not isinstance(text, str): return False
|
|
0 commit comments