在大型且旧的(5 年)代码库中进行单元测试是否值得?
我刚刚加入了一个团队,该团队在过去 5 年里一直在 main-always 模式下工作(基于 java、maven 的项目)。因此,利用单元测试的计划一直在酝酿之中,但从未实现(到目前为止)。优秀的开发团队可以确保代码质量总体良好,并且不存在结构性代码问题,但只是没有编写 jnuit 测试的文化。但在看到了单元测试的好处之后,我成为了推动自动测试采用的孤独战士。
团队布局是这样的:一个单独的测试团队在推出代码之前对功能进行手动测试,而变更管理团队是变更批准和构建的检查门(到目前为止也没有持续集成)。
以下是障碍: 由于代码库庞大,并且一些原始开发人员已经离开团队,任何额外的单元测试可能都太少、太晚。 除此之外,我可能是唯一推动单元测试的人。尽管我的经理一直支持这个想法,但他不希望变革团队因运行测试所需的额外时间而陷入困境。
我认为可以从使用独立的 CI 工具开始,并且变更团队必须在添加测试时更改其脚本以跳过测试。
如果你处于我的立场,你会做什么?
PS:我知道 stackoverflow 上有一个类似的问题,但是在这个一、目的是说服不同的利益相关者以及采取的最佳路径;不是技术比较。
I've just joined a team which has been working in a main-always mode for the last 5 yrs (java, maven based project). Consequently plans to leverage unit testing have always been in the pipeline, never materialising (so far). A Great dev team has ensured that code quality is generally good, and there aren't structural code issues, but there's just no culture of writing jnuit tests. But I, having seen the benefits of unit testing, am a lone warrior here pushing for adoption of auto-testing.
The team layout is such that a separate testing team does manual testing of functionality before rolling out the code, and a change management team is a checkgate for change approvals and builds (no continuous integration either, so far).
Following are the hurdles: Because the code base is huge,and some of the original developers have left the team, any additional unit tests may be too little, too late.
Add to it that I may be the only one pushing for unit testing. Though my manager has been supportive of the idea, he doesnt want the change team to be bogged down by additional time required for the tests to run.
I'm of the opinion that a stand-alone CI tool can be used to start off with, and the change team must alter their scripts to skip tests, as and when they are added.
What would you do in my shoes?
P.S.: I'm aware of a similar question on stackoverflow , but in this one, the aim is to convince the different stakeholders and the best path to takel; not a technology comparison.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(7)
听起来你对这种情况处理得很好。
两件事:
不要指望能够对 5 年历史的项目进行完整的单元测试。假设 5 名开发人员工作了 5 年,那么您的程序员工作时间约为 50,000 小时。假设测试花费的时间与编写代码的时间一样多,那么您在一年内获得 2-3% 的覆盖率就已经相当不错了。
所以:测试新代码,并为旧代码的修改编写测试。花时间/花时间来设置某种 CI。逐渐地,您将建立一系列良好的测试。
既然你显然没有被错误淹没,那就慢慢开始,获得动力。
Sounds like you have a pretty good handle on the situation.
Two things:
Don't expect to be able to fully unit test a 5 year old project. Assuming 5 developers working for 5 years, you're in the neighborhood of 50,000 programmer-hours. Assuming that tests take as much time to write as code, you'd be doing pretty good to get 2-3% coverage in a year.
So: Test new code, and write tests for modifications of older code. Get time / take time to set up CI of some kind. Gradually, you'll build up a nice battery of tests.
Since you're apparently not drowning in bugs, start slow, gain momentum.
编写测试来测试您正在开发并且希望保持稳定的特定功能是值得的。
对于目前没有测试覆盖率的大型现有应用程序,您不会想坐下来一次性编写测试以获得 100% 的单元测试覆盖率,而且您永远不会这样做。您只需挑选出特定的功能来进行测试。我不认为存在太少或太晚的问题;仅对一小部分非常重要的功能进行单元测试总比没有好,现在的一些单元测试比以前没有单元测试要好。
It would be worth writing tests to test specific functionality that you are working on and you want to remain stable.
With a large existing application that has no test coverage at the moment, you wouldn't want to sit down and write tests all in one go in order to get 100% unit test coverage and you never will. You'd just single out specific functionality for testing. I don't think there's such a thing as too little or too late; unit tests for only a tiny bit of very important functionality is better than none at all, and some unit tests now are better than no unit tests ever.
即使在旧项目中,单元测试也是有利的,例如,通过建立单元测试,您可以确定问题不在现有代码中,而是在新代码中(即使您有 QA 流程,错误仍然偶尔会出现) )。此外,它们还可以防止对旧代码的更改引入细微的行为差异。此外,单元测试记录了庞大代码库的预期行为。
现在,采取重大变革绝非易事。第一件也是最直接的事情是强制对所有新代码进行单元测试,这样旧代码库的单元测试的工作量和工作量就不会继续增加。然后,第二部分是采取主动,为旧代码创建一些单元测试。如果您这样做,那么您应该能够说服团队的其他成员帮助为现有代码创建单元测试。如果有必要,想出一些有趣的激励措施,比如承诺为现有代码库创建最多数量的单元测试的团队举办披萨派对。
另外,提醒您的队友,这并不是他们需要放弃正在做的一切的事情……如果他们每天在其他工作之上只为现有组件创建一个单元测试,那么最终您将得到一个对代码库中所有现有组件进行单元测试。
Unit testing is advantageous even in an old project, for example, by establishing unit tests, you can be sure that the problem is not in existing code but in new code (even if you have a QA process, bugs do still get through on occassion). Additionally, they prevent changes to old code from introducing subtle differences in behavior. Also, unit tests document the intended behavior of the huge codebase.
Now, adopting large changes are never easy. The first and most straightforward thing is to mandate unit testing of all new code, so that the effort and workload of unit testing the old codebase doesn't continue to pile up. Then, the second part is to take the initiative, and create some unit tests for the old code. If you do that, then you should be able to convince other members of your team to help with the effort in creating unit tests for existing code. If necessary, come up with fun incentives, like promising a pizza party for the team that creates the largest number of unit tests for the existing code base.
Also, remind your teammates that this isn't something where they need to drop everything that they are doing... if they only create one unit test for an existing component each day on top of their other work, then eventually you will get a unit test for all the existing components in your codebase.
恕我直言,单元测试或任何其他与此相关的测试(功能测试除外)应该经常针对应用程序中关键且不稳定的部分运行。换句话说,单元测试不应该为了编写测试而编写,而是为了确保开发/维护工程师不会在代码中遇到某些条件。
也就是说,您可能还想看看在 CI 服务器中运行的集成测试,更重要的是因为它们更接近功能测试,而且代码也很成熟。根据我的观察,确定要在成熟应用程序中编写的单元测试非常困难,并且在短期内的投资回报率比集成测试要低。
您的案例中的集成测试将确保应用程序的各个层继续与原始开发人员的意图结合在一起。另一方面,单元测试本质上更加本地化,将确保特定区域中的任何新补丁/错误修复确实会在该位置产生副作用。
IMHO, unit tests or any other tests for that matter (except for functional tests) should be run frequently against parts of the application that are critical and volatile, at the same time. In other words, unit tests should not be written for the sake of writing tests, but rather to ensure tha the development/maintenance engineers do not trip over certain conditions in code.
That said, you might also want to take a look at integration tests that run in a CI server, more so because they're closer to the functional tests, and also because the code is mature. From my observations, identifying unit tests to write in a mature application is far difficult and has lesser RoI in the shorter term than integration tests.
Integration tests in your case will ensure that the various tiers of the application continue to be held together with the intentions of the original developers. Unit tests on the other hand, being a bit more localized in nature will ensure that any new patch/bug fix in a particular area does cause side effects in that location.
这将是一项巨大的努力,而回报却很小。而是自动化并扩展当前的测试以确保系统稳定性(我假设在系统级别有一些测试)。我认为您应该关注系统中仍存在大量变化或您计划在不久的将来进行更改的部分。
单元测试很好,但很难改造到现有系统中。如果您只关注明年或更长时间的单元测试,您将失去前进的动力。
It will be a massive effort and returns would be small. Rather automate and expand your current testing to ensure system stability (I assume there is some testing at system level). I think you should focus on parts of the system that still see lots of change or that you plan on changing in the near future.
Unit testing is good but can be difficult to retrofit into an existing system. If you just focus on unit testing for the next year or more you are going to lose forward momentum.
我不会仅仅为了编写测试而编写测试。商业回报是什么?您的企业可能已经遭受了没有单元测试的影响,现在问题已经得到解决。如果我确实添加了测试,我只会将它们添加到会导致最令人不快的结果的代码部分。例如,我会考虑向任何角色/安全相关的代码添加测试。
I would not write tests just to write tests. What would be the business payoff? Your business has likely already suffered the effects of not having unit tests and now the issues have been addressed. If I did add tests, I would only add them to the sections of code that would cause the most unpleasant results. For example, I'd consider adding testing to any role/security related code.
OP所描述的情况主要是一个“心态改变”问题。在当今时代,强迫你的队友养成某种习惯是行不通的。您需要在开发人员和业务利益相关者中注入真正的动力,使其自然采用。我的建议:
The situation which the O.P. has described is majorly a "mindset change" problem. In today's times, forcing your team-mates to adopt a particular habit doesn't work. You need to seed true motivation both in developers and in business stakeholders to make it a natural adoption. My suggestions: