How to fix ER_WINDOW_FUNCTION_IGNORES_FRAME (3599): Window function ignores frame clause in MySQL
MySQL ignores frame clauses when used with ranking and offset window functions like RANK(), ROW_NUMBER(), LAG(), and LEAD(). These functions always operate on the entire partition regardless of frame specifications. Remove the frame clause from affected functions or use frame clauses only with aggregate window functions.
Quick fix
Fixes ER_WINDOW_FUNCTION_IGNORES_FRAME (3599): Window function ignores frame clause
SELECT
employee_id,
salary,
RANK() OVER (PARTITION BY department ORDER BY salary DESC ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) AS rank
FROM employees;- Identify which window functions are in your query
- Remove frame clauses from partition-level functions
- Use frame clauses only with aggregate functions
- Verify frame behavior expectations
SELECTemployee_id,salary,RANK() OVER (PARTITION BY department ORDER BY salary DESC ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) AS rankFROM employees;ER_WINDOW_FUNCTION_IGNORES_FRAME (3599): Window function ignores frame clause
What this error means
MySQL error 3599 occurs when you specify a frame clause (like ROWS BETWEEN or RANGE BETWEEN) with certain window functions that inherently operate on the entire partition. According to SQL standard, these functions should not have frame clauses since they always evaluate across all rows in the partition. MySQL allows the syntax but silently ignores the frame specification, which can lead to unexpected query behavior or confusion about what your query is actually computing. The affected functions are: CUME_DIST(), DENSE_RANK(), LAG(), LEAD(), NTILE(), PERCENT_RANK(), RANK(), and ROW_NUMBER(). Since these functions are designed to rank, number, or offset rows across the partition, frame boundaries do not apply to them.
Typical symptoms
- Frame clause silently ignored when used with RANK(), ROW_NUMBER(), or other ranking functions
- Query returns unexpected results despite adding ROWS or RANGE frame clause
- MySQL warning or error appears in query logs when frame clause is used with partition-level functions
- Performance or result discrepancies after adding frame specifications to ranking functions
Common causes
- Using a frame clause (ROWS BETWEEN, RANGE BETWEEN) with functions designed to operate on entire partitions (RANK, DENSE_RANK, ROW_NUMBER, NTILE, PERCENT_RANK, CUME_DIST, LAG, LEAD)
- Misunderstanding which window functions support frame clauses versus which operate on the full partition
- Copying query patterns from aggregate functions (SUM, AVG, COUNT) and applying them to ranking functions without modification
- Porting queries from other databases that may have different window function semantics
How to fix "ER_WINDOW_FUNCTION_IGNORES_FRAME (3599): Window function ignores frame clause"
Review your query for window functions. Functions like RANK(), ROW_NUMBER(), LAG(), LEAD(), NTILE(), CUME_DIST(), DENSE_RANK(), and PERCENT_RANK() always operate on the entire partition.
Example of problematic code:
SELECT
employee_id,
salary,
RANK() OVER (PARTITION BY department ORDER BY salary DESC ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) AS rank
FROM employees;If you're using RANK(), ROW_NUMBER(), LAG(), LEAD(), NTILE(), CUME_DIST(), DENSE_RANK(), or PERCENT_RANK(), remove any ROWS BETWEEN, RANGE BETWEEN, or GROUPS frame specifications. These functions ignore them anyway.
Fixed example:
SELECT
employee_id,
salary,
RANK() OVER (PARTITION BY department ORDER BY salary DESC) AS rank
FROM employees;Frame clauses are meaningful only with aggregate window functions like SUM(), AVG(), COUNT(), MIN(), MAX(), or with FIRST_VALUE(), LAST_VALUE(), and NTH_VALUE() that actually respect frame definitions.
Correct use of frame clause:
SELECT
employee_id,
salary,
SUM(salary) OVER (PARTITION BY department ORDER BY salary DESC ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) AS running_total
FROM employees;If you need to aggregate over a specific frame of rows (running totals, moving averages), ensure you're using aggregate functions that support frames. If you're trying to rank rows, use the ranking functions without frame clauses, as they always use the entire partition.
Example - running salary total:
SELECT
employee_id,
salary,
SUM(salary) OVER (PARTITION BY department ORDER BY salary DESC ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) AS running_salary_total
FROM employees;Example - ranking without frames (correct approach):
SELECT
employee_id,
salary,
RANK() OVER (PARTITION BY department ORDER BY salary DESC) AS salary_rank
FROM employees;Advanced notes
Default frame behavior in MySQL depends on whether ORDER BY is present: With ORDER BY, the default frame is RANGE BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW. Without ORDER BY, the default is RANGE BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING (the entire partition). This means adding ORDER BY to a query can change results even without an explicit frame clause. For deterministic results, provide explicit frame specifications. The GROUPS frame unit and EXCLUDE clause are parsed but produce errors in MySQL—only ROWS and RANGE are fully supported.
Frequently asked questions
- What does "ER_WINDOW_FUNCTION_IGNORES_FRAME (3599): Window function ignores frame" mean?
- MySQL error 3599 occurs when you specify a frame clause (like ROWS BETWEEN or RANGE BETWEEN) with certain window functions that inherently operate on the entire partition. According to SQL standard, these functions should not have frame clauses since they always evaluate across all rows in the partition. MySQL allows the syntax but silently ignores the frame specification, which can lead to unexpected query behavior or confusion about what your query is actually computing.
- How do I fix "ER_WINDOW_FUNCTION_IGNORES_FRAME (3599): Window function ignores frame"?
- MySQL ignores frame clauses when used with ranking and offset window functions like RANK(), ROW_NUMBER(), LAG(), and LEAD(). These functions always operate on the entire partition regardless of frame specifications. Remove the frame clause from affected functions or use frame clauses only with aggregate window functions.
- What causes "ER_WINDOW_FUNCTION_IGNORES_FRAME (3599): Window function ignores frame"?
- Using a frame clause (ROWS BETWEEN, RANGE BETWEEN) with functions designed to operate on entire partitions (RANK, DENSE_RANK, ROW_NUMBER, NTILE, PERCENT_RANK, CUME_DIST, LAG, LEAD) Misunderstanding which window functions support frame clauses versus which operate on the full partition Copying query patterns from aggregate functions (SUM, AVG, COUNT) and applying them to ranking functions without modification
- Is the "ER_WINDOW_FUNCTION_IGNORES_FRAME (3599): Window function ignores frame" error serious?
- It is a medium-severity error — more of a blocker than a risk. The steps above resolve it.
Official resources & further reading
- 📚MySQL Official Documentation
- 📖dev.mysql.com - window functions frames(Official Docs)
- 📖dev.mysql.com - window function restrictions(Official Docs)
- 🔗