fix(db-mongodb): query 'in' with a comma-delimited value (#8910)

### What?
Fixes the issue with `in` querying when the collection has a join field.

### Why?
When using `.aggregate`, MongoDB doesn't cast a comma delimited value
for the `$in` operator to an array automatically as it's not handled by
Mongoose.

### How?
Sanitizes the incoming value to an array if it should.

Fixes https://github.com/payloadcms/payload/issues/8901
This commit is contained in:
Sasha
2024-10-29 01:41:28 +02:00
committed by GitHub
parent f0edbb79f9
commit 7a7a2f3918
2 changed files with 23 additions and 1 deletions

View File

@@ -78,7 +78,11 @@ export const sanitizeQueryValue = ({
return { operator: formattedOperator, val: undefined } return { operator: formattedOperator, val: undefined }
} }
} }
} else if (Array.isArray(val)) { } else if (Array.isArray(val) || (typeof val === 'string' && val.split(',').length > 1)) {
if (typeof val === 'string') {
formattedValue = createArrayFromCommaDelineated(val)
}
formattedValue = formattedValue.reduce((formattedValues, inVal) => { formattedValue = formattedValue.reduce((formattedValues, inVal) => {
const newValues = [inVal] const newValues = [inVal]
if (!hasCustomID) { if (!hasCustomID) {

View File

@@ -609,6 +609,24 @@ describe('Joins Field', () => {
expect(response.data.Category.relatedPosts.docs[0].title).toStrictEqual('test 3') expect(response.data.Category.relatedPosts.docs[0].title).toStrictEqual('test 3')
}) })
}) })
it('should work id.in command delimited querying with joins', async () => {
const allCategories = await payload.find({ collection: 'categories', pagination: false })
const allCategoriesByIds = await restClient
.GET(`/categories`, {
query: {
where: {
id: {
in: allCategories.docs.map((each) => each.id).join(','),
},
},
},
})
.then((res) => res.json())
expect(allCategories.totalDocs).toBe(allCategoriesByIds.totalDocs)
})
}) })
async function createPost(overrides?: Partial<Post>, locale?: Config['locale']) { async function createPost(overrides?: Partial<Post>, locale?: Config['locale']) {