Skip to content

Commit 6612bd1

Browse files
authored
fix(richtext-lexical): lexicalHTML field was persisted in database even though it should not (#6795)
1 parent ce2ae95 commit 6612bd1

File tree

1 file changed

+74
-56
lines changed
  • packages/richtext-lexical/src/field/features/converters/html/field

1 file changed

+74
-56
lines changed

packages/richtext-lexical/src/field/features/converters/html/field/index.ts

Lines changed: 74 additions & 56 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import type { SerializedEditorState } from 'lexical'
2-
import type { Field, RichTextField } from 'payload/types'
2+
import type { Field, FieldAffectingData, RichTextField } from 'payload/types'
33

44
import type { AdapterProps, LexicalRichTextAdapter } from '../../../../../types.js'
55
import type { SanitizedServerEditorConfig } from '../../../../lexical/config/types.js'
@@ -17,6 +17,12 @@ type Props = {
1717
*/
1818
hidden?: boolean
1919
name: string
20+
/**
21+
* Whether the HTML should be stored in the database
22+
*
23+
* @default false
24+
*/
25+
storeInDB?: boolean
2026
}
2127

2228
/**
@@ -77,6 +83,62 @@ export const consolidateHTMLConverters = ({
7783
return filteredConverters
7884
}
7985

86+
// find the path of this field, as well as its sibling fields, by looking for this `field` in fields and traversing it recursively
87+
function findFieldPathAndSiblingFields(
88+
fields: Field[],
89+
path: string[],
90+
field: FieldAffectingData,
91+
): {
92+
path: string[]
93+
siblingFields: Field[]
94+
} {
95+
for (const curField of fields) {
96+
if (curField === field) {
97+
return {
98+
path: [...path, curField.name],
99+
siblingFields: fields,
100+
}
101+
}
102+
103+
if ('fields' in curField) {
104+
const result = findFieldPathAndSiblingFields(
105+
curField.fields,
106+
'name' in curField ? [...path, curField.name] : [...path],
107+
field,
108+
)
109+
if (result) {
110+
return result
111+
}
112+
} else if ('tabs' in curField) {
113+
for (const tab of curField.tabs) {
114+
const result = findFieldPathAndSiblingFields(
115+
tab.fields,
116+
'name' in tab ? [...path, tab.name] : [...path],
117+
field,
118+
)
119+
if (result) {
120+
return result
121+
}
122+
}
123+
} else if ('blocks' in curField) {
124+
for (const block of curField.blocks) {
125+
if (block?.fields?.length) {
126+
const result = findFieldPathAndSiblingFields(
127+
block.fields,
128+
[...path, curField.name, block.slug],
129+
field,
130+
)
131+
if (result) {
132+
return result
133+
}
134+
}
135+
}
136+
}
137+
}
138+
139+
return null
140+
}
141+
80142
export const lexicalHTML: (
81143
/**
82144
* A string which matches the lexical field name you want to convert to HTML.
@@ -86,7 +148,7 @@ export const lexicalHTML: (
86148
lexicalFieldName: string,
87149
props: Props,
88150
) => Field = (lexicalFieldName, props) => {
89-
const { name = 'lexicalHTML', hidden = true } = props
151+
const { name = 'lexicalHTML', hidden = true, storeInDB = false } = props
90152
return {
91153
name,
92154
type: 'code',
@@ -101,60 +163,7 @@ export const lexicalHTML: (
101163
async ({ collection, field, global, req, siblingData }) => {
102164
const fields = collection ? collection.fields : global.fields
103165

104-
// find the path of this field, as well as its sibling fields, by looking for this `field` in fields and traversing it recursively
105-
function findFieldPathAndSiblingFields(
106-
fields: Field[],
107-
path: string[],
108-
): {
109-
path: string[]
110-
siblingFields: Field[]
111-
} {
112-
for (const curField of fields) {
113-
if (curField === field) {
114-
return {
115-
path: [...path, curField.name],
116-
siblingFields: fields,
117-
}
118-
}
119-
120-
if ('fields' in curField) {
121-
const result = findFieldPathAndSiblingFields(
122-
curField.fields,
123-
'name' in curField ? [...path, curField.name] : [...path],
124-
)
125-
if (result) {
126-
return result
127-
}
128-
} else if ('tabs' in curField) {
129-
for (const tab of curField.tabs) {
130-
const result = findFieldPathAndSiblingFields(
131-
tab.fields,
132-
'name' in tab ? [...path, tab.name] : [...path],
133-
)
134-
if (result) {
135-
return result
136-
}
137-
}
138-
} else if ('blocks' in curField) {
139-
for (const block of curField.blocks) {
140-
if (block?.fields?.length) {
141-
const result = findFieldPathAndSiblingFields(block.fields, [
142-
...path,
143-
curField.name,
144-
block.slug,
145-
])
146-
if (result) {
147-
return result
148-
}
149-
}
150-
}
151-
}
152-
}
153-
154-
return null
155-
}
156-
157-
const foundSiblingFields = findFieldPathAndSiblingFields(fields, [])
166+
const foundSiblingFields = findFieldPathAndSiblingFields(fields, [], field)
158167

159168
if (!foundSiblingFields)
160169
throw new Error(
@@ -204,6 +213,15 @@ export const lexicalHTML: (
204213
})
205214
},
206215
],
216+
beforeChange: [
217+
({ siblingData, value }) => {
218+
if (storeInDB) {
219+
return value
220+
}
221+
delete siblingData[name]
222+
return null
223+
},
224+
],
207225
},
208226
}
209227
}

0 commit comments

Comments
 (0)