Org.assertj.core.api.objectassert.usingRecursivecomparison () Конфигурация не используется для детей.JAVA

Программисты JAVA общаются здесь
Anonymous
Org.assertj.core.api.objectassert.usingRecursivecomparison () Конфигурация не используется для детей.

Сообщение Anonymous »

Наша команда создает веб -сервис с Kotlin и Springboot, который использует Google Cloud Spanner в качестве хранилища данных. В частности, я хотел бы написать на тесте, который выглядит так: < /p>

Код: Выделить всё

@Test
fun saveAndLoadTest() {
val id = UUID.randomUuid().toString()
val expected = Foo(id)
dao.save(expected)

val actual = dao.load(id)
assertThat(actual).isEqualTo(expected)
}
Но это не работает, если у Foo есть поле, которое заполняется временной меткой синнеров, потому что это поле будет отличаться, когда фактическое сравнивается с ожидаемым .

Код: Выделить всё

@Table("Foo")
data class Foo (

@PrimaryKey
val id: String,

// the value of this field will differ before and after the object is written to the database
@Column(spannerCommitTimestamp = true)
val createdTimestamp: Timestamp = Timestamp.now()
)
Чтобы обойти это, я написал функцию расширения, которая настраивает способ, которым сравниваются два экземпляра Foo . Это выглядит примерно так: < /p>

Код: Выделить всё

fun  ObjectAssert.isEqualIgnoringTimestamps(other: T): ObjectAssert {
this.usingRecursiveComparison()
.ignoringFieldsMatchingRegexes("createdTimestamp.*")
.isEqualTo(other)
return this
}
Если я обновлю модульный тест для использования моей функции расширения, утверждение проходит, потому что любое поле, имя которого начинается с CreatedTimestAmp , будет проигнорировано:

Код: Выделить всё

@Test
fun saveAndLoadTest() {
val id = UUID.randomUuid().toString()
val expected = Foo(id)
dao.save(expected)

val actual = dao.load(id)

// at this point, we're basically only checking that the `id` fields are the same
assertThat(actual).isEqualIgnoringTimestamps(expected)
}
Это здорово, но кажется, что org.assertj.core.api.objectassert.usingRecursivecomparison () не используется для детских объектов. Это означает, что если я немного усложню foo , функция расширения перестает работать:

Код: Выделить всё

@Table("Foo")
data class Foo (

@PrimaryKey
val id: String,

// the "recursive" comparison rules won't be applied to this child object
val child: Foo,

@Column(spannerCommitTimestamp = true)
val createdTimestamp: Timestamp = Timestamp.now()
)

< /code>
Теперь модульный тест не выполняется с сообщением об ошибке, которое выглядит следующим образом: < /p>
Expecting:

to be equal to:

when recursively comparing field by field, but found the following difference:

field/property 'child' differ:
- actual value   : Foo(id=cs6ne8m8tilcbhxq3s4ejxn5n, child=null, createdTimestamp=2021-06-18T20:08:37.352000000Z)
- expected value : Foo(id=cs6ne8m8tilcbhxq3s4ejxn5n, child=null, createdTimestamp=2021-06-18T20:08:37.142614000Z)

The recursive comparison was performed with this configuration:
- the fields matching the following regexes were ignored in the comparison: createdTimestamp.*
- these types were compared with the following comparators:
- java.lang.Double -> DoubleComparator[precision=1.0E-15]
- java.lang.Float -> FloatComparator[precision=1.0E-6]
- actual and expected objects and their fields were compared field by field recursively even if they were not of the same type, this allows for example to compare a Person to a PersonDto (call strictTypeChecking(true) to change that behavior).
Проблема здесь, по -видимому, заключается в том, что поля Child.createdtimestamp не игнорируются во время сравнения, даже если я сказал компаратору игнорировать поля, называемые CaneleTimestAmp . Они, конечно, игнорируются на верхнем уровне - просто не в детском объекте.

Код: Выделить всё

fun  ObjectAssert.isEqualIgnoringTimestamps(other: T): ObjectAssert {
this.usingRecursiveComparison()
.ignoringFieldsOfTypes(Timestamp::class.java)
.isEqualTo(other)
return this
}
< /code>
В любом случае, поле CreatedTimeStamp < /code> игнорируется в объекте, но не игнорируется в объекте Has-A.  Объекты (я бы подумал, что это так, потому что это должно быть [b] рекурсивным [/b], но я думаю, что я был неправ)? Я думаю, я мог бы переопределить методы .equals (...) 
и .hashcode () на foo , так что поле CotenceTimestAmp игнорируется, но затем я пропускаю тестовый код в производственном коде, и это заставляет меня чувствовать себя не так совершить время. Это делает его сложно писать модульные тесты, потому что объект изменяется при его сохранении. Как мне обойти эту проблему?

Подробнее здесь: https://stackoverflow.com/questions/680 ... ation-isnt

Вернуться в «JAVA»