Native Trino-compatible scalar functions (trino_*) for the cases where DuckDB's built-ins diverge from Trino on Unicode and byte-level inputs — Trino's simple per-code-point case mapping, code-point reverse, Java-whitespace trim, NFC normalize, and raw-bytes xxhash64/sha512/hmac_sha256
Installing and Loading
INSTALL trino_parity FROM community;
LOAD trino_parity;
Example
INSTALL trino_parity FROM community;
LOAD trino_parity;
-- Trino's upper()/lower() are simple per-code-point mappings
-- (Character.toUpperCase(int)), so German sharp-S is unchanged —
-- DuckDB's built-in upper() gives 'STRAẞE' (U+1E9E):
SELECT trino_upper('straße'); -- 'STRAßE'
-- Java whitespace trim: tab / LF / CR / FF / VT are stripped
-- (DuckDB's built-in trim() only strips spaces):
SELECT trino_trim(E'\tx\n'); -- 'x'
-- Code-point reverse (DuckDB's built-in reverse is grapheme-aware):
SELECT trino_reverse('a😀b'); -- 'b😀a'
-- The catalog of functions this extension provides:
SELECT trino_name, arg_count, category FROM trino_meta(); -- 10 rows
About trino_parity
trino_parity provides native trino_<name>(...) scalar functions for the
specific cases where DuckDB's built-ins diverge from Trino's documented
behaviour on Unicode and byte-level inputs.
It is designed to be loaded server-side by anything that pushes Trino-shaped
predicates down to DuckDB. If a Trino connector naively pushes
WHERE lower(name) = 'apple' down to DuckDB, the filter runs with different
Unicode semantics in each engine, and rows visible to Trino can silently
disappear from the result. This extension supplies only the functions
where that actually happens — where DuckDB's built-in genuinely diverges
and a native C++ reimplementation is required to match Trino. For the large
majority of Trino functions DuckDB's built-in is already equivalent (or a
trivial rename / operator / one-line rewrite), so a caller emits those
directly against DuckDB — no extension needed.
Concrete divergences fixed
| Function | DuckDB built-in | Trino spec | trino_* result |
|---|---|---|---|
upper('ß') (U+00DF) |
'ẞ' (U+1E9E, utf8proc special case) |
'ß' unchanged (simple per-code-point mapping) |
matches Trino |
reverse('cafe'+U+0301) |
grapheme-aware | code-point-only | matches Trino |
trim (tab/LF/CR/FF/VT) |
not stripped | Java Character.isWhitespace strips them |
matches Trino |
xxhash64(varbinary) |
no direct built-in | XXH64, big-endian bytes | matches Trino |
Function inventory
trino_meta() catalogs the ten native functions the extension provides:
- String (ICU):
trino_lower/1,trino_upper/1,trino_reverse/1,trino_trim/1,trino_ltrim/1,trino_rtrim/1,trino_normalize/1— simple per-code-point case mapping (Trino'sCharacter.toUpperCase(int)model — noSpecialCasingexpansions or final-sigma rule), code-point reverse, andCharacter.isWhitespacetrim, via statically-linked ICU vendored into the binary (so Unicode behaviour is independent of the host DuckDB build). - Hash (vendored):
trino_xxhash64/1,trino_sha512/1,trino_hmac_sha256/2— over rawVARBINARY, self-contained (no dependency on thecrypto/hashfuncscommunity extensions).
Aligned Trino functions (e.g. length, abs, year, substring,
regexp_extract) are intentionally NOT shipped — a caller emits them as
bare DuckDB SQL. The full per-function Trino↔DuckDB mapping and the
empirical audits that justify each decision are in the repository's docs/.
Source and full divergence catalog: https://github.com/brikk/duckdb-trino-parity-extension
Added Functions
| function_name | function_type | description | comment | examples |
|---|---|---|---|---|
| trino_hmac_sha256 | scalar | NULL | NULL | |
| trino_lower | scalar | NULL | NULL | |
| trino_ltrim | scalar | NULL | NULL | |
| trino_meta | table_macro | NULL | NULL | |
| trino_normalize | scalar | NULL | NULL | |
| trino_reverse | scalar | NULL | NULL | |
| trino_rtrim | scalar | NULL | NULL | |
| trino_sha512 | scalar | NULL | NULL | |
| trino_trim | scalar | NULL | NULL | |
| trino_upper | scalar | NULL | NULL | |
| trino_xxhash64 | scalar | NULL | NULL |
Overloaded Functions
This extension does not add any function overloads.
Added Types
This extension does not add any types.
Added Settings
This extension does not add any settings.