1688 域名切换——看我空中换引擎

阅读数:3754 2013 年 8 月 1 日

话题:阿里巴巴DevOps语言 & 开发

一、背景

经过 10 多年发展、沉淀,阿里巴巴中文站从最初的单个应用系统发展超过 100 个应用系统,500 个以上域名。

早期有不少域名切换案例,但这次切换跟之前项目规模、复杂度要大许多, 且要求严格,需要一次性全部干干净净的切换。

二、挑战

协调超过 100 个应用系统、几百个域名同时切换,各个应用之间往往有各种依赖关系,一个地方出错很容易引起连锁效应,造成大面故障。所以,在这种情况下,我们必须保证中文站以及各个兄弟部门的业务正常的情况下,完成这个域名切换乾坤大挪移。

同时在商业上,需要保障客户的权益,防止 SEO 流量下降,防止 P4P、外投广告的收益保持稳定,等等,项目组感到压力重大。

三、切换方案

1、切换域名面临的技术挑战

1)一次性整体切换

如果按照应用维度逐一切换到 1688 域,需要考虑 cookie 双域读写和跨域请求问题。cookie 分三类:

a、永久 cookie,保存在用户本地电脑上,比如用户标识,访问行为跟踪,识别是否新用户等。

b、登录状态 cookie(session cookie),全站共享,在主域名下。

c、业务 cookie,各个业务应用读写的 cookie,在子域名或者主域名下。

Web 标准无法实现 cookie 的双域直接读写,只能通过 302 跳转或者内嵌 url 的方式间接实现。但是这种方案对应用浸入性比较大,非常复杂,难以大面积的实施;且即使使用,首 pv 的 cookie 丢失问题同样难以接受。所以,考虑到用户体验和切换效果及实施成本,项目组决定选择一次性整体切换。

2)各应用需要独立修改实施

目前有 150 个左右 web 应用,大约 600 个域名,还有部分数据库保持有模板信息,应用之间的相互依赖关系复杂,很难在同一时刻完成所有应用和数据库内容的修改且一次性发布。所以,必须采取策略保证各应用能够独立发布修改,解除应用之间的改造耦合。

2、方案策略

1)保护罩。给整个中文站所有与外界(用户)交互的应用系统(在系统边界)套上一个保护罩,这个保护罩对内部应用系统的修改实施过程进行保护,使应用的修改发布对外界不影响,这样各个应用之间的依赖关系解耦,各个应用可以逐个独立修改发布,在整个过程屏蔽外界用户的感知,保证在实施过程用户保持在同一个主域名及其子域名(*.alibaba.com)下访问,在实施过程中现有功能不会受到任何影响,网站所有功能照常提供服务。

2)为了保证全套环境——包括应用服务器、数据库、配置服务器、文件系统——在保护罩保护之下,线上(生产)环境支持双模式运行:一个是正式模式(对应域名.alibaba.com),正常用户在正式模式下访问;另外一个是测试模式(对应域名.1688.com),在测试模式下,保护罩不起作用,测试人员看到的效果跟实际代码一致,这样就可以利用线上全套真实环境进行全站联测,线上系统、配置服务器和数据库可以随时进行修改并订正。

3)待所有应用修改完成,全站线上新域名联测,完成联测之后去除保护罩,实现一次性切换。

3、方案实现

1)全站实施支持双域 cookie 工作改造,支持多套域配置,老域名采用老 cookie 配置,新域名采用新 cookie 配置。

2)web 内容输出增加保护罩,在 web 内容完成渲染输出时对内容以及 http head location 替换(考虑到静态内容替换,在 apache 层替换,需要开发一个 apache replace module)。这个模块支持双模式工作,在正式模式下,对输出的 web 内容(已经修的内容),扫描分析并反向替换回老域名模式,即把内容里面发现新域名的替换回到老域名,因此对用户屏蔽了改变,在实施过程用户不会影响现有功能;在测试模式下不做替换,测试模式下访问返回的内容和已经修改的代码保持一致,这样就可以提供线上全套测试解决方案,且可以逐个应用发布上线,应用之间的依赖完全解耦。

3)双模式支持,除了 AliSession 和 apache replace module 对双模式工作支持之外,apache 配置也需要增加虚拟主机配置来支持双域名访问,保证外部用户用老域名访问,内部测试人员和实施过程中 apache 反向代理、httpclient 方式,新域名能访问。

一次性切换,完成所有联测之后,把 apache 替换模块一次性下线(也可以做成开关模式,但最终需要下线),去除系统和用户之间的感知屏蔽层,实现全站一次性切换。

4)切换之后,所有老域名的访问 301 跳转至新域名。

总体方案设计图

替换工作原理图解

4、补偿方案

无论方案多么完美,难免会有些内容(不包含 url)绕过保护罩泄露出去,比如邮件内容,这些内容不经过 web 服务器 request/reponse 模式出去,因此 apache 替换模块不起作用。如果逐一去封闭各个出口,成本会比较大,而且这类途径泄露出去的内容占比很小,所以采用泛域名方式来解决。如保护罩设计图中的路径 2,所有新域名(新增的 *.1688.com 域名)会泛解析到 static 集群,这个集群做 302 跳转到相应的 alibaba.com 的 url,从而保障了可用性。但是对于先前已经提供了 1688 域名的应用,如路径 3,需要单独采取类似的方案。

5、服务器间的访问保护方案

服务器之间通常存在反向代理,或者通过 httpclient、rmi 等调用方式的数据服务访问,一旦这些访问的域名修改为了对应的 1688 域名,没有提前支持,肯定是有问题故障的(因为域名没开发,服务不可达)。我们采取的方案是,对内部环境新域名提前开放,保证服务器之间通过新域名访问可达。

6、测试模式识别

线下环境直接提供两种模式:正式模式和测试模式。为了把测试模式和正式模式区分开,我们采用在 cookie 下记录一个标志来区分。为了方面使用,开发一个简单页面,测试人员在进入测试模式之前,点击这个页面按钮切换模式,这个页面功能在双域下记录一个测试标记 cookie,apache 根据这个来判断是否属于测试模式。在测试模式下,apache replace module 不做替换,apache rewrite rule 不会外部重定向至 alibaba 域的域名。

四、其他问题解决方案

1、基于 cookie 数据统计跟踪断层问题解决

采取的方案是将老域名的永久 cookie 迁移至新域名。实现很简单,成本也很低,在通用 js(覆盖大部分页面)埋入迁移 js 即可。注意在迁移 cookie 的过程中,有可能改变 cookie 的值,因为 cookie 标准的不一样,对于有些值会加引号,使用方没有兼容的话,很容易产生故障。

2、SEO 流量影响的解决

  1. 各重要应用重新在百度站长平台,google,bing 的 webmaster 重新验证新的域名权限。
  2. 重要应用都在百度站长平台网站改版功能中,提交域名切换规则,同时,调整各大搜索引擎爬虫的抓取压力。
  3. 修改 sitemap 文件生成规则,将 sitemap 文件中的 URL 全部替换成新的 URL,同时实施 sitemap 地址安全化。
  4. 修改百度开发适配协议,重新调整 URL 的映射关系。
  5. 对于各应用暴露出去的 RPC 服务,或者 URL 服务,添加到 robots 禁止策略中,禁止各搜索引擎抓取,提升爬虫抓取效率。
  6. 寻求百度,360,sogou,soso 等搜索引擎帮助,请求搜索引擎算法部门实施域名切换,进行数据归一化,索引更新。(依赖新老域名映射清单,便于搜索引擎算法部门实施域名切换)

3、代码替换工具

首先建立核心映射关系表,梳理域名切换转换关系表格,老 <--> 新域名关系,包含一对一和一对多的关系,包括三级域名升级为二级域名,域名换名称等,后续所有工作都围绕这个表格进行。整个梳理过程相当繁琐,对几百个域名逐一沟通确认。

开发代码替换工具,同时可以提供给替换数据库,这个工具依赖的核心是域名映射列表。

五、总结

通过三大利器(保护罩、替换工具、补充模式)解决了切换存在的各种技术难题和大大降低了切换实施成本,并通过 SEO 优化策略确保切换之后影响尽可能小。

1688 域名切换项目正式上线一周全站业务系统非常稳定,未产生任何重大故障,客户反应也比较平滑,项目非常成功,达到了我们的预期目的,同时还顺带解决了一些历史包袱:

1、静态资源(图片、js、css 等)彻底独立于主域名,迁移至无 cookie 环境,解决了历史包袱,节省大量网络带宽消耗。

2、域名优化改善,包括域名合并,不合理域名清理,域名升级等。

作者简介

冯凌圣,阿里巴巴应用架构师,2004 年底加入阿里巴巴,主导过中文站许多重点项目及应用架构、性能优化,独自研制开发 json 安全解决方案、jmemory(java 版嵌入式堆外内存使用,类似简单 memcached 的嵌入式版本),目前主导阿里巴巴中文站应用架构。


感谢丁雪丰对本文的审校。

给 InfoQ 中文站投稿或者参与内容翻译工作,请邮件至editors@cn.infoq.com。也欢迎大家通过新浪微博(@InfoQ)或者腾讯微博(@InfoQ)关注我们,并与我们的编辑和其他读者朋友交流。