diff --git a/test/helpers/NextRESTClient.ts b/test/helpers/NextRESTClient.ts index 723e8abb2..26a6a4974 100644 --- a/test/helpers/NextRESTClient.ts +++ b/test/helpers/NextRESTClient.ts @@ -1,4 +1,5 @@ import type { Where } from 'payload/types' +import type { ParsedQs } from 'qs' import QueryString from 'qs' @@ -22,13 +23,16 @@ type RequestQuery = { } } -function generateQueryString(query: RequestQuery['query']): string { +function generateQueryString(query: RequestQuery['query'], params: ParsedQs): string { + const { where, limit, page, sort, ...rest } = params || {} + const whereFilter = query?.where || where return QueryString.stringify( { - ...(query?.where ? { where: query.where } : {}), - limit: query?.limit, - page: query?.page, - sort: query?.sort, + ...(rest || {}), + ...(whereFilter ? { where: whereFilter } : {}), + limit: query?.limit || limit || undefined, + page: query?.page || page || undefined, + sort: query?.sort || sort || undefined, }, { addQueryPrefix: true, @@ -61,25 +65,27 @@ export class NextRESTClient { this._GRAPHQL_POST = createGraphqlPOST(config) } - private generateRequestParts(path: string): { + private generateRequestParts(path: ValidPath): { + params?: ParsedQs slug: string[] url: string } { - const safePath = path.slice(1) - const slug = safePath.split('/') - const url = `${this.serverURL}${this.config.routes.api}/${safePath}` + const [slugs, params] = path.slice(1).split('?') + const url = `${this.serverURL}${this.config.routes.api}/${slugs}` + return { url, - slug, + slug: slugs.split('/'), + params: params ? QueryString.parse(params) : undefined, } } async DELETE(path: ValidPath, options: RequestInit & RequestQuery = {}): Promise { - const { url, slug } = this.generateRequestParts(path) + const { url, slug, params } = this.generateRequestParts(path) const { query, ...rest } = options || {} - const whereQuery = generateQueryString(query) + const queryParams = generateQueryString(query, params) - const request = new Request(`${url}${whereQuery}`, { + const request = new Request(`${url}${queryParams}`, { ...rest, method: 'DELETE', headers: { @@ -94,11 +100,11 @@ export class NextRESTClient { path: ValidPath, options: Omit & RequestQuery = {}, ): Promise { - const { url, slug } = this.generateRequestParts(path) + const { url, slug, params } = this.generateRequestParts(path) const { query, ...rest } = options || {} - const whereQuery = generateQueryString(query) + const queryParams = generateQueryString(query, params) - const request = new Request(`${url}${whereQuery}`, { + const request = new Request(`${url}${queryParams}`, { ...rest, method: 'GET', headers: new Headers({ @@ -125,11 +131,11 @@ export class NextRESTClient { } async PATCH(path: ValidPath, options: RequestInit & RequestQuery): Promise { - const { url, slug } = this.generateRequestParts(path) + const { url, slug, params } = this.generateRequestParts(path) const { query, ...rest } = options - const whereQuery = generateQueryString(query) + const queryParams = generateQueryString(query, params) - const request = new Request(`${url}${whereQuery}`, { + const request = new Request(`${url}${queryParams}`, { ...rest, method: 'PATCH', headers: new Headers({ @@ -141,9 +147,10 @@ export class NextRESTClient { } async POST(path: ValidPath, options: RequestInit = {}): Promise { - const { url, slug } = this.generateRequestParts(path) + const { url, slug, params } = this.generateRequestParts(path) + const queryParams = generateQueryString({}, params) - const request = new Request(url, { + const request = new Request(`${url}${queryParams}`, { ...options, method: 'POST', headers: new Headers({ diff --git a/test/hooks/collections/ContextHooks/index.ts b/test/hooks/collections/ContextHooks/index.ts index 949960fe0..3b9be3e88 100644 --- a/test/hooks/collections/ContextHooks/index.ts +++ b/test/hooks/collections/ContextHooks/index.ts @@ -13,20 +13,20 @@ const ContextHooks: CollectionConfig = { }, hooks: { beforeOperation: [ - async ({ context, args }) => { + ({ context, args }) => { // eslint-disable-next-line prefer-destructuring const req: PayloadRequest = args.req - if (!req.query || !Object.keys(req.query).length) { + if (req.searchParams.size === 0) { return args } - Object.keys(req.query).forEach((key) => { + req.searchParams.forEach((value, key) => { if (key.startsWith('context_')) { // Strip 'context_' from key, add it to context object and remove it from query params const newKey = key.substring('context_'.length) - context[newKey] = req.query[key] - delete req.query[key] + context[newKey] = value + req.searchParams.delete(key) } }) diff --git a/test/hooks/int.spec.ts b/test/hooks/int.spec.ts index 3954d22b4..dd4a1dd2b 100644 --- a/test/hooks/int.spec.ts +++ b/test/hooks/int.spec.ts @@ -1,9 +1,11 @@ +import type { Payload } from '../../packages/payload/src' import type { NestedAfterReadHook } from './payload-types' -import payload from '../../packages/payload/src' +import { getPayload } from '../../packages/payload/src' import { AuthenticationError } from '../../packages/payload/src/errors' import { devUser, regularUser } from '../credentials' -import { initPayloadTest } from '../helpers/configHelpers' +import { NextRESTClient } from '../helpers/NextRESTClient' +import { startMemoryDB } from '../startMemoryDB' import { afterOperationSlug } from './collections/AfterOperation' import { chainingHooksSlug } from './collections/ChainingHooks' import { contextHooksSlug } from './collections/ContextHooks' @@ -16,15 +18,17 @@ import { import { relationsSlug } from './collections/Relations' import { transformSlug } from './collections/Transform' import { hooksUsersSlug } from './collections/Users' -import { HooksConfig } from './config' +import configPromise, { HooksConfig } from './config' import { dataHooksGlobalSlug } from './globals/Data' -let apiUrl +let restClient: NextRESTClient +let payload: Payload describe('Hooks', () => { 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 () => { @@ -268,18 +272,17 @@ describe('Hooks', () => { context_secretValue: 'data from rest API', }) // send context as query params. It will be parsed by the beforeOperation hook - const response = await fetch(`${apiUrl}/${contextHooksSlug}?${params.toString()}`, { - body: JSON.stringify({ - value: 'wrongvalue', - }), - method: 'post', - }) - - const document = (await response.json()).doc + const { doc } = await restClient + .POST(`/${contextHooksSlug}?${params.toString()}`, { + body: JSON.stringify({ + value: 'wrongvalue', + }), + }) + .then((res) => res.json()) const retrievedDoc = await payload.findByID({ collection: contextHooksSlug, - id: document.id, + id: doc.id, }) expect(retrievedDoc.value).toEqual('data from rest API')