V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
efsg
V2EX  ›  宽带症候群

AdGuard+MosDNS+OpenClash 套娃代理组合

  •  1
     
  •   efsg · 43 天前 · 2512 次点击
    这是一个创建于 43 天前的主题,其中的信息可能已经有所发展或是发生改变。

    重发一遍,完善配置文件,把坑都踩了一遍,教程经验总结

    自行安装 3 个插件,luci-app-openclash luci-app-mosdns luci-app-adguardhome

    OpenClash 配置:

    插件设置 - 模式设置 - 运行模式: 切换到 Fake-IP (增强)模式

    插件设置 - DNS 设置 - 本地 DNS 劫持 选择 禁用

    插件设置 - 流量控制 - 绕过中国大陆 IP 取消勾选

    插件设置 - 流量控制 - 仅允许内网 开启

    插件设置 - IPv6 设置 这页的选项全都关闭就行了

    覆写设置 - 常规设置 这里都不用改,只需要记住 DNS 监听,后面配置 mosdns 要用

    覆写设置 - DNS 设置 - 自定义上游 DNS 服务器 勾选

    覆写设置 - DNS 设置 - 追加上游 DNS 勾选

    覆写设置 - DNS 设置 - 追加默认 DNS 勾选

    覆写设置 - DNS 设置 - Fake-IP 持久化 勾选

    覆写设置 - DNS 设置 页面下方 NameServer ,FallBack ,Default-NameServer 里的 DNS 服务器全都取消勾选,我们只用运营商提供的 DNS 服务器就够了,一般运营商 DNS 都是最快的,也是 CDN 最优化的。

    插件设置 - GEO 数据库订阅 把 GeoIP Dat 和 GeoSite 这两个库的自动更新打开,都选 Loyalsoldier 的版本,这个是用来给 mosdns 用的。

    插件设置 - 开发者选项,添加防火墙规则

    # This script is called by /etc/init.d/openclash
    # Add your custom firewall rules here, they will be added after the end of the OpenClash iptables rules
    
    en_mode=$(uci -q get openclash.config.en_mode)
    proxy_port=$(uci -q get openclash.config.proxy_port)
    
    if [ "$en_mode" == "fake-ip" ]; then
    	LOG_OUT "limit route to only fake ips with proxy port $proxy_port"
    	iptables -t nat -D openclash -p tcp -j REDIRECT --to-ports $proxy_port
    	sleep 1
    
    	LOG_OUT "update telegram ipset"
    	/etc/mosdns/rule/geoip2ipset.sh /etc/openclash/GeoIP.dat telegram
    	iptables -t nat -A openclash -m set --match-set telegram dst -p tcp -j REDIRECT --to-ports $proxy_port
    	sleep 1
    
    	LOG_OUT "update netflix ipset"
    	/etc/mosdns/rule/geoip2ipset.sh /etc/openclash/GeoIP.dat netflix
    	iptables -t nat -A openclash -m set --match-set netflix dst -p tcp -j REDIRECT --to-ports $proxy_port
    	sleep 1
    fi
    
    #  停止 AdguradHome
    LOG_OUT "stop adguardhome"
    /etc/init.d/AdGuardHome stop
    sleep 1
    
    #  开启 AdguradHome
    LOG_OUT "start adguardhome"
    /etc/init.d/AdGuardHome start
    sleep 1
    
    # 停止 Mosdns
    LOG_OUT "stop mosdns"
    /etc/init.d/mosdns stop
    sleep 1
    
    # 开启 Mosdns
    LOG_OUT "start mosdns"
    /etc/init.d/mosdns start
    sleep 1
    
    # 重载 Mosdns
    LOG_OUT "reload mosdns"
    /etc/init.d/mosdns reload
    sleep 1
    
    exit 0
    

    SSH 登录路由器,添加脚本 vi 和 nano 或者 winscp 都行,脚本路径 /etc/mosdns/rule/geoip2ipset.sh

    #!/bin/bash
    
    geoipfile="$1"
    tag="$2"
    tmpdir="/tmp/v2dat"
    FW4=$(command -v fw4)
    
    cd $(cd $(dirname $BASH_SOURCE) && pwd)
    
    mkdir -p "$tmpdir"
    filename=$(basename -- "$geoipfile")
    filename="${filename%.*}"
    filename="$tmpdir/${filename}_$tag.txt"
    
    if [ "$tag" == "telegram" ]; then
        wget -4 --timeout 5 -O "$filename" 'https://mirror.ghproxy.com/https://raw.githubusercontent.com/fernvenue/telegram-cidr-list/master/CIDR.txt'
        if [ "$?" != "0" ]; then
             /usr/bin/v2dat unpack geoip -o "$tmpdir" -f "$tag" "$geoipfile"
        fi
    else
        /usr/bin/v2dat unpack geoip -o "$tmpdir" -f "$tag" "$geoipfile"
    fi
    
    if test -f "$filename"; then
        if [ -n "$FW4" ]; then
            nft add set inet fw4 "$tag" { type ipv4_addr\; flags interval\;  auto-merge\; }
            nft add set inet fw4 "${tag}6" { type ipv6_addr\; flags interval\;  auto-merge\; }
            nft flush set inet fw4 "$tag"
            nft flush set inet fw4 "${tag}6"
        fi
        ipset create "$tag" hash:net -!
        ipset create "${tag}6" hash:net family inet6 -!
        ipset flush "$tag"
        ipset flush "${tag}6"
        while read p; do
            if ! grep -q ":" <<< "$p"; then
                if [ -n "$FW4" ]; then
                    nft add element inet fw4 "$tag" { "$p" }
                fi
                ipset add "$tag" "$p"
            else
                if [ -n "$FW4" ]; then
                    nft add element inet fw4 "${tag}6" { "$p" }
                fi
                ipset add "${tag}6" "$p"
            fi
        done <"$filename"
    else
        echo "$filename missing."
    fi
    
    rm -rf "$tmpdir"
    

    添加脚本执行权限

    chmod a+x /etc/mosdns/rule/geoip2ipset.sh
    

    MosDNS 配置:

    MosDNS - 配置文件 - 自定义

    DNS 转发 - 取消勾选

    GeoData 数据导出 添加标签:

    GeoSite: cn apple-cn category-games@cn geolocation-!cn GeoIP: cn

    自定义配置文件:

    log:
      level: info
      file: "/tmp/mosdns.log"
    
    plugins:
      # 缓存插件
      - tag: cache
        type: cache
        args:
          size: 20480
          lazy_cache_ttl: 86400
          
      # 国内域名
      - tag: geosite_cn
        type: domain_set
        args:
          exps:
            - "lan"
            - "local"
            - "arpa"
          files:
            - "/etc/mosdns/rule/whitelist.txt"
            - "/var/mosdns/geosite_cn.txt"
            - "/var/mosdns/geosite_apple-cn.txt"
            - "/var/mosdns/[email protected]"
    
      # 国内 IP
      - tag: geoip_cn
        type: ip_set
        args:
          files:
            - "/var/mosdns/geoip_cn.txt"
            
      # 国外域名
      - tag: geosite_no_cn
        type: domain_set
        args:
          files:
            - "/etc/mosdns/rule/greylist.txt"
            - "/var/mosdns/geosite_geolocation-!cn.txt"
            
      # 国内 DNS
      - tag: forward_local
        type: forward
        args:
          upstreams:
            - addr: "quic://223.5.5.5"      
            - addr: "tls://1.12.12.12"
              enable_pipeline: true      
            - addr: "tls://120.53.53.53"
              enable_pipeline: true
       
      # 国外 DNS
      # 自己查找低延迟 DNS
      - tag: forward_remote
        type: forward
        args:
          upstreams:
            # 101DNS
            - addr: "tls://101.101.101.101"
              enable_pipeline: true
            # NextDNS HK 节点
            - addr: "https://45.11.104.186"
              insecure_skip_verify: true
            # OpenDNS SANDNOX
            - addr: "tls://208.67.222.2"
              enable_pipeline: true
            # OpenDNS 
            - addr: "tls://208.67.222.222"
              enable_pipeline: true                    
    
      # 私人分流 dns         
      - tag: forward_private
        type: forward
        args:
          upstreams: 
            - addr: "https://doh.apad.pro/dns-query"
              bootstrap: "223.5.5.5" 
    
              
      # 国内解析
      - tag: local_sequence
        type: sequence
        args:
          - exec: $forward_local
            
      # 国外解析
      - tag: remote_sequence
        type: sequence
        args:
          - exec: prefer_ipv4
          - exec: $forward_remote
          
      # 分流解析    
      - tag: private_sequence
        type: sequence
        args:
          - exec: $forward_private
          
      # clash 解析
      - tag: clash_sequence
        type: sequence
        args:
          - exec: forward 127.0.0.1:7874
          - exec: ttl 0
    
      # 有响应终止返回
      - tag: has_resp_sequence
        type: sequence
        args:
          - matches: has_resp
            exec: accept
    
      # fallback 用分流 sequence
      # 返回国外 IP 则用 clash 解析得出 fakeip
      - tag: fallback_sequence
        type: sequence
        args:
          - exec: $private_sequence
          - matches: "!resp_ip $geoip_cn"
            exec: goto clash_sequence
          - exec: accept
          
      # 国外 sequence
      - tag: fallback2_sequence
        type: sequence
        args:
          - exec: $remote_sequence
          - matches: "resp_ip $geoip_cn"
            exec: goto local_sequence
          - exec: goto clash_sequence      
    
      # fallback 用分流 DNS ,超时后用国外 DNS 解析    
      - tag: fallback
        type: fallback
        args:
          primary: fallback_sequence
          secondary: fallback2_sequence
          threshold: 2000
          always_standby: true
    
      # 主要的运行逻辑插件
      # sequence 插件中调用的插件 tag 必须在 sequence 前定义,
      # 否则 sequence 找不到对应插件。
      - tag: main_sequence
        type: sequence
        args:
          # drop https query type
          - matches:
            - qtype 65
            exec: reject 3
    
          # handle local ptr
          - matches:
            - qtype 12
            exec: $local_sequence
          - exec: jump has_resp_sequence
    
          #FakeIP 不缓存
          - matches:
            - qname $geosite_no_cn
            exec: $clash_sequence
          - exec: jump has_resp_sequence
          
          # 缓存
          - exec: $cache
          - exec: jump has_resp_sequence
    
          - matches:
            - qname $geosite_cn
            exec: $local_sequence
          - exec: jump has_resp_sequence
    
          - exec: $fallback
    
      - tag: udp_server
        type: udp_server
        args:
          entry: main_sequence
          listen: ":5335" #mosdns 监听端口
    

    网络 - 防火墙 - 自定义规则,添加规则,重启防火墙

    #5333 是 AdGuardHome 的 DNS 监听端口,两个端口必须一致
    iptables -t nat -A PREROUTING -d 198.18.0.0/16 -p tcp -j REDIRECT --to-ports 7892
    iptables -t nat -A PREROUTING -p udp --dport 53 -j REDIRECT --to-ports 5333
    iptables -t nat -A PREROUTING -p tcp --dport 53 -j REDIRECT --to-ports 5333
    ip6tables -t nat -A PREROUTING -p udp --dport 53 -j REDIRECT --to-ports 5333
    ip6tables -t nat -A PREROUTING -p tcp --dport 53 -j REDIRECT --to-ports 5333
    

    AdGuardHome 配置:

    AdGuardHome - 6060 重定向 - 重定向 53 端口到 AdGuardHome 如果使用上面的 iptables 防火墙规则就忽略这步

    更新并且启动 AdGuardHome ,在 Web 管理页面上,设置 - DNS 设置中,上游 DNS 服务器内只填写一个 mosdns 的地址 127.0.0.1:5335 ,私人反向 DNS 服务器写上 127.0.0.1 。DNS 缓存配置里面,缓存大小看你内存大小填写,乐观缓存勾上。

    对于不想走代理的设备,可以在设置 - 客户端设置中添加,并且把上游 DNS 服务器设置成 127.0.0.1

    查询日志文件 /usr/bin/AdGuardHome/data/querylog.json 会把路由器闪存写满 解决方法:ADG - 常规设置 - 日志配置,取消勾选启用日志,或者将查询日志保留时间改为 6 小时,记得保存

    解决谷歌 Play 商店不能更新:

    ADG - 过滤器 - 添加 DNS 重写,services.googleapis.cn 198.18.1.50

    如果无法使用游戏加速器:OpenClash - 插件设置 - 模式设置,取消勾选 UDP 流量转发

    参考教程: https://blog.openwrtcn.eu.org/dnsling-wu-ran/ https://github.com/IrineSistiana/mosdns/discussions/796

    第 1 条附言  ·  39 天前
    经过测试 AdGuard 的缓存大小可以留空不设置,不开启乐观缓存,也许能解决和 fake-ip 缓存冲突的问题
    第 2 条附言  ·  24 天前
    经过测试 firewall4(nftables)固件无法直接按教程配置,编译时需要把 nftables 换成 iptables ,也可以直接卸载 nftables 然后安装 iptables 替换
    第 3 条附言  ·  23 天前
    firewall4 nftables 的补充说明:
    在 `/etc/nftables.d/10-custom-filter-chains.nft` 添加以下规则,注意每行前面都要有空格

    ```
    chain adg_redirect {
    type nat hook prerouting priority dstnat - 10; policy accept;
    meta nfproto { ipv4, ipv6 } udp dport 53 counter packets 0 bytes 0 redirect to :5333 comment "ADG"
    }
    ```

    这条规则是将 53DNS 劫持到 ADGuardhome 的 DNS 监听端口 5333 ,然后重启 OpenClash 即可
    41 条回复    2024-08-08 22:15:45 +08:00
    tediorelee
        1
    tediorelee  
       43 天前
    插个眼, 不过这个配的好复杂
    winterbells
        2
    winterbells  
       43 天前
    我是用了 easymosdns 的配置,自己懒得折腾了
    noisay
        3
    noisay  
       43 天前
    在 op 不解决 iOS 异常耗电这个问题前,真是用不了一点
    siriussilen
        4
    siriussilen  
       43 天前
    点赞,刚好遇到这个问题
    siriussilen
        5
    siriussilen  
       43 天前
    @noisay 你在说什么? op 和 ios 有啥关系
    efsg
        6
    efsg  
    OP
       43 天前
    @noisay 那个是你 OP 主路由和下面 AP 兼容性有问题,经常还会有 WIFI 断网的问题,而且不止 OpenWrt 主路由会有这个问题,可以说就是 iOS 自己的问题
    hiyoi
        7
    hiyoi  
       43 天前 via Android
    同方案,参考的这个
    https://songchenwen.com/tproxy-split-by-dns

    adguardhome 设置了 10 兆缓存,开了乐观缓存。

    刚开始好好的,用一段时间经常网页打不开,需要清空 adg 缓存,clash 面板清空 fakeip 数据库。

    最后还是换回了 redir-host
    efsg
        8
    efsg  
    OP
       43 天前
    @hiyoi 正文中 Github 上的帖子参考的教程实际上就是你发的这个人的教程,实际上相当于三手了🤣 你可以看一遍我的教程排查一下,我当时遇到了好几个坑都是自己解决的,尤其是那个日志把我搞的一愣一愣的,用一段时间就挂了
    Sekai
        9
    Sekai  
       43 天前
    你这个是新版 MosDNS 的配置吧?我还是用的老版本,一直没换,先 mark 一下,thx !
    Sekai
        10
    Sekai  
       43 天前
    另外我觉得 AdGuardHome 应该放在境外,放国内还是不太行
    efsg
        11
    efsg  
    OP
       43 天前   ❤️ 1
    @Sekai #10 让 AdGuard 当前置 DNS 就是为了能让你可以指定客户端 DNS 不走 Clash 的 Fake-IP ,从而实现 Clash 绕过 NAS
    Ccf
        12
    Ccf  
       42 天前
    跟单用 shellcrash 有啥区别?
    efsg
        13
    efsg  
    OP
       42 天前 via Android
    @Ccf shellclash 可以关闭覆写再开启绕过大陆和局域网设备黑白名单,但我遇到过其它问题所以放弃了,OpenClash 不能同时用 fake-ip 和黑白名单还有绕过大陆,只能狠下心折腾一遍前置 DNS ,这样就能让 Clash 绕过 NAS ,并且用 fake-ip 减少莫名其妙的问题,响应速度更快,也可以绕过大陆
    username1919810
        14
    username1919810  
       42 天前
    @efsg #6 他说的估计是 Clash 长连接 keep alive 有问题导致 FCM 和 APNS 严重耗电的问题吧
    efsg
        15
    efsg  
    OP
       42 天前 via Android
    Meta 内核是可以改 TCP Keep-alive 间隔的
    sq123
        16
    sq123  
       42 天前
    话说大佬,我不是一直开 Openclash 的,这些套娃会不会因为关掉一个而奔溃啊
    zer
        17
    zer  
       42 天前
    现在可以 FakeIP 和黑白名单可以并存呀,但是绕过中国大陆确实不行,我使用的是 0.46.014 版本
    本地 DNS 劫持,改为使用防火墙转发。黑白名单就展示出来了,可以选择不走代理的 IP 或者 MAC 地址
    Earsum
        18
    Earsum  
       42 天前
    说实话有点太复杂了,一旦出了问题不知道从哪开始下手排查。我还是选择 meta + redir-host + nameserver policy +绕过中国大陆的分流方式,国内转发 adguardhome ,国外不同服务走不同节点去 1.1.1.1 和 8.8.8.8
    Earsum
        19
    Earsum  
       42 天前
    而且绕过 dnsmasq 会导致部分功能不可用吧?比如说流媒体解锁检测之类的
    efsg
        20
    efsg  
    OP
       42 天前 via Android
    @Earsum Redir-host 模式如果我 nameserver 不填国外 DNS 然后 DNS 走代理,pikpak 就会把我判定成中国地区限制功能,尝试过 nameserver-policy ,geo 策略 dns 分流无效,而且 nameserver 填国外 DNS 会影响所有的 DNS 响应速度,包括绕过大陆功能,所以放弃
    efsg
        21
    efsg  
    OP
       42 天前 via Android
    @Earsum 正常情况下 nameserver 填国内 DNS ,然后 nameserver-policy 用 geo 国内外 DNS 分流,偏偏我就是会遇到各种莫名其妙的问题,前两天跟隔壁群群友折腾半天死活解决不了,最后换回这套前置 DNS 套娃 fake-ip 方案才行
    Earsum
        22
    Earsum  
       41 天前
    @efsg #20 geosite 分流无效倒是挺奇怪的,是不是格式有问题导致覆写失败了?我贴一下我的 nameserver policy 配置吧。这个配置没有兜底规则。所以我在设置自定义上游 DNS 服务器的 nameserver 中设置了 1.1.1.1 和 8.8.8.8 ,并且进入编辑中将这两个 dns 的指定策略组选择了香港节点。这样配置下来一般没有 dns 泄露,并且解析到的 IP 也是离节点最近的,不会莫名其妙飞到其他国家去。

    "+.cbjq.com":
    - "127.0.0.1:10053"
    "+.steamcommunity.com":
    - "tls://1.1.1.1:853#\U0001F1ED\U0001F1F0 香港节点"
    - "tls://8.8.8.8:853#\U0001F1ED\U0001F1F0 香港节点"
    "+.steamcommunity-a.akamaihd.net":
    - "tls://1.1.1.1:853#\U0001F1ED\U0001F1F0 香港节点"
    - "tls://8.8.8.8:853#\U0001F1ED\U0001F1F0 香港节点"
    "+.community.akamai.steamstatic.com":
    - "tls://1.1.1.1:853#\U0001F1ED\U0001F1F0 香港节点"
    - "tls://8.8.8.8:853#\U0001F1ED\U0001F1F0 香港节点"
    "geosite:youtube":
    - "tls://1.1.1.1:853#\U0001F4F9 油管视频"
    - "tls://8.8.8.8:853#\U0001F4F9 油管视频"
    "geosite:openai":
    - "tls://1.1.1.1:853#\U0001F4AC OpenAi"
    - "tls://8.8.8.8:853#\U0001F4AC OpenAi"
    "geosite:pikpak":
    - "tls://1.1.1.1:853#\U0001F1ED\U0001F1F0 香港节点"
    - "tls://8.8.8.8:853#\U0001F1ED\U0001F1F0 香港节点"
    "geosite:cn,apple,private,steam":
    - "127.0.0.1:10053"

    pikpak 的问题我也遇到过,经过观察发现需要添加以下的规则,其实只要添加 access.pikpak.me 相关的域名规则应该也可以( https://github.com/blackmatrix7/ios_rule_script/issues/1328
    - IP-CIDR,161.117.181.246/32,🇭🇰 香港节点
    - DOMAIN-KEYWORD,pikpak,🇭🇰 香港节点
    lzzh0520
        23
    lzzh0520  
       41 天前
    按流程设置下来,很遗憾,失败了。不知道是不是因为防火墙是 fw4 的问题。回归 adguardhome 与 ssr+的配合,先用着吧。
    Earsum
        24
    Earsum  
       41 天前
    @Earsum #22 自定义上游 DNS 服务器的 default nameserver 我也勾选了,填写的是运营商 dns ,但是因为我没有填写 doh ,所以这个的唯一的作用就是解析各个节点的域名,一般而言节点域名是不会被污染的。
    noisay
        26
    noisay  
       40 天前
    @username1919810 #14 对的,就是这个问题,op 有多个 issue 也提及了这个问题,但一直都没有很好的解决方法~
    mac100
        27
    mac100  
       40 天前
    这个设置 adg 好奇怪,测试 上游 5335 端口 是不通的 但有效果的。还有一个问题开了 IPV6 ,adg 客户端全是 v6 链路地址
    vitoegg
        28
    vitoegg  
       40 天前
    geoip2ipset.sh 里面 Telegram 要下载是为什么?是避免第一次启动的时候本地没有 GEOIP 文件吗
    vitoegg
        29
    vitoegg  
       40 天前
    再请教一下,想了解下 AdGuard 和 MosDNS 都开启了缓存是出于什么考虑呢,我理解有一边开启有效果了
    efsg
        30
    efsg  
    OP
       40 天前
    @vitoegg #28 TG 和 Netflix 都是纯 IP 链接的,DNS 解析器还做不到嗅探 IP 连接,这种的解决方法是这些 IPCIDR 固化走 Clash 的 Fake-IP ,所以你也会看到 ipset 规则是转发到 Clash 的透明端口 7892
    efsg
        31
    efsg  
    OP
       40 天前
    vitoegg
        32
    vitoegg  
       40 天前
    @efsg 嗯嗯,这个我理解。我想问下是 GEOIP 已经下载在本地了/etc/openclash/GeoIP.dat ,TG 为什么还要每次先下载一次,我看 Netflix 就没有这个环节。想看看是不是有什么特别考虑。
    efsg
        33
    efsg  
    OP
       40 天前 via Android
    @vitoegg 可以改一下脚本,加检测跳过这个环节
    efsg
        34
    efsg  
    OP
       40 天前 via Android
    @vitoegg 才发现他的脚本压根就没写 netflix 的部分🤣
    MYDB
        35
    MYDB  
       40 天前 via iPhone
    对于 udp 场景和连回家的需求,仍不完善
    efsg
        36
    efsg  
    OP
       40 天前 via Android
    @MYDB 回家就用 Wireguard 之类的异地组网吧,我用的是 Shadowsocks ,在 Clash 加一个策略组就行
    vitoegg
        37
    vitoegg  
       40 天前
    @vitoegg 我又顺了一下,怎么感觉 AdguardHome 不应该开启缓存,如果开启的话会缓存下来 Fake-IP ,时间久了可能会和 OpenClash 里面的结果对应不上导致连接失败。
    b1t
        38
    b1t  
       34 天前
    这套按照流程配置折腾了好几遍,每次都是 adg 设置 mosdns 为上游,测试上游联不通,实测也确实不通,不知道该从哪开始排查问题
    b1t
        39
    b1t  
       34 天前
    @b1t 对了,把 openclash 关了,反而通了,不知道 openclash 哪里出了问题
    875127234
        40
    875127234  
       31 天前
    clash 感觉有点烂到家了,上个网的问题搞那么多配置。
    出了问题根本不好调试。
    应该重新设计一下,翻墙工具到底应该设置哪些参数。
    mac100
        41
    mac100  
       30 天前
    @875127234 clash 很好了 这个组合下来 很不错的
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   1361 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 36ms · UTC 00:01 · PVG 08:01 · LAX 17:01 · JFK 20:01
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.