User SQL passed through fmt.Sprintf, where every % means something.
Short answer
StackQL builds the final SQL for views and subqueries by substituting the inner query into a template with fmt.Sprintf. A LIKE '%TLS12%' pattern in a query on a view therefore contained characters that Go read as format verbs, and the result failed with sql packet preparation error: near "(": syntax error. The fix replaces the printf-based substitution with explicit placeholder tokens and a literal-safe expander. It was merged as PR #723 and closed issue #472.
The problem
Issue #472, opened in October 2024, showed a query on the azure.network.vw_application_gateways view with ssl_policy NOT LIKE '%TLS12%' failing, while the equivalent query on the base resource worked.
The fix
Templates now carry named tokens instead of %s:
IndirectQueryPlaceholder = "__iql__placeholder_indirect_query__"
ControlOnClausePlaceholder = "__iql__placeholder_control_on_clause__"
- query = fmt.Sprintf(ca.GetQuery(), childQueryStrings...)
+ query = textutil.ExpandPlaceholders(query, textutil.IndirectQueryPlaceholder, childQueryStrings)
ExpandPlaceholders replaces tokens left to right and never interprets the replacement text. Unit tests include a template with NOT LIKE '%TLS12%', and a Robot Framework scenario was updated.
By the numbers
- Repository: stackql/stackql, 1,074 stars (Nov 3, 2026), Go, MIT
- Files changed: 8
- Lines: +164 / -30
- Commits: 1
- Opened: Aug 21, 2026. Merged: Aug 22, 2026. Time to merge: 16 hours
- Review: approved and merged by a maintainer
How the review went
The maintainer approved and merged it alongside PR #722, with "thanks again".
Takeaways
- Never use user text as a format string. Any
%in a SQL literal is fair game forSprintfonce it lands in the template. - Use tokens that can't collide. A long, distinctive placeholder reduces accidental collisions with ordinary SQL text.
FAQ
Where can I read more?
See the pull request and the original issue.
The goal
Templating and user input should never share a syntax. Separating them makes the rewriter safe for whatever SQL people write.