You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Replaces the Studio's post-login auth flow with a new /auth/exchange endpoint to fix partitioned cookie issues.
The old flow tried cookie-based /users/me first, then fell back to exchanging the session ID for a token via /auth/fetch. This broke because the Partitioned cookie set during the transfer redirect is stored under the API host's partition key, not the Studio's - so the cookie is never sent on subsequent cross-site fetches.
The new flow calls /auth/exchange?sid=... with credentials: include, which both sets a cookie under the correct partition key and returns the token in the response body. It then probes /users/me with each auth method (cookie and/or token, depending on loginMethod) in parallel to determine which one actually works.
Cookie mode now sends type=dual to the auth provider instead of type=cookie, so a session ID is always returned in the hash.
The AuthBoundary now has an error state that prevents flashing login providers when auth fails after a redirect. Instead it shows an appropriate error message ("Cookies blocked" for cookie-only mode, "Authentication failed" with retry for other modes).
What to review
createAuthStore.ts has the core flow rewrite - the three-step exchange/probe/decide logic in handleCallbackUrl, plus two new helpers (probeCurrentUser, exchangeSessionForToken)
The race condition guard in AuthBoundary.tsx (the setStatus callback form that prevents state$ from overriding the error state)
The createHrefForProvider change is small but important - cookie mode now sends type=dual
All changes are in the sanity package.
Testing
No automated tests added. The auth flow depends on real browser cookie behavior, cross-origin fetch, and server-side session management that can't be meaningfully mocked in jsdom. The existing test suite passes with no regressions.
Manual testing needed:
Login with dual mode (default) - should prefer cookie auth when available, fall back to token
Login with cookie-only mode in a browser that blocks third-party cookies - should show "Cookies blocked" error
Login with token-only mode - should store token and use bearer auth
Cold load when already authenticated - should work as before
Notes for release
N/A - Part of auth infrastructure improvements. No user-facing API changes.
To run the E2E tests locally, you can use the following environment variables, then run pnpm test:e2e --ui to open the Playwright test runner.
💬 Remember to build the project first with pnpm build:e2e.
SANITY_E2E_PROJECT_ID=ittbm412
SANITY_E2E_BASE_URL=https://e2e-studio-3ts5eu9jk.sanity.dev
SANITY_E2E_DATASET="update depending the project you want to test (pr-12536-chromium-23771369421 || pr-12536-firefox-23771369421 )"
SANITY_E2E_DATASET_CHROMIUM=pr-12536-chromium-23771369421
SANITY_E2E_DATASET_FIREFOX=pr-12536-firefox-23771369421
efps — editor "frames per second". The number of updates assumed to be possible within a second.
Derived from input latency. efps = 1000 / input_latency
Detailed information
🏠 Reference result
The performance result of sanity@latest
Benchmark
latency
p75
p90
p99
blocking time
test duration
arrayI18n (simple-en)
18ms
21ms
25ms
45ms
0ms
5.8s
article (title)
27ms
34ms
59ms
72ms
99ms
7.9s
article (body)
22ms
35ms
51ms
109ms
191ms
5.4s
article (string inside object)
24ms
28ms
40ms
63ms
21ms
6.4s
article (string inside array)
20ms
21ms
24ms
62ms
6ms
6.5s
recipe (name)
11ms
16ms
20ms
54ms
0ms
5.5s
recipe (description)
20ms
23ms
26ms
31ms
0ms
4.5s
recipe (instructions)
6ms
9ms
11ms
30ms
0ms
3.0s
singleString (stringField)
7ms
9ms
11ms
20ms
0ms
4.6s
synthetic (title)
20ms
25ms
52ms
91ms
1262ms
9.5s
synthetic (string inside object)
18ms
19ms
24ms
96ms
989ms
8.7s
🧪 Experiment result
The performance result of this branch
Benchmark
latency
p75
p90
p99
blocking time
test duration
arrayI18n (simple-en)
20ms
21ms
24ms
44ms
7ms
6.3s
article (title)
26ms
36ms
53ms
95ms
72ms
7.4s
article (body)
22ms
31ms
57ms
98ms
198ms
5.5s
article (string inside object)
22ms
27ms
43ms
67ms
0ms
6.3s
article (string inside array)
18ms
21ms
25ms
48ms
9ms
6.1s
recipe (name)
10ms
15ms
24ms
59ms
0ms
5.5s
recipe (description)
19ms
21ms
25ms
32ms
0ms
4.4s
recipe (instructions)
6ms
8ms
11ms
25ms
0ms
3.0s
singleString (stringField)
7ms
9ms
11ms
19ms
0ms
4.5s
synthetic (title)
20ms
24ms
48ms
142ms
1287ms
9.5s
synthetic (string inside object)
19ms
20ms
26ms
89ms
1016ms
8.6s
📚 Glossary
column definitions
benchmark — the name of the test, e.g. "article", followed by the label of the field being measured, e.g. "(title)".
latency — the time between when a key was pressed and when it was rendered. derived from a set of samples. the median (p50) is shown to show the most common latency.
p75 — the 75th percentile of the input latency in the test run. 75% of the sampled inputs in this benchmark were processed faster than this value. this provides insight into the upper range of typical performance.
p90 — the 90th percentile of the input latency in the test run. 90% of the sampled inputs were faster than this. this metric helps identify slower interactions that occurred less frequently during the benchmark.
p99 — the 99th percentile of the input latency in the test run. only 1% of sampled inputs were slower than this. this represents the worst-case scenarios encountered during the benchmark, useful for identifying potential performance outliers.
blocking time — the total time during which the main thread was blocked, preventing user input and UI updates. this metric helps identify performance bottlenecks that may cause the interface to feel unresponsive.
test duration — how long the test run took to complete.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Description
Replaces the Studio's post-login auth flow with a new
/auth/exchangeendpoint to fix partitioned cookie issues./users/mefirst, then fell back to exchanging the session ID for a token via/auth/fetch. This broke because thePartitionedcookie set during the transfer redirect is stored under the API host's partition key, not the Studio's - so the cookie is never sent on subsequent cross-site fetches./auth/exchange?sid=...withcredentials: include, which both sets a cookie under the correct partition key and returns the token in the response body. It then probes/users/mewith each auth method (cookie and/or token, depending onloginMethod) in parallel to determine which one actually works.type=dualto the auth provider instead oftype=cookie, so a session ID is always returned in the hash.errorstate that prevents flashing login providers when auth fails after a redirect. Instead it shows an appropriate error message ("Cookies blocked" for cookie-only mode, "Authentication failed" with retry for other modes).What to review
createAuthStore.tshas the core flow rewrite - the three-step exchange/probe/decide logic inhandleCallbackUrl, plus two new helpers (probeCurrentUser,exchangeSessionForToken)AuthBoundary.tsx(thesetStatuscallback form that preventsstate$from overriding the error state)createHrefForProviderchange is small but important - cookie mode now sendstype=dualAll changes are in the
sanitypackage.Testing
No automated tests added. The auth flow depends on real browser cookie behavior, cross-origin fetch, and server-side session management that can't be meaningfully mocked in jsdom. The existing test suite passes with no regressions.
Manual testing needed:
Notes for release
N/A - Part of auth infrastructure improvements. No user-facing API changes.