经历与经验
我知道一个简单的恶作剧:如果你在网上看到一篇令你不爽的文章,或者仅仅因为字体不是你习惯的“宋体小四”,你都可以对这个站点的Internet服务供应商进行投诉,说根据DMCA协议,这篇文章侵犯了你的版权,其作者未经允许擅自引用了你小学时的一篇作文——你不必知道DMCA和蛋黄派有什么区别——然后等着瞧吧,不久之后这篇文章就会下架。难道他们在下撤销令之前不会调查吗?不会,没有人有那么多时间调查投诉者是个优秀的社会公民还是一个刚从重病区跑出来的精神病。
这个小故事到此为止,现在让我转入正题,对最近的工作做一个回顾。
四月的某一天,我接到客户的电话,被通知几个月前上线的系统中出现了一些不合逻辑的数据。我很快在数据库中改正了错误数据,在一周时间内系统运行正常。然而一周后我又得到通知,系统中出现了大量不合逻辑的结果。这次我剖开代码仔细检查,发现在删除数据时缺少了一些逻辑校验,这些错误数据正是由于频繁删除导致的。
既然知道错误的原因就不难修复,我向来认为这很简单。花了一些时间编写纠正错误数据的脚本后我开始着手修改代码。
然而事实并非如此。
在修改的过程中我发现代码通过各种匪夷的形式纠缠在一起,包括大量无用的变量、弃用的方法、重复的语句、魔术数字、还有同一个类中拥有不同风格的缩排方式,有的甚至根本没有缩排……我并不想在此处说明怎样重构这些代码,这不是本文想要论述的重点。引起我思考的问题是有两个,脏数据很容易出现,为什么测试时没有发现?怎样保证代码结构和编码思想的一致性?
这种问题事先没有发现?直觉告诉我并非如此,我一向很在以自己的直觉。果然,RDMS的bug列表上清晰的记载了由于删除导致的数据错误,但是这些bug全部由我们置成了不改!理由似乎很充分,为了方便补入数据,客户提出在删除操作时由人为机制控制,即不允许随意删除。一旦出现错误数据将由客户方的数据库管理员改正。我想找出支持这个理由的论据,很可惜,我翻遍了邮件和SVN上的所有文档却毫无结果,最后才知道这些信息是与客户口头商议得出的。我立刻拨通电话确认此事,客户倒是挺友善,他们承认这件事,但是已经出现了这种问题,现在需要我们修复,并给出方案来帮助他们改正错误数据。
我很快修正了这些问题,期间通过多次和客户沟通,我明白了一些事情:
1) 根本不存在所谓的数据库管理员。几年前我到大连出差,在检察院亲眼见过一个真正的数据库管理员,那是个稍微有点驼背的老大爷,在遇见我之前一直以为光驱是用来放茶杯的装置;
2) 客户经常把“很少发生”说成“不可能发生”;
3) 其实他们比我更在意操作的简便性和界面的有好度。
在和客户沟通中我们犯的错误是显而易见的:
1) 对需求理解不够,并未做深入分析;
2) 轻易答应了客户的要求,放弃了系统的数据完整性;
3) 对重要的沟通并未形成文档,没有分清责任承担者;
4) 忘记了有可能发生的事最终会发生;
5) 对未来的预见性不够,缺少有效的回复措施。
这件事让我颇为郁闷,以前没做过软件?这些事情以前没有遇到过?没有在书本上看到类似的论述……看来我之前的仅仅是经历,怎样把经历转化经验?我将认真探索其中的答案。
在Windows的系统分区中有一个WINDOWS/AppPatch文件夹,其中是一大堆.dll文件,它们负责系统的兼容性,Windows每次升级都会添加一些.dll文件,看来微软为兼容性问题留了个后门。
作为量身定做的业务系统,我们看起来无需考虑兼容性问题,但至少应该考虑部分扩展性。没错,一些关键问题我正是这样设计的,典型的是权限配置。最初的权限模型只控制到菜单级,但是随着业务的深入,客户提出需要将权限控制到页面的元素级,对于同一个功能,主管想要比操作员看到更多的东西,使用更多的按钮。我为此设计了一个方案,让所有的元素可以在配置文件中配置,并形成了详细的说明文档,将文档群发邮件并上传SVN。这次果然提出了权限修改,我开始暗自得意,但是当我修改配置文件后发现问题依旧。剖开代码才知道,每个开发人员使用了不同的权限控制方法,而且在一些类中竟然发现了多种由同一作者写出的不同控制方法!
我对此得出的结论是:为了保证系统结构和编程思想的完整性,在最初的设计时必须形成类和方法的UML图,而且这些设计只能由一个人或两个配合默契的人完成,作为今后开发的依据随时更新;任何开发人员不得违反设计,如果想要添加方法,必须同设计人员商议;每日进行代码复查,必须即时改正不合规范的代码。看起来我的结论有些极端,我也这么认为,这违背了敏捷的多种原则,但是我仍认为这是目前最有效的方法。
五月初接到了一份需求变更,这次客户为了提高效率,需要我们实现大量的动态功能,还有部分流程的改变,为了讨论此事我特意去见了软件的最终使用者。讨论的结果是我承诺在一个月内完成。
还是先来看几个关于估算的著名案例:
西雅图水手的棒球馆按1995年的估算成本应为2亿五千万美元,最终于1999年建成,耗资5亿1700万美元,超过预算100%;波士顿的BigDig公路建设项目最初估算成本26亿美元,最终总计超过150亿美元;FBI的虚拟案件项目在耗资1亿7千万美元时只交付了1/10的功能,之后被搁置;爱尔兰人力资源管理系统预算880万欧元,在成本超过1亿4千万欧元后被取消;……
估算与实际的偏差由来已久,而且看起来我是在为自己开脱。事实又一次让我没有及时兑现承诺,拍脑门的估算使承诺处于估算范围之外。
似乎对技术的自信让我觉得一个月时间没有问题,现在我倒是想问问自己,自己的生产力是多少?自己的能力值是多少?可笑的是我无法回答。各位不妨也回答一下这两个问题。
最初的一周一切顺利进行,在完成三个模块的修改后我甚至为客户部署了使用版本并得到了认可。临近最后期限时我提交了最终版本,一天后我得到客户的反馈,他们似乎异常愤怒,说我把苹果改成了香蕉。看起来还没有那么糟,至少还是水果。当我通过电话详细沟通后才知道,原来客户的真正意图是将苹果和梨通过某种神奇的力量糅在一起,苹果梨才是他们想要的!
弄清了真正的需求后问题便接踵而至,这个看似简单的修改其实极其复杂,不仅要修改表结构,还必须合理设计一张新表。在测试过程中我在草纸上写了三篇测试用例,我第一次发现测试用例如此重要,没有它们我必将被各种数据弄的头昏脑胀。
再来回顾一下估算的定义,这是一个时间区域,而并非一个确定的值。在拍脑门的估算中我忘记了考虑各种随机事件。处理这些问题虽快,但是它们打断了我的思维,被多次打断的一小时远不能和连续的一小时相提并论。有一个我很奇怪的问题,在将近一年的时间内,对于一个小系统,开发人员仍然只知道自己开发的功能而不知道这些功能怎样和其它功能关联在一起,这使得测试异常困难。
现在看来没有即时兑现承诺是必然的,结果是我在端午节加班两天。
我将最为严重的几个问题总结如下:
1) 一开始就未仔细研究需求;
2) 在需求确认阶段缺少最终用户的参与;
3) 缺少预见性的不良设计;
4) 不良的编码实践。
有些问题我找到了解决的方法,我将努力把这个经历变为经验;有些问题我依然没有找到解决的方法,我希望在今后的工作中找到答案;有些问题无法解决,也许会一直存在下去……
这是我2009年6月在CSDN上写的一篇文章,继CSDN密码泄漏事件后就没有再写blog。现在看起来觉得还挺有意思。
作者:我是8位的
出处:http://www.cnblogs.com/bigmonkey
本文以学习、研究和分享为主,如需转载,请联系本人,标明作者和出处,非商业用途!