block / block/proto-fleet

Make Site / Building / Rack columns sortable in the miner list (server-side sort support)

Open
#687 0 comments 0 reactions 0 assignees View on GitHub
client enhancement multi-site
Dominant language
Go
Stars
55
Forks
16
Avg merge
1d 22h
Merged PRs (30d)
87

Description

## Context

The miner selection modal (Search / Manage miners) now shows Model, IP, **Site, Building, Rack**, and Groups columns (#673). Model, IP, and Name are sortable; **Site, Building, and Rack are not**, because the server has no sort support for placement columns.

## Why it's blocked today

The miner list is server-paginated (50/page), so sorting must be server-side — a client-only sort would only reorder the current page. But the server's sort whitelist doesn't include placement:

- `server/internal/domain/stores/sqlstores/device_query_fragments.go` — `sortExpressions` supports only Name, IP, MAC, Model, Hashrate, Temperature, Power, Efficiency, Firmware, WorkerName.
- `SORT_FIELD_LOCATION` exists in `common.v1.SortField` but is explicitly *reserved/unimplemented* (`renaming_test.go`).
- The fleet miner-list page (`MinerList/sortConfig.ts`) doesn't offer these either — so this would be net-new capability, not just wiring.

## Scope

Add server-side sort for **Site, Building, Rack** (Group sort is lower value and multi-valued — call it out but likely skip):

- **Proto:** add `SORT_FIELD_SITE`, `SORT_FIELD_BUILDING`, `SORT_FIELD_RACK` to `common.v1.SortField` (or repurpose `SORT_FIELD_LOCATION` as a composite site→building→rack ordering). Regen Go/TS/SDK.
- **Server:** add `sortExpressions` entries with the JOINs to the placement/collection + site/building tables, plus matching keyset-pagination expressions (`device_sort.go`) so cursor paging stays correct. Handle NULLs (unplaced miners) with `NULLS LAST`.
- **Client:** extend `SORT_FIELD_BY_COLUMN` in `MinerSelectionList.tsx` (and optionally `MinerList/sortConfig.ts` for the fleet page) so the site/building/rack column headers become sortable.
- **Tests:** server sort + keyset-pagination tests; client sort wiring.

## Notes

- Decide composite vs. discrete: a single `LOCATION` sort (site → building → rack → slot) may match operator intent better than three independent sorts. Worth a quick UX call before implementing.
- Group is multi-valued per miner (a miner can be in several groups), so "sort by group" is ambiguous — recommend leaving Group unsortable.

## Related

- Follows #673 (miner selection modal: columns + nested filters + assignable-only toggle). Client already lists Site/Building/Rack columns; this makes them sortable.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Contributor guide

Open the contributing guide

Research direction

Start with common.v1.SortField and its renaming_test.go coverage, then read server/internal/domain/stores/sqlstores/device_query_fragments.go, device_sort.go, and the client sort mapping in MinerSelectionList.tsx. Compare existing server sort and keyset-pagination tests before resolving the composite-versus-discrete location choice. Done means regenerated clients, correct NULLS LAST cursor sorting, sortable client columns, and passing server and client tests.

Written by the indexing model from the issue text.

Assessment

Tech stack
go, sql, typescript
Domain
backend-api-design, databases, frontend, testing
Issue type
Feature
Difficulty
5/5
Estimated time
Over a week
Activity status
Quiet
Clarity
Mostly clear
Newbie friendliness
45/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.