国外DOH连接优化

近期特殊时期佬友们的上游DOH大部分都挂了,分享几种方式来连接国外DOH,解决特定场景下科学上网的DNS问题。大部分佬友都是客户端科学上网国外域名远程解析可能不涉及此问题。

DOH走代理

不同的应用可能设置方法不太相同,以smartdns和openclash为例简单介绍下。

smartdns设置

1、打开 smartdns → 代理服务器设置,填入http或者socks代理即可(代理需要自行获取)

2、选择需要开启代理的上游dns服务器,高级设置,勾选“使用代理”,保存应用即可

openclash设置

1、打开openclash → 覆写设置 → DNS设置,勾选 “遵循规则”即可

2、在对应的规则列表中添加DOH地址的域名或者IP走代理请求

CF代理DOH

1、通过cf worker的方式代理DOH请求,配合优选可用性和延迟都还可以。

worker脚本
// SPDX-License-Identifier: 0BSD

const doh = 'https://cloudflare-dns.com/dns-query'
const dohjson = 'https://cloudflare-dns.com/dns-query'
const contype = 'application/dns-message'
const jstontype = 'application/dns-json'
const path = ''; // default allow all, must start with '/' if specified, eg. "/dns-query"
const r404 = new Response(null, {status: 404});

// developers.cloudflare.com/workers/runtime-apis/fetch-event/#syntax-module-worker
export default {
    async fetch(r, env, ctx) {
        return handleRequest(r);
    },
};

async function handleRequest(request) {
    // when res is a Promise<Response>, it reduces billed wall-time
    // blog.cloudflare.com/workers-optimization-reduces-your-bill
    let res = r404;
    const { method, headers, url } = request
    const {searchParams, pathname} = new URL(url)
    
    //Check path
    if (!pathname.startsWith(path)) {
        return r404;
    }
    if (method == 'GET' && searchParams.has('dns')) {
        return fetch(doh + '?dns=' + searchParams.get('dns'), {
            method: 'GET',
            headers: {
                'Accept': contype,
            }
        });
    } else if (method === 'POST' && headers.get('content-type') === contype) {
        // streaming out the request body is optimal than awaiting on it
        const rostream = request.body;
        return fetch(doh, {
            method: 'POST',
            headers: {
                'Accept': contype,
                'Content-Type': contype,
            },
            body: rostream,
        });
    } else if (method === 'GET' && headers.get('Accept') === jstontype) {
        const search = new URL(url).search
        return fetch(dohjson + search, {
            method: 'GET',
            headers: {
                'Accept': jstontype,
            }
        });
    }
    return res;
}

2、需要修改path来方式被其余人恶意刷请求数,path以/开头,路径自己随便填写,然后绑定自定义域名,doh 和dohjson变量根据自己情况修改即可。例如path为 “/fanxinxiaozhan”,自定义域名“XXX”,最终DOH地址为:https://XXX/fanxinxiaozhan

3、通过以下命令测试DOH地址是否有效,返回数据则表示没问题。

curl -H ‘accept: application/dns-json’ ‘https://XXX/fanxinxiaozhan?name=seek.nuer.cc&type=A

4、脚本来源于开源项目:https://github.com/tina-hello/doh-cf-workers,大概测试了下每天6w请求(低于CF worker上限10w请求),最好是配合本地DNS分流和缓存减少请求次数

常用DNS和DOH地址

佬友们觉得有用的话别忘了给个小星星哈

21 个赞

感谢大佬分享 :laughing:

2 个赞

感谢教程

1 个赞

目前用的这些

2 个赞

抄作业了 谢谢你

国内的这种没必要用doh了,还影响延迟,直接udp就行

感谢韩师兄分享

主要用于代理

大佬太强了 :tieba_087:

  1. AdGuardHome做DNS服务
  2. 国外服务器部署synchost定时把被墙域名的解析记录更新到AdGuardHome上
  3. 个别漏网之鱼使用AdGuardHome的dns分流(不用社区dns分流方案,自己改代码使用类似clash的规则模式)

四年以来很稳定。

1 个赞

大佬可以的:+1:t2:

国内解封了吗?还是走专线?

没太注意,反正解不解封影响不大

可以细说第二步么

简单说就是在国外vps上查询域名的dns解析记录,再用api更新到AdguardHome的”dns重写“里面。AdguardHome提供了相应的api,域名少的话可以自己写个shell脚本跑,域名多就自己写个程序跑。

各种公开的dns方案都有一些问题:

  1. 使用国内公开DNS,国内没问题国外被污染
  2. 使用smartdns,国外域名使用国外公开dns解析,不论什么协议都会跟随政策被封或被解封
  3. 自己在国外部署dns再代理过去,临时用几天可以,时间长了就被封

目前最稳定的方案就是上面提到的那种,代价也有:部署AdguarHome的成本(国内主机)、国外主机成本、维护域名精力。

感谢分享了,研究一下……

佬友名字是这个? :bili_057:有事厉飞雨,无事韩老魔,杀人放火厉飞雨,万人敬仰韩天尊。

总结一下,smartdns就是DNS服务端的配置,openclash就是代理客户端的配置,通过CF代理的方式就是通用的配置。很好很强大

道友好,带你一起飞驰星海

1 个赞

我worker搭好了,但是30分钟后基本就不可用了…

改了自定义路径不