Skip to content

Commit 00fb6e8

Browse files
authored
fix: upload drawer not loading data for uploads without files (#15150)
### What? Fixes an issue where clicking the `edit` button on an upload relationship field opens an empty drawer **if the related document has no file attached** (`filesRequiredOnCreate: false`). Documents with a file open correctly with all data. ### Why? The drawer ID was only getting set when a file URL existed (`src ? id : undefined`), so documents without files didn’t pass their ID to the drawer. The drawer needs the document ID to display document data. ### How? Updated the drawer ID logic in `fields > Upload > RelationshipContent` from `src ? id : undefined` to `id ?? undefined`. #### Testing Test added to the `upload` suite. **Reported by client.**
1 parent 43c19cb commit 00fb6e8

7 files changed

Lines changed: 154 additions & 1 deletion

File tree

packages/ui/src/fields/Upload/RelationshipContent/index.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,7 @@ export function RelationshipContent(props: Props) {
6868
: undefined
6969

7070
const [DocumentDrawer, _, { openDrawer }] = useDocumentDrawer({
71-
id: src ? id : undefined,
71+
id: id ?? undefined,
7272
collectionSlug,
7373
})
7474

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
import type { CollectionConfig } from 'payload'
2+
3+
import { fileURLToPath } from 'node:url'
4+
import path from 'path'
5+
6+
import { noFilesRequiredSlug } from '../../shared.js'
7+
8+
const filename = fileURLToPath(import.meta.url)
9+
const dirname = path.dirname(filename)
10+
11+
export const NoFilesRequired: CollectionConfig = {
12+
slug: noFilesRequiredSlug,
13+
upload: {
14+
staticDir: path.resolve(dirname, 'uploads'),
15+
filesRequiredOnCreate: false,
16+
},
17+
fields: [
18+
{
19+
name: 'title',
20+
type: 'text',
21+
},
22+
],
23+
}
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
import type { CollectionConfig } from 'payload'
2+
3+
import { noFilesRequiredSlug, relationToNoFilesRequiredSlug } from '../../shared.js'
4+
5+
export const RelationToNoFilesRequired: CollectionConfig = {
6+
slug: relationToNoFilesRequiredSlug,
7+
fields: [
8+
{
9+
name: 'title',
10+
type: 'text',
11+
},
12+
{
13+
name: 'uploadField',
14+
type: 'upload',
15+
relationTo: noFilesRequiredSlug,
16+
},
17+
],
18+
}

test/uploads/config.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@ import { AnyImageTypeCollection } from './collections/AnyImageType/index.js'
1515
import { BulkUploadsCollection } from './collections/BulkUploads/index.js'
1616
import { CustomUploadFieldCollection } from './collections/CustomUploadField/index.js'
1717
import { FileMimeType } from './collections/FileMimeType/index.js'
18+
import { NoFilesRequired } from './collections/NoFilesRequired/index.js'
19+
import { RelationToNoFilesRequired } from './collections/RelationToNoFilesRequired/index.js'
1820
import { SimpleRelationshipCollection } from './collections/SimpleRelationship/index.js'
1921
import { Uploads1 } from './collections/Upload1/index.js'
2022
import { Uploads2 } from './collections/Upload2/index.js'
@@ -791,6 +793,8 @@ export default buildConfigWithDefaults({
791793
AdminThumbnailWithSearchQueries,
792794
AdminThumbnailSize,
793795
AdminUploadControl,
796+
NoFilesRequired,
797+
RelationToNoFilesRequired,
794798
{
795799
slug: 'optional-file',
796800
fields: [],

test/uploads/e2e.spec.ts

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,8 +44,10 @@ import {
4444
mediaWithImageSizeAdminPropsSlug,
4545
mediaWithoutCacheTagsSlug,
4646
mediaWithoutDeleteAccessSlug,
47+
noFilesRequiredSlug,
4748
relationPreviewSlug,
4849
relationSlug,
50+
relationToNoFilesRequiredSlug,
4951
svgOnlySlug,
5052
threeDimensionalSlug,
5153
withMetadataSlug,
@@ -95,6 +97,8 @@ let fileMimeTypeURL: AdminUrlUtil
9597
let svgOnlyURL: AdminUrlUtil
9698
let mediaWithoutDeleteAccessURL: AdminUrlUtil
9799
let mediaWithImageSizeAdminPropsURL: AdminUrlUtil
100+
let noFilesRequiredURL: AdminUrlUtil
101+
let relationToNoFilesRequiredURL: AdminUrlUtil
98102

99103
describe('Uploads', () => {
100104
let page: Page
@@ -137,6 +141,8 @@ describe('Uploads', () => {
137141
svgOnlyURL = new AdminUrlUtil(serverURL, svgOnlySlug)
138142
mediaWithoutDeleteAccessURL = new AdminUrlUtil(serverURL, mediaWithoutDeleteAccessSlug)
139143
mediaWithImageSizeAdminPropsURL = new AdminUrlUtil(serverURL, mediaWithImageSizeAdminPropsSlug)
144+
noFilesRequiredURL = new AdminUrlUtil(serverURL, noFilesRequiredSlug)
145+
relationToNoFilesRequiredURL = new AdminUrlUtil(serverURL, relationToNoFilesRequiredSlug)
140146

141147
const context = await browser.newContext()
142148
await context.grantPermissions(['clipboard-read', 'clipboard-write'])
@@ -1895,4 +1901,34 @@ describe('Uploads', () => {
18951901
const titleField = page.locator('#field-title')
18961902
await expect(titleField).toHaveValue('updated title')
18971903
})
1904+
1905+
test('should show data in drawer when editing relationship to upload collection with filesRequiredOnCreate: false', async () => {
1906+
const uploadDoc = await payload.create({
1907+
collection: noFilesRequiredSlug,
1908+
data: {
1909+
title: 'Upload without file',
1910+
},
1911+
})
1912+
1913+
const relationDoc = await payload.create({
1914+
collection: relationToNoFilesRequiredSlug,
1915+
data: {
1916+
title: 'Relation document',
1917+
uploadField: uploadDoc.id,
1918+
},
1919+
})
1920+
1921+
await page.goto(relationToNoFilesRequiredURL.edit(relationDoc.id))
1922+
1923+
await expect(page.locator('#field-uploadField')).toBeVisible()
1924+
1925+
await page.locator('#field-uploadField .upload-relationship-details__edit').click()
1926+
1927+
const drawer = page.locator('[id^=doc-drawer_no-files-required_]')
1928+
await expect(drawer).toBeVisible()
1929+
1930+
const titleField = drawer.locator('#field-title')
1931+
1932+
await expect(titleField).toHaveValue('Upload without file')
1933+
})
18981934
})

test/uploads/payload-types.ts

Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -105,6 +105,8 @@ export interface Config {
105105
'admin-thumbnail-with-search-queries': AdminThumbnailWithSearchQuery;
106106
'admin-thumbnail-size': AdminThumbnailSize;
107107
'admin-upload-control': AdminUploadControl;
108+
'no-files-required': NoFilesRequired;
109+
'relation-to-no-files-required': RelationToNoFilesRequired;
108110
'optional-file': OptionalFile;
109111
'required-file': RequiredFile;
110112
versions: Version;
@@ -170,6 +172,8 @@ export interface Config {
170172
'admin-thumbnail-with-search-queries': AdminThumbnailWithSearchQueriesSelect<false> | AdminThumbnailWithSearchQueriesSelect<true>;
171173
'admin-thumbnail-size': AdminThumbnailSizeSelect<false> | AdminThumbnailSizeSelect<true>;
172174
'admin-upload-control': AdminUploadControlSelect<false> | AdminUploadControlSelect<true>;
175+
'no-files-required': NoFilesRequiredSelect<false> | NoFilesRequiredSelect<true>;
176+
'relation-to-no-files-required': RelationToNoFilesRequiredSelect<false> | RelationToNoFilesRequiredSelect<true>;
173177
'optional-file': OptionalFileSelect<false> | OptionalFileSelect<true>;
174178
'required-file': RequiredFileSelect<false> | RequiredFileSelect<true>;
175179
versions: VersionsSelect<false> | VersionsSelect<true>;
@@ -1446,6 +1450,36 @@ export interface AdminUploadControl {
14461450
focalX?: number | null;
14471451
focalY?: number | null;
14481452
}
1453+
/**
1454+
* This interface was referenced by `Config`'s JSON-Schema
1455+
* via the `definition` "no-files-required".
1456+
*/
1457+
export interface NoFilesRequired {
1458+
id: string;
1459+
title?: string | null;
1460+
updatedAt: string;
1461+
createdAt: string;
1462+
url?: string | null;
1463+
thumbnailURL?: string | null;
1464+
filename?: string | null;
1465+
mimeType?: string | null;
1466+
filesize?: number | null;
1467+
width?: number | null;
1468+
height?: number | null;
1469+
focalX?: number | null;
1470+
focalY?: number | null;
1471+
}
1472+
/**
1473+
* This interface was referenced by `Config`'s JSON-Schema
1474+
* via the `definition` "relation-to-no-files-required".
1475+
*/
1476+
export interface RelationToNoFilesRequired {
1477+
id: string;
1478+
title?: string | null;
1479+
uploadField?: (string | null) | NoFilesRequired;
1480+
updatedAt: string;
1481+
createdAt: string;
1482+
}
14491483
/**
14501484
* This interface was referenced by `Config`'s JSON-Schema
14511485
* via the `definition` "optional-file".
@@ -1972,6 +2006,14 @@ export interface PayloadLockedDocument {
19722006
relationTo: 'admin-upload-control';
19732007
value: string | AdminUploadControl;
19742008
} | null)
2009+
| ({
2010+
relationTo: 'no-files-required';
2011+
value: string | NoFilesRequired;
2012+
} | null)
2013+
| ({
2014+
relationTo: 'relation-to-no-files-required';
2015+
value: string | RelationToNoFilesRequired;
2016+
} | null)
19752017
| ({
19762018
relationTo: 'optional-file';
19772019
value: string | OptionalFile;
@@ -3363,6 +3405,34 @@ export interface AdminUploadControlSelect<T extends boolean = true> {
33633405
focalX?: T;
33643406
focalY?: T;
33653407
}
3408+
/**
3409+
* This interface was referenced by `Config`'s JSON-Schema
3410+
* via the `definition` "no-files-required_select".
3411+
*/
3412+
export interface NoFilesRequiredSelect<T extends boolean = true> {
3413+
title?: T;
3414+
updatedAt?: T;
3415+
createdAt?: T;
3416+
url?: T;
3417+
thumbnailURL?: T;
3418+
filename?: T;
3419+
mimeType?: T;
3420+
filesize?: T;
3421+
width?: T;
3422+
height?: T;
3423+
focalX?: T;
3424+
focalY?: T;
3425+
}
3426+
/**
3427+
* This interface was referenced by `Config`'s JSON-Schema
3428+
* via the `definition` "relation-to-no-files-required_select".
3429+
*/
3430+
export interface RelationToNoFilesRequiredSelect<T extends boolean = true> {
3431+
title?: T;
3432+
uploadField?: T;
3433+
updatedAt?: T;
3434+
createdAt?: T;
3435+
}
33663436
/**
33673437
* This interface was referenced by `Config`'s JSON-Schema
33683438
* via the `definition` "optional-file_select".

test/uploads/shared.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,3 +45,5 @@ export const anyImagesSlug = 'any-images'
4545
export const mediaWithoutDeleteAccessSlug = 'media-without-delete-access'
4646
export const mediaWithImageSizeAdminPropsSlug = 'media-with-image-size-admin-props'
4747
export const uploads2Slug = 'uploads-2'
48+
export const noFilesRequiredSlug = 'no-files-required'
49+
export const relationToNoFilesRequiredSlug = 'relation-to-no-files-required'

0 commit comments

Comments
 (0)