mirror of
https://github.com/hanzoai/next.js.git
synced 2026-09-24 17:00:51 +00:00
[next-playwright] Use unique cookie values for instant navigation testing lock (#91250)
Co-authored-by: Cursor Agent <[email protected]>
This commit is contained in:
co-authored by
Cursor Agent
parent
63dff61bfc
commit
672b02b270
@@ -12,6 +12,6 @@
|
||||
"devDependencies": {
|
||||
"rimraf": "6.0.1",
|
||||
"next": "workspace:*",
|
||||
"playwright": "^1.40.0"
|
||||
"playwright": "1.58.2"
|
||||
}
|
||||
}
|
||||
|
||||
+2
-2
@@ -255,8 +255,8 @@
|
||||
"octokit": "3.1.0",
|
||||
"outdent": "0.8.0",
|
||||
"pixrem": "5.0.0",
|
||||
"playwright": "1.48.0",
|
||||
"playwright-chromium": "1.48.0",
|
||||
"playwright": "1.58.2",
|
||||
"playwright-chromium": "1.58.2",
|
||||
"postcss": "8.4.31",
|
||||
"postcss-nested": "4.2.1",
|
||||
"postcss-pseudoelements": "5.0.0",
|
||||
|
||||
@@ -26,6 +26,7 @@
|
||||
}
|
||||
},
|
||||
"devDependencies": {
|
||||
"@playwright/test": "1.58.2",
|
||||
"typescript": "5.9.2"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -74,11 +74,14 @@ export async function instant<T>(
|
||||
// navigation-testing-lock.ts, which acquires the in-memory navigation lock.
|
||||
const { hostname } = new URL(resolveURL(page, options))
|
||||
await step('Acquire Instant Lock', () =>
|
||||
page
|
||||
.context()
|
||||
.addCookies([
|
||||
{ name: INSTANT_COOKIE, value: '[0]', domain: hostname, path: '/' },
|
||||
])
|
||||
page.context().addCookies([
|
||||
{
|
||||
name: INSTANT_COOKIE,
|
||||
value: JSON.stringify([0, `p${Math.random()}`]),
|
||||
domain: hostname,
|
||||
path: '/',
|
||||
},
|
||||
])
|
||||
)
|
||||
try {
|
||||
return await fn()
|
||||
|
||||
@@ -167,7 +167,7 @@
|
||||
"@next/react-refresh-utils": "16.2.0-canary.100",
|
||||
"@next/swc": "16.2.0-canary.100",
|
||||
"@opentelemetry/api": "1.6.0",
|
||||
"@playwright/test": "1.51.1",
|
||||
"@playwright/test": "1.58.2",
|
||||
"@rspack/core": "1.6.7",
|
||||
"@storybook/addon-a11y": "8.6.0",
|
||||
"@storybook/addon-essentials": "8.6.0",
|
||||
|
||||
@@ -5,11 +5,6 @@
|
||||
* during instant navigation captures, and owns all cookie state
|
||||
* transitions (pending → captured-MPA, pending → captured-SPA).
|
||||
*
|
||||
* The cookie value is a JSON array:
|
||||
* [0] — pending (waiting to capture)
|
||||
* [1, null] — captured MPA page load
|
||||
* [1, { from, to }] — captured SPA navigation (from/to route trees)
|
||||
*
|
||||
* External actors (Playwright, devtools) set [0] to start a lock scope
|
||||
* and delete the cookie to end one. Next.js writes captured values.
|
||||
* The CookieStore handler distinguishes them by value: pending = external,
|
||||
@@ -22,17 +17,30 @@ import { refreshOnInstantNavigationUnlock } from '../use-action-queue'
|
||||
|
||||
type InstantNavCookieState = 'pending' | 'mpa' | 'spa'
|
||||
|
||||
type InstantCookie =
|
||||
// pending (waiting to capture)
|
||||
| [captured: 0, id: string]
|
||||
// captured MPA page load
|
||||
| [captured: 1, id: string, state: null]
|
||||
// captured SPA navigation (from/to route trees)
|
||||
| [
|
||||
captured: 1,
|
||||
id: string,
|
||||
state: { from: FlightRouterState; to: FlightRouterState | null },
|
||||
]
|
||||
|
||||
function parseCookieValue(raw: string): InstantNavCookieState {
|
||||
try {
|
||||
const parsed = JSON.parse(raw)
|
||||
if (Array.isArray(parsed) && parsed.length >= 2) {
|
||||
return parsed[1] === null ? 'mpa' : 'spa'
|
||||
if (Array.isArray(parsed) && parsed.length >= 3) {
|
||||
const rawState = parsed[2]
|
||||
return rawState === null ? 'mpa' : 'spa'
|
||||
}
|
||||
} catch {}
|
||||
return 'pending'
|
||||
}
|
||||
|
||||
function writeCookieValue(value: unknown[]): void {
|
||||
function writeCookieValue(value: InstantCookie): void {
|
||||
if (typeof cookieStore === 'undefined') {
|
||||
return
|
||||
}
|
||||
@@ -101,7 +109,7 @@ export function startListeningForInstantNavigationCookie(): void {
|
||||
})
|
||||
}
|
||||
|
||||
writeCookieValue([1, null])
|
||||
writeCookieValue([1, `c${Math.random()}`, null])
|
||||
acquireLock()
|
||||
}
|
||||
|
||||
@@ -151,7 +159,7 @@ export function transitionToCapturedSPA(
|
||||
toTree: FlightRouterState | null
|
||||
): void {
|
||||
if (process.env.__NEXT_EXPOSE_TESTING_API) {
|
||||
writeCookieValue([1, { from: fromTree, to: toTree }])
|
||||
writeCookieValue([1, `c${Math.random()}`, { from: fromTree, to: toTree }])
|
||||
}
|
||||
}
|
||||
|
||||
@@ -164,7 +172,7 @@ export function updateCapturedSPAToTree(
|
||||
toTree: FlightRouterState
|
||||
): void {
|
||||
if (process.env.__NEXT_EXPOSE_TESTING_API) {
|
||||
writeCookieValue([1, { from: fromTree, to: toTree }])
|
||||
writeCookieValue([1, `c${Math.random()}`, { from: fromTree, to: toTree }])
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+7
-6
@@ -30,14 +30,15 @@ export type InstantNavCookieData =
|
||||
function parseCookieValue(raw: string): InstantNavCookieData {
|
||||
try {
|
||||
const parsed = JSON.parse(raw)
|
||||
if (Array.isArray(parsed) && parsed.length >= 2) {
|
||||
if (parsed[1] === null) {
|
||||
if (Array.isArray(parsed) && parsed.length >= 3) {
|
||||
const rawState = parsed[2]
|
||||
if (rawState === null) {
|
||||
return { state: 'mpa' }
|
||||
}
|
||||
// SPA capture: parsed[1] is { from, to }
|
||||
if (typeof parsed[1] === 'object' && parsed[1] !== null) {
|
||||
const fromTree: FlightRouterState = parsed[1].from ?? ['', {}]
|
||||
const toTree: FlightRouterState | null = parsed[1].to ?? null
|
||||
// SPA capture: rawState is { from, to }
|
||||
if (typeof rawState === 'object' && rawState !== null) {
|
||||
const fromTree: FlightRouterState = rawState.from ?? ['', {}]
|
||||
const toTree: FlightRouterState | null = rawState.to ?? null
|
||||
return { state: 'spa', fromTree, toTree }
|
||||
}
|
||||
return { state: 'spa', fromTree: ['', {}], toTree: null }
|
||||
|
||||
+2
-2
@@ -44,7 +44,7 @@ export function InstantNavsPanel() {
|
||||
if (typeof cookieStore !== 'undefined') {
|
||||
cookieStore.set({
|
||||
name: COOKIE_NAME,
|
||||
value: '[0]',
|
||||
value: JSON.stringify([0, `p${Math.random()}`]),
|
||||
path: '/',
|
||||
})
|
||||
}
|
||||
@@ -55,7 +55,7 @@ export function InstantNavsPanel() {
|
||||
if (typeof cookieStore !== 'undefined') {
|
||||
cookieStore.set({
|
||||
name: COOKIE_NAME,
|
||||
value: '[0]',
|
||||
value: JSON.stringify([0, `p${Math.random()}`]),
|
||||
path: '/',
|
||||
})
|
||||
}
|
||||
|
||||
Generated
+50
-62
@@ -460,11 +460,11 @@ importers:
|
||||
specifier: 5.0.0
|
||||
version: 5.0.0
|
||||
playwright:
|
||||
specifier: 1.48.0
|
||||
version: 1.48.0
|
||||
specifier: 1.58.2
|
||||
version: 1.58.2
|
||||
playwright-chromium:
|
||||
specifier: 1.48.0
|
||||
version: 1.48.0
|
||||
specifier: 1.58.2
|
||||
version: 1.58.2
|
||||
postcss:
|
||||
specifier: 8.4.31
|
||||
version: 8.4.31
|
||||
@@ -668,7 +668,7 @@ importers:
|
||||
version: 0.554.0([email protected])
|
||||
next:
|
||||
specifier: 16.0.8
|
||||
version: 16.0.8(@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected])
|
||||
version: 16.0.8(@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected])
|
||||
next-themes:
|
||||
specifier: ^0.4.6
|
||||
version: 0.4.6([email protected]([email protected]))([email protected])
|
||||
@@ -726,16 +726,16 @@ importers:
|
||||
dependencies:
|
||||
fumadocs-core:
|
||||
specifier: 15.7.12
|
||||
version: 15.7.12(@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected])
|
||||
version: 15.7.12(@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected])
|
||||
fumadocs-mdx:
|
||||
specifier: 11.10.0
|
||||
version: 11.10.0([email protected](@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected]))([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected])
|
||||
version: 11.10.0([email protected](@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected]))([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected])
|
||||
fumadocs-ui:
|
||||
specifier: 15.7.12
|
||||
version: 15.7.12(@types/[email protected](@types/[email protected]))(@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected])([email protected])
|
||||
version: 15.7.12(@types/[email protected](@types/[email protected]))(@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected])([email protected])
|
||||
next:
|
||||
specifier: 15.5.8
|
||||
version: 15.5.8(@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected])
|
||||
version: 15.5.8(@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected])
|
||||
react:
|
||||
specifier: npm:[email protected]
|
||||
version: 19.3.0-canary-5e9eedb5-20260312
|
||||
@@ -831,8 +831,8 @@ importers:
|
||||
specifier: workspace:*
|
||||
version: link:../../packages/next
|
||||
playwright:
|
||||
specifier: ^1.40.0
|
||||
version: 1.48.0
|
||||
specifier: 1.58.2
|
||||
version: 1.58.2
|
||||
rimraf:
|
||||
specifier: 6.0.1
|
||||
version: 6.0.1
|
||||
@@ -1237,8 +1237,8 @@ importers:
|
||||
specifier: 1.6.0
|
||||
version: 1.6.0
|
||||
'@playwright/test':
|
||||
specifier: 1.51.1
|
||||
version: 1.51.1
|
||||
specifier: 1.58.2
|
||||
version: 1.58.2
|
||||
'@rspack/core':
|
||||
specifier: 1.6.7
|
||||
version: 1.6.7(@swc/[email protected])
|
||||
@@ -1412,7 +1412,7 @@ importers:
|
||||
version: 3.0.0
|
||||
axe-playwright:
|
||||
specifier: 2.0.3
|
||||
version: 2.0.3([email protected]1.1)
|
||||
version: 2.0.3([email protected]8.2)
|
||||
babel-loader:
|
||||
specifier: 10.0.0
|
||||
version: 10.0.0(@babel/[email protected])([email protected](@swc/[email protected](@swc/[email protected]))([email protected]))
|
||||
@@ -1872,11 +1872,10 @@ importers:
|
||||
version: 0.7.3
|
||||
|
||||
packages/next-playwright:
|
||||
dependencies:
|
||||
'@playwright/test':
|
||||
specifier: '>=1.0.0'
|
||||
version: 1.51.1
|
||||
devDependencies:
|
||||
'@playwright/test':
|
||||
specifier: 1.58.2
|
||||
version: 1.58.2
|
||||
typescript:
|
||||
specifier: 5.9.2
|
||||
version: 5.9.2
|
||||
@@ -2040,8 +2039,8 @@ importers:
|
||||
specifier: ^2.0.5
|
||||
version: 2.0.5
|
||||
playwright-chromium:
|
||||
specifier: 1.48.0
|
||||
version: 1.48.0
|
||||
specifier: 1.58.2
|
||||
version: 1.58.2
|
||||
split2:
|
||||
specifier: ^4.2.0
|
||||
version: 4.2.0
|
||||
@@ -5032,8 +5031,8 @@ packages:
|
||||
resolution: {integrity: sha512-cq8o4cWH0ibXh9VGi5P20Tu9XF/0fFXl9EUinr9QfTM7a7p0oTA4iJRCQWppXR1Pg8dSM0UCItCkPwsk9qWWYA==}
|
||||
engines: {node: ^12.20.0 || ^14.18.0 || >=16.0.0}
|
||||
|
||||
'@playwright/[email protected]1.1':
|
||||
resolution: {integrity: sha512-nM+kEaTSAoVlXmMPH10017vn3FSiFqr/bh4fKg9vmAdMfd9SDqRZNvPSiAHADc/itWak+qPvMPZQOPwCBW7k7Q==}
|
||||
'@playwright/[email protected]8.2':
|
||||
resolution: {integrity: sha512-akea+6bHYBBfA9uQqSYmlJXn61cTa+jbO87xVLCWbTqbWadRVmhxlXATaOjOgcBaWU4ePo0wB41KMFv3o35IXA==}
|
||||
engines: {node: '>=18'}
|
||||
hasBin: true
|
||||
|
||||
@@ -15032,13 +15031,8 @@ packages:
|
||||
resolution: {integrity: sha512-nDywThFk1i4BQK4twPQ6TA4RT8bDY96yeuCVBWL3ePARCiEKDRSrNGbFIgUJpLp+XeIR65v8ra7WuJOFUBtkMA==}
|
||||
engines: {node: '>=8'}
|
||||
|
||||
playwright-chromium@1.48.0:
|
||||
resolution: {integrity: sha512-jPFKhB4+zGEcAwc+h1mTLa8L08Rb+FwGKFqd/o7mWSGyxAtwBu5R4QxSG/a8KcHbewOj4DLBUVVK2N/uKrYmiQ==}
|
||||
engines: {node: '>=18'}
|
||||
hasBin: true
|
||||
|
||||
[email protected]:
|
||||
resolution: {integrity: sha512-RBvzjM9rdpP7UUFrQzRwR8L/xR4HyC1QXMzGYTbf1vjw25/ya9NRAVnXi/0fvFopjebvyPzsmoK58xxeEOaVvA==}
|
||||
playwright-chromium@1.58.2:
|
||||
resolution: {integrity: sha512-SCoQ3hjBs7FfO46CoOtgAUg77BuYwCni1bzQgm47IUyLBTipnGkLxLnaUNRKXvPYO4hAyt8++Z6wVShVnhrzmw==}
|
||||
engines: {node: '>=18'}
|
||||
hasBin: true
|
||||
|
||||
@@ -15047,13 +15041,13 @@ packages:
|
||||
engines: {node: '>=18'}
|
||||
hasBin: true
|
||||
|
||||
playwright@1.48.0:
|
||||
resolution: {integrity: sha512-qPqFaMEHuY/ug8o0uteYJSRfMGFikhUysk8ZvAtfKmUK3kc/6oNl/y3EczF8OFGYIi/Ex2HspMfzYArk6+XQSA==}
|
||||
playwright-core@1.58.2:
|
||||
resolution: {integrity: sha512-yZkEtftgwS8CsfYo7nm0KE8jsvm6i/PTgVtB8DL726wNf6H2IMsDuxCpJj59KDaxCtSnrWan2AeDqM7JBaultg==}
|
||||
engines: {node: '>=18'}
|
||||
hasBin: true
|
||||
|
||||
[email protected]1.1:
|
||||
resolution: {integrity: sha512-kkx+MB2KQRkyxjYPc3a0wLZZoDczmppyGJIvQ43l+aZihkaVvmu/21kiyaHeHjiFxjxNNFnUncKmcGIyOojsaw==}
|
||||
[email protected]8.2:
|
||||
resolution: {integrity: sha512-vA30H8Nvkq/cPBnNw4Q8TWz1EJyqgpuinBcHET0YVJVFldr8JDNiU9LaWAE1KqSkRYazuaBhTpB5ZzShOezQ6A==}
|
||||
engines: {node: '>=18'}
|
||||
hasBin: true
|
||||
|
||||
@@ -22595,9 +22589,9 @@ snapshots:
|
||||
|
||||
'@pkgr/[email protected]': {}
|
||||
|
||||
'@playwright/[email protected]1.1':
|
||||
'@playwright/[email protected]8.2':
|
||||
dependencies:
|
||||
playwright: 1.51.1
|
||||
playwright: 1.58.2
|
||||
|
||||
'@polka/[email protected]': {}
|
||||
|
||||
@@ -23949,7 +23943,7 @@ snapshots:
|
||||
jest-serializer-html: 7.1.0
|
||||
jest-watch-typeahead: 2.2.2([email protected](@types/[email protected](patch_hash=rvl3vkomen3tospgr67bzubfyu))([email protected]))
|
||||
nyc: 15.1.0
|
||||
playwright: 1.48.0
|
||||
playwright: 1.58.2
|
||||
storybook: 8.6.0([email protected])
|
||||
transitivePeerDependencies:
|
||||
- '@swc/helpers'
|
||||
@@ -25615,14 +25609,14 @@ snapshots:
|
||||
axe-core: 4.10.0
|
||||
mustache: 4.2.0
|
||||
|
||||
[email protected]([email protected]1.1):
|
||||
[email protected]([email protected]8.2):
|
||||
dependencies:
|
||||
'@types/junit-report-builder': 3.0.2
|
||||
axe-core: 4.10.0
|
||||
axe-html-reporter: 2.2.11([email protected])
|
||||
junit-report-builder: 5.1.1
|
||||
picocolors: 1.1.1
|
||||
playwright: 1.51.1
|
||||
playwright: 1.58.2
|
||||
|
||||
[email protected]:
|
||||
dependencies:
|
||||
@@ -29628,7 +29622,7 @@ snapshots:
|
||||
[email protected]:
|
||||
optional: true
|
||||
|
||||
[email protected](@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected]):
|
||||
[email protected](@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected]):
|
||||
dependencies:
|
||||
'@formatjs/intl-localematcher': 0.6.1
|
||||
'@orama/orama': 3.1.13
|
||||
@@ -29649,20 +29643,20 @@ snapshots:
|
||||
unist-util-visit: 5.0.0
|
||||
optionalDependencies:
|
||||
'@types/react': 19.2.10
|
||||
next: 15.5.8(@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected])
|
||||
next: 15.5.8(@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected])
|
||||
react: 19.3.0-canary-5e9eedb5-20260312
|
||||
react-dom: 19.3.0-canary-5e9eedb5-20260312([email protected])
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
|
||||
[email protected]([email protected](@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected]))([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]):
|
||||
[email protected]([email protected](@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected]))([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]):
|
||||
dependencies:
|
||||
'@mdx-js/mdx': 3.1.1
|
||||
'@standard-schema/spec': 1.0.0
|
||||
chokidar: 4.0.3
|
||||
esbuild: 0.25.9
|
||||
estree-util-value-to-estree: 3.5.0
|
||||
fumadocs-core: 15.7.12(@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected])
|
||||
fumadocs-core: 15.7.12(@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected])
|
||||
js-yaml: 4.1.0
|
||||
lru-cache: 11.2.1
|
||||
picocolors: 1.1.1
|
||||
@@ -29674,12 +29668,12 @@ snapshots:
|
||||
unist-util-visit: 5.0.0
|
||||
zod: 4.1.13
|
||||
optionalDependencies:
|
||||
next: 15.5.8(@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected])
|
||||
next: 15.5.8(@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected])
|
||||
react: 19.3.0-canary-5e9eedb5-20260312
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
|
||||
[email protected](@types/[email protected](@types/[email protected]))(@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected])([email protected]):
|
||||
[email protected](@types/[email protected](@types/[email protected]))(@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected])([email protected]):
|
||||
dependencies:
|
||||
'@radix-ui/react-accordion': 1.2.12(@types/[email protected](@types/[email protected]))(@types/[email protected])([email protected]([email protected]))([email protected])
|
||||
'@radix-ui/react-collapsible': 1.1.12(@types/[email protected](@types/[email protected]))(@types/[email protected])([email protected]([email protected]))([email protected])
|
||||
@@ -29692,7 +29686,7 @@ snapshots:
|
||||
'@radix-ui/react-slot': 1.2.3(@types/[email protected])([email protected])
|
||||
'@radix-ui/react-tabs': 1.1.13(@types/[email protected](@types/[email protected]))(@types/[email protected])([email protected]([email protected]))([email protected])
|
||||
class-variance-authority: 0.7.1
|
||||
fumadocs-core: 15.7.12(@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected])
|
||||
fumadocs-core: 15.7.12(@types/[email protected])([email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]))([email protected]([email protected]))([email protected])
|
||||
lodash.merge: 4.6.2
|
||||
next-themes: 0.4.6([email protected]([email protected]))([email protected])
|
||||
postcss-selector-parser: 7.1.0
|
||||
@@ -29703,7 +29697,7 @@ snapshots:
|
||||
tailwind-merge: 3.3.1
|
||||
optionalDependencies:
|
||||
'@types/react': 19.2.10
|
||||
next: 15.5.8(@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected])
|
||||
next: 15.5.8(@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected])
|
||||
tailwindcss: 4.1.13
|
||||
transitivePeerDependencies:
|
||||
- '@mixedbread/sdk'
|
||||
@@ -31659,7 +31653,7 @@ snapshots:
|
||||
jest-process-manager: 0.4.0([email protected])
|
||||
jest-runner: 29.7.0
|
||||
nyc: 15.1.0
|
||||
playwright-core: 1.48.0
|
||||
playwright-core: 1.51.1
|
||||
rimraf: 3.0.2
|
||||
uuid: 8.3.2
|
||||
transitivePeerDependencies:
|
||||
@@ -34031,7 +34025,7 @@ snapshots:
|
||||
|
||||
[email protected]: {}
|
||||
|
||||
[email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]):
|
||||
[email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]):
|
||||
dependencies:
|
||||
'@next/env': 15.5.8
|
||||
'@swc/helpers': 0.5.15
|
||||
@@ -34050,7 +34044,7 @@ snapshots:
|
||||
'@next/swc-win32-arm64-msvc': 15.5.7
|
||||
'@next/swc-win32-x64-msvc': 15.5.7
|
||||
'@opentelemetry/api': 1.9.0
|
||||
'@playwright/test': 1.51.1
|
||||
'@playwright/test': 1.58.2
|
||||
babel-plugin-react-compiler: 0.0.0-experimental-1371fcb-20260227
|
||||
sass: 1.77.8
|
||||
sharp: 0.34.4
|
||||
@@ -34058,7 +34052,7 @@ snapshots:
|
||||
- '@babel/core'
|
||||
- babel-plugin-macros
|
||||
|
||||
[email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]1.1)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]):
|
||||
[email protected](@babel/[email protected])(@opentelemetry/[email protected])(@playwright/[email protected]8.2)([email protected])([email protected])([email protected]([email protected]))([email protected])([email protected]):
|
||||
dependencies:
|
||||
'@next/env': 16.0.8
|
||||
'@swc/helpers': 0.5.15
|
||||
@@ -34077,7 +34071,7 @@ snapshots:
|
||||
'@next/swc-win32-arm64-msvc': 16.0.8
|
||||
'@next/swc-win32-x64-msvc': 16.0.8
|
||||
'@opentelemetry/api': 1.9.0
|
||||
'@playwright/test': 1.51.1
|
||||
'@playwright/test': 1.58.2
|
||||
babel-plugin-react-compiler: 0.0.0-experimental-1371fcb-20260227
|
||||
sass: 1.77.8
|
||||
sharp: 0.34.4
|
||||
@@ -35128,23 +35122,17 @@ snapshots:
|
||||
dependencies:
|
||||
find-up: 3.0.0
|
||||
|
||||
playwright-chromium@1.48.0:
|
||||
playwright-chromium@1.58.2:
|
||||
dependencies:
|
||||
playwright-core: 1.48.0
|
||||
|
||||
[email protected]: {}
|
||||
playwright-core: 1.58.2
|
||||
|
||||
[email protected]: {}
|
||||
|
||||
playwright@1.48.0:
|
||||
dependencies:
|
||||
playwright-core: 1.48.0
|
||||
optionalDependencies:
|
||||
fsevents: 2.3.2
|
||||
playwright-core@1.58.2: {}
|
||||
|
||||
[email protected]1.1:
|
||||
[email protected]8.2:
|
||||
dependencies:
|
||||
playwright-core: 1.51.1
|
||||
playwright-core: 1.58.2
|
||||
optionalDependencies:
|
||||
fsevents: 2.3.2
|
||||
|
||||
|
||||
@@ -116,7 +116,8 @@ describe.each([['', '/docs']])(
|
||||
const script = document.createElement('script')
|
||||
script.src = "${next.url}/_next/static/chunks/pages/_app.js"
|
||||
|
||||
script.onerror = (err) => {
|
||||
script.onerror = (error) => {
|
||||
console.error('script error', error)
|
||||
statusEl.innerText = 'error'
|
||||
}
|
||||
script.onload = () => {
|
||||
@@ -126,7 +127,13 @@ describe.each([['', '/docs']])(
|
||||
})()`
|
||||
|
||||
// ensure direct port with mismatching port is blocked
|
||||
const browser = await webdriver(`http://127.0.0.1:${port}`, '/about')
|
||||
const browser = await webdriver(
|
||||
`http://127.0.0.1:${port}`,
|
||||
'/about',
|
||||
{
|
||||
permissions: ['local-network-access'],
|
||||
}
|
||||
)
|
||||
await browser.eval(scriptSnippet)
|
||||
|
||||
await retry(async () => {
|
||||
@@ -136,6 +143,7 @@ describe.each([['', '/docs']])(
|
||||
})
|
||||
|
||||
// ensure different host is blocked
|
||||
// Requires local-network-access permission to send a request to next.url
|
||||
await browser.get(`https://example.vercel.sh/`)
|
||||
await browser.eval(scriptSnippet)
|
||||
|
||||
@@ -145,7 +153,11 @@ describe.each([['', '/docs']])(
|
||||
)
|
||||
})
|
||||
|
||||
expect(next.cliOutput).toContain('Cross origin request detected from')
|
||||
expect(next.cliOutput).toContain(
|
||||
// We're not sending an Origin header
|
||||
// TODO: redundant spacing
|
||||
'Cross origin request detected to'
|
||||
)
|
||||
} finally {
|
||||
server.close()
|
||||
}
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import { nextTestSetup } from 'e2e-utils'
|
||||
import { retry } from 'next-test-utils'
|
||||
|
||||
describe('use-router-with-rewrites', () => {
|
||||
const { next } = nextTestSetup({
|
||||
@@ -68,30 +69,33 @@ describe('use-router-with-rewrites', () => {
|
||||
const browser = await next.browser('/rewrite-to-same-segment/0')
|
||||
await browser.elementById('router-push').click()
|
||||
|
||||
await retry(async () => {
|
||||
expect(await browser.elementByCss('p').text()).toBe('1')
|
||||
})
|
||||
const url = new URL(await browser.url())
|
||||
expect(url.pathname + url.search).toBe('/rewrite-to-same-segment/1')
|
||||
|
||||
expect(await browser.elementByCss('p').text()).toBe('1')
|
||||
})
|
||||
|
||||
it('should preserve current pathname when using useRouter.replace with rewrites on dynamic route', async () => {
|
||||
const browser = await next.browser('/rewrite-to-same-segment/0')
|
||||
await browser.elementById('router-replace').click()
|
||||
|
||||
await retry(async () => {
|
||||
expect(await browser.elementByCss('p').text()).toBe('2')
|
||||
})
|
||||
const url = new URL(await browser.url())
|
||||
expect(url.pathname + url.search).toBe('/rewrite-to-same-segment/2')
|
||||
|
||||
expect(await browser.elementByCss('p').text()).toBe('2')
|
||||
})
|
||||
|
||||
it('should preserve current pathname when using Link with rewrites on dynamic route', async () => {
|
||||
const browser = await next.browser('/rewrite-to-same-segment/0')
|
||||
await browser.elementByCss('a').click()
|
||||
|
||||
await retry(async () => {
|
||||
expect(await browser.elementByCss('p').text()).toBe('3')
|
||||
})
|
||||
const url = new URL(await browser.url())
|
||||
expect(url.pathname + url.search).toBe('/rewrite-to-same-segment/3')
|
||||
|
||||
expect(await browser.elementByCss('p').text()).toBe('3')
|
||||
})
|
||||
})
|
||||
})
|
||||
|
||||
@@ -17,6 +17,7 @@ import {
|
||||
check,
|
||||
getRedboxHeader,
|
||||
normalizeManifest,
|
||||
retry,
|
||||
} from 'next-test-utils'
|
||||
import cheerio from 'cheerio'
|
||||
|
||||
@@ -245,11 +246,12 @@ function runTests({ dev }) {
|
||||
|
||||
await browser.eval('window.beforeNav = 1')
|
||||
await browser.elementByCss(`#${id}`).click()
|
||||
await check(() => browser.eval('window.location.pathname'), pathname)
|
||||
|
||||
expect(JSON.parse(await browser.elementByCss('#query').text())).toEqual(
|
||||
navQuery
|
||||
)
|
||||
await retry(async () => {
|
||||
expect(JSON.parse(await browser.elementByCss('#query').text())).toEqual(
|
||||
navQuery
|
||||
)
|
||||
})
|
||||
expect(await browser.eval('window.location.pathname')).toBe(pathname)
|
||||
expect(await browser.eval('window.location.hash')).toBe(hash)
|
||||
expect(
|
||||
|
||||
@@ -12,6 +12,7 @@ import {
|
||||
Locator,
|
||||
Request as PlaywrightRequest,
|
||||
Response as PlaywrightResponse,
|
||||
BrowserContextOptions,
|
||||
} from 'playwright'
|
||||
import path from 'path'
|
||||
|
||||
@@ -19,10 +20,13 @@ type EventType = 'request' | 'response'
|
||||
|
||||
type PageLog = { source: string; message: string; args: unknown[] }
|
||||
|
||||
export type Permissions = BrowserContextOptions['permissions']
|
||||
|
||||
let page: Page
|
||||
let browser: Browser | undefined
|
||||
let context: BrowserContext | undefined
|
||||
let contextHasJSEnabled: boolean = true
|
||||
let contextPermissions: Permissions = undefined
|
||||
let pageLogs: Array<Promise<PageLog> | PageLog> = []
|
||||
let websocketFrames: Array<{ payload: string | Buffer }> = []
|
||||
|
||||
@@ -167,7 +171,8 @@ export class Playwright<TCurrent = undefined> {
|
||||
javaScriptEnabled: boolean,
|
||||
ignoreHTTPSErrors: boolean,
|
||||
headless: boolean,
|
||||
userAgent: string | undefined
|
||||
userAgent: string | undefined,
|
||||
permissions: Permissions
|
||||
) {
|
||||
let device
|
||||
|
||||
@@ -182,7 +187,13 @@ export class Playwright<TCurrent = undefined> {
|
||||
}
|
||||
|
||||
if (browser) {
|
||||
if (contextHasJSEnabled !== javaScriptEnabled) {
|
||||
if (
|
||||
contextHasJSEnabled !== javaScriptEnabled ||
|
||||
// Even triggers on same set of permissions, but we don't want to deal
|
||||
// with the complexity of diffing them, so we just always recreate the
|
||||
// context when permissions are set.
|
||||
contextPermissions !== permissions
|
||||
) {
|
||||
// If we have switched from having JS enable/disabled we need to recreate the context.
|
||||
await teardown(this.teardownTracing.bind(this))
|
||||
await context?.close()
|
||||
@@ -192,8 +203,10 @@ export class Playwright<TCurrent = undefined> {
|
||||
ignoreHTTPSErrors,
|
||||
...(userAgent ? { userAgent } : {}),
|
||||
...device,
|
||||
permissions,
|
||||
})
|
||||
contextHasJSEnabled = javaScriptEnabled
|
||||
contextPermissions = permissions
|
||||
}
|
||||
return
|
||||
}
|
||||
@@ -205,6 +218,7 @@ export class Playwright<TCurrent = undefined> {
|
||||
ignoreHTTPSErrors,
|
||||
...(userAgent ? { userAgent } : {}),
|
||||
...device,
|
||||
permissions,
|
||||
})
|
||||
contextHasJSEnabled = javaScriptEnabled
|
||||
}
|
||||
@@ -214,14 +228,16 @@ export class Playwright<TCurrent = undefined> {
|
||||
await page?.close()
|
||||
}
|
||||
|
||||
async launchBrowser(browserName: string, launchOptions: Record<string, any>) {
|
||||
async launchBrowser(
|
||||
browserName: string,
|
||||
launchOptions: { headless: boolean }
|
||||
) {
|
||||
if (browserName === 'safari') {
|
||||
return await webkit.launch(launchOptions)
|
||||
} else if (browserName === 'firefox') {
|
||||
return await firefox.launch({
|
||||
...launchOptions,
|
||||
firefoxUserPrefs: {
|
||||
...launchOptions.firefoxUserPrefs,
|
||||
// The "fission.webContentIsolationStrategy" pref must be
|
||||
// set to 1 on Firefox due to the bug where a new history
|
||||
// state is pushed on a page reload.
|
||||
@@ -231,9 +247,13 @@ export class Playwright<TCurrent = undefined> {
|
||||
},
|
||||
})
|
||||
} else {
|
||||
let launchArgs: string[] = []
|
||||
if (!launchOptions.headless) {
|
||||
launchArgs.push('--auto-open-devtools-for-tabs')
|
||||
}
|
||||
return await chromium.launch({
|
||||
devtools: !launchOptions.headless,
|
||||
...launchOptions,
|
||||
args: launchArgs,
|
||||
ignoreDefaultArgs: ['--disable-back-forward-cache'],
|
||||
})
|
||||
}
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import { debugPrint, getFullUrl } from 'next-test-utils'
|
||||
import os from 'os'
|
||||
import {
|
||||
Permissions,
|
||||
Playwright,
|
||||
PlaywrightNavigationWaitUntil,
|
||||
} from './browsers/playwright'
|
||||
@@ -48,6 +49,7 @@ if (typeof afterAll === 'function') {
|
||||
}
|
||||
|
||||
export interface WebdriverOptions {
|
||||
permissions?: Permissions
|
||||
/**
|
||||
* whether to wait for React hydration to finish
|
||||
*/
|
||||
@@ -121,6 +123,7 @@ export default async function webdriver(
|
||||
extraHTTPHeaders,
|
||||
locale,
|
||||
disableJavaScript,
|
||||
permissions,
|
||||
ignoreHTTPSErrors,
|
||||
headless,
|
||||
cpuThrottleRate,
|
||||
@@ -141,7 +144,8 @@ export default async function webdriver(
|
||||
Boolean(ignoreHTTPSErrors),
|
||||
// allow headless to be overwritten for a particular test
|
||||
typeof headless !== 'undefined' ? headless : !!process.env.HEADLESS,
|
||||
userAgent
|
||||
userAgent,
|
||||
permissions
|
||||
)
|
||||
;(global as any).browserName = browserName
|
||||
|
||||
|
||||
@@ -48,7 +48,7 @@
|
||||
"minimist": "^1.2.8",
|
||||
"picocolors": "1.0.1",
|
||||
"pidusage-tree": "^2.0.5",
|
||||
"playwright-chromium": "1.48.0",
|
||||
"playwright-chromium": "1.58.2",
|
||||
"split2": "^4.2.0",
|
||||
"tree-kill": "^1.2.2"
|
||||
}
|
||||
|
||||
@@ -348,7 +348,7 @@ export async function newBrowserSession(options: {
|
||||
}): Promise<BrowserSession> {
|
||||
const browser = await chromium.launch({
|
||||
headless: options.headless ?? process.env.HEADLESS !== 'false',
|
||||
devtools: true,
|
||||
args: options.headless ? undefined : ['--auto-open-devtools-for-tabs'],
|
||||
timeout: 60000,
|
||||
})
|
||||
const context = await browser.newContext({
|
||||
|
||||
Reference in New Issue
Block a user