I'm using the RIO monad and RIO libraries and want to add logging. The RIO log functions, like logInfo
, take a Utf8Builder
as parameter, which is a wrapper around a ByteString
builder. I would like to efficiently insert log statements in my code. However, I am not sure how to transform simple Text
, String
and ByteString
values into the appropriate Builder.
This does not type-check:
logInfo $ "Identifier: " <> UUID.toByteString myId
where myId
is a UUID
value. The type checker error is
• Couldn't match expected type ‘Utf8Builder’
with actual type ‘bytestring-0.10.10.0:Data.ByteString.Lazy.Internal.ByteString’
I tried converting the UUID into Text
instead, tried to use encodeUtf8Builder
and then wrap the resulting Builder
in an Utf8Builder
, but to no avail.
My gut feeling says that logging should simply work, without lots of conversions; so I am probably missing the obvious route. How can I simply log values using the RIO logger?
What you want is a
Display
instance for yourUUID
, which will allow you combine withUtf8Builder
efficiently and easily use it in your logs.The only reason why
displayBytesUtf8
can be used is because you know the content is in ascii. In other words it is your responsibility when creatingDisplay
instance that it produces correctly encoded utf8 bytes.After that you can use it in your logs like so:
Creating
Display
instance isn't strictly speaking necessary, you can just use a helper function if you don't want to create orphan instances or wrapper newtypes. This will do just fine:Reason why I mention
Display
is because it is idiomatic approach in RIO for logging with custom types.