feat: collections can use custom database operations (#7675)
## Description
Adds option to override default database operations for a collection
```ts
import { CollectionConfig } from 'payload/types';
export const Collection: CollectionConfig = {
slug: 'example-collection',
// Database operations for this collection
db: {
create: () => {},
deleteMany: () => {},
deleteOne: () => {},
find: () => {},
findOne: () => {},
updateOne: () => {}
},
fields: [
{
name: 'someField',
type: 'text',
},
],
}
```
Co-authored-by: Dan Ribbens <dan.ribbens@gmail.com>
This commit is contained in:
68
test/collections-db/config.ts
Normal file
68
test/collections-db/config.ts
Normal file
@@ -0,0 +1,68 @@
|
||||
import type { CollectionConfig } from '../../packages/payload/types'
|
||||
|
||||
import { buildConfigWithDefaults } from '../buildConfigWithDefaults'
|
||||
import { devUser } from '../credentials'
|
||||
|
||||
export const doc = {
|
||||
id: -1,
|
||||
customData: true,
|
||||
}
|
||||
export const docs = [doc]
|
||||
|
||||
const collectionWithDb = (collectionSlug: string): CollectionConfig => {
|
||||
return {
|
||||
slug: collectionSlug,
|
||||
db: {
|
||||
// @ts-expect-error
|
||||
create: () => {
|
||||
return doc
|
||||
},
|
||||
// @ts-expect-error
|
||||
deleteOne: () => {
|
||||
return docs
|
||||
},
|
||||
// Only used in deleteUserPreferences on user collections
|
||||
// @ts-expect-error
|
||||
deleteMany: () => {
|
||||
return docs
|
||||
},
|
||||
// @ts-expect-error
|
||||
find: () => {
|
||||
return { docs }
|
||||
},
|
||||
// @ts-expect-error
|
||||
findOne: () => {
|
||||
return doc
|
||||
},
|
||||
// @ts-expect-error
|
||||
updateOne: () => {
|
||||
return { ...doc, updated: true }
|
||||
},
|
||||
},
|
||||
fields: [
|
||||
{
|
||||
name: 'name',
|
||||
type: 'text',
|
||||
},
|
||||
],
|
||||
}
|
||||
}
|
||||
|
||||
export const collectionSlug = 'collection-db'
|
||||
export default buildConfigWithDefaults({
|
||||
// @ts-expect-error
|
||||
collections: [collectionWithDb(collectionSlug)],
|
||||
graphQL: {
|
||||
schemaOutputFile: './test/collections-db/schema.graphql',
|
||||
},
|
||||
|
||||
onInit: async (payload) => {
|
||||
await payload.create({
|
||||
collection: 'users',
|
||||
data: {
|
||||
email: devUser.email,
|
||||
password: devUser.password,
|
||||
},
|
||||
})
|
||||
},
|
||||
})
|
||||
110
test/collections-db/int.spec.ts
Normal file
110
test/collections-db/int.spec.ts
Normal file
@@ -0,0 +1,110 @@
|
||||
import payload from '../../packages/payload/src'
|
||||
import { devUser } from '../credentials'
|
||||
import { initPayloadTest } from '../helpers/configHelpers'
|
||||
import { collectionSlug } from './config'
|
||||
import { doc } from './config'
|
||||
|
||||
require('isomorphic-fetch')
|
||||
|
||||
let apiUrl
|
||||
let jwt
|
||||
|
||||
const headers = {
|
||||
'Content-Type': 'application/json',
|
||||
}
|
||||
const { email, password } = devUser
|
||||
|
||||
describe('Collection Database Operations', () => {
|
||||
// --__--__--__--__--__--__--__--__--__
|
||||
// Boilerplate test setup/teardown
|
||||
// --__--__--__--__--__--__--__--__--__
|
||||
beforeAll(async () => {
|
||||
const { serverURL } = await initPayloadTest({ __dirname, init: { local: false } })
|
||||
apiUrl = `${serverURL}/api`
|
||||
|
||||
const response = await fetch(`${apiUrl}/users/login`, {
|
||||
body: JSON.stringify({
|
||||
email,
|
||||
password,
|
||||
}),
|
||||
headers,
|
||||
method: 'POST',
|
||||
})
|
||||
|
||||
const data = await response.json()
|
||||
jwt = data.token
|
||||
})
|
||||
|
||||
afterAll(async () => {
|
||||
if (typeof payload.db.destroy === 'function') {
|
||||
await payload.db.destroy(payload)
|
||||
}
|
||||
})
|
||||
|
||||
// --__--__--__--__--__--__--__--__--__
|
||||
// Local API
|
||||
// --__--__--__--__--__--__--__--__--__
|
||||
|
||||
it('collection DB Create', async () => {
|
||||
const result = await payload.create({
|
||||
collection: collectionSlug,
|
||||
data: {
|
||||
id: doc.id,
|
||||
},
|
||||
})
|
||||
|
||||
expect(result.id).toEqual(doc.id)
|
||||
expect(result.customData).toEqual(doc.customData)
|
||||
})
|
||||
|
||||
it('collection DB Update', async () => {
|
||||
const where = { id: { equals: doc.id } }
|
||||
const result = await payload.update({
|
||||
collection: collectionSlug,
|
||||
where,
|
||||
data: {
|
||||
id: doc.id,
|
||||
},
|
||||
})
|
||||
|
||||
expect(result.docs[0].id).toEqual(doc.id)
|
||||
expect(result.docs[0].customData).toEqual(doc.customData)
|
||||
expect(result.docs[0].updated).toEqual(true)
|
||||
})
|
||||
|
||||
it('collection DB Find', async () => {
|
||||
const where = { id: { equals: doc.id } }
|
||||
const result = await payload.find({
|
||||
collection: collectionSlug,
|
||||
where,
|
||||
})
|
||||
|
||||
expect(result.docs[0].id).toEqual(doc.id)
|
||||
expect(result.docs[0].customData).toEqual(doc.customData)
|
||||
})
|
||||
|
||||
it('collection DB Find One', async () => {
|
||||
const result = await payload.findByID({
|
||||
collection: collectionSlug,
|
||||
id: doc.id,
|
||||
})
|
||||
|
||||
expect(result.id).toEqual(doc.id)
|
||||
expect(result.customData).toEqual(doc.customData)
|
||||
})
|
||||
|
||||
it('collection DB Delete', async () => {
|
||||
const where = { id: { equals: doc.id } }
|
||||
|
||||
const result = await payload.delete({
|
||||
collection: collectionSlug,
|
||||
depth: 0,
|
||||
user: devUser,
|
||||
where,
|
||||
})
|
||||
|
||||
expect(result.docs[0].id).toEqual(doc.id)
|
||||
expect(result.docs[0].customData).toEqual(doc.customData)
|
||||
expect(result.errors).toHaveLength(0)
|
||||
})
|
||||
})
|
||||
Reference in New Issue
Block a user