Skip to content

Commit 0e3b273

Browse files
committed
chore: roll driver to 1.61.0-beta-1781285686000
Ported upstream changes: - #40843 page.localStorage()/sessionStorage() (WebStorage API) - #40849 context.credentials() WebAuthn virtual authenticator - #40932 APIResponse.securityDetails()/serverAddr() - #41162 ScreencastFrame.timestamp() - #40916 screencast cursor and size options - #40844 comma-separated testIdAttribute (getByTestId now uses internal:testid) - #40718 waitForEventInfo replaced with fire-and-forget __waitInfo__ - #40780 protocol Page.close split into close and runBeforeUnload - #40801 Frame.expect failures are now protocol errors with errorDetails - #41014 connectOverCDP allowed for WebKit, artifactsDir option
1 parent 1b7d164 commit 0e3b273

42 files changed

Lines changed: 1184 additions & 51 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

README.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -10,9 +10,9 @@ Playwright is a Java library to automate [Chromium](https://www.chromium.org/Hom
1010

1111
| | Linux | macOS | Windows |
1212
| :--- | :---: | :---: | :---: |
13-
| Chromium <!-- GEN:chromium-version -->148.0.7778.96<!-- GEN:stop --> | :white_check_mark: | :white_check_mark: | :white_check_mark: |
14-
| WebKit <!-- GEN:webkit-version -->26.4<!-- GEN:stop --> ||||
15-
| Firefox <!-- GEN:firefox-version -->150.0.2<!-- GEN:stop --> | :white_check_mark: | :white_check_mark: | :white_check_mark: |
13+
| Chromium <!-- GEN:chromium-version -->149.0.7827.55<!-- GEN:stop --> | :white_check_mark: | :white_check_mark: | :white_check_mark: |
14+
| WebKit <!-- GEN:webkit-version -->26.5<!-- GEN:stop --> ||||
15+
| Firefox <!-- GEN:firefox-version -->151.0<!-- GEN:stop --> | :white_check_mark: | :white_check_mark: | :white_check_mark: |
1616

1717
## Documentation
1818

examples/pom.xml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@
1010
<name>Playwright Client Examples</name>
1111
<properties>
1212
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
13-
<playwright.version>1.60.0</playwright.version>
13+
<playwright.version>1.61.0</playwright.version>
1414
</properties>
1515
<dependencies>
1616
<dependency>

playwright/src/main/java/com/microsoft/playwright/APIResponse.java

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,20 @@ public interface APIResponse {
5555
* @since v1.16
5656
*/
5757
boolean ok();
58+
/**
59+
* Returns SSL and other security information. Resolves to {@code null} for non-HTTPS responses. For redirected requests,
60+
* returns the information for the last request in the redirect chain.
61+
*
62+
* @since v1.61
63+
*/
64+
SecurityDetails securityDetails();
65+
/**
66+
* Returns the IP address and port of the server. Resolves to {@code null} if the server address is not available. For
67+
* redirected requests, returns the information for the last request in the redirect chain.
68+
*
69+
* @since v1.61
70+
*/
71+
ServerAddr serverAddr();
5872
/**
5973
* Contains the status code of the response (e.g., 200 for a success).
6074
*

playwright/src/main/java/com/microsoft/playwright/BrowserContext.java

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -563,6 +563,13 @@ public WaitForPageOptions setTimeout(double timeout) {
563563
* @since v1.45
564564
*/
565565
Clock clock();
566+
/**
567+
* Virtual WebAuthn authenticator for this context. Lets tests seed credentials and intercept {@code
568+
* navigator.credentials.create()} / {@code navigator.credentials.get()} ceremonies.
569+
*
570+
* @since v1.61
571+
*/
572+
Credentials credentials();
566573
/**
567574
* Debugger allows to pause and resume the execution.
568575
*

playwright/src/main/java/com/microsoft/playwright/BrowserType.java

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -124,6 +124,10 @@ public ConnectOptions setTimeout(double timeout) {
124124
}
125125
}
126126
class ConnectOverCDPOptions {
127+
/**
128+
* If specified, browser artifacts (such as traces and downloads) are saved into this directory.
129+
*/
130+
public Path artifactsDir;
127131
/**
128132
* Additional HTTP headers to be sent with connect request. Optional.
129133
*/
@@ -153,6 +157,13 @@ class ConnectOverCDPOptions {
153157
*/
154158
public Double timeout;
155159

160+
/**
161+
* If specified, browser artifacts (such as traces and downloads) are saved into this directory.
162+
*/
163+
public ConnectOverCDPOptions setArtifactsDir(Path artifactsDir) {
164+
this.artifactsDir = artifactsDir;
165+
return this;
166+
}
156167
/**
157168
* Additional HTTP headers to be sent with connect request. Optional.
158169
*/
Lines changed: 238 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,238 @@
1+
/*
2+
* Copyright (c) Microsoft Corporation.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package com.microsoft.playwright;
18+
19+
import com.microsoft.playwright.options.*;
20+
import java.util.*;
21+
22+
/**
23+
* {@code Credentials} is a virtual WebAuthn authenticator scoped to a {@code BrowserContext}. It lets tests register
24+
* passkeys and answer {@code navigator.credentials.create()} / {@code navigator.credentials.get()} ceremonies in the page,
25+
* without a real authenticator or hardware security key.
26+
*
27+
* <p> There are two common ways to use it:
28+
*
29+
* <p> <strong>Usage: seed a known credential</strong>
30+
* <pre>{@code
31+
* BrowserContext context = browser.newContext();
32+
*
33+
* // A passkey your backend already provisioned for a test user.
34+
* context.credentials().create("example.com", new Credentials.CreateOptions()
35+
* .setId(knownCredentialId) // base64url
36+
* .setUserHandle(knownUserHandle) // base64url
37+
* .setPrivateKey(knownPrivateKey) // base64url PKCS#8 (DER)
38+
* .setPublicKey(knownPublicKey)); // base64url SPKI (DER)
39+
* context.credentials().install();
40+
*
41+
* Page page = context.newPage();
42+
* page.navigate("https://example.com/login");
43+
* // The page's navigator.credentials.get() is answered with the seeded passkey.
44+
* }</pre>
45+
*
46+
* <p> <strong>Usage: capture a passkey, then reuse it</strong>
47+
* <pre>{@code
48+
* // setup test: let the app register a passkey, then save it.
49+
* BrowserContext context = browser.newContext();
50+
* context.credentials().install();
51+
*
52+
* Page page = context.newPage();
53+
* page.navigate("https://example.com/register");
54+
* page.getByRole(AriaRole.BUTTON, new Page.GetByRoleOptions().setName("Create a passkey")).click();
55+
*
56+
* // Read back the passkey the page registered — it includes the private key.
57+
* VirtualCredential credential = context.credentials().get(
58+
* new Credentials.GetOptions().setRpId("example.com")).get(0);
59+
* Files.writeString(Paths.get("playwright/.auth/passkey.json"), new Gson().toJson(credential));
60+
* }</pre>
61+
* <pre>{@code
62+
* // later test: seed the captured passkey so the app starts already enrolled.
63+
* VirtualCredential credential = new Gson().fromJson(
64+
* Files.readString(Paths.get("playwright/.auth/passkey.json")), VirtualCredential.class);
65+
* BrowserContext context = browser.newContext();
66+
* context.credentials().create(credential.rpId, new Credentials.CreateOptions()
67+
* .setId(credential.id)
68+
* .setUserHandle(credential.userHandle)
69+
* .setPrivateKey(credential.privateKey)
70+
* .setPublicKey(credential.publicKey));
71+
* context.credentials().install();
72+
*
73+
* Page page = context.newPage();
74+
* page.navigate("https://example.com/login");
75+
* // navigator.credentials.get() resolves the captured passkey — already signed in.
76+
* }</pre>
77+
*
78+
* <p> <strong>Defaults</strong>
79+
*/
80+
public interface Credentials {
81+
class CreateOptions {
82+
/**
83+
* Base64url-encoded credential id. Auto-generated if omitted.
84+
*/
85+
public String id;
86+
/**
87+
* Base64url-encoded PKCS#8 (DER) private key. Auto-generated if omitted.
88+
*/
89+
public String privateKey;
90+
/**
91+
* Base64url-encoded SPKI (DER) public key. Auto-generated if omitted.
92+
*/
93+
public String publicKey;
94+
/**
95+
* Base64url-encoded user handle. Auto-generated if omitted.
96+
*/
97+
public String userHandle;
98+
99+
/**
100+
* Base64url-encoded credential id. Auto-generated if omitted.
101+
*/
102+
public CreateOptions setId(String id) {
103+
this.id = id;
104+
return this;
105+
}
106+
/**
107+
* Base64url-encoded PKCS#8 (DER) private key. Auto-generated if omitted.
108+
*/
109+
public CreateOptions setPrivateKey(String privateKey) {
110+
this.privateKey = privateKey;
111+
return this;
112+
}
113+
/**
114+
* Base64url-encoded SPKI (DER) public key. Auto-generated if omitted.
115+
*/
116+
public CreateOptions setPublicKey(String publicKey) {
117+
this.publicKey = publicKey;
118+
return this;
119+
}
120+
/**
121+
* Base64url-encoded user handle. Auto-generated if omitted.
122+
*/
123+
public CreateOptions setUserHandle(String userHandle) {
124+
this.userHandle = userHandle;
125+
return this;
126+
}
127+
}
128+
class GetOptions {
129+
/**
130+
* Only return the credential with this base64url-encoded id.
131+
*/
132+
public String id;
133+
/**
134+
* Only return credentials for this relying party id.
135+
*/
136+
public String rpId;
137+
138+
/**
139+
* Only return the credential with this base64url-encoded id.
140+
*/
141+
public GetOptions setId(String id) {
142+
this.id = id;
143+
return this;
144+
}
145+
/**
146+
* Only return credentials for this relying party id.
147+
*/
148+
public GetOptions setRpId(String rpId) {
149+
this.rpId = rpId;
150+
return this;
151+
}
152+
}
153+
/**
154+
* Installs the virtual WebAuthn authenticator into the context, overriding {@code navigator.credentials.create()} and
155+
* {@code navigator.credentials.get()} in all current and future pages. Call this before the page first touches {@code
156+
* navigator.credentials}.
157+
*
158+
* <p> Required: until {@link com.microsoft.playwright.Credentials#install Credentials.install()} is called, no interception is
159+
* in place and the page sees the platform's native (or absent) WebAuthn behaviour. Seeding credentials with {@link
160+
* com.microsoft.playwright.Credentials#create Credentials.create()} without installing populates the authenticator, but
161+
* the page will never see those credentials.
162+
*
163+
* @since v1.61
164+
*/
165+
void install();
166+
/**
167+
* Seeds a virtual WebAuthn credential and returns it.
168+
*
169+
* <p> With only {@code rpId}, generates a fresh **ECDSA P-256** keypair, credential id and user handle. The seeded credential
170+
* is discoverable (resident), so the page can resolve it from both username-then-passkey and usernameless passkey flows.
171+
* The returned object carries the private and public keys, so it can be persisted to disk and re-seeded in a later test.
172+
*
173+
* <p> To **import a known credential**, supply all four of {@code id}, {@code userHandle}, {@code privateKey} and {@code
174+
* publicKey} together.
175+
*
176+
* <p> Call {@link com.microsoft.playwright.Credentials#install Credentials.install()} before navigating to a page that uses
177+
* WebAuthn.
178+
*
179+
* @param rpId Relying party id (typically the site's effective domain).
180+
* @since v1.61
181+
*/
182+
default VirtualCredential create(String rpId) {
183+
return create(rpId, null);
184+
}
185+
/**
186+
* Seeds a virtual WebAuthn credential and returns it.
187+
*
188+
* <p> With only {@code rpId}, generates a fresh **ECDSA P-256** keypair, credential id and user handle. The seeded credential
189+
* is discoverable (resident), so the page can resolve it from both username-then-passkey and usernameless passkey flows.
190+
* The returned object carries the private and public keys, so it can be persisted to disk and re-seeded in a later test.
191+
*
192+
* <p> To **import a known credential**, supply all four of {@code id}, {@code userHandle}, {@code privateKey} and {@code
193+
* publicKey} together.
194+
*
195+
* <p> Call {@link com.microsoft.playwright.Credentials#install Credentials.install()} before navigating to a page that uses
196+
* WebAuthn.
197+
*
198+
* @param rpId Relying party id (typically the site's effective domain).
199+
* @since v1.61
200+
*/
201+
VirtualCredential create(String rpId, CreateOptions options);
202+
/**
203+
* Removes a credential from the authenticator by its id. Works for any credential currently held — both those seeded with
204+
* {@link com.microsoft.playwright.Credentials#create Credentials.create()} and those the page registered itself by calling
205+
* {@code navigator.credentials.create()}.
206+
*
207+
* @param id Base64url-encoded credential id.
208+
* @since v1.61
209+
*/
210+
void delete(String id);
211+
/**
212+
* Returns every credential currently held by the authenticator, optionally filtered by {@code rpId} or {@code id}. This
213+
* includes both credentials seeded with {@link com.microsoft.playwright.Credentials#create Credentials.create()} and
214+
* credentials the page registered itself by calling {@code navigator.credentials.create()}.
215+
*
216+
* <p> Each returned credential includes its private and public keys, so a passkey the app just registered can be saved and
217+
* re-seeded into a later test with {@link com.microsoft.playwright.Credentials#create Credentials.create()} — see the
218+
* second example in the class overview.
219+
*
220+
* @since v1.61
221+
*/
222+
default List<VirtualCredential> get() {
223+
return get(null);
224+
}
225+
/**
226+
* Returns every credential currently held by the authenticator, optionally filtered by {@code rpId} or {@code id}. This
227+
* includes both credentials seeded with {@link com.microsoft.playwright.Credentials#create Credentials.create()} and
228+
* credentials the page registered itself by calling {@code navigator.credentials.create()}.
229+
*
230+
* <p> Each returned credential includes its private and public keys, so a passkey the app just registered can be saved and
231+
* re-seeded into a later test with {@link com.microsoft.playwright.Credentials#create Credentials.create()} — see the
232+
* second example in the class overview.
233+
*
234+
* @since v1.61
235+
*/
236+
List<VirtualCredential> get(GetOptions options);
237+
}
238+

playwright/src/main/java/com/microsoft/playwright/Frame.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2965,7 +2965,7 @@ default Object evalOnSelectorAll(String selector, String expression) {
29652965
* <p> {@code ElementHandle} instances can be passed as an argument to the {@link com.microsoft.playwright.Frame#evaluate
29662966
* Frame.evaluate()}:
29672967
* <pre>{@code
2968-
* ElementHandle bodyHandle = frame.evaluate("document.body");
2968+
* ElementHandle bodyHandle = frame.evaluateHandle("document.body");
29692969
* String html = (String) frame.evaluate("([body, suffix]) => body.innerHTML + suffix", Arrays.asList(bodyHandle, "hello"));
29702970
* bodyHandle.dispose();
29712971
* }</pre>
@@ -3005,7 +3005,7 @@ default Object evaluate(String expression) {
30053005
* <p> {@code ElementHandle} instances can be passed as an argument to the {@link com.microsoft.playwright.Frame#evaluate
30063006
* Frame.evaluate()}:
30073007
* <pre>{@code
3008-
* ElementHandle bodyHandle = frame.evaluate("document.body");
3008+
* ElementHandle bodyHandle = frame.evaluateHandle("document.body");
30093009
* String html = (String) frame.evaluate("([body, suffix]) => body.innerHTML + suffix", Arrays.asList(bodyHandle, "hello"));
30103010
* bodyHandle.dispose();
30113011
* }</pre>

playwright/src/main/java/com/microsoft/playwright/Page.java

Lines changed: 18 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4529,7 +4529,7 @@ default Object evalOnSelectorAll(String selector, String expression) {
45294529
* <p> {@code ElementHandle} instances can be passed as an argument to the {@link com.microsoft.playwright.Page#evaluate
45304530
* Page.evaluate()}:
45314531
* <pre>{@code
4532-
* ElementHandle bodyHandle = page.evaluate("document.body");
4532+
* ElementHandle bodyHandle = page.evaluateHandle("document.body");
45334533
* String html = (String) page.evaluate("([body, suffix]) => body.innerHTML + suffix", Arrays.asList(bodyHandle, "hello"));
45344534
* bodyHandle.dispose();
45354535
* }</pre>
@@ -4571,7 +4571,7 @@ default Object evaluate(String expression) {
45714571
* <p> {@code ElementHandle} instances can be passed as an argument to the {@link com.microsoft.playwright.Page#evaluate
45724572
* Page.evaluate()}:
45734573
* <pre>{@code
4574-
* ElementHandle bodyHandle = page.evaluate("document.body");
4574+
* ElementHandle bodyHandle = page.evaluateHandle("document.body");
45754575
* String html = (String) page.evaluate("([body, suffix]) => body.innerHTML + suffix", Arrays.asList(bodyHandle, "hello"));
45764576
* bodyHandle.dispose();
45774577
* }</pre>
@@ -5808,6 +5808,18 @@ default boolean isVisible(String selector) {
58085808
* @since v1.59
58095809
*/
58105810
void clearPageErrors();
5811+
/**
5812+
* Provides access to the page's {@code localStorage} for the current origin. See {@code WebStorage}.
5813+
*
5814+
* @since v1.61
5815+
*/
5816+
WebStorage localStorage();
5817+
/**
5818+
* Provides access to the page's {@code sessionStorage} for the current origin. See {@code WebStorage}.
5819+
*
5820+
* @since v1.61
5821+
*/
5822+
WebStorage sessionStorage();
58115823
/**
58125824
* Returns up to (currently) 200 last console messages from this page. See {@link
58135825
* com.microsoft.playwright.Page#onConsoleMessage Page.onConsoleMessage()} for more details.
@@ -7552,8 +7564,8 @@ default String ariaSnapshot() {
75527564
* <p> When all steps combined have not finished during the specified {@code timeout}, this method throws a {@code
75537565
* TimeoutError}. Passing zero timeout disables this.
75547566
*
7555-
* <p> <strong>NOTE:</strong> {@link com.microsoft.playwright.Page#tap Page.tap()} the method will throw if {@code hasTouch} option of the browser
7556-
* context is false.
7567+
* <p> <strong>NOTE:</strong> {@link com.microsoft.playwright.Page#tap Page.tap()} will throw if the {@code hasTouch} option of the browser context is
7568+
* false.
75577569
*
75587570
* @param selector A selector to search for an element. If there are multiple elements satisfying the selector, the first will be used.
75597571
* @since v1.8
@@ -7575,8 +7587,8 @@ default void tap(String selector) {
75757587
* <p> When all steps combined have not finished during the specified {@code timeout}, this method throws a {@code
75767588
* TimeoutError}. Passing zero timeout disables this.
75777589
*
7578-
* <p> <strong>NOTE:</strong> {@link com.microsoft.playwright.Page#tap Page.tap()} the method will throw if {@code hasTouch} option of the browser
7579-
* context is false.
7590+
* <p> <strong>NOTE:</strong> {@link com.microsoft.playwright.Page#tap Page.tap()} will throw if the {@code hasTouch} option of the browser context is
7591+
* false.
75807592
*
75817593
* @param selector A selector to search for an element. If there are multiple elements satisfying the selector, the first will be used.
75827594
* @since v1.8

0 commit comments

Comments
 (0)