feat: passing auth test suite

This commit is contained in:
Jarrod Flesch
2024-02-15 14:57:53 -05:00
parent ef82489040
commit 6a1a83cc2b
25 changed files with 95 additions and 58 deletions

View File

@@ -27,6 +27,7 @@
"prepublishOnly": "pnpm clean && pnpm build"
},
"dependencies": {
"bson": "^6.3.0",
"bson-ext": "^4.0.3",
"bson-objectid": "2.0.4",
"deepmerge": "4.3.1",

View File

@@ -2,7 +2,7 @@ import type { PathToQuery } from 'payload/database'
import type { Field, Payload } from 'payload/types'
import type { Operator } from 'payload/types'
import objectID from 'bson-objectid'
import { ObjectId } from 'bson'
import mongoose from 'mongoose'
import { getLocalizedPaths } from 'payload/database'
import { fieldAffectsData } from 'payload/types'
@@ -196,7 +196,7 @@ export async function buildSearchParam({
if (typeof formattedValue === 'string') {
if (mongoose.Types.ObjectId.isValid(formattedValue)) {
result.value.$or.push({ [path]: { [operatorKey]: objectID(formattedValue) } })
result.value.$or.push({ [path]: { [operatorKey]: new ObjectId(formattedValue) } })
} else {
;(Array.isArray(field.relationTo) ? field.relationTo : [field.relationTo]).forEach(
(relationTo) => {

View File

@@ -26,6 +26,10 @@ function loginResolver(collection: Collection) {
context.headers['Set-Cookie'] = cookie
if (collection.config.auth.removeTokenFromResponses) {
delete result.token
}
return result
}

View File

@@ -11,7 +11,13 @@ function meResolver(collection: Collection): any {
depth: 0,
req: isolateTransactionID(context.req),
}
return meOperation(options)
const result = await meOperation(options)
if (collection.config.auth.removeTokenFromResponses) {
delete result.token
}
return result
}
return resolver

View File

@@ -29,6 +29,11 @@ function refreshResolver(collection: Collection) {
collectionConfig: collection.config,
})
context.headers['Set-Cookie'] = cookie
if (collection.config.auth.removeTokenFromResponses) {
delete result.refreshedToken
}
return result
}

View File

@@ -25,6 +25,11 @@ function resetPasswordResolver(collection: Collection) {
collectionConfig: collection.config,
})
context.headers['Set-Cookie'] = cookie
if (collection.config.auth.removeTokenFromResponses) {
delete result.token
}
return result
}

View File

@@ -24,13 +24,15 @@ export const login: CollectionRouteHandler = async ({ req, collection }) => {
collectionConfig: collection.config,
})
if (collection.config.auth.removeTokenFromResponses) {
delete result.token
}
return Response.json(
{
exp: result.exp,
// TODO(translate)
message: 'Auth Passed',
token: result.token,
user: result.user,
...result,
},
{
headers: new Headers({

View File

@@ -12,6 +12,10 @@ export const me: CollectionRouteHandler = async ({ req, collection }) => {
currentToken,
})
if (collection.config.auth.removeTokenFromResponses) {
delete result.token
}
return Response.json(
{
...result,

View File

@@ -31,13 +31,15 @@ export const refresh: CollectionRouteHandler = async ({ req, collection }) => {
collectionConfig: collection.config,
})
if (collection.config.auth.removeTokenFromResponses) {
delete result.refreshedToken
}
return Response.json(
{
exp: result.exp,
// TODO(translate)
message: 'Token refresh successful',
token: result.refreshedToken,
user: result.user,
...result,
},
{
headers: new Headers({

View File

@@ -24,12 +24,15 @@ export const resetPassword: CollectionRouteHandler = async ({ req, collection })
collectionConfig: collection.config,
})
if (collection.config.auth.removeTokenFromResponses) {
delete result.token
}
return Response.json(
{
// TODO(translate)
message: 'Password reset successfully.',
token: result.token,
user: result.user,
...result,
},
{
headers: new Headers({

View File

@@ -48,7 +48,7 @@
"dependencies": {
"@payloadcms/graphql": "workspace:^",
"@payloadcms/translations": "workspace:^",
"bson-objectid": "2.0.4",
"bson": "^6.3.0",
"conf": "10.2.0",
"console-table-printer": "2.11.2",
"dataloader": "2.2.2",

View File

@@ -51,7 +51,13 @@ async function localLogin<TSlug extends keyof GeneratedTypes['collections']>(
showHiddenFields,
}
return loginOperation<TSlug>(args)
const result = await loginOperation<TSlug>(args)
if (collection.config.auth.removeTokenFromResponses) {
delete result.token
}
return result
}
export default localLogin

View File

@@ -34,12 +34,18 @@ async function localResetPassword<T extends keyof GeneratedTypes['collections']>
)
}
return resetPasswordOperation({
const result = await resetPasswordOperation({
collection,
data,
overrideAccess,
req: await createLocalReq(options, payload),
})
if (collection.config.auth.removeTokenFromResponses) {
delete result.token
}
return result
}
export default localResetPassword

View File

@@ -230,10 +230,6 @@ export const loginOperation = async <TSlug extends keyof GeneratedTypes['collect
result,
})
if (collectionConfig.auth.removeTokenFromResponses) {
delete result.token
}
// /////////////////////////////////////
// Return results
// /////////////////////////////////////

View File

@@ -55,7 +55,7 @@ export const meOperation = async ({
if (currentToken) {
const decoded = jwt.decode(currentToken) as jwt.JwtPayload
if (decoded) result.exp = decoded.exp
if (!collection.config.auth.removeTokenFromResponses) result.token = currentToken
result.token = currentToken
}
}

View File

@@ -116,9 +116,5 @@ export const refreshOperation = async (incomingArgs: Arguments): Promise<Result>
// Return results
// /////////////////////////////////////
if (collectionConfig.auth.removeTokenFromResponses) {
delete result.refreshedToken
}
return result
}

View File

@@ -105,10 +105,12 @@ export const resetPasswordOperation = async (args: Arguments): Promise<Result> =
})
if (shouldCommit) await commitTransaction(req)
return {
token: collectionConfig.auth.removeTokenFromResponses ? undefined : token,
const result = {
token,
user: fullUser,
}
return result
} catch (error: unknown) {
await killTransaction(req)
throw error

View File

@@ -1,9 +1,9 @@
import ObjectID from 'bson-objectid'
import { ObjectId } from 'bson'
import type { Field, FieldHook } from '../config/types'
const generateID: FieldHook = ({ operation, value }) =>
(operation !== 'create' ? value : false) || new ObjectID().toHexString()
(operation !== 'create' ? value : false) || new ObjectId().toHexString()
export const baseIDField: Field = {
name: 'id',

View File

@@ -16,7 +16,7 @@ export const updateHandler: PayloadHandler = async ({ req, routeParams }) => {
return Response.json(
{
...doc,
doc,
message: payloadRequest.t('general:updatedSuccessfully'),
},
{

View File

@@ -1,4 +1,4 @@
import ObjectID from 'bson-objectid'
import { ObjectId } from 'bson'
export const isValidID = (
value: number | string,
@@ -8,6 +8,6 @@ export const isValidID = (
if (typeof value === 'number' && !Number.isNaN(value)) return true
if (type === 'ObjectID') {
return ObjectID.isValid(String(value))
return ObjectId.isValid(String(value))
}
}

View File

@@ -45,7 +45,7 @@
"@monaco-editor/react": "4.5.1",
"@payloadcms/translations": "workspace:^",
"body-scroll-lock": "4.0.0-beta.0",
"bson-objectid": "2.0.4",
"bson": "^6.3.0",
"date-fns": "2.30.0",
"deep-equal": "2.2.2",
"flatley": "5.2.0",

View File

@@ -1,4 +1,4 @@
import ObjectID from 'bson-objectid'
import { ObjectId } from 'bson'
import equal from 'deep-equal'
import type { FieldAction, FormState, FormField, Row } from './types'
@@ -105,7 +105,7 @@ export function fieldReducer(state: FormState, action: FieldAction): FormState {
const withNewRow = [...(state[path]?.rows || [])]
const newRow: Row = {
id: new ObjectID().toHexString(),
id: new ObjectId().toHexString(),
blockType: blockType || undefined,
collapsed: false,
}
@@ -147,7 +147,7 @@ export function fieldReducer(state: FormState, action: FieldAction): FormState {
const rowsMetadata = [...(state[path]?.rows || [])]
rowsMetadata[rowIndex] = {
id: new ObjectID().toHexString(),
id: new ObjectId().toHexString(),
blockType: blockType || undefined,
collapsed: false,
}
@@ -183,10 +183,10 @@ export function fieldReducer(state: FormState, action: FieldAction): FormState {
const rowsMetadata = state[path]?.rows || []
const duplicateRowMetadata = deepCopyObject(rowsMetadata[rowIndex])
if (duplicateRowMetadata.id) duplicateRowMetadata.id = new ObjectID().toHexString()
if (duplicateRowMetadata.id) duplicateRowMetadata.id = new ObjectId().toHexString()
const duplicateRowState = deepCopyObject(rows[rowIndex])
if (duplicateRowState.id) duplicateRowState.id = new ObjectID().toHexString()
if (duplicateRowState.id) duplicateRowState.id = new ObjectId().toHexString()
// If there are subfields
if (Object.keys(duplicateRowState).length > 0) {

View File

@@ -1,7 +1,7 @@
/* eslint-disable no-param-reassign */
import type { TFunction } from '@payloadcms/translations'
import ObjectID from 'bson-objectid'
import { ObjectId } from 'bson'
import type { User } from 'payload/auth'
import type { NonPresentationalField, Data, SanitizedConfig } from 'payload/types'
@@ -96,7 +96,7 @@ export const addFieldStatePromise = async ({
const { promises, rowMetadata } = arrayValue.reduce(
(acc, row, i) => {
const rowPath = `${path}${field.name}.${i}.`
row.id = row?.id || new ObjectID().toHexString()
row.id = row?.id || new ObjectId().toHexString()
state[`${rowPath}id`] = {
initialValue: row.id,
@@ -173,7 +173,7 @@ export const addFieldStatePromise = async ({
const rowPath = `${path}${field.name}.${i}.`
if (block) {
row.id = row?.id || new ObjectID().toHexString()
row.id = row?.id || new ObjectId().toHexString()
state[`${rowPath}id`] = {
initialValue: row.id,

20
pnpm-lock.yaml generated
View File

@@ -301,6 +301,9 @@ importers:
packages/db-mongodb:
dependencies:
bson:
specifier: ^6.3.0
version: 6.3.0
bson-ext:
specifier: ^4.0.3
version: 4.0.3
@@ -595,9 +598,9 @@ importers:
'@payloadcms/translations':
specifier: workspace:^
version: link:../translations
bson-objectid:
specifier: 2.0.4
version: 2.0.4
bson:
specifier: ^6.3.0
version: 6.3.0
conf:
specifier: 10.2.0
version: 10.2.0
@@ -1273,9 +1276,9 @@ importers:
body-scroll-lock:
specifier: 4.0.0-beta.0
version: 4.0.0-beta.0
bson-objectid:
specifier: 2.0.4
version: 2.0.4
bson:
specifier: ^6.3.0
version: 6.3.0
date-fns:
specifier: 2.30.0
version: 2.30.0
@@ -7108,6 +7111,11 @@ packages:
engines: {node: '>=14.20.1'}
dev: false
/bson@6.3.0:
resolution: {integrity: sha512-balJfqwwTBddxfnidJZagCBPP/f48zj9Sdp3OJswREOgsJzHiQSaOIAtApSgDQFYgHqAvFkp53AFSqjMDZoTFw==}
engines: {node: '>=16.20.1'}
dev: false
/buffer-crc32@0.2.13:
resolution: {integrity: sha512-VO9Ht/+p3SN7SKWqcrgEzjGbRSJYTx+Q1pTQC0wrWqHx0vpJraQ6GtHx8tvcg1rlK1byhU5gccxgOgj7B0TDkQ==}
dev: true

View File

@@ -10,7 +10,6 @@ import { startMemoryDB } from '../startMemoryDB'
import configPromise from './config'
import { namedSaveToJWTValue, saveToJWTKey, slug } from './shared'
let apiUrl
let restClient: NextRESTClient
let payload: Payload
@@ -333,7 +332,7 @@ describe('Auth', () => {
let data
beforeAll(async () => {
const response = await restClient.POST(`/${slug}/payload-preferences/${key}`, {
const response = await restClient.POST(`/payload-preferences/${key}`, {
body: JSON.stringify({
value: { property },
}),
@@ -350,7 +349,7 @@ describe('Auth', () => {
})
it('should read', async () => {
const response = await restClient.GET(`/${slug}/payload-preferences/${key}`, {
const response = await restClient.GET(`/payload-preferences/${key}`, {
headers: {
Authorization: `JWT ${token}`,
},
@@ -361,7 +360,7 @@ describe('Auth', () => {
})
it('should update', async () => {
const response = await restClient.POST(`/${slug}/payload-preferences/${key}`, {
const response = await restClient.POST(`/payload-preferences/${key}`, {
body: JSON.stringify({
value: { property: 'updated', property2: 'test' },
}),
@@ -388,7 +387,7 @@ describe('Auth', () => {
})
it('should delete', async () => {
const response = await restClient.DELETE(`/${slug}/payload-preferences/${key}`, {
const response = await restClient.DELETE(`/payload-preferences/${key}`, {
headers: {
Authorization: `JWT ${token}`,
},
@@ -606,14 +605,6 @@ describe('Auth', () => {
})
})
describe('REST API', () => {
it('should respond from route handlers', async () => {
const test = await fetch(`${apiUrl}/api/test`)
expect(test.status).toStrictEqual(200)
})
})
describe('API Key', () => {
it('should authenticate via the correct API key user', async () => {
const usersQuery = await payload.find({