Files
payload/test/plugin-import-export/collections/Pages.ts
Patrik 2a59c5bf8c fix(plugin-import-export): export field dropdown to properly label and path fields in named/unnamed tabs (#13180)
### What?

Fixes the export field selection dropdown to correctly differentiate
between fields in named and unnamed tabs.

### Why?

Previously, when a `tabs` field contained both named and unnamed tabs,
subfields with the same `name` would appear as duplicates in the
dropdown (e.g. `Tab To CSV`, `Tab To CSV`). Additionally, selecting a
field from a named tab would incorrectly map it to the unnamed version
due to shared labels and missing path prefixes.

### How?

- Updated the `reduceFields` utility to manually construct the field
path and label using the tab’s `name` if present.
- Ensured unnamed tabs treat subfields as top-level and skip prefixing
altogether.
- Adjusted label prefix logic to show `Named Tab > Field Name` when
appropriate.


#### Before
<img width="169" height="79" alt="Screenshot 2025-07-15 at 2 55 14 PM"
src="https://github.com/user-attachments/assets/2ab2d19e-41a3-4be2-8496-1da2a79f88e1"
/>

#### After
<img width="211" height="79" alt="Screenshot 2025-07-15 at 2 50 38 PM"
src="https://github.com/user-attachments/assets/0620e96a-71cd-4eb1-9396-30d461ed47a5"
/>
2025-07-15 16:41:07 -04:00

221 lines
4.7 KiB
TypeScript

import type { CollectionConfig } from 'payload'
import { pagesSlug } from '../shared.js'
export const Pages: CollectionConfig = {
slug: pagesSlug,
labels: {
singular: { en: 'Page', es: 'Página' },
plural: { en: 'Pages', es: 'Páginas' },
},
admin: {
useAsTitle: 'title',
},
versions: {
drafts: true,
},
fields: [
{
name: 'title',
label: { en: 'Title', es: 'Título', de: 'Titel' },
type: 'text',
required: true,
},
{
name: 'localized',
type: 'text',
localized: true,
},
{
name: 'custom',
type: 'text',
defaultValue: 'my custom csv transformer',
custom: {
'plugin-import-export': {
toCSV: ({ value, columnName, row, siblingDoc }) => {
return String(value) + ' toCSV'
},
},
},
},
{
name: 'customRelationship',
type: 'relationship',
relationTo: 'users',
custom: {
'plugin-import-export': {
toCSV: ({ value, columnName, row }) => {
if (value && typeof value === 'object' && 'id' in value && 'email' in value) {
row[`${columnName}_id`] = (value as { id: number | string }).id
row[`${columnName}_email`] = (value as { email: string }).email
}
},
},
},
},
{
name: 'group',
type: 'group',
fields: [
{
name: 'value',
type: 'text',
defaultValue: 'group value',
},
{
name: 'ignore',
type: 'text',
},
{
name: 'array',
type: 'array',
fields: [
{
name: 'field1',
type: 'text',
},
{
name: 'field2',
type: 'text',
},
],
},
{
name: 'custom',
type: 'text',
defaultValue: 'my custom csv transformer',
custom: {
'plugin-import-export': {
toCSV: ({ value, columnName, row, siblingDoc, doc }) => {
return String(value) + ' toCSV'
},
},
},
},
],
},
{
type: 'tabs',
tabs: [
{
label: 'No Name',
fields: [
{
name: 'tabToCSV',
type: 'text',
defaultValue: 'my custom csv transformer',
custom: {
'plugin-import-export': {
toCSV: ({ value, columnName, row, siblingDoc, doc }) => {
return String(value) + ' toCSV'
},
},
},
},
],
},
{
name: 'namedTab',
fields: [
{
name: 'tabToCSV',
type: 'text',
defaultValue: 'my custom csv transformer',
custom: {
'plugin-import-export': {
toCSV: ({ value, columnName, row, siblingDoc, doc }) => {
return String(value) + ' toCSV'
},
},
},
},
],
},
],
},
{
name: 'array',
type: 'array',
fields: [
{
name: 'field1',
type: 'text',
},
{
name: 'field2',
type: 'text',
},
],
},
{
name: 'blocks',
type: 'blocks',
blocks: [
{
slug: 'hero',
fields: [
{
name: 'title',
type: 'text',
},
],
},
{
slug: 'content',
fields: [
{
name: 'richText',
type: 'richText',
},
],
},
],
},
{
name: 'author',
type: 'relationship',
relationTo: 'users',
},
{
name: 'virtualRelationship',
type: 'text',
virtual: 'author.name',
},
{
name: 'virtual',
type: 'text',
virtual: true,
hooks: {
afterRead: [() => 'virtual value'],
},
},
{
name: 'hasManyNumber',
type: 'number',
hasMany: true,
},
{
name: 'relationship',
type: 'relationship',
relationTo: 'users',
},
{
name: 'excerpt',
label: 'Excerpt',
type: 'text',
},
{
name: 'hasOnePolymorphic',
type: 'relationship',
relationTo: ['users', 'posts'],
hasMany: false,
},
{
name: 'hasManyPolymorphic',
type: 'relationship',
relationTo: ['users', 'posts'],
hasMany: true,
},
],
}