From Agile To DevOps - 微软开发部门 DevOps 经验谈

在 2013 年 11 月 13 日,我们正式发行了 Visual Studio 2013,以及全新的 Visual Studio Online 服务。但在服务发表之后,Visual Studio Online 却发⽣了异常,造成七个小时服务中断,这是因为在服务上线时,我们没有预想到它会⾯临如此大的流量冲击,所以仅使⽤⼀个扩展单元(Scale Unit)来运行我们的服务,但在欧洲和美国的服务上线时,我们的系统遭遇了流量的顶峰,必须要同时提供服务给上百万的使⽤者,系统不足以乘载这么大量的使用者导致服务中断。在技术上来说,这次的上线过程可说是⼀个⾎淋淋的惨痛经验,就算我们拥有许多已经开发完成,但暂时透过功能开关(Feature flag)隐藏,等待着推出给使⽤者的新功能,却无法监控服务与服务的网络层级问题,才会造成在线服务中断,这些监控机制其实对我们来说才是最重要的,也因为这次的教训,这些机制马上被我们列入接下来的主要开发项目中。



图一, Visual Studio 2013 发表时, Visual Studio Online 因为过⼤流量造成的服务中断,但在市场层⾯来说,这次的服务发表其实是非常成功的,因为 Visual Studio Online 的使⽤者每个月以成倍速度成⻑。(而且在接下来的一年中,使⽤服务的⼈数持续成⻑,已拥有超过两百万名使⽤者)


在新功能开发与在线维运中取得平衡


⼀开始,Visual Studio Online 只有使⽤芝加哥数据中心的⼀个扩展单元(Scale Unit)提供服务。我们当然知道服务如果要能够稳定运行,必须具备横向扩展 (Scale out)到多个地区的能力,也要让每个地区的部署可以独⽴进⾏不互相干扰,但总是有更多重要的新功能等着我们开发,让我们不得不将这些事情往后排。⽽在经过了 Visual Studio Online 上线时惨痛的教训之后,我们决定推迟新功能开发,优先专注在提供稳定的服务上,我们调整了 Visual Studio Online 部署更新流程,改为使⽤循序渐进部署(Canary Release)⽅式。不变部署到芝加哥数据中心的动作,⽽是在部署到芝加哥数据中心之前,增加⼀个部署阶段,称之为 SU0 (Scale Unit 0)。 在新的流程中,每⼀个 Sprint 开发完成之后,都会先部署到圣安东尼奥 (SU0),也是我们工作所在地。然后我们会在内部进⾏⼀⼩段时间的新功能试⽤,当功能都没有问题时,才会进行下一阶段部署到芝加哥(SU1)。而如果我们在 SU0 遇到问题时,我们就可以实时停⽌部署过程并回头修正问题,不会影响到其他部署单位的服务。在这之后,我们也陆陆续续把其他 Azure 数据中心加⼊我们的部署流程,在 2014 年秋天时,我们加入阿姆斯特丹部署阶段(SU5),很快地我们将要增加澳洲作为下⼀个部署阶段。我们主要是透过 Visual Studio Release Management 来处理整个部署流程,也透过 Release Management 来将产品部署到全世界。



图⼆,在 2013 年 11 月, Visual Studio Online 由单一数据中⼼扩展为多个,这让我们可以进⾏循序渐进部署( Canary Release ) 及提供服务到全球。


在下图中可以清楚看到我们一直强调维持在线服务质量的结果。在 2013 年 11 ⽉时是 43 LSIs,⽽在六个⽉后,我们已经减低到了 7 LSIs,并且只有两个是公开的服务,我们也持续在 DevOps 上学习成长,让我们提供的服务更加稳定。



图三,相较于 6 个⽉之前 (2013 年 11 月 ) 发⽣了 43 次 LSIs,Visual Studio Online 在 2014 年 4 ⽉只发⽣了 7 次 LSIs ,只有 2 个是发⽣在公开的功能中。


从 Agile 到 DevOps 的过程


微软拥抱 Agile 超过七年,并汲取了 XP(eXtreme Programming)的精华,使⽤更为 SOLID 的⽅式改善了超过 15x 个技术债。我们透过 Scrum,搭配跨部门或是不同的产品线协同合作,来训练每⼀个团队成员,并专注在创造对于客户更有价值的产品,这也让我们在推出 Visual Studio 2010 时,在客⼾中获得了空前好评。 在发表 VS2010 之后,我们知道是时候开始将 Team Foundation Server 转换为 SaaS 服务了。我们决定使用 Azure 作为 SaaS 版本的 TFS(也就是现在的 Visual Studio Online)的服务运⾏平台,这也代表着我们必须开始把资源投注在 DevOps 上,也必须将我们过去使用 Agile 的经验,延伸到 DevOps 之中,但这两者⼜有什么差别呢?在使用 Agile 时,⼤家往往习惯遵循经验丰富的 Product Owner 规划,有经验的 Product Owner 也会准备好 backlog 让⼤家进⾏开发。相较之下,DevOps 的精神可以说是从使用中学习。


在 DevOps 的开发流程中,我们会直接开发具有实验性质的新功能,发行到正式环境并收集用户对于这些功能的使⽤状况及反馈,以此为基础来决定下⼀轮 backlog 的内容,同时也由于在 DevOps 中,发⾏新功能是没有负担⽽且可靠的,所以我们可以经常的进行新功能的部署,快速的开发新产品或是测试市场反应的新功能,并且很迅速的从第一线使用者的使⽤体验中得到回馈,再将所获得的资料作为规划下一轮 backlog 的基础。相较于在传统的软件开发流程,我们总是会假设性的进行产品⼤范围的规划与使⽤情境想象,再经过漫⻑的开发过程,最后才能投入到市场一次定生死, DevOps 讲求的是直接根据市场反应来修正产品的功能,与其不断假设用户可能的需求以及行为,DevOps 会直接开发新功能,投⼊市场取得产品营运的状况以及使⽤者的回馈,马上根据这些回馈修改⾃己产品来更贴近用户。这也让产品开发的⾵险⼤大降低,缩短从开发到获得市场反应的时程,并且可以实时修正产品方向,让产品永远是针对使⽤者的需求提供服务。


在图四之中,DevOps 延伸了 Agile 的四个准则进⾏开发。



图四,从 Agile 延伸到 DevOps 。


和大部分一开始就提供云端服务的公司不同,我们并不是一开始就有提供 SaaS 版本的服务,大部分的客⼾原本都是购买软件在⾃己公司内部使用(像是 Team Foundation Server,从最早的 2005 版本到目前最新的 2015 版本)。⽽在我们决定开发 Visual Studio Online 时,我们决定让云端和地端版本的 Visual Studio Online 使⽤同⼀份程序代码基础进行开发,并优先进⾏云端部分的功能开发。当⼯程师签入程序代码时,会⾺上触发持续整合的流程进行软件建置、自动化测试及检查。每三周 Sprint 结束之后,我们就会更新云端版本的产品,在 Visual Studio Online 中提供新功能给使⽤者抢先使⽤,累积了 4~5 个 Sprint 后,我们就会发⾏地端版本 Team Foundation Server 季度的更新 Patch 檔。(参考图五)不论在 Agile 或 DevOps 之中,持续整合(Continuous Integration)的机制都是十分重要的,我们可以设定持续整合服务器在程序代码被签入时第⼀时间被执 ⾏,并同时进⾏程序代码建置、⾃动化测试及产⽣程序代码质量报告,让我们在第一时间确认被签入的程序代码是否有潜在风险,也让问题可以在第⼀时间被解决,这么一来可以避免掉许多以往系统上线时可能发生的环境问题,甚⾄是产品部署问题,随时确保版本控制系统(Version Control)中的程序代码是可靠的。并透过自动化让程序代码维持水平时,也不会增加⼤家开发的负担。



图五、我们使用同一份程序代码来同时满足 Visual Studio Online 和 Team Foundation Server ,每三周会将最新版本的 Release 发行到 Visual Studio Online ,每⼀季发⾏一次 TFS 的更新。当我们发行 TFS 的主要更新时,其实也是由⽬前 Visual Studio Online 功能⽽来的。


控制功能曝光对象


当你开始使用 DevOps 的流程经营一个服务时,你会开始习惯频繁的发⾏新版本,就像我们在开发 Visual Studio Online 时,每隔三周(⼀个 Sprint)会发行⼀次最新的版本到在线服务。这也同时让我们有很多将新功能曝光的机会,因此我们必须对于要能够让哪些⼈看到这些新功能进⾏管理,以下是⼀些⽐比较常⾒的问题:

1.如何开发跨 Sprint 的需求?

2.如果有功能必须调整时,我们如何透过实验来获得使用者的操作体验以及反馈(例如 A/B Testing)?

3.如何在你准备好将产品推出到市场之前,隐藏在线的新功能不被使⽤者发现?


基于以上这些原因,我们开始使⽤用了⼀个叫做功能开关模式( Feature flag pattern ) 的方法来控制新功能要让谁可以使用。功能开关其实是⼀种算法,用来控制所有正式环境中的功能可以被谁看到。当团队开始开发一个新功能时,你可以在功能开关服务( feature flag service ) 注册这个功能,它默认是关闭不会被任何⼈人看到的,而当你的功能开发完成,准备好给某些⼈试用时,你可以在正式环境中针对特定使用者或群组开放你的功能。当你想要修改某个功能时,你只要关闭它的开关,不需要经过任何在线版本的发⾏或更动,就可以让这个功能不会被任何⼈人看到或使用。 透过控制各种功能的开放与关闭,使用功能开关(feature flags)也提供了一个在正式环境进行测试的⽅法,我们通常会先对⾃⼰⼈开放新功能进⾏开发或测试,再来开放给先⾏使⽤者们试用,最后都没有问题才会开放给其他⼤部分的使用者。透过功能开关,并搭配观察新功能在在线运行的效能和使⽤者的使用状况,可以让我们确保新服务不会有意料之外的问题发⽣。 ⽽在某些⾓度来说,其实这也是循序渐进部署(Canary Release)另⼀⽅面的延伸,不会让系统存在潜在风险时(例如在在线环境时某些被期待的功能无法顺利使用),就一次⾯对大量的使用者,⽽造成⼤部分使用者不好的使用体验,而是透过逐步开放的⽅式,让⼤多数人的使用者体验都是好的,若有问题也能实时停止开放,修正后再提供给使用者。

原文地址:http://blog.sina.com.cn/s/blog_6408cdc70102w75e.html


.NET社区新闻,深度好文,微信中搜索dotNET跨平台或扫描二维码关注

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/323260.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

selenium以及chromdrive安装

selenium的安装比较简单,直接pip install selenium就可以了 看有些网上写的chromedrive安装好麻烦啊,我win10自己试了下,感觉并不需要配置那么多环境变量。 直接性 http://npm.taobao.org/mirrors/chromedriver/ 找到相应的chrome版本即可 至…

通过C#/.NET API使用CNTK

CNTK v2.2.0提供C#API来建立、训练和评估CNTK模型。 本节概要介绍了CNTK C#API。 在CNTK github respository中可以找到C#训练示例。 使用C#/ .NET管理API构建深层神经网络 CNTK C#API 通过CNTKLib命名空间提供基本操作。 CNTK操作需要一个或两个具有必要参数的输入…

Kafka Controller Redesign 方案

转载自 Kafka Controller Redesign 方案 Kafka Controller 是 Kafka 的核心组件,在前面的文章中,已经详细讲述过 Controller 部分的内容。在过去的几年根据大家在生产环境中应用的反馈,Controller 也积累了一些比较大的问题,而针…

做个人网站的原因

昨天b站上看视频,浏览评论时,看到一个网址 https://xiaoyou66.com/ 博主写了大概一百篇的文章,我进来的时候真的是被这js特效给惊到了,个人网站也能变得这么二次元嘛,讲实话,光是看这酷炫的页面都比较有欲望…

一文理解Netty模型架构

转载自 一文理解Netty模型架构 本文基于Netty4.1展开介绍相关理论模型,使用场景,基本组件、整体架构,知其然且知其所以然,希望给读者提供学习实践参考。 1 Netty简介 Netty是 一个异步事件驱动的网络应用程序框架,用…

尝试涉猎更多领域

昨天b站上看视频,浏览评论时,看到一个网址 https://xiaoyou66.com/ 博主写了大概一百篇的文章,我进来的时候真的是被这js特效给惊到了,个人网站也能变得这么二次元嘛,讲实话,光是看这酷炫的页面都比较有欲望…

聊聊分布式事务,再说说解决方案

前言 最近很久没有写博客了,一方面是因为公司事情最近比较忙,另外一方面是因为在进行 CAP 的下一阶段的开发工作,不过目前已经告一段落了。 接下来还是开始我们今天的话题,说说分布式事务,或者说是我眼中的分布式事务&…

Redis+Tomcat+Nginx集群实现Session共享,Tomcat Session共享

转载自 RedisTomcatNginx集群实现Session共享,Tomcat Session共享 一、Session共享使用tomcat-cluster-redis-session-manager插件实现 插件地址见: https://github.com/ran-jit/tomcat-cluster-redis-session-manager 该插件支持Tomcat7、Tomcat8、To…

个人博客搭建

先下载node.js 用npm或cnpm安装hexo cnpm install hexo 再创建一个文件夹,在文件夹目录下打开cmd 输入 hexo init 输入 hexo s 这就在本地算是完成了一个博客的创建 新建博客hexo n ‘Hello world’ hexo clean hexo s 就可以再次启动,这样 记得先 cn…

C#使用Xamarin开发可移植移动应用进阶篇(10.综合演练,来一份增删改查CRUD)

说点什么.. 呃 也有半个月没更新了. 本来这篇的Demo早就写完了,文章也构思好了.迟迟没发布..是因为实在太忙.. 项目要上线..各种 你们懂的.. 正赶上自己十一人生大事..结婚..所以..忙的那叫一个脚不沾地啊. 今天的学习内容? 使用我们前面所学的技术,写一个增删改查. 效果如下…

hexo部署在码云出现样式问题

然而本地服务器并没有任何问题 重建一个 重新建一个仓库 还是这种情况,回头再找原因,两次都是这种情况,就是配置错了 借用 https://blog.csdn.net/xiangwanpeng/article/details/53155642 https://blog.csdn.net/qq_29347295/article/deta…

当你输入一个网址的时候,实际会发生什么?

转载自 当你输入一个网址的时候,实际会发生什么? 译文:http://igoro.com/archive/what-really-happens-when-you-navigate-to-a-url/ 作为一个软件开发者,你一定会对网络应用如何工作有一个完整的层次化的认知,同样这里也包括这些应用所…

SIMD via C#

简介 TL;DR 我们为C#(准确地说是.NET Core)引入了一套全新的机制,使得C# 以后可以像C/C 一样直接使用intrinsic functions 来直接操作Intel CPU 的大多数SIMD 指令了(从SSE 到AVX2)。 (注意是以后&#xff…

Ae做一个立体地球

Ae做一个立体地球 拿到一张照片 将它变成标题的地球 在AE里 即可变成一个地球 看上去亮多了,再定个关键帧即可旋转

ASP.NET Core 处理 404 Not Found

问题 在没有修改任何配置的情况下,这是用户使用 Chrome 访问不存在的URL时会看到的内容: 幸运的是,处理错误状态代码非常简单,我们将在下面介绍三种技术。 解决方案 在以前的ASP.NET MVC版本中,主要在 web.config 中处…

搭建一个二次元博客

小叙: 因为前段日子尝试过自己搭建网站,也在b站发了视频,奈何技术太菜,被喷的严重。所以决定重构一下网站,改成一个个人博客。这里非常感谢小游提供的主题,感谢他对这么优秀的主题的推广。 如果你正好也要…

从头编写 asp.net core 2.0 web api 基础框架 (5) EF CRUD

Github源码地址:https://github.com/solenovex/Building-asp.net-core-2-web-api-starter-template-from-scratch 这是第一大部分的最后一小部分。要完成CRUD的操作。 Repository Pattern 我们可以直接在Controller访问DbContext,但是可能会有一些问题: …

做这个网站原因之二

讲讲我最近干了什么事吧以及以后该干啥 其实大部分我学到的东西,都写在博客上了,可以通过博客看到一个人的学习轨迹。除了这些,我也尝试拍些视频去学习一些新的东西。视频剪辑,特效什么的都在尝试。 有个视频我也只是随便尝试尝试…

spring cloud+dotnet core搭建微服务架构:配置中心续(五)

前言 上一章最后讲了,更新配置以后需要重启客户端才能生效,这在实际的场景中是不可取的。由于目前Steeltoe配置的重载只能由客户端发起,没有实现处理程序侦听服务器更改事件,所以还没办法实现彻底实现这一功能。这一章的例子&…

聊聊最近吧

讲讲我最近干了什么事吧以及以后该干啥 其实大部分我学到的东西,都写在博客上了,可以通过博客看到一个人的学习轨迹。除了这些,我也尝试拍些视频去学习一些新的东西。视频剪辑,特效什么的都在尝试。 有个视频我也只是随便尝试尝试…