manuelmauro/algonaut

Handling of different transaction field encodings in requests and responses

Closed this issue · 0 comments

While trying to fix the deserialization of SignedTransaction (which we get from the API in PendingTransaction) I noticed that some fields have different encodings when the transaction is part of a request or response:

  • Address: request: byte array, response: base32 string.
  • HashDigest: request: byte array, response: base64 string.
  • Signature: request: byte array, response: base64 string.

The easy way to fix it is by writing the serializers and deserializers respectively (serialize into a byte array and expect a base32 or base64 string as input to deserialize), but I'm not sure that this is correct. I'd expect object = deserialize(serialize(object)) to work, and with this mechanism it doesn't.

I'm not sure about alternatives: creating different API objects (in this case a different ApiSignedTransaction for the request and response) "only" to handle different encodings might be overkill. Making the deserialization flexible, by allowing multiple encodings, seems messy so wouldn't see it as an option.

Edit: Maybe we can inject a deserializer for these fields at runtime? The default deserializer would be the inverse of the serializer and we would override it for the API calls. Not sure if possible with serde.

Relatedly, the Java integration tests which we're porting, often use a serialized transaction representation as reference: https://github.com/algorand/java-algorand-sdk/blob/840cf26043f475e43938c64fbda4526a874c258f/src/test/java/com/algorand/algosdk/account/TestAccount.java#L157
Not sure that I like these tests, but they show an inconvenience with the "asymmetric" solution: we can't just serialize transactions with the SDK to use them as inputs for these tests, we have to instead submit them to the network and use the API version (returned by pending transactions) instead. In some cases this also may not be possible, as e.g. an incomplete multisig transaction can't be submitted to the network.

Edit: Also want to note that (from our side at least) this is not related with the msg pack encoding used in the requests vs. the JSON encoding used in the response. Serializing the transactions to JSON instead of msg pack expectedly doesn't change the value's encoding.