Sorting
Sorting
Section titled “Sorting”Sort criteria for collection queries
Overview
Section titled “Overview”Sorting allows clients to specify the order of resources in collection responses. Multiple sort criteria are applied in sequence.
Sort Object
Section titled “Sort Object”A sort specifies ordering for a single attribute:
{ "attribute": "created_at", "direction": "desc"}Fields
Section titled “Fields”| Field | Type | Required | Description |
|---|---|---|---|
attribute | string | Yes | Attribute to sort by |
direction | string | Yes | Sort direction |
Direction Values
Section titled “Direction Values”| Value | SQL Equivalent | Description |
|---|---|---|
asc | ASC | Ascending (smallest first) |
desc | DESC | Descending (largest first) |
Sort Arrays
Section titled “Sort Arrays”Multiple sorts create compound ordering:
{ "sorts": [ { "attribute": "status", "direction": "asc" }, { "attribute": "created_at", "direction": "desc" } ]}Order of Application
Section titled “Order of Application”Sorts are applied in array order:
{ "sorts": [ { "attribute": "country_code", "direction": "asc" }, { "attribute": "city", "direction": "asc" }, { "attribute": "name", "direction": "asc" } ]}// SQL: ORDER BY country_code ASC, city ASC, name ASCPrimary sort is first, then secondary, etc.
Allowed Sorts
Section titled “Allowed Sorts”Servers MUST define which attributes are sortable:
{ "sorts": { "self": ["name", "created_at", "updated_at", "status", "total_amount"] }}Validation
Section titled “Validation”- Sorting on non-allowed attributes MUST return an error
- Servers SHOULD expose allowed sorts via
mesh.describe
Error Response
Section titled “Error Response”{ "errors": [{ "code": "INVALID_ARGUMENTS", "message": "Sort attribute not allowed: secret_score", "retryable": false, "source": { "pointer": "/call/arguments/sorts/0/attribute" }, "details": { "attribute": "secret_score", "allowed": ["name", "created_at", "status"] } }]}Default Sorting
Section titled “Default Sorting”Server Defaults
Section titled “Server Defaults”When no sort is specified, servers SHOULD apply a default sort:
- By primary key (
id) ascending - By creation timestamp (
created_at) descending - By a natural ordering attribute
Servers MUST document their default sort behavior.
Stable Sorting
Section titled “Stable Sorting”For pagination stability, servers SHOULD include a unique attribute (like id) as the final sort criterion, even if not explicitly requested:
// Client requests{ "sorts": [{ "attribute": "status", "direction": "asc" }] }
// Server applies (for stability)// ORDER BY status ASC, id ASCSort Direction Semantics
Section titled “Sort Direction Semantics”Ascending (asc)
Section titled “Ascending (asc)”| Type | Order |
|---|---|
| Numbers | 1, 2, 3, 10, 100 |
| Strings | A, B, C, a, b, c (locale-dependent) |
| Dates | Oldest first |
| Booleans | false, true |
| Nulls | First or last (implementation-defined) |
Descending (desc)
Section titled “Descending (desc)”| Type | Order |
|---|---|
| Numbers | 100, 10, 3, 2, 1 |
| Strings | c, b, a, C, B, A (locale-dependent) |
| Dates | Newest first |
| Booleans | true, false |
| Nulls | First or last (implementation-defined) |
Null Handling
Section titled “Null Handling”Servers SHOULD document null ordering behavior:
| Behavior | Description |
|---|---|
nulls_first | Nulls sort before non-null values |
nulls_last | Nulls sort after non-null values |
Common Sort Patterns
Section titled “Common Sort Patterns”Chronological (Newest First)
Section titled “Chronological (Newest First)”{ "sorts": [ { "attribute": "created_at", "direction": "desc" } ]}Alphabetical
Section titled “Alphabetical”{ "sorts": [ { "attribute": "name", "direction": "asc" } ]}Priority/Status Ordering
Section titled “Priority/Status Ordering”{ "sorts": [ { "attribute": "priority", "direction": "asc" }, { "attribute": "created_at", "direction": "asc" } ]}Geographic (with Distance)
Section titled “Geographic (with Distance)”{ "sorts": [ { "attribute": "distance", "direction": "asc" } ]}Examples
Section titled “Examples”Single Sort
Section titled “Single Sort”{ "call": { "function": "orders.list", "version": "1", "arguments": { "sorts": [ { "attribute": "created_at", "direction": "desc" } ] } }}Multiple Sorts
Section titled “Multiple Sorts”{ "arguments": { "sorts": [ { "attribute": "status", "direction": "asc" }, { "attribute": "priority", "direction": "desc" }, { "attribute": "created_at", "direction": "asc" } ] }}With Filtering
Section titled “With Filtering”{ "arguments": { "filters": [ { "attribute": "status", "operator": "in", "value": ["pending", "processing"] } ], "sorts": [ { "attribute": "created_at", "direction": "desc" } ], "pagination": { "limit": 25 } }}Location-Based Sort
Section titled “Location-Based Sort”{ "call": { "function": "locations.list", "version": "1", "arguments": { "filters": [ { "attribute": "type", "operator": "equals", "value": "pickup_point" }, { "attribute": "country_code", "operator": "equals", "value": "FI" } ], "sorts": [ { "attribute": "distance", "direction": "asc" }, { "attribute": "name", "direction": "asc" } ], "pagination": { "limit": 10 } } }}Full Query Example
Section titled “Full Query Example”{ "protocol": { "name": "mesh", "version": "0.1.0" }, "id": "req_sorted", "call": { "function": "tracking_events.list", "version": "1", "arguments": { "fields": { "self": ["id", "status", "location", "occurred_at"] }, "filters": [ { "attribute": "shipment_id", "operator": "equals", "value": "ship_12345" } ], "sorts": [ { "attribute": "occurred_at", "direction": "desc" } ], "pagination": { "limit": 100 } } }}Discovery
Section titled “Discovery”Functions SHOULD advertise sortable attributes via mesh.describe:
{ "result": { "function": "orders.list", "query": { "sorts": { "self": ["id", "order_number", "status", "total_amount", "created_at", "updated_at"] }, "default_sort": [ { "attribute": "created_at", "direction": "desc" } ] } }}