5. Our own plan-to-SQL translator, identical in Go and TS
sqlfilter.Translate (Go) and planToSql / drizzleFilter (TS) translate exactly the operators generated policies produce (and, or, not, comparisons, in, startsWith/endsWith/contains, null checks),...
Context
Cerbos query plans must become SQL WHERE clauses. @cerbos/orm-drizzle 0.1.0 does not escape % and _ in startsWith, so a path like /u_1/ would also match /uX1/, widening access. Go has no maintained adapter.
Decision
sqlfilter.Translate (Go) and planToSql / drizzleFilter (TS) translate exactly the operators generated policies produce (and, or, not, comparisons, in, startsWith/endsWith/contains, null checks), escape LIKE wildcards with ESCAPE '\', and refuse everything else. Output is byte-for-byte identical across languages (conformance plans/).
Consequences
- An unexpected plan is an error, never a wider query.
- Conditions that use other operators cannot be used in list filters;
zaccessauthors see the error in tests. drizzleFilterrenders throughplanToSql, so Drizzle users get the same SQL with bound columns.