覆盖 Java System.currentTimeMillis 以测试时间敏感代码 [英] Override Java System.currentTimeMillis for testing time sensitive code

查看:32
本文介绍了覆盖 Java System.currentTimeMillis 以测试时间敏感代码的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

除了手动更改主机上的系统时钟之外,是否有其他方法可以通过代码或 JVM 参数覆盖当前时间,如通过 System.currentTimeMillis 呈现的那样?

一点背景:

我们有一个系统运行许多会计工作,这些工作的大部分逻辑围绕当前日期(即一个月的第一天、一年的第一天等)

不幸的是,许多遗留代码调用了诸如 new Date()Calendar.getInstance() 之类的函数,它们最终都调用了 System.currentTimeMillis.

出于测试目的,目前,我们不得不手动更新系统时钟以操纵代码认为测试正在运行的时间和日期.

所以我的问题是:

有没有办法覆盖 System.currentTimeMillis 返回的内容?例如,告诉 JVM 在从该方法返回之前自动添加或减去一些偏移量?

提前致谢!

解决方案

强烈建议您不要弄乱系统时钟,而是硬着头皮重构遗留代码以使用可替换的时钟.理想情况下这应该通过依赖注入来完成,但即使你使用了一个可替换的单例,你也会获得可测试性.

这几乎可以通过搜索和替换单例版本实现自动化:

  • Calendar.getInstance() 替换为 Clock.getInstance().getCalendarInstance().
  • new Date() 替换为 Clock.getInstance().newDate()
  • System.currentTimeMillis() 替换为 Clock.getInstance().currentTimeMillis()

(根据需要等)

一旦您迈出了第一步,您就可以一次用 DI 替换单例.

Is there a way, either in code or with JVM arguments, to override the current time, as presented via System.currentTimeMillis, other than manually changing the system clock on the host machine?

A little background:

We have a system that runs a number of accounting jobs that revolve much of their logic around the current date (ie 1st of the month, 1st of the year, etc)

Unfortunately, a lot of the legacy code calls functions such as new Date() or Calendar.getInstance(), both of which eventually call down to System.currentTimeMillis.

For testing purposes, right now, we are stuck with manually updating the system clock to manipulate what time and date the code thinks that the test is being run.

So my question is:

Is there a way to override what is returned by System.currentTimeMillis? For example, to tell the JVM to automatically add or subtract some offset before returning from that method?

Thanks in advance!

解决方案

I strongly recommend that instead of messing with the system clock, you bite the bullet and refactor that legacy code to use a replaceable clock. Ideally that should be done with dependency injection, but even if you used a replaceable singleton you would gain testability.

This could almost be automated with search and replace for the singleton version:

  • Replace Calendar.getInstance() with Clock.getInstance().getCalendarInstance().
  • Replace new Date() with Clock.getInstance().newDate()
  • Replace System.currentTimeMillis() with Clock.getInstance().currentTimeMillis()

(etc as required)

Once you've taken that first step, you can replace the singleton with DI a bit at a time.

这篇关于覆盖 Java System.currentTimeMillis 以测试时间敏感代码的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆