Good SQL formatting is about making the structure of a query visible: one clause per line, one column per line, consistent keyword casing, and qualified column names, so that a reader can see what the query touches without parsing it in their head. SQL is whitespace-insensitive, which means the database does not care how you format it, but reviewers and your future self care enormously. A well-formatted query reveals its joins, its filters, and its grouping at a glance and produces small, readable diffs when it changes. This guide lays out a set of conventions that hold up in code review, with before-and-after examples.
Does formatting affect how a query runs?
No, formatting has zero effect on results or performance, because the SQL parser ignores insignificant whitespace and treats keywords case-insensitively. SELECT, select, and Select are the same token, and a query written on one long line runs identically to the same query spread over twenty. That is precisely why a style guide is worth having: since the machine does not constrain you, the only discipline comes from convention. Every formatting choice below is made purely to help humans read, review, and safely edit the query, never to change what it does.
Should keywords be uppercase?
Uppercase reserved keywords with lowercase identifiers is the most widely used convention, because the contrast lets the eye separate the query’s skeleton from its data. When SELECT, FROM, JOIN, and WHERE are uppercase and your table and column names are lowercase, the clauses stand out as landmarks. The alternative, all-lowercase everything, is also perfectly readable and some teams prefer it; what matters is that the whole codebase agrees. Compare:
-- inconsistent, hard to scan
select id, Name, created_at FROM Users where STATUS = 'active';
-- consistent: uppercase keywords, lowercase identifiers
SELECT id, name, created_at
FROM users
WHERE status = 'active';
The second version reads as a set of labelled sections. Pick uppercase or lowercase for keywords, write it into your style guide, and enforce it, so that casing never becomes a thing people argue about in review. One subtlety worth deciding up front is how you treat built-in function names such as COUNT, SUM, and COALESCE. Many teams uppercase these along with the reserved keywords, since they are part of the language rather than your data, while keeping table and column names lowercase. Whatever you choose, apply it uniformly: a query that uppercases COUNT but lowercases sum reads as though two people wrote it.
Where should lines break?
Break before every major clause and put every selected column and every join condition on its own line, so the query becomes a vertical list you can scan top to bottom. A one-line query hides its structure; a vertically laid-out query exposes it. The rule is: SELECT, FROM, each JOIN, WHERE, GROUP BY, HAVING, and ORDER BY each start a new line, and within the select list each expression sits on its own line. This has a practical payoff beyond looks: when you add or remove one column, the diff is a single line, which makes review and blame far clearer.
SELECT
u.id,
u.name,
u.email,
o.total
FROM users AS u
JOIN orders AS o
ON o.user_id = u.id
WHERE u.status = 'active'
AND o.total > 100
ORDER BY o.total DESC;
Notice the join condition sits on an indented continuation line under the JOIN, and the second WHERE condition is indented under the first. That indentation signals “this belongs to the clause above” without you having to read the keywords.
Leading or trailing commas?
Both comma styles are valid, and the choice is mostly about which class of mistake you want to make obvious. Trailing commas, with the comma at the end of each line, read the way English does and feel natural to most people. Leading commas, with the comma at the start of each line, make a missing comma visually obvious and keep the diff for a newly added column confined to that one new line. The table sums up the trade-off:
| Aspect | Trailing commas | Leading commas |
|---|---|---|
| Look | id, at line end |
, id at line start |
| Missing-comma bugs | Easy to overlook | Immediately visible |
| Diff when adding a column | Touches previous line too | Single new line |
| Familiarity | Reads naturally | Takes adjustment |
Neither is objectively correct. Choose one per project and apply it everywhere; the cost of mixing the two is that the eye keeps having to re-adjust.
How should I handle aliases and column qualification?
In any query touching more than one table, give each table a short alias and qualify every column with it, so a reader never has to guess which table a column comes from. In the example above, u and o make u.id and o.total unambiguous. Unqualified columns in a multi-table query are a readability and correctness hazard: if two tables both have a created_at column, an unqualified reference is ambiguous, and even when it is not, the reader has to remember which table owns it. Keep aliases short but meaningful, and write the AS keyword for column aliases to make them obvious. In a single-table query, aliases add little and can be skipped. The general principle: the more tables involved, the more every column should be qualified.
How do I format joins and subqueries clearly?
Format joins so the join type, the table, and the condition are each easy to find, and indent subqueries so their boundaries are unmistakable. Always write the join type explicitly. JOIN alone means INNER JOIN in standard SQL, but spelling out INNER JOIN, LEFT JOIN, and so on removes any doubt about intent for the next reader. Put the ON condition on its own indented line beneath the join. For subqueries, indent the inner query one level and keep its own clauses formatted by the same rules, so it reads as a self-contained block:
SELECT
u.name,
recent.order_count
FROM users AS u
LEFT JOIN (
SELECT
user_id,
COUNT(*) AS order_count
FROM orders
WHERE created_at >= '2026-01-01'
GROUP BY user_id
) AS recent
ON recent.user_id = u.id
ORDER BY recent.order_count DESC;
The indented parentheses and the nested clause layout make it clear where the subquery starts and stops. A deeply nested query is often a sign to refactor into a common table expression (a WITH clause), which many find even more readable because it names each step and reads top to bottom.
How do I apply a style consistently?
Apply your style automatically rather than by hand, because consistency is the whole point and humans are unreliable at it. Once you have decided on casing, line breaks, comma placement, and indentation, the fastest way to keep a query base uniform is to run queries through a formatter that encodes those choices, so no one spends review time on whitespace. A client-side SQL formatter reformats a pasted query in your browser, which matters here because SQL frequently contains real table names, column names, and sometimes literal values from your schema that you would rather not send to a third-party server just to tidy the indentation. Format locally, paste the clean result back, and keep the sensitive structure of your database on your own machine.
The heart of SQL style is a single idea: use whitespace to make structure visible. One clause per line, one column per line, explicit join types, qualified columns, and a consistent casing and comma convention turn even a large query into something a reviewer can read like prose. None of it changes what the query does, and all of it changes how quickly the next person can understand and safely modify it.