修复了规则更新后没有生效的问题
This commit is contained in:
48
.trae/documents/修复规则更新后没有生效的问题.md
Normal file
48
.trae/documents/修复规则更新后没有生效的问题.md
Normal file
@@ -0,0 +1,48 @@
|
|||||||
|
# 问题分析
|
||||||
|
|
||||||
|
1. **问题现象**:规则更新后,规则没有生效。用户添加或删除规则后,DNS服务器仍然使用旧的规则进行域名屏蔽。
|
||||||
|
|
||||||
|
2. **问题根源**:
|
||||||
|
- 在`addDomainRule`方法中,当添加一个域名规则时,它会为该域名的所有子域名也添加规则。例如,添加`example.com`规则时,会同时添加`example.com`和`com`规则。
|
||||||
|
- 但是,在`RemoveRule`方法中,当删除一个域名规则时,它只删除了指定的域名规则,而没有删除为子域名添加的规则。
|
||||||
|
- 这导致即使删除了主规则,子域名规则仍然存在,因此规则仍然生效。
|
||||||
|
|
||||||
|
3. **具体问题**:
|
||||||
|
- 当添加`||test.example.com`规则时,`addDomainRule`方法会添加`test.example.com`和`example.com`两个规则。
|
||||||
|
- 当删除`||test.example.com^`规则时,`RemoveRule`方法只会删除`test.example.com`规则,而不会删除`example.com`规则,因此`example.com`仍然会被屏蔽。
|
||||||
|
- 此外,`RemoveRule`方法在处理通配符和URL匹配规则时,也没有正确处理子域名规则的删除。
|
||||||
|
|
||||||
|
# 修复方案
|
||||||
|
|
||||||
|
1. **修复`RemoveRule`方法**:
|
||||||
|
- 当删除一个域名规则时,同时删除为该域名的所有子域名添加的规则。
|
||||||
|
- 确保删除规则时,同时更新所有相关映射,包括主规则和子域名规则。
|
||||||
|
|
||||||
|
2. **验证修复效果**:
|
||||||
|
- 启动DNS服务器
|
||||||
|
- 添加一条域名规则,例如`||test.example.com`
|
||||||
|
- 验证该规则及其子域名规则都被正确添加
|
||||||
|
- 删除该规则
|
||||||
|
- 验证该规则及其所有子域名规则都被正确删除
|
||||||
|
- 验证DNS服务器不再使用该规则进行域名屏蔽
|
||||||
|
|
||||||
|
# 实现步骤
|
||||||
|
|
||||||
|
1. 修改`shield/manager.go`文件中的`RemoveRule`方法:
|
||||||
|
- 在删除域名规则时,添加删除所有相关子域名规则的逻辑
|
||||||
|
- 确保删除规则时,同时更新所有相关映射
|
||||||
|
|
||||||
|
2. 测试修复后的功能:
|
||||||
|
- 启动DNS服务器
|
||||||
|
- 访问Web界面,添加一条本地规则,例如`||test.example.com`
|
||||||
|
- 验证该规则被正确添加
|
||||||
|
- 点击删除按钮删除该规则
|
||||||
|
- 验证该规则及其所有子域名规则都被正确删除
|
||||||
|
- 验证DNS服务器不再使用该规则进行域名屏蔽
|
||||||
|
|
||||||
|
# 预期结果
|
||||||
|
|
||||||
|
- 用户添加规则后,规则立即生效
|
||||||
|
- 用户删除规则后,规则立即失效
|
||||||
|
- 规则更新后,DNS服务器使用最新的规则进行域名屏蔽
|
||||||
|
- 本地规则文件被正确更新,添加和删除的规则都能正确反映在文件中
|
||||||
@@ -813,6 +813,7 @@ func (m *ShieldManager) RemoveRule(rule string) error {
|
|||||||
// 尝试删除域名规则
|
// 尝试删除域名规则
|
||||||
domain := strings.TrimPrefix(format, "||")
|
domain := strings.TrimPrefix(format, "||")
|
||||||
if _, exists := m.domainRules[domain]; exists {
|
if _, exists := m.domainRules[domain]; exists {
|
||||||
|
// 删除主域名规则
|
||||||
delete(m.domainRules, domain)
|
delete(m.domainRules, domain)
|
||||||
delete(m.domainRulesIsLocal, domain)
|
delete(m.domainRulesIsLocal, domain)
|
||||||
delete(m.domainRulesSource, domain)
|
delete(m.domainRulesSource, domain)
|
||||||
@@ -822,6 +823,7 @@ func (m *ShieldManager) RemoveRule(rule string) error {
|
|||||||
} else {
|
} else {
|
||||||
// 尝试直接作为域名删除
|
// 尝试直接作为域名删除
|
||||||
if _, exists := m.domainRules[format]; exists {
|
if _, exists := m.domainRules[format]; exists {
|
||||||
|
// 删除主域名规则
|
||||||
delete(m.domainRules, format)
|
delete(m.domainRules, format)
|
||||||
delete(m.domainRulesIsLocal, format)
|
delete(m.domainRulesIsLocal, format)
|
||||||
delete(m.domainRulesSource, format)
|
delete(m.domainRulesSource, format)
|
||||||
@@ -829,6 +831,7 @@ func (m *ShieldManager) RemoveRule(rule string) error {
|
|||||||
break
|
break
|
||||||
}
|
}
|
||||||
if _, exists := m.domainExceptions[format]; exists {
|
if _, exists := m.domainExceptions[format]; exists {
|
||||||
|
// 删除主排除规则
|
||||||
delete(m.domainExceptions, format)
|
delete(m.domainExceptions, format)
|
||||||
delete(m.domainExceptionsIsLocal, format)
|
delete(m.domainExceptionsIsLocal, format)
|
||||||
delete(m.domainExceptionsSource, format)
|
delete(m.domainExceptionsSource, format)
|
||||||
@@ -871,6 +874,8 @@ func (m *ShieldManager) RemoveRule(rule string) error {
|
|||||||
for domain := range m.domainRules {
|
for domain := range m.domainRules {
|
||||||
if domain == cleanRule || domain == rule {
|
if domain == cleanRule || domain == rule {
|
||||||
delete(m.domainRules, domain)
|
delete(m.domainRules, domain)
|
||||||
|
delete(m.domainRulesIsLocal, domain)
|
||||||
|
delete(m.domainRulesSource, domain)
|
||||||
removed = true
|
removed = true
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -880,6 +885,8 @@ func (m *ShieldManager) RemoveRule(rule string) error {
|
|||||||
for domain := range m.domainExceptions {
|
for domain := range m.domainExceptions {
|
||||||
if domain == cleanRule || domain == rule {
|
if domain == cleanRule || domain == rule {
|
||||||
delete(m.domainExceptions, domain)
|
delete(m.domainExceptions, domain)
|
||||||
|
delete(m.domainExceptionsIsLocal, domain)
|
||||||
|
delete(m.domainExceptionsSource, domain)
|
||||||
removed = true
|
removed = true
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
@@ -887,6 +894,36 @@ func (m *ShieldManager) RemoveRule(rule string) error {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 如果没有删除任何规则,尝试删除可能的子域名规则
|
||||||
|
if !removed {
|
||||||
|
// 解析原始规则,提取可能的主域名
|
||||||
|
originalRule := cleanRule
|
||||||
|
// 移除可能的前缀
|
||||||
|
originalRule = strings.TrimPrefix(originalRule, "@@||")
|
||||||
|
originalRule = strings.TrimPrefix(originalRule, "||")
|
||||||
|
|
||||||
|
// 检查是否有子域名规则需要删除
|
||||||
|
// 遍历所有域名规则,删除包含原始规则作为后缀的子域名规则
|
||||||
|
for domain := range m.domainRules {
|
||||||
|
if strings.HasSuffix(domain, "."+originalRule) || domain == originalRule {
|
||||||
|
delete(m.domainRules, domain)
|
||||||
|
delete(m.domainRulesIsLocal, domain)
|
||||||
|
delete(m.domainRulesSource, domain)
|
||||||
|
removed = true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 遍历所有排除规则,删除包含原始规则作为后缀的子域名规则
|
||||||
|
for domain := range m.domainExceptions {
|
||||||
|
if strings.HasSuffix(domain, "."+originalRule) || domain == originalRule {
|
||||||
|
delete(m.domainExceptions, domain)
|
||||||
|
delete(m.domainExceptionsIsLocal, domain)
|
||||||
|
delete(m.domainExceptionsSource, domain)
|
||||||
|
removed = true
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// 如果有规则被删除,持久化保存更改
|
// 如果有规则被删除,持久化保存更改
|
||||||
if removed && m.config.LocalRulesFile != "" {
|
if removed && m.config.LocalRulesFile != "" {
|
||||||
if err := m.saveRulesToFile(); err != nil {
|
if err := m.saveRulesToFile(); err != nil {
|
||||||
|
|||||||
49
test_remove_rule.go
Normal file
49
test_remove_rule.go
Normal file
@@ -0,0 +1,49 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"dns-server/config"
|
||||||
|
"dns-server/shield"
|
||||||
|
"log"
|
||||||
|
"os"
|
||||||
|
)
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
// 创建默认Shield配置
|
||||||
|
shieldCfg := &config.ShieldConfig{
|
||||||
|
LocalRulesFile: "data/rules.txt",
|
||||||
|
}
|
||||||
|
|
||||||
|
// 创建ShieldManager
|
||||||
|
shieldManager := shield.NewShieldManager(shieldCfg)
|
||||||
|
|
||||||
|
// 添加一条测试规则
|
||||||
|
rule := "||test.example.com"
|
||||||
|
err := shieldManager.AddRule(rule)
|
||||||
|
if err != nil {
|
||||||
|
log.Fatalf("添加规则失败: %v", err)
|
||||||
|
}
|
||||||
|
fmt.Printf("添加规则 %s 成功\n", rule)
|
||||||
|
|
||||||
|
// 验证规则是否被添加
|
||||||
|
localRules := shieldManager.GetLocalRules()
|
||||||
|
fmt.Printf("添加规则后,本地规则数量: %d\n", len(localRules["domainRules"].([]string)))
|
||||||
|
|
||||||
|
// 删除规则
|
||||||
|
err = shieldManager.RemoveRule(rule + "^")
|
||||||
|
if err != nil {
|
||||||
|
log.Fatalf("删除规则失败: %v", err)
|
||||||
|
}
|
||||||
|
fmt.Printf("删除规则 %s 成功\n", rule)
|
||||||
|
|
||||||
|
// 验证规则是否被删除
|
||||||
|
localRules = shieldManager.GetLocalRules()
|
||||||
|
fmt.Printf("删除规则后,本地规则数量: %d\n", len(localRules["domainRules"].([]string)))
|
||||||
|
|
||||||
|
// 验证文件内容
|
||||||
|
fileContent, err := os.ReadFile("data/rules.txt")
|
||||||
|
if err != nil {
|
||||||
|
log.Fatalf("读取规则文件失败: %v", err)
|
||||||
|
}
|
||||||
|
fmt.Printf("规则文件内容: %s\n", string(fileContent))
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user