chore: adds schema path to useFieldPath provider, more passing tests

This commit is contained in:
Jarrod Flesch
2024-02-20 15:56:11 -05:00
parent 726596d568
commit a5e2fa80e8
58 changed files with 483 additions and 316 deletions

View File

@@ -19,6 +19,27 @@ export const PostsCollection: CollectionConfig = {
relationTo: mediaSlug,
type: 'upload',
},
{
name: 'blocksField',
type: 'blocks',
blocks: [
{
slug: 'block1',
fields: [
{
type: 'group',
name: 'group1',
fields: [
{
type: 'text',
name: 'group1Text',
},
],
},
],
},
],
},
],
slug: postsSlug,
}

View File

@@ -2,11 +2,11 @@ import type { Request } from 'express'
import { Strategy } from 'passport-strategy'
import type { Payload } from '../../../packages/payload/src/payload'
import type { Payload } from '../../../packages/payload/src'
import { buildConfigWithDefaults } from '../../buildConfigWithDefaults'
import { usersSlug } from './shared'
export const slug = 'users'
export const strategyName = 'test-local'
export class CustomStrategy extends Strategy {
@@ -23,7 +23,7 @@ export class CustomStrategy extends Strategy {
}
this.ctx
.find({
collection: slug,
collection: usersSlug,
where: {
code: {
equals: req.headers.code,
@@ -36,8 +36,8 @@ export class CustomStrategy extends Strategy {
.then((users) => {
if (users.docs && users.docs.length) {
const user = users.docs[0]
user.collection = slug
user._strategy = `${slug}-${strategyName}`
user.collection = usersSlug
user._strategy = `${usersSlug}-${strategyName}`
this.success(user)
} else {
this.error(null)
@@ -52,7 +52,7 @@ export default buildConfigWithDefaults({
},
collections: [
{
slug,
slug: usersSlug,
auth: {
disableLocalStrategy: true,
strategies: [

View File

@@ -1,10 +1,15 @@
import payload from '../../../packages/payload/src'
import { initPayloadTest } from '../../helpers/configHelpers'
import { slug } from './config'
import type { Payload } from '../../../packages/payload/src'
import { getPayload } from '../../../packages/payload/src'
import { NextRESTClient } from '../../helpers/NextRESTClient'
import { startMemoryDB } from '../../startMemoryDB'
import configPromise from './config'
import { usersSlug } from './shared'
require('isomorphic-fetch')
let apiUrl
let payload: Payload
let restClient: NextRESTClient
const [code, secret, name] = ['test', 'strategy', 'Tester']
@@ -14,8 +19,9 @@ const headers = {
describe('AuthStrategies', () => {
beforeAll(async () => {
const { serverURL } = await initPayloadTest({ __dirname, init: { local: false } })
apiUrl = `${serverURL}/api`
const config = await startMemoryDB(configPromise)
payload = await getPayload({ config })
restClient = new NextRESTClient(payload.config)
})
afterAll(async () => {
@@ -26,21 +32,19 @@ describe('AuthStrategies', () => {
describe('create user', () => {
beforeAll(async () => {
await fetch(`${apiUrl}/${slug}`, {
await restClient.POST(`/${usersSlug}`, {
body: JSON.stringify({
code,
secret,
name,
}),
headers,
method: 'post',
})
})
it('should return a logged in user from /me', async () => {
const response = await fetch(`${apiUrl}/${slug}/me`, {
const response = await restClient.GET(`/${usersSlug}/me`, {
headers: {
...headers,
code,
secret,
},

View File

@@ -0,0 +1 @@
export const usersSlug = 'users'

View File

@@ -1,21 +1,25 @@
import payload from '../../../packages/payload/src'
import type { Payload } from '../../../packages/payload/src'
import { getPayload } from '../../../packages/payload/src'
import { devUser } from '../../credentials'
import { initPayloadTest } from '../../helpers/configHelpers'
import { RESTClient } from '../../helpers/rest'
import { NextRESTClient } from '../../helpers/NextRESTClient'
import { startMemoryDB } from '../../startMemoryDB'
import { collectionSlug } from './config'
import configPromise from './config'
require('isomorphic-fetch')
let client: RESTClient
let restClient: NextRESTClient
let payload: Payload
describe('Remove token from auth responses', () => {
beforeAll(async () => {
const config = await initPayloadTest({ __dirname, init: { local: false } })
const { serverURL } = config
client = new RESTClient(config, { serverURL, defaultSlug: collectionSlug })
const config = await startMemoryDB(configPromise)
payload = await getPayload({ config })
restClient = new NextRESTClient(payload.config)
await client.endpoint(`/api/${collectionSlug}/first-register`, 'post', devUser)
await client.login()
await restClient.POST(`/${collectionSlug}/first-register`, {
body: JSON.stringify(devUser),
})
await restClient.login({ slug: collectionSlug, credentials: devUser })
})
afterAll(async () => {
@@ -25,27 +29,28 @@ describe('Remove token from auth responses', () => {
})
it('should not include token in response from /login', async () => {
const { status, data } = await client.endpoint(`/api/${collectionSlug}/login`, 'post', devUser)
expect(status).toBe(200)
expect(data.token).not.toBeDefined()
expect(data.user.email).toBeDefined()
const result = await restClient.login({
slug: collectionSlug,
credentials: devUser,
})
expect(result.token).not.toBeDefined()
expect(result.user.email).toBeDefined()
})
it('should not include token in response from /me', async () => {
const { status, data } = await client.endpointWithAuth(`/api/${collectionSlug}/me`)
expect(status).toBe(200)
expect(data.token).not.toBeDefined()
expect(data.user.email).toBeDefined()
const response = await restClient.GET(`/${collectionSlug}/me`)
const result = await response.json()
expect(response.status).toBe(200)
expect(result.token).not.toBeDefined()
expect(result.user.email).toBeDefined()
})
it('should not include token in response from /refresh-token', async () => {
const { status, data } = await client.endpointWithAuth(
`/api/${collectionSlug}/refresh-token`,
'post',
)
expect(status).toBe(200)
expect(data.refreshedToken).not.toBeDefined()
expect(data.user.email).toBeDefined()
const response = await restClient.POST(`/${collectionSlug}/refresh-token`)
const result = await response.json()
expect(response.status).toBe(200)
expect(result.refreshedToken).not.toBeDefined()
expect(result.user.email).toBeDefined()
})
it('should not include token in response from /reset-password', async () => {
@@ -55,17 +60,13 @@ describe('Remove token from auth responses', () => {
disableEmail: true,
})
const { status, data } = await client.endpoint(
`/api/${collectionSlug}/reset-password`,
'post',
{
token,
password: devUser.password,
},
)
const response = await restClient.POST(`/${collectionSlug}/reset-password`, {
body: JSON.stringify({ token, password: devUser.password }),
})
const result = await response.json()
expect(status).toBe(200)
expect(data.token).not.toBeDefined()
expect(data.user.email).toBeDefined()
expect(response.status).toBe(200)
expect(result.token).not.toBeDefined()
expect(result.user.email).toBeDefined()
})
})

View File

@@ -1,18 +1,16 @@
import type { IndexDirection, IndexOptions } from 'mongoose'
import { GraphQLClient } from 'graphql-request'
import type { MongooseAdapter } from '../../packages/db-mongodb/src/index'
import type { SanitizedConfig } from '../../packages/payload/src/config/types'
import type { Payload } from '../../packages/payload/src'
import type { PaginatedDocs } from '../../packages/payload/src/database/types'
import type { RichTextField } from './payload-types'
import type { GroupField } from './payload-types'
import payload from '../../packages/payload/src'
import { getPayload } from '../../packages/payload/src'
import { devUser } from '../credentials'
import { initPayloadTest } from '../helpers/configHelpers'
import { NextRESTClient } from '../helpers/NextRESTClient'
import { isMongoose } from '../helpers/isMongoose'
import { RESTClient } from '../helpers/rest'
import configPromise from '../uploads/config'
import { startMemoryDB } from '../startMemoryDB'
import { arrayDefaultValue } from './collections/Array'
import { blocksDoc } from './collections/Blocks/shared'
import { dateDoc } from './collections/Date/shared'
@@ -28,8 +26,8 @@ import {
} from './collections/Tabs/constants'
import { tabsDoc } from './collections/Tabs/shared'
import { defaultText } from './collections/Text/shared'
import configPromise from './config'
import { clearAndSeedEverything } from './seed'
import { GroupField } from './payload-types'
import {
arrayFieldsSlug,
blockFieldsSlug,
@@ -39,22 +37,19 @@ import {
textFieldsSlug,
} from './slugs'
let client: RESTClient
let graphQLClient: GraphQLClient
let serverURL: string
let config: SanitizedConfig
let token: string
let restClient: NextRESTClient
let user: any
let payload: Payload
describe('Fields', () => {
beforeAll(async () => {
;({ serverURL } = await initPayloadTest({ __dirname, init: { local: false } }))
config = await configPromise
client = new RESTClient(config, { defaultSlug: 'point-fields', serverURL })
const graphQLURL = `${serverURL}${config.routes.api}${config.routes.graphQL}`
graphQLClient = new GraphQLClient(graphQLURL)
token = await client.login()
const config = await startMemoryDB(configPromise)
payload = await getPayload({ config })
restClient = new NextRESTClient(payload.config)
await restClient.login({
slug: 'users',
credentials: devUser,
})
user = await payload.login({
collection: 'users',
@@ -67,8 +62,10 @@ describe('Fields', () => {
beforeEach(async () => {
await clearAndSeedEverything(payload)
client = new RESTClient(config, { defaultSlug: 'point-fields', serverURL })
await client.login()
await restClient.login({
slug: 'users',
credentials: devUser,
})
})
describe('text', () => {
@@ -1061,14 +1058,12 @@ describe('Fields', () => {
}
}
}`
const response = await graphQLClient.request(
query,
{},
{
Authorization: `JWT ${token}`,
},
)
const { docs }: PaginatedDocs<RichTextField> = response.RichTextFields
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
})
.then((res) => res.json())
const { docs }: PaginatedDocs<RichTextField> = data.RichTextFields
const uploadElement = docs[0].richText.find((el) => el.type === 'upload') as any
expect(uploadElement.value.media.filename).toStrictEqual('payload.png')
})

View File

@@ -1,8 +1,6 @@
import type { SerializedEditorState, SerializedParagraphNode } from 'lexical'
import { GraphQLClient } from 'graphql-request'
import type { SanitizedConfig } from '../../packages/payload/src/config/types'
import type { Payload } from '../../packages/payload/src'
import type { PaginatedDocs } from '../../packages/payload/src/database/types'
import type {
SerializedBlockNode,
@@ -12,10 +10,10 @@ import type {
} from '../../packages/richtext-lexical/src'
import type { LexicalField, LexicalMigrateField, RichTextField } from './payload-types'
import payload from '../../packages/payload/src'
import { initPayloadTest } from '../helpers/configHelpers'
import { RESTClient } from '../helpers/rest'
import configPromise from '../uploads/config'
import { getPayload } from '../../packages/payload/src'
import { devUser } from '../credentials'
import { NextRESTClient } from '../helpers/NextRESTClient'
import { startMemoryDB } from '../startMemoryDB'
import { arrayDoc } from './collections/Array/shared'
import { lexicalDocData } from './collections/Lexical/data'
import { lexicalMigrateDocData } from './collections/LexicalMigrate/data'
@@ -23,6 +21,7 @@ import { richTextDocData } from './collections/RichText/data'
import { generateLexicalRichText } from './collections/RichText/generateLexicalRichText'
import { textDoc } from './collections/Text/shared'
import { uploadsDoc } from './collections/Upload/shared'
import configPromise from './config'
import { clearAndSeedEverything } from './seed'
import {
arrayFieldsSlug,
@@ -33,10 +32,8 @@ import {
uploadsSlug,
} from './slugs'
let client: RESTClient
let graphQLClient: GraphQLClient
let serverURL: string
let config: SanitizedConfig
let payload: Payload
let restClient: NextRESTClient
let token: string
let createdArrayDocID: number | string = null
@@ -46,19 +43,17 @@ let createdRichTextDocID: number | string = null
describe('Lexical', () => {
beforeAll(async () => {
;({ serverURL } = await initPayloadTest({ __dirname, init: { local: false } }))
config = await configPromise
client = new RESTClient(config, { defaultSlug: richTextFieldsSlug, serverURL })
const graphQLURL = `${serverURL}${config.routes.api}${config.routes.graphQL}`
graphQLClient = new GraphQLClient(graphQLURL)
token = await client.login()
const config = await startMemoryDB(configPromise)
payload = await getPayload({ config })
restClient = new NextRESTClient(payload.config)
})
beforeEach(async () => {
await clearAndSeedEverything(payload)
client = new RESTClient(config, { defaultSlug: richTextFieldsSlug, serverURL })
await client.login()
await restClient.login({
slug: 'users',
credentials: devUser,
})
createdArrayDocID = (
await payload.find({

View File

@@ -155,7 +155,10 @@ export class NextRESTClient {
return this._PATCH(request, { params: { slug } })
}
async POST(path: ValidPath, options: RequestInit & { file?: boolean } = {}): Promise<Response> {
async POST(
path: ValidPath,
options: RequestInit & RequestOptions & { file?: boolean } = {},
): Promise<Response> {
const { url, slug, params } = this.generateRequestParts(path)
const queryParams = generateQueryString({}, params)
@@ -176,15 +179,23 @@ export class NextRESTClient {
password: string
}
slug: string
}): Promise<string> {
this.token = await this.POST(`/${slug}/login`, {
}): Promise<{ [key: string]: any }> {
const response = await this.POST(`/${slug}/login`, {
body: JSON.stringify(
credentials ? { ...credentials } : { email: devUser.email, password: devUser.password },
),
})
.then((res) => res.json())
.then((data) => data.token)
const result = await response.json()
return this.token
this.token = result.token
if (!result.token) {
// If the token is not in the response body, then we can extract it from the cookies
const setCookie = response.headers.get('Set-Cookie')
const tokenMatchResult = setCookie?.match(/payload-token=(?<token>.+?);/)
this.token = tokenMatchResult?.groups?.token
}
return result
}
}

View File

@@ -13,9 +13,9 @@ export const Media: CollectionConfig = {
type: 'text',
required: true,
},
{
name: 'caption',
type: 'richText',
},
// {
// name: 'caption',
// type: 'richText',
// },
],
}

View File

@@ -13,8 +13,6 @@ import { seed } from './seed'
import { mobileBreakpoint } from './shared'
import { formatLivePreviewURL } from './utilities/formatLivePreviewURL'
const mockModulePath = path.resolve(__dirname, './mocks/mockFSModule.js')
export default buildConfigWithDefaults({
admin: {
livePreview: {
@@ -25,16 +23,6 @@ export default buildConfigWithDefaults({
collections: ['pages', 'posts'],
globals: ['header', 'footer'],
},
webpack: (config) => ({
...config,
resolve: {
...config.resolve,
alias: {
...config?.resolve?.alias,
fs: mockModulePath,
},
},
}),
},
cors: ['http://localhost:3001'],
csrf: ['http://localhost:3001'],

View File

@@ -9,6 +9,7 @@ import { traverseRichText } from '../../packages/live-preview/src/traverseRichTe
import { getPayload } from '../../packages/payload/src'
import getFileByPath from '../../packages/payload/src/uploads/getFileByPath'
import { fieldSchemaToJSON } from '../../packages/payload/src/utilities/fieldSchemaToJSON'
import { NextRESTClient } from '../helpers/NextRESTClient'
import { startMemoryDB } from '../startMemoryDB'
import { Pages } from './collections/Pages'
import { postsSlug } from './collections/Posts'
@@ -18,6 +19,11 @@ import { tenantsSlug } from './shared'
const schemaJSON = fieldSchemaToJSON(Pages.fields)
let payload: Payload
let restClient: NextRESTClient
function collectionPopulationRequestHandler({ endpoint }: { endpoint: string }) {
return restClient.GET(`/${endpoint}`)
}
describe('Collections - Live Preview', () => {
let serverURL
@@ -29,6 +35,7 @@ describe('Collections - Live Preview', () => {
beforeAll(async () => {
const config = await startMemoryDB(configPromise)
payload = await getPayload({ config })
restClient = new NextRESTClient(payload.config)
tenant = await payload.create({
collection: tenantsSlug,
@@ -140,6 +147,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(mergedData.title).toEqual('Test Page (Changed)')
@@ -165,6 +173,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(mergedData.hero.media).toMatchObject(media)
@@ -183,6 +192,7 @@ describe('Collections - Live Preview', () => {
},
initialData: mergedData,
serverURL,
collectionPopulationRequestHandler,
})
expect(mergedDataWithoutUpload.hero.media).toBeFalsy()
@@ -210,6 +220,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge1.richTextSlate).toHaveLength(1)
@@ -236,6 +247,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge2.richTextSlate).toHaveLength(1)
@@ -295,6 +307,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge1.richTextLexical.root.children).toHaveLength(2)
@@ -340,6 +353,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge2.richTextLexical.root.children).toHaveLength(1)
@@ -362,6 +376,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge1._numberOfRequests).toEqual(1)
@@ -383,6 +398,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge1._numberOfRequests).toEqual(1)
@@ -404,6 +420,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge1._numberOfRequests).toEqual(1)
@@ -428,6 +445,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge1._numberOfRequests).toEqual(1)
@@ -457,6 +475,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge2._numberOfRequests).toEqual(0)
@@ -482,6 +501,7 @@ describe('Collections - Live Preview', () => {
},
initialData,
serverURL,
collectionPopulationRequestHandler,
})
expect(merge1.tab.relationshipInTab).toMatchObject(testPost)
@@ -518,6 +538,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge1._numberOfRequests).toEqual(1)
@@ -574,6 +595,7 @@ describe('Collections - Live Preview', () => {
initialData: merge1,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge2._numberOfRequests).toEqual(1)
@@ -649,6 +671,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge1._numberOfRequests).toEqual(2)
@@ -711,6 +734,7 @@ describe('Collections - Live Preview', () => {
initialData: merge1,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge2._numberOfRequests).toEqual(1)
@@ -776,6 +800,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge1._numberOfRequests).toEqual(2)
@@ -842,6 +867,7 @@ describe('Collections - Live Preview', () => {
initialData: merge1,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge2._numberOfRequests).toEqual(1)
@@ -895,6 +921,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge1._numberOfRequests).toEqual(0)
@@ -954,6 +981,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
// Check that the relationship on the first has been removed
@@ -982,6 +1010,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge1._numberOfRequests).toEqual(1)
@@ -1027,6 +1056,7 @@ describe('Collections - Live Preview', () => {
externallyUpdatedRelationship,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
expect(merge2._numberOfRequests).toEqual(1)
@@ -1184,6 +1214,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
// Check that the blocks have been reordered
@@ -1216,6 +1247,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
// Check that the block has been removed
@@ -1235,6 +1267,7 @@ describe('Collections - Live Preview', () => {
initialData,
serverURL,
returnNumberOfRequests: true,
collectionPopulationRequestHandler,
})
// Check that the block has been removed

View File

@@ -7,13 +7,17 @@ import removeFiles from '../helpers/removeFiles'
import { Uploads1 } from './collections/Upload1'
import Uploads2 from './collections/Upload2'
import AdminThumbnailCol from './collections/admin-thumbnail'
import { audioSlug, enlargeSlug, mediaSlug, reduceSlug, relationSlug } from './shared'
import {
audioSlug,
enlargeSlug,
mediaSlug,
reduceSlug,
relationSlug,
unstoredMediaSlug,
} from './shared'
export default buildConfigWithDefaults({
serverURL: undefined,
paths: {
configDir: __dirname,
},
collections: [
{
slug: relationSlug,
@@ -44,7 +48,7 @@ export default buildConfigWithDefaults({
slug: 'gif-resize',
upload: {
staticURL: '/media-gif',
staticDir: './media-gif',
staticDir: path.resolve(__dirname, './media-gif'),
mimeTypes: ['image/gif'],
resizeOptions: {
position: 'center',
@@ -75,7 +79,7 @@ export default buildConfigWithDefaults({
slug: 'no-image-sizes',
upload: {
staticURL: '/no-image-sizes',
staticDir: './no-image-sizes',
staticDir: path.resolve(__dirname, './no-image-sizes'),
mimeTypes: ['image/png', 'image/jpg', 'image/jpeg'],
resizeOptions: {
position: 'center',
@@ -89,7 +93,7 @@ export default buildConfigWithDefaults({
slug: 'object-fit',
upload: {
staticURL: '/object-fit',
staticDir: './object-fit',
staticDir: path.resolve(__dirname, './object-fit'),
mimeTypes: ['image/png', 'image/jpg', 'image/jpeg'],
imageSizes: [
{
@@ -125,7 +129,7 @@ export default buildConfigWithDefaults({
upload: {
focalPoint: false,
staticURL: '/crop-only',
staticDir: './crop-only',
staticDir: path.resolve(__dirname, './crop-only'),
mimeTypes: ['image/png', 'image/jpg', 'image/jpeg'],
imageSizes: [
{
@@ -152,7 +156,7 @@ export default buildConfigWithDefaults({
upload: {
crop: false,
staticURL: '/focal-only',
staticDir: './focal-only',
staticDir: path.resolve(__dirname, './focal-only'),
mimeTypes: ['image/png', 'image/jpg', 'image/jpeg'],
imageSizes: [
{
@@ -178,7 +182,7 @@ export default buildConfigWithDefaults({
slug: mediaSlug,
upload: {
staticURL: '/media',
staticDir: './media',
staticDir: path.resolve(__dirname, './media'),
// crop: false,
// focalPoint: false,
mimeTypes: [
@@ -284,7 +288,7 @@ export default buildConfigWithDefaults({
slug: enlargeSlug,
upload: {
staticURL: '/enlarge',
staticDir: './media/enlarge',
staticDir: path.resolve(__dirname, './media/enlarge'),
mimeTypes: [
'image/png',
'image/jpg',
@@ -332,7 +336,7 @@ export default buildConfigWithDefaults({
slug: reduceSlug,
upload: {
staticURL: '/reduce',
staticDir: './media/reduce',
staticDir: path.resolve(__dirname, './media/reduce'),
mimeTypes: [
'image/png',
'image/jpg',
@@ -374,7 +378,7 @@ export default buildConfigWithDefaults({
slug: 'media-trim',
upload: {
staticURL: '/media-trim',
staticDir: './media-trim',
staticDir: path.resolve(__dirname, './media-trim'),
mimeTypes: ['image/png', 'image/jpg', 'image/jpeg'],
trimOptions: 0,
imageSizes: [
@@ -404,7 +408,7 @@ export default buildConfigWithDefaults({
fields: [],
},
{
slug: 'unstored-media',
slug: unstoredMediaSlug,
upload: {
staticURL: '/media',
disableLocalStorage: true,
@@ -416,7 +420,7 @@ export default buildConfigWithDefaults({
upload: {
// Either use another web server like `npx serve -l 4000` (http://localhost:4000) or use the static server from the previous collection to serve the media folder (http://localhost:3000/media)
staticURL: 'http://localhost:3000/media',
staticDir: './media',
staticDir: path.resolve(__dirname, './media'),
},
fields: [],
},
@@ -427,7 +431,7 @@ export default buildConfigWithDefaults({
slug: 'optional-file',
upload: {
staticURL: '/optional',
staticDir: './optional',
staticDir: path.resolve(__dirname, './optional'),
filesRequiredOnCreate: false,
},
fields: [],
@@ -436,7 +440,7 @@ export default buildConfigWithDefaults({
slug: 'required-file',
upload: {
staticURL: '/required',
staticDir: './required',
staticDir: path.resolve(__dirname, './required'),
filesRequiredOnCreate: true,
},
fields: [],

View File

@@ -12,7 +12,14 @@ import getFileByPath from '../../packages/payload/src/uploads/getFileByPath'
import { NextRESTClient } from '../helpers/NextRESTClient'
import { startMemoryDB } from '../startMemoryDB'
import configPromise from './config'
import { enlargeSlug, mediaSlug, reduceSlug, relationSlug, usersSlug } from './shared'
import {
enlargeSlug,
mediaSlug,
reduceSlug,
relationSlug,
unstoredMediaSlug,
usersSlug,
} from './shared'
const getMimeType = (
filePath: string,
@@ -214,7 +221,7 @@ describe('Collections - Uploads', () => {
formData.append('file', fileBlob)
// unstored media
const response = await restClient.POST(`/${mediaSlug}`, {
const response = await restClient.POST(`/${unstoredMediaSlug}`, {
body: formData,
file: true,
})
@@ -368,8 +375,8 @@ describe('Collections - Uploads', () => {
const expectedPath = path.join(__dirname, './media')
// Check that previously existing files were removed
expect(await fileExists(path.join(expectedPath, mediaDoc.filename))).toBe(true)
expect(await fileExists(path.join(expectedPath, mediaDoc.sizes.icon.filename))).toBe(true)
expect(await fileExists(path.join(expectedPath, mediaDoc.filename))).toBe(false)
expect(await fileExists(path.join(expectedPath, mediaDoc.sizes.icon.filename))).toBe(false)
})
it('update - update many', async () => {
@@ -404,8 +411,8 @@ describe('Collections - Uploads', () => {
const expectedPath = path.join(__dirname, './media')
// Check that previously existing files were removed
expect(await fileExists(path.join(expectedPath, mediaDoc.filename))).toBe(true)
expect(await fileExists(path.join(expectedPath, mediaDoc.sizes.icon.filename))).toBe(true)
expect(await fileExists(path.join(expectedPath, mediaDoc.filename))).toBe(false)
expect(await fileExists(path.join(expectedPath, mediaDoc.sizes.icon.filename))).toBe(false)
})
it('should remove existing media on re-upload', async () => {
@@ -462,7 +469,7 @@ describe('Collections - Uploads', () => {
// Replace the temp file with a new one
const newFilePath = path.resolve(__dirname, './temp-renamed.png')
const newFile = await getFileByPath(newFilePath)
newFile.name = 'temp-renamed.png'
newFile.name = 'temp-renamed-second.png'
const updatedMediaDoc = (await payload.update({
collection: mediaSlug,
@@ -474,6 +481,7 @@ describe('Collections - Uploads', () => {
})) as unknown as { docs: Media[] }
// Check that the replacement file was created and the old one was removed
expect(updatedMediaDoc.docs[0].filename).toEqual(newFile.name)
expect(await fileExists(path.join(expectedPath, updatedMediaDoc.docs[0].filename))).toBe(true)
expect(await fileExists(path.join(expectedPath, mediaDoc.filename))).toBe(false)
})
@@ -588,13 +596,13 @@ describe('Collections - Uploads', () => {
const formData = new FormData()
formData.append('file', await bufferToFileBlob(path.join(__dirname, './image.png')))
const response = await restClient.POST(`/${mediaSlug}`, {
body: formData,
file: true,
})
expect(response.status).toBe(200)
const { doc } = await restClient
.POST(`/${mediaSlug}`, {
body: formData,
file: true,
})
.then((res) => res.json())
const { doc } = await response.json()
const response2 = await restClient.DELETE(`/${mediaSlug}/${doc.id}`)
expect(response2.status).toBe(200)
@@ -605,12 +613,12 @@ describe('Collections - Uploads', () => {
const formData = new FormData()
formData.append('file', await bufferToFileBlob(path.join(__dirname, './image.png')))
const response = await restClient.POST(`/${mediaSlug}`, {
body: formData,
file: true,
})
expect(response.status).toBe(200)
const { doc } = await response.json()
const { doc } = await restClient
.POST(`/${mediaSlug}`, {
body: formData,
file: true,
})
.then((res) => res.json())
const { errors } = await restClient
.DELETE(`/${mediaSlug}`, {

View File

@@ -11,3 +11,5 @@ export const enlargeSlug = 'enlarge'
export const reduceSlug = 'reduce'
export const adminThumbnailSlug = 'admin-thumbnail'
export const unstoredMediaSlug = 'unstored-media'

View File

@@ -1,13 +1,10 @@
import type { CollectionConfig } from '../../../packages/payload/src/collections/config/types'
import { extractTranslations } from 'payload/dist/translations-new/extractTranslations'
import CollectionVersionButton from '../elements/CollectionVersionButton'
import CollectionVersionsButton from '../elements/CollectionVersionsButton'
import { CustomPublishButton } from '../elements/CustomSaveButton'
import { draftCollectionSlug } from '../slugs'
const labels = extractTranslations(['version:draft', 'version:published', 'version:status'])
const DraftPosts: CollectionConfig = {
access: {
read: ({ req: { user } }) => {

View File

@@ -1,20 +1,21 @@
import { GraphQLClient, request } from 'graphql-request'
import type { Payload } from '../../packages/payload/src'
import payload from '../../packages/payload/src'
import { getPayload } from '../../packages/payload/src'
import { devUser } from '../credentials'
import { initPayloadTest } from '../helpers/configHelpers'
import { NextRESTClient } from '../helpers/NextRESTClient'
import { startMemoryDB } from '../startMemoryDB'
import AutosavePosts from './collections/Autosave'
import configPromise from './config'
import AutosaveGlobal from './globals/Autosave'
import { clearAndSeedEverything } from './seed'
import { autosaveCollectionSlug, draftCollectionSlug } from './slugs'
let payload: Payload
let restClient: NextRESTClient
let collectionLocalPostID: string
let collectionLocalVersionID
let graphQLURL
let graphQLClient
let token
let collectionGraphQLPostID
@@ -34,10 +35,9 @@ const formatGraphQLID = (id: number | string) =>
describe('Versions', () => {
beforeAll(async () => {
const config = await configPromise
const { serverURL } = await initPayloadTest({ __dirname, init: { local: false } })
graphQLURL = `${serverURL}${config.routes.api}${config.routes.graphQL}`
const config = await startMemoryDB(configPromise)
payload = await getPayload({ config })
restClient = new NextRESTClient(payload.config)
const login = `
mutation {
@@ -48,10 +48,11 @@ describe('Versions', () => {
token
}
}`
const { data } = await restClient
.GRAPHQL_POST({ body: JSON.stringify({ query: login }) })
.then((res) => res.json())
const response = await request(graphQLURL, login)
token = response.loginUser.token
graphQLClient = new GraphQLClient(graphQLURL, { headers: { Authorization: `JWT ${token}` } })
token = data.loginUser.token
})
beforeEach(async () => {
@@ -67,10 +68,7 @@ describe('Versions', () => {
})
collectionLocalPostID = autosavePost.id
const updatedPost: {
_status?: string
title: string
} = await payload.update({
await payload.update({
id: collectionLocalPostID,
collection,
data: {
@@ -788,10 +786,16 @@ describe('Versions', () => {
}
}`
const response = await graphQLClient.request(query)
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
headers: {
Authorization: `JWT ${token}`,
},
})
.then((res) => res.json())
const data = response.createAutosavePost
collectionGraphQLPostID = data.id
collectionGraphQLPostID = data.createAutosavePost.id
})
describe('Create', () => {
it('should allow a new doc to be created with draft status', async () => {
@@ -808,11 +812,16 @@ describe('Versions', () => {
}
}`
const response = await graphQLClient.request(query)
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
headers: {
Authorization: `JWT ${token}`,
},
})
.then((res) => res.json())
const data = response.createAutosavePost
expect(data._status).toStrictEqual('draft')
expect(data.createAutosavePost._status).toStrictEqual('draft')
})
})
@@ -831,7 +840,12 @@ describe('Versions', () => {
createdAt
}
}`
await graphQLClient.request(update)
await restClient.GRAPHQL_POST({
body: JSON.stringify({ query: update }),
headers: {
Authorization: `JWT ${token}`,
},
})
// language=graphQL
const query = `query {
@@ -844,9 +858,16 @@ describe('Versions', () => {
}
}`
const response = await graphQLClient.request(query)
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
headers: {
Authorization: `JWT ${token}`,
},
})
.then((res) => res.json())
collectionGraphQLVersionID = response.versionsAutosavePosts.docs[0].id
collectionGraphQLVersionID = data.versionsAutosavePosts.docs[0].id
})
it('should allow read of versions by version id', async () => {
@@ -862,13 +883,18 @@ describe('Versions', () => {
}
}`
const response = await graphQLClient.request(query)
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
headers: {
Authorization: `JWT ${token}`,
},
})
.then((res) => res.json())
const data = response.versionAutosavePost
expect(data.id).toBeDefined()
expect(data.parent.id).toStrictEqual(collectionGraphQLPostID)
expect(data.version.title).toStrictEqual(updatedTitle2)
expect(data.versionAutosavePost.id).toBeDefined()
expect(data.versionAutosavePost.parent.id).toStrictEqual(collectionGraphQLPostID)
expect(data.versionAutosavePost.version.title).toStrictEqual(updatedTitle2)
})
it('should allow read of versions by querying version content', async () => {
@@ -887,10 +913,16 @@ describe('Versions', () => {
}
}`
const response = await graphQLClient.request(query)
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
headers: {
Authorization: `JWT ${token}`,
},
})
.then((res) => res.json())
const data = response.versionsAutosavePosts
const doc = data.docs[0]
const doc = data.versionsAutosavePosts.docs[0]
expect(doc.id).toBeDefined()
expect(doc.parent.id).toStrictEqual(collectionGraphQLPostID)
@@ -911,7 +943,12 @@ describe('Versions', () => {
createdAt
}
}`
await graphQLClient.request(update)
await restClient.GRAPHQL_POST({
body: JSON.stringify({ query: update }),
headers: {
Authorization: `JWT ${token}`,
},
})
// language=graphQL
const query = `query {
@@ -924,9 +961,16 @@ describe('Versions', () => {
}
}`
const response = await graphQLClient.request(query)
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
headers: {
Authorization: `JWT ${token}`,
},
})
.then((res) => res.json())
collectionGraphQLVersionID = response.versionsAutosavePosts.docs[0].id
collectionGraphQLVersionID = data.versionsAutosavePosts.docs[0].id
})
it('should allow a version to be restored', async () => {
// Update it
@@ -939,7 +983,12 @@ describe('Versions', () => {
createdAt
}
}`
await graphQLClient.request(update)
await restClient.GRAPHQL_POST({
body: JSON.stringify({ query: update }),
headers: {
Authorization: `JWT ${token}`,
},
})
// restore a versionsPost
const restore = `mutation {
@@ -948,7 +997,12 @@ describe('Versions', () => {
}
}`
await graphQLClient.request(restore)
await restClient.GRAPHQL_POST({
body: JSON.stringify({ query: restore }),
headers: {
Authorization: `JWT ${token}`,
},
})
const query = `query {
AutosavePost(id: ${formatGraphQLID(collectionGraphQLPostID)}) {
@@ -956,9 +1010,16 @@ describe('Versions', () => {
}
}`
const response = await graphQLClient.request(query)
const data = response.AutosavePost
expect(data.title).toStrictEqual(collectionGraphQLOriginalTitle)
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
headers: {
Authorization: `JWT ${token}`,
},
})
.then((res) => res.json())
expect(data.AutosavePost.title).toStrictEqual(collectionGraphQLOriginalTitle)
})
})
})
@@ -973,7 +1034,7 @@ describe('Versions', () => {
slug: globalSlug,
})
const updatedGlobal = await payload.updateGlobal({
await payload.updateGlobal({
data: {
title: title2,
},
@@ -1179,7 +1240,12 @@ describe('Versions', () => {
title
}
}`
await graphQLClient.request(update)
await restClient.GRAPHQL_POST({
body: JSON.stringify({ query: update }),
headers: {
Authorization: `JWT ${token}`,
},
})
// language=graphQL
const query = `query {
@@ -1193,9 +1259,16 @@ describe('Versions', () => {
}
}`
const response = await graphQLClient.request(query)
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
headers: {
Authorization: `JWT ${token}`,
},
})
.then((res) => res.json())
globalGraphQLVersionID = response.versionsAutosaveGlobal.docs[0].id
globalGraphQLVersionID = data.versionsAutosaveGlobal.docs[0].id
})
describe('Read', () => {
it('should allow read of versions by version id', async () => {
@@ -1209,12 +1282,17 @@ describe('Versions', () => {
}
}`
const response = await graphQLClient.request(query)
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
headers: {
Authorization: `JWT ${token}`,
},
})
.then((res) => res.json())
const data = response.versionAutosaveGlobal
expect(data.id).toBeDefined()
expect(data.version.title).toStrictEqual(globalGraphQLOriginalTitle)
expect(data.versionAutosaveGlobal.id).toBeDefined()
expect(data.versionAutosaveGlobal.version.title).toStrictEqual(globalGraphQLOriginalTitle)
})
it('should allow read of versions by querying version content', async () => {
@@ -1230,10 +1308,16 @@ describe('Versions', () => {
}
}`
const response = await graphQLClient.request(query)
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
headers: {
Authorization: `JWT ${token}`,
},
})
.then((res) => res.json())
const data = response.versionsAutosaveGlobal
const doc = data.docs[0]
const doc = data.versionsAutosaveGlobal.docs[0]
expect(doc.id).toBeDefined()
expect(doc.version.title).toStrictEqual(globalGraphQLOriginalTitle)
@@ -1249,7 +1333,12 @@ describe('Versions', () => {
}
}`
await graphQLClient.request(restore)
await restClient.GRAPHQL_POST({
body: JSON.stringify({ query: restore }),
headers: {
Authorization: `JWT ${token}`,
},
})
const query = `query {
AutosaveGlobal {
@@ -1257,9 +1346,15 @@ describe('Versions', () => {
}
}`
const response = await graphQLClient.request(query)
const data = response.AutosaveGlobal
expect(data.title).toStrictEqual(globalGraphQLOriginalTitle)
const { data } = await restClient
.GRAPHQL_POST({
body: JSON.stringify({ query }),
headers: {
Authorization: `JWT ${token}`,
},
})
.then((res) => res.json())
expect(data.AutosaveGlobal.title).toStrictEqual(globalGraphQLOriginalTitle)
})
})
})