Ordered from warm-up to advanced. Each problem builds on a different CTE skill that interviewers test.
Problem 1Warm-up
Filter Before Joining
Write a CTE that pre-filters an orders table to the last 90 days, then join it to a customers table. This tests whether you understand that CTEs let you break a query into readable steps. The naive approach puts the date filter in the WHERE clause after the join. The CTE approach filters first, making the join smaller and the logic clearer.
Skills tested: Basic CTE syntax, query readability, filter pushdown
Problem 2Intermediate
Multi-Step Aggregation
Chain two CTEs: the first aggregates daily revenue per product, the second ranks products by total revenue. The final SELECT pulls the top 5. This is the bread-and-butter CTE pattern. Each CTE does one thing. The result reads top-to-bottom like a recipe.
Skills tested: Chained CTEs, aggregation, ranking
Problem 3Intermediate
CTE for Deduplication
Given a table with duplicate user events (same user_id, same event_type, same timestamp), use a CTE with ROW_NUMBER to keep only the first occurrence per user per event type. Then aggregate the deduplicated result. This pattern appears constantly in real pipelines where source data has duplicates.
Skills tested: ROW_NUMBER inside CTE, deduplication, combining CTEs with window functions
Problem 4Advanced
Recursive Org Chart Traversal
Given an employees table with manager_id, write a recursive CTE that builds the full reporting chain from CEO to every employee. Include a depth column. This is the classic recursive CTE problem. The anchor member selects the root (WHERE manager_id IS NULL). The recursive member joins back to the CTE itself.
Skills tested: Recursive CTE syntax, anchor/recursive members, tree traversal
Problem 5Advanced
Recursive Date Spine
Generate a continuous date series from 2024-01-01 to 2024-12-31 using a recursive CTE, then LEFT JOIN daily revenue data onto it. Days with no revenue should show 0. This solves the 'missing dates' problem that trips up many candidates. Without a date spine, gaps in your data become invisible.
Skills tested: Recursive date generation, LEFT JOIN to fill gaps, COALESCE for defaults