Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
48 changes: 48 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ Please note that some of these tips might not be relevant for all RDBMSs.
- [You can (but shouldn't always) `GROUP BY` column position](#you-can-but-shouldnt-always-group-by-column-position)
- [Create a grand total with `GROUP BY ROLLUP`](#create-a-grand-total-with-group-by-rollup)
- [Use `EXCEPT` to find the difference between two tables](#use-except-to-find-the-difference-between-two-tables)
- [Transform relational data to JSON with aggregation functions](#transform-relational-data-to-json-with-aggregation-functions)

### Performance

Expand Down Expand Up @@ -447,6 +448,53 @@ FROM employees

```

-----
### Transform relational data to JSON with aggregation functions

Use JSON functions like `json_agg` and `json_build_object` to transform relational data into structured JSON, perfect for APIs or nested reporting.

```SQL
-- Basic aggregation into JSON array:
SELECT
dept_no
, json_agg(employee_name) AS employees
FROM employees
GROUP BY dept_no
;

-- Create nested JSON objects:
SELECT
dept_no
, json_agg(
json_build_object(
'name', employee_name,
'salary', salary,
'hire_date', hire_date
)
) AS employee_details
FROM employees
GROUP BY dept_no
;

-- Complex nested structure with ordering:
SELECT
json_build_object(
'department', dept_no,
'total_salary', SUM(salary),
'employees', json_agg(
json_build_object(
'name', employee_name,
'salary', salary
) ORDER BY salary DESC
)
) AS department_summary
FROM employees
GROUP BY dept_no
;
```

Note: JSON functions are available in PostgreSQL, MySQL 5.7+, and most modern databases, but syntax may vary between RDBMSs.

## Performance

### `NOT EXISTS` is faster than `NOT IN` if your column allows `NULL`
Expand Down