背景

有一些服务在没有SSL证书的情况下,在chrome中使用受限。例如:alist下载的东西后缀名为crxdownload且永远显示正在下载/immich无法复制分享链接。而之前使用tplink自带的ddns,它不支持客户部署SSL(辣鸡tplink,论坛上好多年前就有一群用户吵着要SSL,客户团队只会说已经和研发提过了)

NO-IP(失败)

此段用于记录一次失败过程,若需查看正确教程请跳至下一段

起初我看到tplink路由器支持对no-ip的ddns,所以在no-ip上注册了账号并获取到了域名,在路由器上略加设置后成功解析了,但是我在nginx上设置子域名后发现访问失败。查看文档发现免费账号仅支持主域名解析,月付1.99刀才支持泛域名解析,忍痛付费后nginx解析成功~

接下来要对这个域名进行SSL证书颁发,因为是家庭服务器嘛,ISP已经把80和443端口封掉了,只能通过DNS验证所有权,使用certbot找letsencrypt生成了一条验证信息,去NO-IP控制台对域名把信息添加进TXT记录中(没错这也是付费用户才有的功能!),回到certbot进行下一步,提示验证成功并给我了四个文件

最后当我把文件添加进Nginx Proxy Manager(下文简称NPM)时,NPM报了一些错误,而我在互联网上找不到相关文档或是和我处境相同的人。我不确定NPM需要一个什么样的证书,但明显不是certbot默认选项生成的格式。所以我放弃了此方案,转而寻求cloudflare巨佬的帮助。

cloudflare

有请真神出场

域名申请与转移

cloudflare register可选的域名后缀相当有限,godaddy又太贵,还是选择阿里云注册一个域名吧。创建模板并审批之类的跳过不提(早就有了,要我提我也想不起来),拿到域名后在cloudflare主页点击添加域,输入域名点击继续,选择免费计划,随后cf会给你两个dns名称服务器,去阿里云dns设定的地方把默认的服务器改掉,等待约一小时后进行下一步。

DDNS

首先需要一个API TOKEN,用于程序自动对DNS的修改。在cf主页左侧点击管理账户->账户API令牌,创建一个新令牌并赋予它区域DNS的编辑与读取(可能不需要读取,我反正都加了)权限,区域资源选择上一步拿到的域名地址,生成令牌后记录一下,后面两个地方要用。

我选择用docker部署cloudflare-ddns,使用很简单,基本按照demo的compose改一下就能用。这里贴一下我的compose(已脱敏)

services:
  cloudflare-ddns:
    image: favonia/cloudflare-ddns:latest
    network_mode: host
    restart: always
    user: "1000:100"
    # unraid的smb user id其它系统请使用"id"指令查询
    read_only: true
    cap_drop: [all]
    security_opt: [no-new-privileges:true]
    environment:
      - CLOUDFLARE_API_TOKEN=demo_token
      # 填你的API_TOKEN
      - DOMAINS=demo.com,*.demo.com
      # 填你的域名

运行后等个一分钟查看cf控制台,应该可以看到多了两条记录。

SSL

NPM内置了一大堆域名商的自动申请证书接口(大赞),点击SSL Certificates->Add SSL Certificate->Let's Encrypt,填写你的域名与泛域名(和compose文件中的DOMAINS项一致),勾选Use a DNS Challenge,选择Cloudflare,在Credentials File Content的dns_cloudflare_api_token=后填写API TOKEN,勾选同意服务协议后保存,等待一会应该就能看到一个证书出现了(如果和我一样报了个关于python的错误,请再试一次)