siyuan-note/siyuan · warning
attribute view sort values changed; retry the drag
Error message
attribute view sort values changed; retry the drag
What it means
For views with active sorts, applyAttributeViewRowOrder replays the sorts on a cloned view and compares the resulting item order with the pre-sort order. If the sort changes the order, the underlying sort-key values changed since the drag preview (so accepting the drag would silently conflict with the sort), and the commit is rejected for retry.
Source
Thrown at kernel/model/attribute_view_row_sort.go:261
// 预览之后字段值可能变化,提交时再次校验,不能悄悄接受冲突的落点。
copyView, copyErr := cloneAttributeViewRowSort(attrView)
if nil != copyErr {
return copyErr
}
candidate := copyView.GetView(view.ID)
setAttributeViewRowOrder(candidate, change.RowOrder)
collections, renderErr := renderAttributeViewRowSortCollections(copyView, candidate, false)
if nil != renderErr {
return renderErr
}
collection := collections[*change.ValidateGroup]
if nil == collection {
return av.ErrViewNotFound
}
ordered := attributeViewRowSortIDs(collection.GetItems())
av.Sort(collection.(av.Viewable), copyView)
if !slices.Equal(ordered, attributeViewRowSortIDs(collection.GetItems())) {
return errors.New("attribute view sort values changed; retry the drag")
}
}
setAttributeViewRowOrder(view, change.RowOrder)
return nil
}
func isAttributeViewRowOrderOperation(data any) bool {
switch value := data.(type) {
case *attributeViewRowOrderChange:
return nil != value
case map[string]any:
_, ok := value["rowOrder"]
return ok
}
return false
}
func setAttributeViewRowOrder(view *av.View, order *attributeViewRowOrder) {View on GitHub (pinned to 8641553a1f)
Solutions
- Reload the view, re-run the drag preview against current sort values, and retry the commit
- Resolve/refresh the changed sort-key values first, then re-submit the row order
- Accept that a manual drag on a sorted view may be overridden — re-apply the drag after values settle
Example fix
// before
applyAttributeViewRowOrder(tx, avID, viewID, encodedFromPreview)
// after
if err := applyAttributeViewRowOrder(tx, avID, viewID, encodedFromPreview); err != nil {
// sort values changed: reload and rebuild the payload
view := loadView(avID, viewID)
applyAttributeViewRowOrder(tx, avID, viewID, buildFromView(view))
} Defensive patterns
Strategy: retry
Validate before calling
const sortedKeys = getSortKeyValues(avID, viewID);
if (!deepEqual(sortedKeys, previewSortKeyValues)) {
preview = rebuildDragPreview(avID, viewID); // values changed, redo preview
} Try / catch
try {
await sortAttributeViewRow(avID, viewID, encodedChange);
} catch (e) {
if (String(e.msg).includes("sort values changed")) {
await reloadAttributeView(avID);
await retryDragCommit();
}
} Prevention
- Commit drags promptly before background sort values refresh
- Handle remote edits to sort-key columns by cancelling pending drags
- Re-run the drag preview after any cell edit in sorted views
When it happens
Trigger: Calling sortAttributeViewRow on a sorted view where a cell value used by the sort was modified between preview and commit — another client edited a sort-key field, a computed/rollup value refreshed, or sync updated rows.
Common situations: Collaborative editing where another user changes a date/number field used for sorting; background recalculation of relation/rollup values; sync applying remote edits to sort columns mid-drag.
Understand the failure class
Background: "Invalid state transition" errors: "status must be X, actually Y", "already rejected/charging/uninstalled", "cannot ... while running" — what they mean when a library rejects your call — this error's family across 31 libraries.
Related errors
- attribute view order changed; retry the drag
- attribute view rows changed; retry the drag
- attribute view drop target changed; retry the drag
- attribute view groups changed; retry the drag
- no attribute view rows selected
AI-assisted analysis of siyuan-note/siyuan@8641553a1f (2026-09-11).
Data as JSON: /api/errors/79a7fabb093df6e5.
Report an issue: GitHub.