Query the Top Ten Customers by Recent Spend
VisaSoftware Engineer I · Online AssessmentLast updated
This problem tests proficiency in SQL aggregation, window functions, and joining across normalized transactional tables to perform time-bound analysis.
Problem Statement
Given three tables representing a retail database, write a single PostgreSQL query to identify the top 10 customers based on their total spend during the last 30 days.
Database Schema
users(id, name)orders(id, user_id, order_date)line_items(id, order_id, quantity, unit_price)
Requirements
- Consider a 30-day half-open window:
[current_date - 30 days, current_date). - Calculate the total spend as the sum of
quantity * unit_pricefor all items in completed orders within this window. - Return the
user_id,name, andtotal_spend. - If two users have the same
total_spend, rank the user with the smalleruser_idhigher. - The output should be limited to the top 10 records.
Example Input
If the current date is 2023-10-31, a transaction on 2023-10-01 is included, but a transaction on 2023-09-30 is excluded.
Edge Cases
- Users with zero spend in the window should not be included.
- A user may have multiple orders; ensure all orders are aggregated per user.
- Ensure the join correctly handles orders with no line items (if any).
-- Expected output format:
SELECT user_id, name, total_spend
FROM ...
ORDER BY ...
LIMIT 10;
Hints
Hint 1
Use a JOIN to connect the three tables and filter the `order_date` using the `CURRENT_DATE` and `INTERVAL` keywords.
Hint 2
Group the results by `user_id` and `name` before calculating the sum of the product of quantity and price.
Hint 3
Use the ORDER BY clause with two columns: first by total spend descending, then by user_id ascending to break ties.
Follow-up questions
- How would you modify this query if you needed to calculate a rolling 30-day average spend per user instead of a sum?
- If the 'orders' table contains millions of rows, what indexes would you add to optimize this specific query performance?
- How would you handle a scenario where 'unit_price' in the line_items table is NULL due to promotional items; should they be treated as zero or excluded?
Solution walkthrough is for members
Get the full walkthrough with reference code and complexity analysis, plus Kitty Coach at 300 messages a day. Hints, the code runner and community answers stay free.