5

最近,我在工作中继承了一个业务关键项目以“增强”。在过去的五年中,该代码已被开发并通过了许多人的手。不再在公司工作的顾问和全职员工扼杀了这个非常微妙和过于敏感的应用程序。我们大多数人都必须处理遗留代码或此类项目......这是作为开发人员的一部分......但是......

有零单元和零系统测试。逻辑在存储过程、视图(是的,我说的是视图)和代码之间相互混合(有时无缘无故地重复)。文档?是的,对。我害怕。是的,即使是最小的“调整”或重构也是非常神圣的。一个小事故,我的雇主就会遭受重大的收入损失和潜在的法律问题。

那么,有什么建议吗?我的第一个想法是开始针对现有代码编写断言/单元测试。然而,这只能到此为止,因为存储过程中嵌入了很多逻辑。(我知道它可以测试存储过程,但从历史上看,它比单元测试源代码逻辑要困难得多)。另一种或附加的方法是比较应用程序执行功能之前和之后的数据库状态,进行一些代码更改,然后进行数据库状态比较。

4

7 回答 7

3

我只是重写了企业文件系统最复杂的子系统的数千行,使其成为多线程的,所以所有这些都来自经验。如果重写是合理的(如果重写是为了显着增强功能,或者如果现有代码阻碍了更多增强),那么这里是指针:

  1. 你首先需要对自己的能力有信心才能做到这一点。只有当您对所涉及的技术有足够的经验时,才会出现这种情况。

  2. 沟通,沟通,沟通。让所有相关的利益相关者知道,这是一团糟,这是有风险的,这不能匆忙完成,这需要零碎完成——一次攻击一个区域。

  3. 由内而外地了解系统。记录每一个细微差别、技巧和技巧。记录整体设计。向任何老前辈询问您无法证明的任何代码存在的历史原因。这些是你不想踩的地雷——你可能会认为那些是无用的代码,然后在摆脱它们后后悔。

  4. 单元测试。通过任何已经存在的测试套件运行系统,否则首先为现有代码编写测试,如果它们不存在。

  5. 在重写过程中到处乱扔调试代码 - 断言、日志记录、控制台打印(您应该能够打开和关闭它们,以及指定不同级别的输出,即控制详细程度)。根据我的经验,这是必须的,并且在重写期间有很大帮助。

  6. 浏览代码时,列出所有需要完成的事情——你需要找出的事情、需要编写测试的事情、需要提问的事情、提醒你如何重构某些部分的注释代码,任何可能影响你重写的东西......你不能忘记任何东西!我使用 Outlook 任务执行此操作(只需确保您使用的任何内容始终在您面前 - 这是我一坐在桌子上就打开的第一个应用程序)。如果我被打断了,我会写下我一直在思考的任何事情,并暗示在回到任务后从哪里继续。

  7. 尝试在重写中避免黑客攻击(这是您重写它的原因之一)。想想你遇到的棘手问题。与其他人讨论它们并将你的想法与他们相提并论(没有什么比这更好的了),并提出干净的解决方案。查看您放入待办事项列表的所有任务 - 为现有设计制作 10,000 英尺的图片,然后决定新重写的外观(在模块、子模块、它们如何组合在一起等方面)。

  8. 先解决最棘手的问题。这将使您免于遇到在隧道尽头附近无法解决的问题,并使您免于后退。当然,您需要知道最棘手的问题是什么——因此,在您尝试现有代码时,最好首先记录所有内容。

于 2010-01-10T06:01:29.830 回答
2
  1. 获得一份非常明确的要求清单。

  2. 确保你有隐含的要求和明确的要求——即它必须使用哪些程序,以及如何使用。

  3. 编写当前使用方式的所有场景和用例。

  4. 写很多单元测试。

  5. 编写大量集成测试来测试程序与它必须使用的现有程序的集成。

  6. 与使用该程序的每个人交谈,以找出更多隐含的要求。

  7. 在投入生产之前测试、测试、测试更改。

  8. 青色:)

于 2010-01-10T02:59:58.137 回答
2

除了@Sudhanshu 的伟大清单之外的两件事(在某种程度上,不同意他的#8):

首先,请注意,未经测试的代码是有缺陷的代码——您开始使用的代码几乎肯定不能正常工作,因为“正确”的任何定义都不是“像未经修改的代码一样工作”。也就是说,准备好发现系统中的意外行为,向系统中的专家询问该行为,并让他们得出结论认为它没有按照应有的方式工作。让他们做好准备——警告他们,如果没有测试或其他文档,就没有理由认为它按照他们认为的方式工作。

下一篇:重构低悬的果实 放轻松,慢慢来,小心翼翼。注意代码中的一些简单的东西——比如重复——并测试所有包含重复的方法,然后消除它。起泡,冲洗,重复。在进行更改之前不要为所有内容编写测试,而是为您正在更改的任何内容编写测试。这样,它在每个阶段都保持可发布,并且您不断增加价值,不断改进代码库。

我说了“两件事”,但我想我会添加第三件事:管理期望。让您的客户知道您对这项任务有多么害怕;让他们知道他们有多么糟糕。让他们知道进展会有多缓慢,并让他们知道您会随时告知他们进展情况(当然,这样做)。您的客户可能认为他/她要求“只是一点点修复”——而功能确实可能只改变一点点——但这并不意味着这不会是大量工作和大量时间。你明白这一点;您的客户也需要这样做。

于 2010-01-10T18:33:30.620 回答
2

我以前遇到过这个问题,我已经四处询问(在堆栈溢出之前),这本书一直被推荐给我。http://www.amazon.com/Working-Effectively-Legacy-Michael-Feathers/dp/0131177052

于 2010-01-10T18:38:33.293 回答
1

问问自己:你想达到什么目标?你的使命是什么?你有多少时间?成功的衡量标准是什么?存在哪些风险?你如何减轻和处理它们?

除非你知道你想要达到什么,否则不要碰任何东西。

代码可能是“坏的”,但这意味着什么?代码工作正常吗?所以如果你重写代码让它做同样的事情你会花很多时间重写一些引入错误的东西所以代码做同样的事情?达到什么目的?

您可以做的最简单的事情就是记录系统的功能。我并不是说要编写没人会读到的令人麻木的 Word 文档。我的意思是编写关键功能测试,必要时重构代码以允许编写此类测试。

于 2010-01-10T03:03:00.783 回答
1

你说你害怕接触代码是因为法律、收入损失和零文档。那你看懂代码了吗?您应该做的第一件事是记录它,并确保在考虑重构之前理解它。一旦你完成了这些并确定了问题区域,就按照最小更改的最大收益的顺序列出你的重构建议,并逐步对其进行攻击。在以下情况下,重构更有意义:代码的预期寿命会很长,会添加新功能,错误修复很多。至于测试数据库状态——我最近参与了一个项目,这正是我们成功所做的。

于 2010-01-10T04:29:09.800 回答
1

是否有可能将 DB 和非 DB 部分分开,以便 DBA 可以应对存储过程和数据库本身的挑战,从而让您腾出时间来处理系统的其他部分?这也假设有一个 DBA 可以加强并承担应用程序的这一部分。

如果那是不可能的,那么我会建议看看代码库有多大,以及是否有可能获得一些帮助,所以这并不全靠你。虽然这可以被视为回避责任,但关键是事情不应该通常只掌握在一个人手中,因为它们有时会消失。

祝你好运!

于 2010-01-12T18:03:59.890 回答