Unable to evolve Enum by appending new fields.
See original GitHub issueWhen I have an enum serialized in the vault as this:
@CordaSerializable
enum class MyEnum { A, B, C }
and then in later version of my cordapp I update it to:
@CordaSerializationTransformEnumDefaults(
CordaSerializationTransformEnumDefault("E", "C"),
CordaSerializationTransformEnumDefault("D", "C")
)
@CordaSerializable
enum class MyEnum { A, B, C, D, E }
then I receive such exception: java.io.NotSerializableException: Constants have been reordered, additions must be appended to the end
.
Looking at the unit tests it seems that they test this scenario: Node A receives serialized enum from node B. This received enum has new constants added and the required annotation added and node A has only “old” enum constants. Node A is able to deserialize as required transforms are described in the deserialized enum from node B. That seems to work nicely.
My scenario is vice versa. I have some enum in my vault and I just want to add new constants to it. After adding new constants and the annotation and starting up the nodes I try to retrieve a state with that enum but I get an aforementioned exception.
Same issue when appending a single new value. And the same issue when appending same value without using CordaSerializationTransformEnumDefaults
(only using CordaSerializationTransformEnumDefault
)
Happened on V3.1
Issue Analytics
- State:
- Created 5 years ago
- Comments:9 (2 by maintainers)
I was trying to fix it myself and have come up with the following. Here it is checked whether the enum constants have been reordered: https://github.com/corda/corda/blob/release-V3.X/node-api/src/main/kotlin/net/corda/nodeapi/internal/serialization/amqp/EnumEvolutionSerializer.kt#L111
When replicating my use case then
ordinals
is bigger (it has new constants which are found on the classpath) thanserialisedOrds
(it contains only ‘old’ constants which were present during serialization). As it is bigger, thenfilterNot
finds those new constants and assumes that something was reordered and throws. I added an additional check to applyfilterNot
on ‘smaller’ collection, like that:With this fix all existing tests in
EnumEvolveTests
passed and I was able to perform the enum update which I described in the issue description.I know that in future versions of corda whole serialization will be overhauled but could you tell if this would be safe to do until I can start using newer corda?
Fixed.