update(ClashRuleProvider): 支持拖动排序自动生成的规则

This commit is contained in:
wumode
2025-07-08 22:29:46 +08:00
parent f9c60a0683
commit 61b752b6ba
4 changed files with 31 additions and 10 deletions

View File

@@ -457,7 +457,7 @@
"name": "Clash Rule Provider",
"description": "随时为Clash添加一些额外的规则。",
"labels": "工具",
"version": "1.3.0",
"version": "1.2.7",
"icon": "Mihomo_Meta_A.png",
"author": "wumode",
"level": 1,

View File

@@ -39,7 +39,7 @@ class ClashRuleProvider(_PluginBase):
# 插件图标
plugin_icon = "Mihomo_Meta_A.png"
# 插件版本
plugin_version = "1.2.6"
plugin_version = "1.2.7"
# 插件作者
plugin_author = "wumode"
# 作者主页
@@ -965,13 +965,22 @@ class ClashRuleProvider(_PluginBase):
def __insert_ruleset(self):
outbounds = []
new_outbounds = []
rules_existed = self._clash_rule_parser.filter_rules_by_lambda(
lambda r: r.rule_type == RuleType.RULE_SET and r.payload.startswith(self._ruleset_prefix)
)
actions_existed = [ClashRuleParser.action_string(r.action) for r in rules_existed]
for rule in self._ruleset_rule_parser.rules:
action_str = f"{rule.action.value}" if isinstance(rule.action, Action) else rule.action
action_str = ClashRuleParser.action_string(rule.action)
if action_str not in outbounds:
outbounds.append(action_str)
if action_str not in new_outbounds and action_str not in actions_existed:
new_outbounds.append(action_str)
self._clash_rule_parser.remove_rules(lambda r: r.rule_type == RuleType.RULE_SET and
r.payload.startswith(self._ruleset_prefix))
for outbound in outbounds:
r.payload.startswith(self._ruleset_prefix) and
ClashRuleParser.action_string(r.action) not in outbounds
)
for outbound in new_outbounds:
clash_rule = ClashRuleParser.parse_rule_line(f"RULE-SET,{self._ruleset_prefix}{outbound},{outbound}")
if not self._clash_rule_parser.has_rule(clash_rule):
self._clash_rule_parser.insert_rule_at_priority(clash_rule, 0)
@@ -1340,7 +1349,7 @@ class ClashRuleProvider(_PluginBase):
# 通过 ruleset rules 添加 rule-providers
self._rule_provider = {}
for rule in self._ruleset_rule_parser.rules:
action_str = f"{rule.action.value}" if isinstance(rule.action, Action) else rule.action
action_str = ClashRuleParser.action_string(rule.action)
rule_provider_name = f'{self._ruleset_prefix}{action_str}'
if rule_provider_name not in self._rule_provider:
path_name = hashlib.sha256(action_str.encode('utf-8')).hexdigest()[:10]

View File

@@ -397,6 +397,10 @@ class ClashRuleParser:
return conditions
@staticmethod
def action_string(action: Union[Action, str]) -> str:
return action.value if isinstance(action, Action) else action
def parse_rules(self, rules_text: str) -> List[Union[ClashRule, LogicRule, MatchRule]]:
"""Parse multiple rules from text, preserving order and priority"""
self.rules = []
@@ -603,6 +607,10 @@ class ClashRuleParser:
return True
def filter_rules_by_lambda(self, condition: Callable[[Union[ClashRule, LogicRule, MatchRule]], bool]):
"""Filter rules by lambda"""
return [rule for rule in self.rules if condition(rule)]
def filter_rules_by_type(self, rule_type: RuleType) -> List[ClashRule]:
"""Filter rules by type"""
return [rule for rule in self.rules
@@ -614,9 +622,13 @@ class ClashRuleParser:
def has_rule(self, clash_rule: Union[ClashRule, LogicRule, MatchRule]) -> bool:
for rule in self.rules:
if rule.rule_type == clash_rule.rule_type and rule.action == clash_rule.action \
and rule.payload == clash_rule.payload:
return True
if rule.rule_type != RuleType.MATCH:
if rule.rule_type == clash_rule.rule_type and rule.action == clash_rule.action \
and rule.payload == clash_rule.payload:
return True
else:
if rule.rule_type == clash_rule.rule_type and rule.action == clash_rule.action:
return True
return False
def reorder_rules(

View File

@@ -7401,7 +7401,7 @@ return (_ctx, _cache) => {
variant: "tonal"
}, {
default: _withCtx(() => _cache[166] || (_cache[166] = [
_createTextVNode(" 请输入 V2Ray 格式的节点链接,例如:"),
_createTextVNode(" 请输入 V2RayN 格式的分享链接,例如:"),
_createElementVNode("br", null, null, -1),
_createElementVNode("code", null, "vmess://xxxx", -1),
_createElementVNode("br", null, null, -1),