From 5e3dc77f1d011c14f0f547c93dbb871a6ddc5a19 Mon Sep 17 00:00:00 2001 From: Deluan Date: Sat, 5 Sep 2026 02:19:30 -0400 Subject: [PATCH] fix(pglite): pick random songs by id instead of rowid PostgreSQL has no rowid; getRandomSongs failed with 'column media_file.rowid does not exist'. The two-pass shape is kept on the primary key. --- persistence/mediafile_repository.go | 25 ++++++++++++------------- 1 file changed, 12 insertions(+), 13 deletions(-) diff --git a/persistence/mediafile_repository.go b/persistence/mediafile_repository.go index a54c128ec..65f709d67 100644 --- a/persistence/mediafile_repository.go +++ b/persistence/mediafile_repository.go @@ -238,33 +238,32 @@ func (r *mediaFileRepository) hydrateArtwork(mfs model.MediaFiles) { hydrateMediaFileArtwork(r.ctx, r.db, mfs) } -// GetRandom uses two passes so the random sort runs over a narrow rowid index instead of the -// wide media_file row: pick random rowids first, then hydrate only those. +// GetRandom uses two passes so the random sort runs over the narrow primary key index instead +// of the wide media_file row: pick random ids first, then hydrate only those. func (r *mediaFileRepository) GetRandom(options ...model.QueryOptions) (model.MediaFiles, error) { var opt model.QueryOptions if len(options) > 0 { opt = options[0] } - rowidQuery := Select("media_file.rowid").From(r.tableName) - rowidQuery = r.applyFilters(rowidQuery, model.QueryOptions{Filters: opt.Filters}) - rowidQuery = r.applyLibraryFilter(rowidQuery) - rowidQuery = rowidQuery.OrderBy("random()") + idQuery := Select("media_file.id").From(r.tableName) + idQuery = r.applyFilters(idQuery, model.QueryOptions{Filters: opt.Filters}) + idQuery = r.applyLibraryFilter(idQuery) + idQuery = idQuery.OrderBy("random()") if opt.Max > 0 { - rowidQuery = rowidQuery.Limit(uint64(opt.Max)) + idQuery = idQuery.Limit(uint64(opt.Max)) } - var rowids []int64 - if err := r.queryAllSlice(rowidQuery, &rowids); err != nil { + var ids []string + if err := r.queryAllSlice(idQuery, &ids); err != nil { return nil, err } - if len(rowids) == 0 { + if len(ids) == 0 { return model.MediaFiles{}, nil } - // Re-shuffle in Phase 2: `WHERE rowid IN (...)` returns rows in ascending rowid order, not - // the random order from Phase 1. Sorting only the (<=Max) hydrated rows is negligible. - sq := r.selectMediaFile().Where(Eq{"media_file.rowid": rowids}).OrderBy("random()") + // Re-shuffle in Phase 2: `WHERE id IN (...)` does not keep the random order from Phase 1. + sq := r.selectMediaFile().Where(Eq{"media_file.id": ids}).OrderBy("random()") var res dbMediaFiles if err := r.queryAll(sq, &res); err != nil { return nil, err