Python Tutorial
Python MySQL - Order By
Sort query results ascending or descending, by one column or several.
Sort Ascending
ORDER BY sorts the result. The default direction is ascending (ASC).
import mysql.connector
conn = mysql.connector.connect(
host="localhost", user="root", password="secret", database="mydatabase")
cursor = conn.cursor()
cursor.execute("SELECT * FROM customers ORDER BY name")
for row in cursor.fetchall():
print(row) # rows sorted A -> Z by nameSort Descending
cursor.execute("SELECT * FROM customers ORDER BY name DESC") # Z -> ASort by Multiple Columns
List several columns; ties on the first are broken by the next, each with its own direction.
cursor.execute(
"SELECT * FROM orders ORDER BY customer_id ASC, amount DESC")
# grouped by customer, and within each customer the biggest orders firstColumns Vs Values
Parameters (%s) can only stand in for values, not for column or table names or the sort direction. To sort by a user-chosen column, validate it against an allowlist first.
allowed = {"name", "address", "id"} # whitelist of real columns
column = user_input if user_input in allowed else "id"
direction = "DESC" if descending else "ASC"
sql = f"SELECT * FROM customers ORDER BY {column} {direction}"
cursor.execute(sql)Never drop raw user input into a column name — that reopens SQL injection. Map it through a fixed allowlist as shown.
NULLs and Sorting
In MySQL, NULL values sort first in ascending order and last in descending. Push them where you want with an expression:
cursor.execute(
"SELECT * FROM customers ORDER BY address IS NULL, address ASC")
# rows with an address first, NULLs lastBest Practices
- Combine
ORDER BYwithLIMITfor "top N" queries. - Index the columns you sort on frequently to avoid slow filesort operations.
- Allowlist column names when the sort field comes from user input.
- Add a tie-breaker column (like
id) for deterministic ordering.
Try It Yourself
Exercise 1: Return the 5 most expensive orders.
Show solution
cursor.execute(
"SELECT * FROM orders ORDER BY amount DESC LIMIT 5")Exercise 2: Why can't you pass a column name as a %s parameter for ORDER BY?
Show solution
Parameters only substitute values, not identifiers. Validate a user-chosen column against an allowlist and interpolate it safely.
📘 Real-World Deep Dive
Knowing <strong>MySQL Order By (MySQL)</strong> well is what turns MySQL from a curiosity into a daily tool — you'll reach for it in nearly every real project.
Real-Life Scenario
An end-to-end usage of MySQL Order By that you'd actually see in a data pipeline or analytics notebook.
Real-Life Example
SELECT id, name FROM users ORDER BY name ASC LIMIT 50;Expected Output
(no output)Common mistakes
- Reading with the default cursor returns tuples — switch to
DictCursorfor named access. - Strings without parameter binding produce SQL-injection holes — never use f-strings in queries.
- Connecting through a long-lived daemon pool: make sure
pool_reset_connectionis on to avoid session state leakage. - Treating MySQL Order By as a black box without reading the docs — the API has subtle defaults that bite when you scale.
🚀 Performance & Best Practices
- Use prepared statements (
cursor.executemany) for bulk inserts. - Fetch with
cursor.fetchmany(1000)in streams instead offetchall(). - Use
pymysql's server-side cursors for very large result sets. - When working with MySQL, prefer vectorised / batched operations over Python loops.
🧪 Try It Yourself
- Reproduce the snippet on a representative slice of your own data.
- Profile the snippet with
cProfileortimeitand find the single biggest improvement. - Generalise the snippet into a small, reusable function you can drop into future projects.