mirror of
https://github.com/ACL4SSR/ACL4SSR.git
synced 2026-11-05 20:26:44 +08:00
Merge pull request #423 from dajiaohuang/fix/domain-mrs-pattern-inputs
Fix domain MRS conversion patterns
This commit is contained in:
2 files changed
+71
-4
No files matched your search
@@ -214,6 +214,15 @@ def parse_list_rule_line(line):
|
||||
def is_domain_rule_type(rule_type):
|
||||
return rule_type in ('DOMAIN', 'DOMAIN-SUFFIX', 'DOMAIN-KEYWORD', 'DOMAIN-REGEX')
|
||||
|
||||
def format_mrs_domain_rule(rule_type, rule_value):
|
||||
"""Translate supported Clash domain rules to MRS domain patterns."""
|
||||
if rule_type == 'DOMAIN':
|
||||
return rule_value
|
||||
if rule_type == 'DOMAIN-SUFFIX':
|
||||
# MRS uses +. to match both the suffix and its root domain.
|
||||
return f'+.{rule_value}'
|
||||
return f'{rule_type},{rule_value}'
|
||||
|
||||
def is_ip_rule_type(rule_type):
|
||||
return rule_type in ('IP-CIDR', 'IP-CIDR6', 'IP-SUFFIX', 'IP-ASN')
|
||||
|
||||
@@ -257,7 +266,7 @@ def split_yaml_file(filepath):
|
||||
unique_domains = sorted(set(domains))
|
||||
domain_yaml = "payload:\n"
|
||||
for rule_type, d in unique_domains:
|
||||
domain_yaml += f" - {rule_type},{d}\n"
|
||||
domain_yaml += f" - {format_mrs_domain_rule(rule_type, d)}\n"
|
||||
write_file(f"{base_name}_domain.yaml", domain_yaml)
|
||||
if ips:
|
||||
unique_ips = sorted(set(ips))
|
||||
@@ -290,7 +299,7 @@ def split_list_file(filepath):
|
||||
unique_domains = sorted(set(domains))
|
||||
domain_text = ""
|
||||
for rule_type, d in unique_domains:
|
||||
domain_text += f"{rule_type},{d}\n"
|
||||
domain_text += f"{format_mrs_domain_rule(rule_type, d)}\n"
|
||||
write_file(f"{base_name}_domain.list", domain_text)
|
||||
if ips:
|
||||
unique_ips = sorted(set(ips))
|
||||
@@ -343,7 +352,7 @@ def generate_clash_provider_yaml(domain_list, ip_list, filename, title="payload"
|
||||
if unique_domains:
|
||||
domain_yaml = f"{title}:\n"
|
||||
for domain in unique_domains:
|
||||
domain_yaml += f" - DOMAIN-SUFFIX,{domain}\n"
|
||||
domain_yaml += f" - {format_mrs_domain_rule('DOMAIN-SUFFIX', domain)}\n"
|
||||
write_file(f"{base_name}_domain.yaml", domain_yaml)
|
||||
|
||||
# IP 规则 - YAML 格式
|
||||
@@ -372,7 +381,7 @@ def generate_clash_ruleset_list(domain_list, ip_list, filename, title="GFWList")
|
||||
if unique_domains:
|
||||
domain_text = ""
|
||||
for domain in unique_domains:
|
||||
domain_text += f"DOMAIN-SUFFIX,{domain}\n"
|
||||
domain_text += f"{format_mrs_domain_rule('DOMAIN-SUFFIX', domain)}\n"
|
||||
write_file(f"{base_name}_domain.list", domain_text)
|
||||
|
||||
# IP 规则 - text 格式
|
||||
|
||||
@@ -0,0 +1,58 @@
|
||||
import importlib.util
|
||||
import tempfile
|
||||
import unittest
|
||||
from pathlib import Path
|
||||
|
||||
|
||||
SCRIPT = Path(__file__).resolve().parents[1] / "gfwlist_parser.py"
|
||||
SPEC = importlib.util.spec_from_file_location("gfwlist_parser", SCRIPT)
|
||||
assert SPEC is not None and SPEC.loader is not None
|
||||
PARSER = importlib.util.module_from_spec(SPEC)
|
||||
SPEC.loader.exec_module(PARSER)
|
||||
|
||||
|
||||
class MrsDomainPatternTests(unittest.TestCase):
|
||||
def test_generated_clash_rules_are_preserved_and_mrs_inputs_are_patterns(self):
|
||||
domain = "synthetic.example.invalid"
|
||||
ip = "192.0.2.1"
|
||||
|
||||
with tempfile.TemporaryDirectory() as temporary_directory:
|
||||
root = Path(temporary_directory)
|
||||
provider = root / "provider.yaml"
|
||||
ruleset = root / "ruleset.list"
|
||||
|
||||
PARSER.generate_clash_provider_yaml([domain], [ip], str(provider))
|
||||
PARSER.generate_clash_ruleset_list([domain], [ip], str(ruleset))
|
||||
PARSER.split_yaml_file(str(provider))
|
||||
PARSER.split_list_file(str(ruleset))
|
||||
|
||||
self.assertIn(f"DOMAIN-SUFFIX,{domain}", provider.read_text(encoding="utf-8"))
|
||||
self.assertIn(f"DOMAIN-SUFFIX,{domain}\n", ruleset.read_text(encoding="utf-8"))
|
||||
self.assertEqual(
|
||||
(root / "provider_domain.yaml").read_text(encoding="utf-8"),
|
||||
f"payload:\n - +.{domain}\n",
|
||||
)
|
||||
self.assertEqual(
|
||||
(root / "ruleset_domain.list").read_text(encoding="utf-8"),
|
||||
f"+.{domain}\n",
|
||||
)
|
||||
self.assertEqual(
|
||||
(root / "provider_ip.yaml").read_text(encoding="utf-8"),
|
||||
f"payload:\n - {ip}/32\n",
|
||||
)
|
||||
self.assertEqual(
|
||||
(root / "ruleset_ip.list").read_text(encoding="utf-8"),
|
||||
f"{ip}/32\n",
|
||||
)
|
||||
|
||||
def test_exact_and_suffix_rule_mappings(self):
|
||||
domain = "synthetic.example.invalid"
|
||||
self.assertEqual(PARSER.format_mrs_domain_rule("DOMAIN", domain), domain)
|
||||
self.assertEqual(
|
||||
PARSER.format_mrs_domain_rule("DOMAIN-SUFFIX", domain),
|
||||
f"+.{domain}",
|
||||
)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
unittest.main()
|
||||
Reference in new issue
Block a user