74805a7019
Honor a signed comma-list ?sort= param on list_games/list_sessions/ list_purchases via a new games/sorting.py (SortSpec + per-model maps + parse_sort_terms + apply_sort). Backend applies the full multi-term list. Unknown sort keys are ignored with a user-facing warning toast (never a 400), surfacing #65 link drift without breaking hand-editable URLs. Named string/compound roles throughout (SortKey, SortString, AnnotationName, OrderField, SortTerm, SortResult) so signatures say which value goes where. Includes an N+1 select_related/prefetch_related prereq on the list querysets. Adjacent follow-ups filed: #73 (header UI), #74 (FindFilter unify; also owns the unused FindFilter.direction/page/per_page fields), #75 (purchase search), #76 (shared list_view helper). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>