Skip to content

Commit

Permalink
[TH2-5265] fixed: codec can't encode fields with type LocalDateTime
Browse files Browse the repository at this point in the history
…, `LocalDate`, `LocalTime` and value with timezone (#13)

* Updated sailfish: `3.4.260`
  • Loading branch information
Nikita-Smirnov-Exactpro authored Dec 19, 2024
1 parent 187923a commit 6fcee5f
Show file tree
Hide file tree
Showing 5 changed files with 54 additions and 6 deletions.
6 changes: 5 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# th2-codec-fix-ng 0.1.1
# th2-codec-fix-ng 0.1.2

This codec can be used in dirty mode for decoding and encoding messages via the FIX protocol.

Expand Down Expand Up @@ -47,6 +47,10 @@ Component benchmark results available [here](docs/benchmarks/jmh-benchmark.md).

## Release notes

### 0.1.2
+ fixed: codec can't encode fields with type `LocalDateTime`, `LocalDate`, `LocalTime` and value with timezone
+ Updated sailfish: `3.4.260`

### 0.1.1
+ `decodeDelimiter` setting option added.
+ Updated th2 gradle plugin `0.1.6` (th2-bom: `4.9.0`)
Expand Down
2 changes: 1 addition & 1 deletion gradle.properties
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
kotlin.code.style=official
kotlin_version=1.8.22
release_version=0.1.1
release_version=0.1.2

vcs_url=https://github.com/th2-net/th2-codec-fix-ng
7 changes: 4 additions & 3 deletions src/main/kotlin/com/exactpro/th2/codec/fixng/FixNgCodec.kt
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import com.exactpro.sf.common.messages.structures.IDictionaryStructure
import com.exactpro.sf.common.messages.structures.IFieldStructure
import com.exactpro.sf.common.messages.structures.IMessageStructure
import com.exactpro.sf.common.messages.structures.StructureUtils
import com.exactpro.sf.comparison.conversion.MultiConverter
import com.exactpro.th2.codec.api.IPipelineCodec
import com.exactpro.th2.codec.api.IReportingContext
import com.exactpro.th2.codec.fixng.FixNgCodecFactory.Companion.PROTOCOL
Expand Down Expand Up @@ -356,9 +357,9 @@ class FixNgCodec(dictionary: IDictionaryStructure, settings: FixNgCodecSettings)
value is String -> {
try {
when (field.primitiveType) {
LocalDateTime::class.java -> LocalDateTime.parse(value)
LocalDate::class.java -> LocalDate.parse(value)
LocalTime::class.java -> LocalTime.parse(value)
LocalDateTime::class.java -> MultiConverter.convert<LocalDateTime>(value, LocalDateTime::class.java)
LocalDate::class.java -> MultiConverter.convert<LocalDate>(value, LocalDate::class.java)
LocalTime::class.java -> MultiConverter.convert<LocalTime>(value, LocalTime::class.java)
java.lang.Boolean::class.java -> when {
value.equals("true", true) -> true
value.equals("false", true) -> false
Expand Down
35 changes: 35 additions & 0 deletions src/test/kotlin/com/exactpro/th2/codec/fixng/FixNgCodecTest.kt
Original file line number Diff line number Diff line change
Expand Up @@ -534,6 +534,15 @@ class FixNgCodecTest {
expectedMessage = parsedMessageWithNestedGroups
)

@ParameterizedTest
@MethodSource("configs")
fun `encode time zone`(isDirty: Boolean, delimiter: Char) = encodeTest(
MSG_TIME_ZONE,
isDirty,
delimiter,
parsedMessage = parsedMessageWithTimezone
)

private fun createCodec(delimiter: Char = '', decodeValuesToStrings: Boolean = false): FixNgCodec {
return FixNgCodec(dictionary, FixNgCodecSettings(
dictionary = "",
Expand Down Expand Up @@ -873,6 +882,31 @@ class FixNgCodecTest {
)
)

private val parsedMessageWithTimezone = ParsedMessage(
MessageId("test_alias", Direction.OUTGOING, 0L, Instant.now(), emptyList()),
EventId("test_id", "test_book", "test_scope", Instant.now()),
"TimeZoneTestMessage",
mutableMapOf("encode-mode" to "dirty"),
PROTOCOL,
mutableMapOf(
"header" to mutableMapOf(
"MsgSeqNum" to 10947,
"SenderCompID" to "SENDER",
"SendingTime" to "2023-04-19T10:36:07.415088Z",
"TargetCompID" to "RECEIVER",
"BeginString" to "FIXT.1.1",
"BodyLength" to 295,
"MsgType" to "TEST_4"
),
"TransactTime" to "2018-02-05T10:38:08.000008Z",
"TotalVolumeTradedDate" to "2018-02-05Z",
"TotalVolumeTradedTime" to "10:38:08.000008Z",
"trailer" to mutableMapOf(
"CheckSum" to "122"
)
)
)

companion object {
private const val DIRTY_MODE_WARNING_PREFIX = "Dirty mode WARNING: "

Expand Down Expand Up @@ -902,6 +936,7 @@ class FixNgCodecTest {
private const val MSG_NESTED_OPT_COMPONENTS_MISSED_ALL_OUTER_FIELDS_AND_REQ_INNER_FIELD = "8=FIXT.1.19=5935=TEST_249=MZHOT056=INET34=12558=text_110=191"

private const val MSG_NESTED_GROUPS = "8=FIXT.1.19=8835=TEST_349=MZHOT056=INET34=12573=2398=3399=1399=2399=3398=3399=3399=2399=110=211"
private const val MSG_TIME_ZONE = "8=FIXT.1.19=12335=TEST_449=SENDER56=RECEIVER34=1094752=20230419-10:36:07.41508860=20180205-10:38:08.000008449=20180205450=10:38:0810=206"

@JvmStatic
fun configs() = listOf(
Expand Down
10 changes: 9 additions & 1 deletion src/test/resources/dictionary.xml
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?><!--
~ Copyright 2023 Exactpro (Exactpro Systems Limited)
~ Copyright 2023-2024 Exactpro (Exactpro Systems Limited)
~
~ Licensed under the Apache License, Version 2.0 (the "License");
~ you may not use this file except in compliance with the License.
Expand Down Expand Up @@ -7385,6 +7385,14 @@
<attribute name="MessageType" type="java.lang.String">TEST_3</attribute>
<field name="OuterGroup" reference="component-OuterGroup"/>
</message>
<message name="TimeZoneTestMessage">
<attribute name="entity_type" type="java.lang.String">Message</attribute>
<attribute name="IsAdmin" type="java.lang.Boolean">false</attribute>
<attribute name="MessageType" type="java.lang.String">TEST_4</attribute>
<field name="TransactTime" reference="field-TransactTime" required="true"/>
<field name="TotalVolumeTradedDate" reference="field-TotalVolumeTradedDate" required="true"/>
<field name="TotalVolumeTradedTime" reference="field-TotalVolumeTradedTime" required="true"/>
</message>
<message id="component-OuterComponent" name="OuterComponent">
<attribute name="entity_type" type="java.lang.String">Component</attribute>
<field name="InnerComponent" reference="component-InnerComponent" required="true"/>
Expand Down

0 comments on commit 6fcee5f

Please sign in to comment.