diff --git a/ProxyFilter/Shadowsocks.py b/ProxyFilter/Shadowsocks.py index 802d784..3f39f39 100644 --- a/ProxyFilter/Shadowsocks.py +++ b/ProxyFilter/Shadowsocks.py @@ -61,32 +61,34 @@ ssFilterRules = { 'remark': { 'optional': False, 'default': '', - 'type': str + 'type': str, + 'format': baseFunc.toStr }, 'server': { 'optional': True, 'type': str, - 'format': lambda s: s.lower().strip(), + 'format': baseFunc.toStrTidy, 'filter': baseFunc.isHost, 'errMsg': 'Illegal server address' }, 'port': { 'optional': True, 'type': int, - 'format': lambda i: int(i), + 'format': baseFunc.toInt, 'filter': baseFunc.isPort, 'errMsg': 'Illegal port number' }, 'method': { 'optional': True, 'type': str, - 'format': lambda s: s.replace('_', '-').lower().strip(), + 'format': lambda s: baseFunc.toStrTidy(s).replace('_', '-'), 'filter': lambda method: method in ssMethodList, 'errMsg': 'Unknown Shadowsocks method' }, 'passwd': { 'optional': True, - 'type': str + 'type': str, + 'format': baseFunc.toStr }, 'plugin': { 'optional': False, @@ -99,14 +101,15 @@ ssFilterRules = { 'type': { 'optional': True, 'type': str, - 'format': Plugin.pluginFormat, + 'format': lambda pluginType: Plugin.pluginFormat(baseFunc.toStrTidy(pluginType)), 'filter': Plugin.isPlugin, 'errMsg': 'Unknown SIP003 plugin' }, 'param': { 'optional': False, 'default': '', - 'type': str + 'type': str, + 'format': baseFunc.toStr } } } @@ -125,9 +128,9 @@ def ssFilter(rawInfo: dict, isExtra: bool) -> tuple[bool, str or dict]: } """ try: - if not isExtra: + if not isExtra: # 去除非必要参数 ssFilterRules['rootObject'].pop('remark') - return baseFunc.rulesFilter(rawInfo, ssFilterRules, { + return baseFunc.ruleFilter(rawInfo, ssFilterRules, { 'type': 'ss' }) except: diff --git a/ProxyFilter/ShadowsocksR.py b/ProxyFilter/ShadowsocksR.py index 024a545..af238aa 100644 --- a/ProxyFilter/ShadowsocksR.py +++ b/ProxyFilter/ShadowsocksR.py @@ -73,68 +73,85 @@ ssrObfsList = [ # ShadowsocksR混淆方式 'random_head', ] +def __ssrProtocol(protocol) -> str: + protocol = baseFunc.toStrTidy(protocol).replace('-', '_') + if protocol == '': + return 'origin' + return protocol + +def __ssrObfs(obfs) -> str: + obfs = baseFunc.toStrTidy(obfs).replace('-', '_') + if obfs == '': + return 'plain' + return obfs + ssrFilterRules = { 'rootObject': { 'remark': { 'optional': False, 'default': '', - 'type': str + 'type': str, + 'format': baseFunc.toStr }, 'group': { 'optional': False, 'default': '', - 'type': str + 'type': str, + 'format': baseFunc.toStr }, 'server': { 'optional': True, 'type': str, - 'format': lambda s: s.lower().strip(), + 'format': baseFunc.toStrTidy, 'filter': baseFunc.isHost, 'errMsg': 'Illegal server address' }, 'port': { 'optional': True, 'type': int, - 'format': lambda i: int(i), + 'format': baseFunc.toInt, 'filter': baseFunc.isPort, 'errMsg': 'Illegal port number' }, 'method': { 'optional': True, 'type': str, - 'format': lambda s: s.replace('_', '-').lower().strip(), + 'format': lambda s: baseFunc.toStrTidy(s).replace('_', '-'), 'filter': lambda method: method in ssrMethodList, 'errMsg': 'Unknown ShadowsocksR method' }, 'passwd': { 'optional': True, - 'type': str + 'type': str, + 'format': baseFunc.toStr }, 'protocol': { 'optional': False, 'default': 'origin', 'type': str, - 'format': lambda s: s.replace('-', '_').lower().strip(), - 'filter': lambda method: method in ssrProtocolList, + 'format': __ssrProtocol, + 'filter': lambda protocol: protocol in ssrProtocolList, 'errMsg': 'Unknown ShadowsocksR protocol' }, 'protocolParam': { 'optional': False, 'default': '', - 'type': str + 'type': str, + 'format': baseFunc.toStr }, 'obfs': { 'optional': False, 'default': 'plain', 'type': str, - 'format': lambda s: s.replace('-', '_').lower().strip(), - 'filter': lambda method: method in ssrObfsList, + 'format': __ssrObfs, + 'filter': lambda obfs: obfs in ssrObfsList, 'errMsg': 'Unknown ShadowsocksR obfs' }, 'obfsParam': { 'optional': False, 'default': '', - 'type': str + 'type': str, + 'format': baseFunc.toStr } } } @@ -153,11 +170,18 @@ def ssrFilter(rawInfo: dict, isExtra: bool) -> tuple[bool, str or dict]: } """ try: - if not isExtra: + if not isExtra: # 去除非必要参数 ssrFilterRules['rootObject'].pop('remark') ssrFilterRules['rootObject'].pop('group') - return baseFunc.rulesFilter(rawInfo, ssrFilterRules, { + status, result = baseFunc.ruleFilter(rawInfo, ssrFilterRules, { 'type': 'ssr' }) + if not status: # 节点格式错误 + return False, result + if result['protocol'] == 'origin': # origin无参数 + result['protocolParam'] = '' + if result['obfs'] == 'plain': # plain无参数 + result['obfsParam'] = '' + return True, result except: return False, 'Unknown error' diff --git a/ProxyFilter/VMess.py b/ProxyFilter/VMess.py index 2a7c82a..3acb430 100644 --- a/ProxyFilter/VMess.py +++ b/ProxyFilter/VMess.py @@ -312,16 +312,21 @@ def vmessFilter(rawInfo: dict, isExtra: bool) -> tuple[bool, str or dict]: } """ try: - if not isExtra: + if not isExtra: # 去除非必要参数 vmessFilterRules['rootObject'].pop('remark') status, result = baseFunc.ruleFilter(rawInfo, vmessFilterRules, { 'type': 'vmess' }) - if not status: + if not status: # 节点格式错误 return False, result - - # TODO: host -> sni - + stream = result['stream'] + if stream['secure'] is not None and stream['secure']['sni'] == '': # 未指定SNI + if stream['type'] == 'tcp' and stream['obfs'] is not None: + stream['secure']['sni'] = stream['obfs']['host'].split(',')[0] + elif stream['type'] == 'ws': + stream['secure']['sni'] = stream['host'] + elif stream['type'] == 'h2': + stream['secure']['sni'] = stream['host'].split(',')[0] return True, result except: return False, 'Unknown error' diff --git a/ProxyFilter/baseFunc.py b/ProxyFilter/baseFunc.py index 01b0956..a1ed2d1 100644 --- a/ProxyFilter/baseFunc.py +++ b/ProxyFilter/baseFunc.py @@ -5,7 +5,6 @@ import re import IPy import copy - def isHost(host: str) -> bool: """ 判断host是否合法 @@ -70,7 +69,7 @@ def toStr(raw) -> str: # change to str elif isinstance(raw, str): return raw elif isinstance(raw, bytes): - return str(raw, encoding='utf-8') + return str(raw, encoding = 'utf-8') else: raise Exception('type not allowed') @@ -81,7 +80,7 @@ def toBool(raw) -> bool: # change to bool if isinstance(raw, int): raw = str(raw) elif isinstance(raw, bytes): - raw = str(raw, encoding='utf-8') + raw = str(raw, encoding = 'utf-8') elif not isinstance(raw, str): raise Exception('type not allowed') raw = raw.strip().lower() diff --git a/demo.py b/demo.py index a16424f..06b5d9c 100644 --- a/demo.py +++ b/demo.py @@ -1,29 +1,20 @@ import ProxyFilter as Filter info = { - 'type': 'vmess', + 'type': 'ss', 'remark': 'ok', 'server': b'127.0.0.1 ', 'port': b"12345", 'method': 'aes-128_gcm', - 'id': 'eb6273f1-a98f-59f6-ba52-945f11dee100', - 'aid': '64', - 'stream': { - 'type': 'tcp', - 'obfs': { - 'host': '343.re', - 'path': '/test' - }, - 'secure': {} + 'passwd': 'dnomd343', + 'protocol': 'auth_chain-a', + 'protocolParam': '123', + # 'obfs': b"http-simple", + 'obfsParam': b'123', + 'plugin': { + 'type': 'OBFS_server', + 'param': 'obfs=tls' } - # 'stream': { - # 'type': 'grpc', - # 'service': 'test', - # 'secure': { - # 'sni': 'ip.343.re', - # 'verify': False - # } - # } } status, data = Filter.filte(info, isExtra = True)