From a9ad7c771e9c3e6c56760512dfddecdbb0dfbeab Mon Sep 17 00:00:00 2001 From: Jarrod Flesch <30633324+JarrodMFlesch@users.noreply.github.com> Date: Tue, 1 Jul 2025 15:23:11 -0400 Subject: [PATCH] fix(ui): bulk upload redirecting to relationship documents when added (#13001) Fixes https://github.com/payloadcms/payload/issues/12786 --- packages/ui/src/elements/BulkUpload/index.tsx | 5 +- test/uploads/collections/BulkUploads/index.ts | 23 ++++++ .../collections/SimpleRelationship/index.ts | 14 ++++ test/uploads/config.ts | 4 + test/uploads/e2e.spec.ts | 23 ++++++ test/uploads/payload-types.ts | 73 +++++++++++++++++++ test/uploads/shared.ts | 1 + 7 files changed, 142 insertions(+), 1 deletion(-) create mode 100644 test/uploads/collections/BulkUploads/index.ts create mode 100644 test/uploads/collections/SimpleRelationship/index.ts diff --git a/packages/ui/src/elements/BulkUpload/index.tsx b/packages/ui/src/elements/BulkUpload/index.tsx index 3bd36075e..1fba50a5c 100644 --- a/packages/ui/src/elements/BulkUpload/index.tsx +++ b/packages/ui/src/elements/BulkUpload/index.tsx @@ -8,6 +8,7 @@ import React from 'react' import { toast } from 'sonner' import { useConfig } from '../../providers/Config/index.js' +import { EditDepthProvider } from '../../providers/EditDepth/index.js' import { useTranslation } from '../../providers/Translation/index.js' import { UploadControlsProvider } from '../../providers/UploadControls/index.js' import { Drawer, useDrawerDepth } from '../Drawer/index.js' @@ -77,7 +78,9 @@ export function BulkUploadDrawer() { - + + + diff --git a/test/uploads/collections/BulkUploads/index.ts b/test/uploads/collections/BulkUploads/index.ts new file mode 100644 index 000000000..2b1f9ea5c --- /dev/null +++ b/test/uploads/collections/BulkUploads/index.ts @@ -0,0 +1,23 @@ +import type { CollectionConfig } from 'payload' + +import { bulkUploadsSlug } from '../../shared.js' + +export const BulkUploadsCollection: CollectionConfig = { + slug: bulkUploadsSlug, + upload: true, + admin: { + useAsTitle: 'title', + }, + fields: [ + { + type: 'text', + name: 'title', + required: true, + }, + { + name: 'relationship', + type: 'relationship', + relationTo: ['simple-relationship'], + }, + ], +} diff --git a/test/uploads/collections/SimpleRelationship/index.ts b/test/uploads/collections/SimpleRelationship/index.ts new file mode 100644 index 000000000..a0533ff00 --- /dev/null +++ b/test/uploads/collections/SimpleRelationship/index.ts @@ -0,0 +1,14 @@ +import type { CollectionConfig } from 'payload' + +export const SimpleRelationshipCollection: CollectionConfig = { + slug: 'simple-relationship', + admin: { + useAsTitle: 'title', + }, + fields: [ + { + type: 'text', + name: 'title', + }, + ], +} diff --git a/test/uploads/config.ts b/test/uploads/config.ts index 5c5efe5d1..04b8c34ff 100644 --- a/test/uploads/config.ts +++ b/test/uploads/config.ts @@ -11,7 +11,9 @@ import { AdminThumbnailFunction } from './collections/AdminThumbnailFunction/ind import { AdminThumbnailSize } from './collections/AdminThumbnailSize/index.js' import { AdminThumbnailWithSearchQueries } from './collections/AdminThumbnailWithSearchQueries/index.js' import { AdminUploadControl } from './collections/AdminUploadControl/index.js' +import { BulkUploadsCollection } from './collections/BulkUploads/index.js' import { CustomUploadFieldCollection } from './collections/CustomUploadField/index.js' +import { SimpleRelationshipCollection } from './collections/SimpleRelationship/index.js' import { Uploads1 } from './collections/Upload1/index.js' import { Uploads2 } from './collections/Upload2/index.js' import { @@ -880,6 +882,8 @@ export default buildConfigWithDefaults({ staticDir: path.resolve(dirname, './media'), }, }, + BulkUploadsCollection, + SimpleRelationshipCollection, ], onInit: async (payload) => { const uploadsDir = path.resolve(dirname, './media') diff --git a/test/uploads/e2e.spec.ts b/test/uploads/e2e.spec.ts index 9daf36475..cb0bc1a16 100644 --- a/test/uploads/e2e.spec.ts +++ b/test/uploads/e2e.spec.ts @@ -28,6 +28,7 @@ import { adminUploadControlSlug, animatedTypeMedia, audioSlug, + bulkUploadsSlug, constructorOptionsSlug, customFileNameMediaSlug, customUploadFieldSlug, @@ -82,6 +83,7 @@ let constructorOptionsURL: AdminUrlUtil let consoleErrorsFromPage: string[] = [] let collectErrorsFromPage: () => boolean let stopCollectingErrorsFromPage: () => boolean +let bulkUploadsURL: AdminUrlUtil describe('Uploads', () => { let page: Page @@ -119,6 +121,7 @@ describe('Uploads', () => { withoutEnlargementResizeOptionsURL = new AdminUrlUtil(serverURL, withoutEnlargeSlug) threeDimensionalURL = new AdminUrlUtil(serverURL, threeDimensionalSlug) constructorOptionsURL = new AdminUrlUtil(serverURL, constructorOptionsSlug) + bulkUploadsURL = new AdminUrlUtil(serverURL, bulkUploadsSlug) const context = await browser.newContext() page = await context.newPage() @@ -1193,6 +1196,26 @@ describe('Uploads', () => { // ensure the prefix field is still filled with the original value await expect(page.locator('#field-prefix')).toHaveValue('should-preserve') }) + + test('should not redirect to created relationship document inside the bulk upload drawer', async () => { + await page.goto(bulkUploadsURL.list) + await page.locator('.list-header__title-actions button', { hasText: 'Bulk Upload' }).click() + await page.setInputFiles('.dropzone input[type="file"]', path.resolve(dirname, './image.png')) + + await page.locator('#field-title').fill('Upload title 1') + const bulkUploadForm = page.locator('.bulk-upload--file-manager') + const relationshipField = bulkUploadForm.locator('#field-relationship') + await relationshipField.locator('.relationship-add-new__add-button').click() + + const collectionForm = page.locator('.collection-edit') + await collectionForm.locator('#field-title').fill('Related Document Title') + await saveDocAndAssert(page) + await collectionForm.locator('.doc-drawer__header-close').click() + + await expect(bulkUploadForm.locator('.relationship--single-value__text')).toHaveText( + 'Related Document Title', + ) + }) }) describe('remote url fetching', () => { diff --git a/test/uploads/payload-types.ts b/test/uploads/payload-types.ts index 67d1536d5..fcccd753d 100644 --- a/test/uploads/payload-types.ts +++ b/test/uploads/payload-types.ts @@ -111,6 +111,8 @@ export interface Config { 'list-view-preview': ListViewPreview; 'three-dimensional': ThreeDimensional; 'constructor-options': ConstructorOption; + 'bulk-uploads': BulkUpload; + 'simple-relationship': SimpleRelationship; users: User; 'payload-locked-documents': PayloadLockedDocument; 'payload-preferences': PayloadPreference; @@ -162,6 +164,8 @@ export interface Config { 'list-view-preview': ListViewPreviewSelect | ListViewPreviewSelect; 'three-dimensional': ThreeDimensionalSelect | ThreeDimensionalSelect; 'constructor-options': ConstructorOptionsSelect | ConstructorOptionsSelect; + 'bulk-uploads': BulkUploadsSelect | BulkUploadsSelect; + 'simple-relationship': SimpleRelationshipSelect | SimpleRelationshipSelect; users: UsersSelect | UsersSelect; 'payload-locked-documents': PayloadLockedDocumentsSelect | PayloadLockedDocumentsSelect; 'payload-preferences': PayloadPreferencesSelect | PayloadPreferencesSelect; @@ -1465,6 +1469,39 @@ export interface ConstructorOption { focalX?: number | null; focalY?: number | null; } +/** + * This interface was referenced by `Config`'s JSON-Schema + * via the `definition` "bulk-uploads". + */ +export interface BulkUpload { + id: string; + title: string; + relationship?: { + relationTo: 'simple-relationship'; + value: string | SimpleRelationship; + } | null; + updatedAt: string; + createdAt: string; + url?: string | null; + thumbnailURL?: string | null; + filename?: string | null; + mimeType?: string | null; + filesize?: number | null; + width?: number | null; + height?: number | null; + focalX?: number | null; + focalY?: number | null; +} +/** + * This interface was referenced by `Config`'s JSON-Schema + * via the `definition` "simple-relationship". + */ +export interface SimpleRelationship { + id: string; + title?: string | null; + updatedAt: string; + createdAt: string; +} /** * This interface was referenced by `Config`'s JSON-Schema * via the `definition` "users". @@ -1672,6 +1709,14 @@ export interface PayloadLockedDocument { relationTo: 'constructor-options'; value: string | ConstructorOption; } | null) + | ({ + relationTo: 'bulk-uploads'; + value: string | BulkUpload; + } | null) + | ({ + relationTo: 'simple-relationship'; + value: string | SimpleRelationship; + } | null) | ({ relationTo: 'users'; value: string | User; @@ -3065,6 +3110,34 @@ export interface ConstructorOptionsSelect { focalX?: T; focalY?: T; } +/** + * This interface was referenced by `Config`'s JSON-Schema + * via the `definition` "bulk-uploads_select". + */ +export interface BulkUploadsSelect { + title?: T; + relationship?: T; + updatedAt?: T; + createdAt?: T; + url?: T; + thumbnailURL?: T; + filename?: T; + mimeType?: T; + filesize?: T; + width?: T; + height?: T; + focalX?: T; + focalY?: T; +} +/** + * This interface was referenced by `Config`'s JSON-Schema + * via the `definition` "simple-relationship_select". + */ +export interface SimpleRelationshipSelect { + title?: T; + updatedAt?: T; + createdAt?: T; +} /** * This interface was referenced by `Config`'s JSON-Schema * via the `definition` "users_select". diff --git a/test/uploads/shared.ts b/test/uploads/shared.ts index 3e8944e84..f33d5663a 100644 --- a/test/uploads/shared.ts +++ b/test/uploads/shared.ts @@ -31,3 +31,4 @@ export const skipAllowListSafeFetchMediaSlug = 'skip-allow-list-safe-fetch-media export const listViewPreviewSlug = 'list-view-preview' export const threeDimensionalSlug = 'three-dimensional' export const constructorOptionsSlug = 'constructor-options' +export const bulkUploadsSlug = 'bulk-uploads'