test: stabilize frequent fails (#13318)

Adjusts tests that "flake" frequently.
This commit is contained in:
Jarrod Flesch
2025-07-30 08:52:01 -04:00
committed by GitHub
parent e7124f6176
commit a22f27de1c
13 changed files with 47 additions and 71 deletions

View File

@@ -15,7 +15,9 @@ export const GroupByHeader: React.FC<{
}> = ({ collectionConfig, groupByFieldPath, groupByValue, heading }) => { }> = ({ collectionConfig, groupByFieldPath, groupByValue, heading }) => {
return ( return (
<header className={baseClass}> <header className={baseClass}>
<h4 className={`${baseClass}__heading`}>{heading}</h4> <h4 className={`${baseClass}__heading`} data-group-id={groupByValue}>
{heading}
</h4>
<ListSelection <ListSelection
collectionConfig={collectionConfig} collectionConfig={collectionConfig}
label={heading} label={heading}

View File

@@ -6,7 +6,7 @@ import { devUser } from 'credentials.js'
import { openDocControls } from 'helpers/e2e/openDocControls.js' import { openDocControls } from 'helpers/e2e/openDocControls.js'
import { openNav } from 'helpers/e2e/toggleNav.js' import { openNav } from 'helpers/e2e/toggleNav.js'
import path from 'path' import path from 'path'
import { email, wait } from 'payload/shared' import { wait } from 'payload/shared'
import { fileURLToPath } from 'url' import { fileURLToPath } from 'url'
import type { PayloadTestSDK } from '../helpers/sdk/index.js' import type { PayloadTestSDK } from '../helpers/sdk/index.js'
@@ -16,7 +16,6 @@ import {
closeNav, closeNav,
ensureCompilationIsDone, ensureCompilationIsDone,
exactText, exactText,
getRoutes,
initPageConsoleErrorCatch, initPageConsoleErrorCatch,
login, login,
saveDocAndAssert, saveDocAndAssert,
@@ -71,7 +70,6 @@ describe('Access Control', () => {
let disabledFields: AdminUrlUtil let disabledFields: AdminUrlUtil
let serverURL: string let serverURL: string
let context: BrowserContext let context: BrowserContext
let logoutURL: string
let authFields: AdminUrlUtil let authFields: AdminUrlUtil
beforeAll(async ({ browser }, testInfo) => { beforeAll(async ({ browser }, testInfo) => {
@@ -98,17 +96,6 @@ describe('Access Control', () => {
await ensureCompilationIsDone({ page, serverURL, noAutoLogin: true }) await ensureCompilationIsDone({ page, serverURL, noAutoLogin: true })
await login({ page, serverURL }) await login({ page, serverURL })
await ensureCompilationIsDone({ page, serverURL })
const {
admin: {
routes: { logout: logoutRoute },
},
routes: { admin: adminRoute },
} = getRoutes({})
logoutURL = `${serverURL}${adminRoute}${logoutRoute}`
}) })
describe('fields', () => { describe('fields', () => {
@@ -515,6 +502,13 @@ describe('Access Control', () => {
describe('global', () => { describe('global', () => {
test('should restrict update access based on document field', async () => { test('should restrict update access based on document field', async () => {
await payload.updateGlobal({
slug: userRestrictedGlobalSlug,
data: {
name: 'dev@payloadcms.com',
},
})
await page.goto(userRestrictedGlobalURL.global(userRestrictedGlobalSlug)) await page.goto(userRestrictedGlobalURL.global(userRestrictedGlobalSlug))
await expect(page.locator('#field-name')).toBeVisible() await expect(page.locator('#field-name')).toBeVisible()
await expect(page.locator('#field-name')).toHaveValue(devUser.email) await expect(page.locator('#field-name')).toHaveValue(devUser.email)

View File

@@ -75,6 +75,7 @@ export const testEslintConfig = [
'createFolder', 'createFolder',
'createFolderFromDoc', 'createFolderFromDoc',
'assertURLParams', 'assertURLParams',
'uploadImage',
], ],
}, },
], ],

View File

@@ -131,13 +131,23 @@ describe('JSON', () => {
const jsonField = page.locator('.json-field:not(.read-only) #field-customJSON') const jsonField = page.locator('.json-field:not(.read-only) #field-customJSON')
await expect(jsonField).toContainText('"default": "value"') await expect(jsonField).toContainText('"default": "value"')
const originalHeight = const boundingBox = await page
(await page.locator('.json-field:not(.read-only) #field-customJSON').boundingBox())?.height || .locator('.json-field:not(.read-only) #field-customJSON')
0 .boundingBox()
await page.locator('#set-custom-json').click() await expect(() => expect(boundingBox).not.toBeNull()).toPass()
const newHeight = const originalHeight = boundingBox!.height
(await page.locator('.json-field:not(.read-only) #field-customJSON').boundingBox())?.height ||
0 // click the button to set custom JSON
expect(newHeight).toBeGreaterThan(originalHeight) await page.locator('#set-custom-json').click({ delay: 1000 })
const newBoundingBox = await page
.locator('.json-field:not(.read-only) #field-customJSON')
.boundingBox()
await expect(() => expect(newBoundingBox).not.toBeNull()).toPass()
const newHeight = newBoundingBox!.height
await expect(() => {
expect(newHeight).toBeGreaterThan(originalHeight)
}).toPass()
}) })
}) })

View File

@@ -23,7 +23,6 @@ import { AdminUrlUtil } from '../../../helpers/adminUrlUtil.js'
import { assertToastErrors } from '../../../helpers/assertToastErrors.js' import { assertToastErrors } from '../../../helpers/assertToastErrors.js'
import { initPayloadE2ENoConfig } from '../../../helpers/initPayloadE2ENoConfig.js' import { initPayloadE2ENoConfig } from '../../../helpers/initPayloadE2ENoConfig.js'
import { reInitializeDB } from '../../../helpers/reInitializeDB.js' import { reInitializeDB } from '../../../helpers/reInitializeDB.js'
import { RESTClient } from '../../../helpers/rest.js'
import { POLL_TOPASS_TIMEOUT, TEST_TIMEOUT_LONG } from '../../../playwright.config.js' import { POLL_TOPASS_TIMEOUT, TEST_TIMEOUT_LONG } from '../../../playwright.config.js'
import { relationshipFieldsSlug, textFieldsSlug } from '../../slugs.js' import { relationshipFieldsSlug, textFieldsSlug } from '../../slugs.js'
const filename = fileURLToPath(import.meta.url) const filename = fileURLToPath(import.meta.url)
@@ -33,7 +32,6 @@ const dirname = path.resolve(currentFolder, '../../')
const { beforeAll, beforeEach, describe } = test const { beforeAll, beforeEach, describe } = test
let payload: PayloadTestSDK<Config> let payload: PayloadTestSDK<Config>
let client: RESTClient
let page: Page let page: Page
let serverURL: string let serverURL: string
// If we want to make this run in parallel: test.describe.configure({ mode: 'parallel' }) // If we want to make this run in parallel: test.describe.configure({ mode: 'parallel' })
@@ -59,12 +57,6 @@ describe('relationship', () => {
uploadsDir: path.resolve(dirname, './collections/Upload/uploads'), uploadsDir: path.resolve(dirname, './collections/Upload/uploads'),
}) })
if (client) {
await client.logout()
}
client = new RESTClient({ defaultSlug: 'users', serverURL })
await client.login()
await ensureCompilationIsDone({ page, serverURL }) await ensureCompilationIsDone({ page, serverURL })
}) })
@@ -693,7 +685,7 @@ describe('relationship', () => {
await createRelationshipFieldDoc({ value: textDoc.id, relationTo: 'text-fields' }) await createRelationshipFieldDoc({ value: textDoc.id, relationTo: 'text-fields' })
await page.goto(url.list) await page.goto(url.list)
await wait(300) await wait(1000) // wait for page to load
await addListFilter({ await addListFilter({
page, page,

View File

@@ -17,7 +17,6 @@ import {
import { AdminUrlUtil } from '../../../helpers/adminUrlUtil.js' import { AdminUrlUtil } from '../../../helpers/adminUrlUtil.js'
import { initPayloadE2ENoConfig } from '../../../helpers/initPayloadE2ENoConfig.js' import { initPayloadE2ENoConfig } from '../../../helpers/initPayloadE2ENoConfig.js'
import { reInitializeDB } from '../../../helpers/reInitializeDB.js' import { reInitializeDB } from '../../../helpers/reInitializeDB.js'
import { RESTClient } from '../../../helpers/rest.js'
import { POLL_TOPASS_TIMEOUT, TEST_TIMEOUT_LONG } from '../../../playwright.config.js' import { POLL_TOPASS_TIMEOUT, TEST_TIMEOUT_LONG } from '../../../playwright.config.js'
import { uploadsSlug } from '../../slugs.js' import { uploadsSlug } from '../../slugs.js'
@@ -28,7 +27,6 @@ const dirname = path.resolve(currentFolder, '../../')
const { beforeAll, beforeEach, describe } = test const { beforeAll, beforeEach, describe } = test
let payload: PayloadTestSDK<Config> let payload: PayloadTestSDK<Config>
let client: RESTClient
let page: Page let page: Page
let serverURL: string let serverURL: string
// If we want to make this run in parallel: test.describe.configure({ mode: 'parallel' }) // If we want to make this run in parallel: test.describe.configure({ mode: 'parallel' })
@@ -57,12 +55,6 @@ describe('Upload', () => {
uploadsDir: path.resolve(dirname, './collections/Upload/uploads'), uploadsDir: path.resolve(dirname, './collections/Upload/uploads'),
}) })
if (client) {
await client.logout()
}
client = new RESTClient({ defaultSlug: 'users', serverURL })
await client.login()
await ensureCompilationIsDone({ page, serverURL }) await ensureCompilationIsDone({ page, serverURL })
}) })

View File

@@ -57,17 +57,6 @@ test.describe('Group By', () => {
password: devUser.password, password: devUser.password,
}, },
}) })
// Fetch category IDs from already-seeded data
const categories = await payload.find({
collection: 'categories',
limit: 1,
sort: 'title',
where: { title: { equals: 'Category 1' } },
})
const [category1] = categories.docs
category1Id = category1?.id as number | string
}) })
beforeEach(async () => { beforeEach(async () => {
@@ -649,7 +638,12 @@ test.describe('Group By', () => {
await firstTable.locator('.row-1 .cell-_select input').check() await firstTable.locator('.row-1 .cell-_select input').check()
await firstTable.locator('.list-selection__button[aria-label="Delete"]').click() await firstTable.locator('.list-selection__button[aria-label="Delete"]').click()
const modalId = `[id^="${category1Id}-confirm-delete-many-docs"]` const firstGroupID = await firstTable
.locator('.group-by-header__heading')
.getAttribute('data-group-id')
const modalId = `[id^="${firstGroupID}-confirm-delete-many-docs"]`
await expect(page.locator(modalId)).toBeVisible()
// Confirm trash (skip permanent delete) // Confirm trash (skip permanent delete)
await page.locator(`${modalId} #confirm-action`).click() await page.locator(`${modalId} #confirm-action`).click()

View File

@@ -18,6 +18,7 @@ export const openListFilters = async (
): Promise<{ ): Promise<{
filterContainer: Locator filterContainer: Locator
}> => { }> => {
await expect(page.locator(togglerSelector)).toBeVisible()
const filterContainer = page.locator(filterContainerSelector).first() const filterContainer = page.locator(filterContainerSelector).first()
const isAlreadyOpen = await filterContainer.isVisible() const isAlreadyOpen = await filterContainer.isVisible()

View File

@@ -44,8 +44,8 @@ describe('i18n', () => {
const context = await browser.newContext() const context = await browser.newContext()
page = await context.newPage() page = await context.newPage()
initPageConsoleErrorCatch(page)
initPageConsoleErrorCatch(page)
await ensureCompilationIsDone({ page, serverURL }) await ensureCompilationIsDone({ page, serverURL })
}) })
beforeEach(async () => { beforeEach(async () => {

View File

@@ -13,7 +13,6 @@ import {
import { AdminUrlUtil } from '../../../helpers/adminUrlUtil.js' import { AdminUrlUtil } from '../../../helpers/adminUrlUtil.js'
import { initPayloadE2ENoConfig } from '../../../helpers/initPayloadE2ENoConfig.js' import { initPayloadE2ENoConfig } from '../../../helpers/initPayloadE2ENoConfig.js'
import { reInitializeDB } from '../../../helpers/reInitializeDB.js' import { reInitializeDB } from '../../../helpers/reInitializeDB.js'
import { RESTClient } from '../../../helpers/rest.js'
import { POLL_TOPASS_TIMEOUT, TEST_TIMEOUT_LONG } from '../../../playwright.config.js' import { POLL_TOPASS_TIMEOUT, TEST_TIMEOUT_LONG } from '../../../playwright.config.js'
const filename = fileURLToPath(import.meta.url) const filename = fileURLToPath(import.meta.url)
@@ -22,7 +21,6 @@ const dirname = path.resolve(currentFolder, '../../')
const { beforeAll, beforeEach, describe } = test const { beforeAll, beforeEach, describe } = test
let client: RESTClient
let page: Page let page: Page
let serverURL: string let serverURL: string
// If we want to make this run in parallel: test.describe.configure({ mode: 'parallel' }) // If we want to make this run in parallel: test.describe.configure({ mode: 'parallel' })
@@ -48,12 +46,6 @@ describe('Rich Text', () => {
uploadsDir: [path.resolve(dirname, './collections/Upload/uploads')], uploadsDir: [path.resolve(dirname, './collections/Upload/uploads')],
}) })
if (client) {
await client.logout()
}
client = new RESTClient({ defaultSlug: 'users', serverURL })
await client.login()
await ensureCompilationIsDone({ page, serverURL }) await ensureCompilationIsDone({ page, serverURL })
}) })

View File

@@ -66,6 +66,9 @@ describe('Live Preview', () => {
const context = await browser.newContext() const context = await browser.newContext()
page = await context.newPage() page = await context.newPage()
initPageConsoleErrorCatch(page)
await ensureCompilationIsDone({ page, serverURL })
user = await payload user = await payload
.login({ .login({
collection: 'users', collection: 'users',
@@ -75,10 +78,6 @@ describe('Live Preview', () => {
}, },
}) })
?.then((res) => res.user) // TODO: this type is wrong ?.then((res) => res.user) // TODO: this type is wrong
initPageConsoleErrorCatch(page)
await ensureCompilationIsDone({ page, serverURL })
}) })
beforeEach(async () => { beforeEach(async () => {

View File

@@ -86,11 +86,10 @@ describe('Localization', () => {
page = await context.newPage() page = await context.newPage()
initPageConsoleErrorCatch(page) initPageConsoleErrorCatch(page)
await ensureCompilationIsDone({ page, serverURL })
client = new RESTClient({ defaultSlug: 'users', serverURL }) client = new RESTClient({ defaultSlug: 'users', serverURL })
await client.login() await client.login()
await ensureCompilationIsDone({ page, serverURL })
}) })
beforeEach(async () => { beforeEach(async () => {

View File

@@ -58,6 +58,10 @@ describe('Query Presets', () => {
context = await browser.newContext() context = await browser.newContext()
page = await context.newPage() page = await context.newPage()
initPageConsoleErrorCatch(page)
await ensureCompilationIsDone({ page, serverURL })
user = await payload user = await payload
.login({ .login({
collection: 'users', collection: 'users',
@@ -80,10 +84,6 @@ describe('Query Presets', () => {
depth: 0, depth: 0,
}) })
?.then((res) => res.docs[0]) ?.then((res) => res.docs[0])
initPageConsoleErrorCatch(page)
await ensureCompilationIsDone({ page, serverURL })
}) })
beforeEach(async () => { beforeEach(async () => {