squirrel
Fluent SQL generation for golang
Squirrel is a Go library that lets you build SQL queries piece by piece in code instead of writing raw SQL strings, handling escaping and placeholder formatting for you.
What Squirrel Does
Squirrel is a Go library that makes it easier to write SQL queries by building them piece by piece instead of writing raw SQL strings. Think of it like assembling a query from building blocks—you can add a WHERE clause here, a JOIN there, and Squirrel handles turning it all into valid SQL for you. The payoff is cleaner code and the ability to conditionally add query parts without messy string concatenation.
How It Works
Instead of writing SELECT * FROM users WHERE age > 21 LIMIT 10 as a string, you write it in Go code: sq.Select("*").From("users").Where(sq.Gt{"age": 21}).Limit(10). Each method chains onto the previous one, letting you build up a complete query. When you're done, you call ToSql() and Squirrel gives you back the finished SQL string, the parameter values, and any errors. You can also execute it directly against your database using RunWith().
The library handles the annoying details: it properly escapes values to prevent SQL injection, converts your Go conditions into SQL WHERE clauses, manages placeholder characters (so if you're using PostgreSQL you can use $1, $2 instead of ?), and keeps your query building code readable even when you need to conditionally add filters based on user input.
Who Would Use It
Any Go developer building a backend service or API would find this useful. Say you're building a user search feature where users can filter by name, age, and signup date—some filters might be empty. Instead of writing separate SQL queries for every combination, you'd build one query object and only add the WHERE conditions that apply. Database administrators might also appreciate that the generated SQL is explicit and readable, not hidden away in string templates.
Notable Tradeoff
Squirrel is intentionally not an ORM—it doesn't map database rows to Go structs automatically. It only handles building and running SQL. This keeps it lightweight and straightforward, but if you need automatic object mapping you'd need to use a different tool or add it yourself.
Where it fits
- Build a user search feature with optional filters without writing separate SQL for each combination.
- Generate parameterized SQL safely without manual string concatenation.
- Switch placeholder styles between databases, like using $1, $2 for PostgreSQL.
- Execute built queries directly against a database using RunWith().