fix(catalog): wrap series-name DISTINCT in subquery so ORDER BY LOWER(...) works
Postgres rejects ORDER BY expressions that aren't in the SELECT list when SELECT DISTINCT is used (\"ORDER BY expressions must appear in select list\"). The original listDistinctAudiobookSeriesWithSource emitted SELECT DISTINCT BTRIM(s.series_name) with ORDER BY LOWER(BTRIM(s.series_name)) and failed with that error, which surfaced as a 500 on every /api/v1/catalog/filters request that hit the audiobook-series facet. Push the DISTINCT into an inline subquery aliased as \"names\"; the outer SELECT then orders by LOWER(name) without running afoul of the distinct-vs-order rule. Same trimming + case-folding behaviour for sort, same trimmed literal returned. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 4.7
parent
3357c49d72
commit
3e35da7f0c
@@ -762,9 +762,14 @@ func listDistinctPeopleByKindWithSource(
|
||||
|
||||
// listDistinctAudiobookSeriesWithSource returns distinct series_name values
|
||||
// from audiobook_series joined onto the scoped result set. Names are trimmed
|
||||
// and case-folded in the ORDER BY so the picker doesn't show duplicates that
|
||||
// differ only by whitespace or casing — the literal series_name is still
|
||||
// and case-folded for sort so the picker doesn't show duplicates that differ
|
||||
// only by whitespace or casing — the literal trimmed series_name is still
|
||||
// returned so existing rules continue to match.
|
||||
//
|
||||
// The DISTINCT happens in an inline subquery (rather than directly on the
|
||||
// outer SELECT) so the outer ORDER BY can apply LOWER(...) without violating
|
||||
// Postgres' "ORDER BY expressions must appear in select list" rule for
|
||||
// SELECT DISTINCT.
|
||||
func listDistinctAudiobookSeriesWithSource(
|
||||
ctx context.Context,
|
||||
pool *pgxpool.Pool,
|
||||
@@ -777,13 +782,15 @@ func listDistinctAudiobookSeriesWithSource(
|
||||
return []string{}, nil
|
||||
}
|
||||
query := fmt.Sprintf(`
|
||||
SELECT DISTINCT BTRIM(s.series_name) AS series_name
|
||||
FROM %s
|
||||
JOIN audiobook_series s ON s.content_id = mi.content_id
|
||||
%s
|
||||
AND s.series_name IS NOT NULL
|
||||
AND BTRIM(s.series_name) <> ''
|
||||
ORDER BY LOWER(BTRIM(s.series_name)) ASC
|
||||
SELECT name FROM (
|
||||
SELECT DISTINCT BTRIM(s.series_name) AS name
|
||||
FROM %s
|
||||
JOIN audiobook_series s ON s.content_id = mi.content_id
|
||||
%s
|
||||
AND s.series_name IS NOT NULL
|
||||
AND BTRIM(s.series_name) <> ''
|
||||
) names
|
||||
ORDER BY LOWER(name) ASC
|
||||
`, fromClause, browseFilterPrefix(whereClause))
|
||||
return queryDistinctStrings(ctx, pool, query, args)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user