MEMO_TEXT is up to 28 arbitrary bytes. Horizon exposes memo_bytes alongside memo for exactly this reason.
The rules
- Validate (
utf8.ValidStringin Go) before writing memo text to aTEXTorJSONcolumn, or store the raw bytes. - Treat any string you didn’t validate yourself as bytes. That includes asset codes, home domains and data entry values.
What goes wrong
- PostgreSQL rejects the row with invalid byte sequence for encoding “UTF8”, and ingestion stops at that ledger until someone intervenes.
- A JSON encoder substitutes U+FFFD, so the memo a deposit is routed by no longer matches what the sender wrote.