Подтвердить что ты не робот

Как я могу высмеять фактическую дату JodaTime?

Я хочу протестировать этот метод:

 public FirmOrder findActiveByModelColor(ModelColor modelColor) {
   Query query = em.createQuery("FROM FirmOrder fo WHERE fo.modelColor = :modelColor AND fo.year = :year AND fo.month = :month");
   query.setParameter("modelColor", modelColor);
   query.setParameter("year", new DateTime().year().get());
   query.setParameter("month", new DateTime().monthOfYear().get());
   return (FirmOrder) query.getSingleResult();
 }

но мне нужно DateTime().year().get() и DateTime().dayOfMonth().get(), чтобы всегда возвращать ту же дату

ТКС

4b9b3361

Ответ 1

Если вы не можете добавить объект factory, как было предложено skaffman, вы можете использовать DateTimeUtils.setCurrentMillisFixed().

Ответ 2

Затем вам нужно определить интерфейс Clock и ввести его в свой класс

public interface Clock {
    DateTime getCurrentDateTime();
}

то

Clock clock;

public FirmOrder findActiveByModelColor(ModelColor modelColor) {
   Query query = em.createQuery("FROM FirmOrder fo WHERE fo.modelColor = :modelColor AND fo.year = :year AND fo.month = :month");
   query.setParameter("modelColor", modelColor);
   query.setParameter("year", clock.getCurrentDateTime().year().get());
   query.setParameter("month", clock.getCurrentDateTime().dayOfMonth().get());
   return (FirmOrder) query.getSingleResult();
 }

Затем ваш тест может внедрить реализацию Clock (например, используя насмешливую структуру), которая всегда возвращает фиксированное время.

Я использую интерфейс Clock много в своих собственных материалах, и я по-прежнему удивлен, что он не является частью одной из распространенных библиотек. У меня две реализации, которые я использую много, WallClock и StoppedClock (что полезно для тестов, использующих фиксированное время).

Ответ 3

Похоже, единственный вариант - использовать функцию ответа, чтобы опубликовать этот комментарий:

Следующая часть вашего кода может привести к ошибкам, которые трудно обнаружить:

query.setParameter("year", new DateTime().year().get());
query.setParameter("month", new DateTime().monthOfYear().get());

Предположим, что сегодня это последний день 2011 года, и эта часть кода называется 1 nano секундой до нового года и что первый оператор занимает более 1 nano секунды для завершения. Это означает, что год будет установлен на 2011 год, а на месяц до 1, но он должен был быть лучшим либо до 2011/12, либо в 2012 году.

Хотя это статистически очень маловероятно, но логически это может произойти:)

Вы должны создать один экземпляр DateTime и использовать его для заполнения как year, так и month.

Ответ 4

Это легко, если использовать JMockit Ожидания насмешливого API:

@Test
public void findActiveByModelColor()
{
    new NonStrictExpectations()
    {
        @Cascading DateTime dt;

        {
            dt.year().get(); result = 2010;
            dt.monthOfYear().get(); result = 12;
        }
    };

    FirmOrder fo = testedObject.findActiveByModelColor(modelColor);

    // asserts...
}