一个典型的服务发布网络架构如下:

  1. ICP的各类服务(http, socket等)经由防火墙发布到外网;
  2. 用户侧的设备访问防火墙外网侧的发布地址(可以是wan接口IP,可以是专门用于服务发布的保留IP)的指定端口(例如 TCP 443);
  3. 防火墙通过NAT映射策略导向隐藏于身后的真实服务器所提供的服务(例如 172.16.1.10, TCP 443)。

这种发布环境拥有ISP提供的专线服务,拥有1个或多个固定的公网IP,结合DNS服务,用户总是可以根据域名访问到目标服务。但是当服务侧不具备固定IP条件时,用户便无法顺利定位服务,而当服务侧连公网环境都不具备时,将没有任何通过正常途径发布服务的可能。
* 很多运营商会将用户置于区域级别的NAT中,用户并不直接处于外网,而是被一层内部网络所包裹,同时,并非所有运营商支持切换用户宽带到公网环境。

针对这些情况的解决方案较多:虚拟专网、借助公网服务器进行反弹连接、DDNS。究其本质,是提供可达的第三方进行服务转发,同时借助域名系统来实现透明切换。

方案先决条件简述
VPN-发布搭载VPN服务的第三方服务器服务侧接入VPN服务器,由VPN服务器代为发布到公网。
VPN-直连搭载VPN服务的第三方服务器建立VPN服务器,客户侧和服务侧同时拨入,主要应用场景:外网访问内网安全级别较高的资源。
反弹连接搭载反弹连接服务的第三方服务器原理与“VPN-发布”相同,区别在于不使用VPN,而是使用反弹模式进行主动连接。
DDNS需要公网IP实时更新DNS记录的公网IP,使用户能定位到最新的IP地址。DNS更新具有延迟。

DDNS并不足以覆盖所有应用场景,最重要的先决条件就是需要具备公网环境。如果能满足这一条件,对外发布服务时使用域名,实时更新当前IP到这个域名记录即可让用户总能根据域名定位到服务。

最简单的DDNS实现

  1. 准备一个域名,新建一个A记录,例如 test.chenxin.info;
  2. 查询自己的外网IP;
  3. 更新这条DNS记录为查询到的IP。

这样,最简陋,但是拥有基础功能的一套动态域名系统就完成了。需要注意的是,除了要求公网环境这个缺陷,DDNS的另一个缺陷是DNS缓存问题,在刚切换完IP时,用户侧大多数时候无法实时发现,而是需要等待旧的DNS记录失效(这个失效时间叫做TTL),所以TTL建议设置为运营商所允许的最小值(这个值在大多数情况下是600,也即10分钟)以减少生效等待时间。

扩展:自动完成任务

上面那套流程的实际可操作性几乎为0,只有将第二、三两步的工作自动化,这套系统才具有实际意义。
* 域名服务商提供的域名管理API各不相同,但本质一样,阿里云的API因为复杂的鉴权算法,SHELL条件下几乎不可能实现,可以考虑借助官方SDK或批处理工具进行服务调用,或者直接使用阿里的云解析API开发一套对应的更新客户端。

将脚本设为定时任务以后,一个真正可用的DDNS部署就完成了(案例使用GODADDY测试)。

扩展二:批量和C/S

如果有多个域名或者多个网络需要配置DDNS,按上述做法将脚本部署在每一个网络里即可,维护工作并不算便利,但这种配置属于一次性部署,尚在可接受的范围内。

相较而言,更大的问题是安全隐患——脚本里存放了Api Key和Api Secret。当脚本部署在自己控制之外的环境时,由客户端直接对接域名服务商的API这种方案就变得不可接受。解决办法是:増设DDNS服务端作为前置机。

将敏感信息保存在服务端,从而避免暴露。客户端访问DDNS服务端,服务端取到对端IP即可进行更新,中间也可以省略掉客户端获取外网IP这一步骤——因为请求到服务端时,服务端可以直接获知。

因为DDNS服务端直接对外,却又无法区分客户端来源,所以就需要额外为DDNS服务也配置一套鉴权规则。例如,为每个域名绑定独立的KEY,在header里或者 body里附带key参数,这就可以避免由于相同的KEY被不同客户端使用而导致的潜在越权威胁。

更进一步,为DDNS服务端建立账户系统,并将KEY绑定到账号,或者直接下放到账号进行管理,由每个账号维护自己的域名和KEY,这就是一套功能完整的DDNS服务商系统了(比如花生壳,不过DDNS只是它们的服务之一)。

客户端一:

客户端二:

关于DNS本身

域名系统的工作模式是这样:在域名注册机构处(阿里云、 GoDaddy、新网等)购得域名后,注册商会为域名登记一个或多个NameServer,所有的解析工作都由NameServer来完成。

注册商和NameServer服务其实是两个角色,绝大多数人在阿里云购买了域名后,会在阿里云的管理后台进行域名维护工作——新建记录,更新记录,删除记录(因为阿里云提供了完全合格的域名解析服务,所以这也是推荐的管理方式)……

事实上,在这个使用场景里阿里云同时担任了注册商和NameServer服务提供商两个角色,具体的解析工作完全可以交由第三方、甚至自建的域名解析服务来完成,只需要在阿里云的后台将NameServer设置为实际的域名服务器即可完成切换。