payloadcms / payloadcms/payload

Switching list-view tabs (All / By Folder / Trash) wipes the collection's saved preferences (columns, sort, limit)

Open Beginner friendly
#17,666 2 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Dominant language
TypeScript
Stars
44.8k
Forks
4.2k
Avg merge
2d 21h
Merged PRs (30d)
53

Description

Describe the Bug

DefaultListViewTabs saves which sub-view is active with:

// @payloadcms/ui/dist/elements/DefaultListViewTabs/index.js (3.87.0, ~line 41)
await setPreference(`collection-${collectionConfig.slug}`, {
  listViewType: newViewType
});

setPreference defaults to merge = false (providers/Preferences/index.js, line 76), so this call replaces the entire collection-<slug> preference record with { listViewType } — silently destroying the user's saved columns, sort, limit and any other list preferences, every time they click between "All " and "By Folder" (or Trash).

We confirmed the mechanism by reading the payload-preferences record before/after a tab click: a record containing { limit, columns, listViewType } is reduced to { listViewType: "folders" } by a single click on the By Folder pill.

This hits folder-enabled upload collections hardest: users add the Folder column, visit By Folder to organise, come back — and their column setup is gone. Non-technical editors experience this as "my columns keep randomly disappearing".

Reproduction steps

  1. Any collection with folders: true (or trash: true) so the tab pills render.
  2. In the list view, add a column via the Columns panel (e.g. Folder). Confirm the collection-<slug> preference record now contains columns.
  3. Click By Folder, then All .
  4. The added column is gone; the preference record contains only { listViewType }.

Expected / Actual

  • Expected: switching tabs remembers the active sub-view without touching other saved preferences.
  • Actual: every tab switch replaces the whole preference record.

Proposed fix

Pass the existing merge flag (one argument):

  await setPreference(`collection-${collectionConfig.slug}`, {
    listViewType: newViewType
- });
+ }, true);

Note the same handler is also inlined (minified) in dist/exports/client/index.js, which is what some import sites actually execute — the fix needs to land in the source so both builds pick it up. We've been running this exact change in production via a pnpm patch with no side effects.

Environment

  • Payload: 3.86.0 (found), verified still present in 3.87.0 source
  • @payloadcms/db-postgres, @payloadcms/next
  • Next.js: 16.2.11
  • Node: 22.14.0
  • pnpm 10.30.3, macOS / Vercel

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start with the DefaultListViewTabs handler and providers/Preferences/index.js, then reproduce the tab switch while inspecting the payload-preferences record. Check the source path that generates the mentioned dist/exports/client/index.js build. Done means switching tabs preserves columns, sort, limit, and other existing preferences while updating listViewType.

Written by the indexing model from the issue text.

Assessment

Tech stack
nextjs, typescript
Domain
frontend
Issue type
Bug
Difficulty
2/5
Estimated time
1-3 hours
Activity status
Quiet
Clarity
Clearly specified
Newbie friendliness
78/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.