下面列出了怎么用org.openqa.selenium.ImmutableCapabilities的API类实例代码及写法,或者点击链接到github查看源代码。
protected RemoteSession(
Dialect downstream,
Dialect upstream,
HttpHandler codec,
SessionId id,
Map<String, Object> capabilities) {
this.downstream = Require.nonNull("Downstream dialect", downstream);
this.upstream = Require.nonNull("Upstream dialect", upstream);
this.codec = Require.nonNull("Codec", codec);
this.id = Require.nonNull("Session id", id);
this.capabilities = Require.nonNull("Capabilities", capabilities);
File tempRoot = new File(StandardSystemProperty.JAVA_IO_TMPDIR.value(), id.toString());
Require.stateCondition(tempRoot.mkdirs(), "Could not create directory %s", tempRoot);
this.filesystem = TemporaryFilesystem.getTmpFsBasedOn(tempRoot);
CommandExecutor executor = new ActiveSessionCommandExecutor(this);
this.driver = new Augmenter().augment(new RemoteWebDriver(
executor,
new ImmutableCapabilities(getCapabilities())));
}
@Test
public void convertEverythingToFirstMatchOnlyifPayloadContainsAlwaysMatchSectionAndOssCapabilities() {
List<Capabilities> capabilities = create(ImmutableMap.of(
"desiredCapabilities", ImmutableMap.of(
"browserName", "firefox",
"platform", "WINDOWS"),
"capabilities", ImmutableMap.of(
"alwaysMatch", singletonMap(
"platformName", "macos"),
"firstMatch", asList(
singletonMap("browserName", "foo"),
singletonMap("browserName", "firefox")))));
assertEquals(asList(
// From OSS
new ImmutableCapabilities("browserName", "firefox", "platform", "WINDOWS"),
// Generated from OSS
new ImmutableCapabilities("browserName", "firefox", "platformName", "windows"),
// From the actual W3C capabilities
new ImmutableCapabilities("browserName", "foo", "platformName", "macos"),
new ImmutableCapabilities("browserName", "firefox", "platformName", "macos")),
capabilities);
}
@Test
public void factoriesFoundViaServiceLoadersAreUsedFirst() {
WebDriver driver = Mockito.mock(WebDriver.class);
Capabilities caps = new ImmutableCapabilities("browserName", "chrome");
DriverProvider provider = new StubbedProvider(caps, driver);
ActiveSessionFactory sessionFactory = new ActiveSessionFactory(new NullTracer()) {
@Override
protected Iterable<DriverProvider> loadDriverProviders() {
return ImmutableSet.of(provider);
}
};
ActiveSession session = sessionFactory.apply(
new CreateSessionRequest(ImmutableSet.of(Dialect.W3C), caps, ImmutableMap.of()))
.get();
assertEquals(driver, session.getWrappedDriver());
}
@Test
public void shouldForwardTextMessageToServer() throws URISyntaxException, InterruptedException {
HttpClient.Factory clientFactory = HttpClient.Factory.createDefault();
// Create a backend server which will capture any incoming text message
AtomicReference<String> text = new AtomicReference<>();
CountDownLatch latch = new CountDownLatch(1);
Server<?> backend = createBackendServer(latch, text, "");
// Push a session that resolves to the backend server into the session map
SessionId id = new SessionId(UUID.randomUUID());
sessions.add(new Session(id, backend.getUrl().toURI(), new ImmutableCapabilities()));
// Now! Send a message. We expect it to eventually show up in the backend
WebSocket socket = clientFactory.createClient(proxyServer.getUrl())
.openSocket(new HttpRequest(GET, String.format("/session/%s/cdp", id)), new WebSocket.Listener(){});
socket.sendText("Cheese!");
assertThat(latch.await(5, SECONDS)).isTrue();
assertThat(text.get()).isEqualTo("Cheese!");
socket.close();
}
@Before
public void setUp() throws URISyntaxException {
Tracer tracer = DefaultTestTracer.createTracer();
EventBus bus = new GuavaEventBus();
URI uri = new URI("http://localhost:1234");
Capabilities stereotype = new ImmutableCapabilities("cheese", "brie");
node = LocalNode.builder(tracer, bus, uri, uri, null)
.add(stereotype, new TestSessionFactory((id, caps) -> new Session(id, uri, caps)))
.build();
CreateSessionResponse sessionResponse = node.newSession(
new CreateSessionRequest(
ImmutableSet.of(W3C),
stereotype,
ImmutableMap.of()))
.orElseThrow(() -> new AssertionError("Unable to create session"));
session = sessionResponse.getSession();
}
@Test
public void firstMatchSeparatesCapsForDifferentBrowsers() throws IOException {
Capabilities caps = new ImmutableCapabilities(
"moz:firefoxOptions", EMPTY_MAP,
"browserName", "chrome");
Map<String, Object> params = singletonMap("desiredCapabilities", caps);
Command command = new Command(null, DriverCommand.NEW_SESSION, params);
HttpResponse response = new HttpResponse();
response.setStatus(HTTP_OK);
response.setContent(utf8String(
"{\"sessionId\": \"23456789\", \"status\": 0, \"value\": {}}"));
RecordingHttpClient client = new RecordingHttpClient(response);
new ProtocolHandshake().createSession(client, command);
Map<String, Object> handshakeRequest = getRequestPayloadAsMap(client);
List<Map<String, Object>> capabilities = mergeW3C(handshakeRequest);
assertThat(capabilities).contains(
singletonMap("moz:firefoxOptions", EMPTY_MAP),
singletonMap("browserName", "chrome"));
}
@Test
public void successfulResponseGetsParsedProperly() {
Capabilities caps = new ImmutableCapabilities("cheese", "peas");
Map<String, ?> payload =
ImmutableMap.of(
"status", 0,
"value", caps.asMap(),
"sessionId", "cheese is opaque");
InitialHandshakeResponse initialResponse = new InitialHandshakeResponse(
0,
200,
payload);
ProtocolHandshake.Result result =
new JsonWireProtocolResponse().getResponseFunction().apply(initialResponse);
assertThat(result).isNotNull();
assertThat(result.getDialect()).isEqualTo(Dialect.OSS);
Response response = result.createResponse();
assertThat(response.getState()).isEqualTo("success");
assertThat((int) response.getStatus()).isEqualTo(0);
assertThat(response.getValue()).isEqualTo(caps.asMap());
}
@Test
public void canHandleSwitchToFrameByNameCommand() throws IOException {
CommandExecutor executor = prepareExecutorMock(
echoCapabilities,
valueResponder(Arrays.asList(
ImmutableMap.of(ELEMENT_KEY, UUID.randomUUID().toString()),
ImmutableMap.of(ELEMENT_KEY, UUID.randomUUID().toString()))));
RemoteWebDriver driver = new RemoteWebDriver(executor, new ImmutableCapabilities());
WebDriver driver2 = driver.switchTo().frame("frameName");
assertThat(driver2).isSameAs(driver);
verify(executor).execute(argThat(
command -> command.getName().equals(DriverCommand.NEW_SESSION)));
verify(executor).execute(argThat(
command -> command.getName().equals(DriverCommand.FIND_ELEMENTS)));
verify(executor).execute(argThat(
command -> Optional.of(command)
.filter(cmd -> cmd.getName().equals(DriverCommand.SWITCH_TO_FRAME))
.filter(cmd -> cmd.getParameters().size() == 1)
.filter(cmd -> isWebElement(cmd.getParameters().get("id")))
.isPresent()));
verifyNoMoreInteractions(executor);
}
@Test
public void canCreateARedisBackedSessionMap() throws URISyntaxException {
SessionMap sessions = new RedisBackedSessionMap(tracer, uri);
Session expected = new Session(
new SessionId(UUID.randomUUID()),
new URI("http://example.com/foo"),
new ImmutableCapabilities("cheese", "beyaz peynir"));
sessions.add(expected);
SessionMap reader = new RedisBackedSessionMap(tracer, uri);
Session seen = reader.get(expected.getId());
assertThat(seen).isEqualTo(expected);
}
@Test
public void shouldDoNothingIfOssPayloadMatchesAValidMergedW3CPayload() {
Map<String, String> caps = ImmutableMap.of(
"browserName", "cheese",
"se:cake", "more cheese");
Map<String, Object> payload= ImmutableMap.of(
"desiredCapabilities", caps,
"capabilities", ImmutableMap.of(
"alwaysMatch", ImmutableMap.of("browserName", "cheese"),
"firstMatch", singletonList(ImmutableMap.of("se:cake", "more cheese"))));
List<Capabilities> allCaps = getCapabilities(payload);
assertThat(allCaps).containsExactly(new ImmutableCapabilities(caps));
}
@Test
public void shouldIgnoreAw3CProtocolReply() {
Capabilities caps = new ImmutableCapabilities("cheese", "peas");
Map<String, Map<String, Object>> payload =
ImmutableMap.of(
"value", ImmutableMap.of(
"capabilities", caps.asMap(),
"sessionId", "cheese is opaque"));
InitialHandshakeResponse initialResponse = new InitialHandshakeResponse(
0,
200,
payload);
ProtocolHandshake.Result result =
new JsonWireProtocolResponse().getResponseFunction().apply(initialResponse);
assertThat(result).isNull();
}
@Test
public void shouldNotUseFactoriesThatDoNotSupportTheCapabilities() {
SessionFactory toBeIgnored = mock(SessionFactory.class);
when(toBeIgnored.test(any())).thenReturn(false);
when(toBeIgnored.apply(any())).thenThrow(new AssertionError("Must not be called"));
ActiveSession session = mock(ActiveSession.class);
SessionFactory toBeUsed = mock(SessionFactory.class);
when(toBeUsed.test(any())).thenReturn(true);
when(toBeUsed.apply(any())).thenReturn(Optional.of(session));
NewSessionPipeline pipeline = NewSessionPipeline.builder()
.add(toBeIgnored)
.add(toBeUsed)
.create();
ActiveSession seen =
pipeline.createNewSession(NewSessionPayload.create(new ImmutableCapabilities()));
assertEquals(session, seen);
verify(toBeIgnored, atLeast(1)).test(any());
}
@Test
public void canGetTheUriOfASessionWithoutNeedingUrl() throws URISyntaxException {
SessionMap sessions = new RedisBackedSessionMap(tracer, uri);
Session expected = new Session(
new SessionId(UUID.randomUUID()),
new URI("http://example.com/foo"),
new ImmutableCapabilities());
sessions.add(expected);
SessionMap reader = new RedisBackedSessionMap(tracer, uri);
URI seen = reader.getUri(expected.getId());
assertThat(seen).isEqualTo(expected.getUri());
}
@Test
public void canHandleElementGeRectCommand() throws IOException {
CommandExecutor executor = prepareExecutorMock(
echoCapabilities,
valueResponder(ImmutableMap.of("x", 10, "y", 20, "width", 100, "height", 200)));
RemoteWebDriver driver = new RemoteWebDriver(executor, new ImmutableCapabilities());
RemoteWebElement element = new RemoteWebElement();
element.setParent(driver);
element.setId(UUID.randomUUID().toString());
Rectangle rect = element.getRect();
assertThat(rect).isEqualTo(new Rectangle(new Point(10, 20), new Dimension(100, 200)));
verifyCommands(
executor, driver.getSessionId(),
new CommandPayload(DriverCommand.GET_ELEMENT_RECT, ImmutableMap.of("id", element.getId())));
}
@Test
public void canHandleElementCssPropertyCommand() throws IOException {
CommandExecutor executor = prepareExecutorMock(echoCapabilities, valueResponder("red"));
RemoteWebDriver driver = new RemoteWebDriver(executor, new ImmutableCapabilities());
RemoteWebElement element = new RemoteWebElement();
element.setParent(driver);
element.setId(UUID.randomUUID().toString());
String color = element.getCssValue("color");
assertThat(color).isEqualTo("red");
verifyCommands(
executor, driver.getSessionId(),
new CommandPayload(DriverCommand.GET_ELEMENT_VALUE_OF_CSS_PROPERTY,
ImmutableMap.of("id", element.getId(), "propertyName", "color")));
}
@Test
public void canHandleElementGetAttributeCommand() throws IOException {
CommandExecutor executor = prepareExecutorMock(echoCapabilities, valueResponder("test"));
RemoteWebDriver driver = new RemoteWebDriver(executor, new ImmutableCapabilities());
RemoteWebElement element = new RemoteWebElement();
element.setParent(driver);
element.setId(UUID.randomUUID().toString());
String attr = element.getAttribute("id");
assertThat(attr).isEqualTo("test");
verifyCommands(
executor, driver.getSessionId(),
new CommandPayload(DriverCommand.GET_ELEMENT_ATTRIBUTE, ImmutableMap.of(
"id", element.getId(), "name", "id")));
}
@Test
public void testShouldBeAbleToDisableSnapshotOnException() {
if (!(driver instanceof RemoteWebDriver)) {
System.out.println("Skipping test: driver is not a remote webdriver");
return;
}
Capabilities caps = new ImmutableCapabilities("webdriver.remote.quietExceptions", true);
WebDriver noScreenshotDriver = new WebDriverBuilder().get(caps);
noScreenshotDriver.get(pages.simpleTestPage);
assertThatExceptionOfType(NoSuchElementException.class)
.isThrownBy(() -> noScreenshotDriver.findElement(By.id("doesnayexist")))
.satisfies(e -> {
Throwable t = e;
while (t != null) {
assertThat(t).isNotInstanceOf(ScreenshotException.class);
t = t.getCause();
}
});
}
@Test
public void canHandleGetCookiesCommand() throws IOException {
CommandExecutor executor = prepareExecutorMock(
echoCapabilities,
valueResponder(Arrays.asList(
ImmutableMap.of("name", "cookie1", "value", "value1", "sameSite", "Lax"),
ImmutableMap.of("name", "cookie2", "value", "value2"))));
RemoteWebDriver driver = new RemoteWebDriver(executor, new ImmutableCapabilities());
Set<Cookie> cookies = driver.manage().getCookies();
assertThat(cookies)
.hasSize(2)
.contains(
new Cookie.Builder("cookie1", "value1").sameSite("Lax").build(),
new Cookie("cookie2", "value2"));
verifyCommands(
executor, driver.getSessionId(),
new CommandPayload(DriverCommand.GET_ALL_COOKIES, ImmutableMap.of()));
}
@Test
public void requestShouldIncludeJsonWireProtocolCapabilities() throws IOException {
Map<String, Object> params = singletonMap("desiredCapabilities", new ImmutableCapabilities());
Command command = new Command(null, DriverCommand.NEW_SESSION, params);
HttpResponse response = new HttpResponse();
response.setStatus(HTTP_OK);
response.setContent(utf8String(
"{\"value\": {\"sessionId\": \"23456789\", \"capabilities\": {}}}"));
RecordingHttpClient client = new RecordingHttpClient(response);
new ProtocolHandshake().createSession(client, command);
Map<String, Object> json = getRequestPayloadAsMap(client);
assertThat(json.get("desiredCapabilities")).isEqualTo(EMPTY_MAP);
}
@Test
public void canHandleSetImplicitWaitCommand() throws IOException {
CommandExecutor executor = prepareExecutorMock(echoCapabilities, nullResponder);
RemoteWebDriver driver = new RemoteWebDriver(executor, new ImmutableCapabilities());
driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS);
verifyCommands(
executor, driver.getSessionId(),
new CommandPayload(DriverCommand.SET_TIMEOUT, ImmutableMap.of("implicit", 10000L)));
}
public ActiveSession createNewSession(NewSessionPayload payload) {
return payload.stream()
.map(caps -> {
for (Function<Capabilities, Capabilities> mutator : mutators) {
caps = mutator.apply(caps);
}
return caps;
})
.map(caps -> factories.stream()
.filter(factory -> factory.test(caps))
.map(factory -> factory.apply(
new CreateSessionRequest(
payload.getDownstreamDialects(),
caps,
ImmutableMap.of())))
.filter(Optional::isPresent)
.map(Optional::get)
.findFirst())
.filter(Optional::isPresent)
.map(Optional::get)
.findFirst()
.orElseGet(
() -> fallback.apply(
new CreateSessionRequest(
payload.getDownstreamDialects(),
new ImmutableCapabilities(),
ImmutableMap.of()))
.orElseThrow(
() -> new SessionNotCreatedException(
"Unable to create session from " + payload))
);
}
/**
* Stream the {@link Capabilities} encoded in the payload used to create this instance. The
* {@link Stream} will start with a {@link Capabilities} object matching the OSS capabilities, and
* will then expand each of the "{@code firstMatch}" and "{@code alwaysMatch}" contents as defined
* in the W3C WebDriver spec. The OSS {@link Capabilities} are listed first because converting the
* OSS capabilities to the equivalent W3C capabilities isn't particularly easy, so it's hoped that
* this approach gives us the most compatible implementation.
*
* @return The capabilities as a stream.
* @throws IOException On file system I/O error.
*/
public Stream<Capabilities> stream() throws IOException {
// OSS first
Stream<Map<String, Object>> oss = Stream.of(getOss());
// And now W3C
Stream<Map<String, Object>> w3c = getW3C();
return Stream.concat(oss, w3c)
.filter(Objects::nonNull)
.map(this::applyTransforms)
.filter(Objects::nonNull)
.distinct()
.map(ImmutableCapabilities::new);
}
private Capabilities rewriteCapabilities(RemoteWebDriver driver) {
// Rewrite the se:options if necessary
Object rawSeleniumOptions = driver.getCapabilities().getCapability("se:options");
if (rawSeleniumOptions == null || rawSeleniumOptions instanceof Map) {
@SuppressWarnings("unchecked") Map<String, Object> original = (Map<String, Object>) rawSeleniumOptions;
Map<String, Object> updated = new TreeMap<>(original == null ? new HashMap<>() : original);
String cdpPath = String.format("/session/%s/se/cdp", driver.getSessionId());
updated.put("cdp", rewrite(cdpPath));
return new PersistentCapabilities(driver.getCapabilities()).setCapability("se:options", updated);
}
return ImmutableCapabilities.copyOf(driver.getCapabilities());
}
@Test
public void canHandleElementIsDisplayedCommand() throws IOException {
CommandExecutor executor = prepareExecutorMock(echoCapabilities, valueResponder(true));
RemoteWebDriver driver = new RemoteWebDriver(executor, new ImmutableCapabilities());
RemoteWebElement element = new RemoteWebElement();
element.setParent(driver);
element.setId(UUID.randomUUID().toString());
assertThat(element.isDisplayed()).isTrue();
verifyCommands(
executor, driver.getSessionId(),
new CommandPayload(DriverCommand.IS_ELEMENT_DISPLAYED, ImmutableMap.of("id", element.getId())));
}
public Result createSession(HttpClient client, Command command)
throws IOException {
Capabilities desired = (Capabilities) command.getParameters().get("desiredCapabilities");
desired = desired == null ? new ImmutableCapabilities() : desired;
int threshold = (int) Math.min(Runtime.getRuntime().freeMemory() / 10, Integer.MAX_VALUE);
FileBackedOutputStream os = new FileBackedOutputStream(threshold);
try (
CountingOutputStream counter = new CountingOutputStream(os);
Writer writer = new OutputStreamWriter(counter, UTF_8);
NewSessionPayload payload = NewSessionPayload.create(desired)) {
payload.writeTo(writer);
try (InputStream rawIn = os.asByteSource().openBufferedStream();
BufferedInputStream contentStream = new BufferedInputStream(rawIn)) {
Optional<Result> result = createSession(client, contentStream, counter.getCount());
if (result.isPresent()) {
Result toReturn = result.get();
LOG.info(String.format("Detected dialect: %s", toReturn.dialect));
return toReturn;
}
}
} finally {
os.reset();
}
throw new SessionNotCreatedException(
String.format(
"Unable to create new remote session. " +
"desired capabilities = %s",
desired));
}
/**
* Actually create a new WebDriver session. The returned webdriver is not guaranteed to be a
* {@link RemoteWebDriver}.
*/
public WebDriver build() {
if (options.isEmpty() && additionalCapabilities.isEmpty()) {
throw new SessionNotCreatedException("Refusing to create session without any capabilities");
}
Plan plan = getPlan();
CommandExecutor executor;
if (plan.isUsingDriverService()) {
AtomicReference<DriverService> serviceRef = new AtomicReference<>();
executor = new SpecCompliantExecutor(
() -> {
if (serviceRef.get() != null && serviceRef.get().isRunning()) {
throw new SessionNotCreatedException(
"Attempt to start the underlying service more than once");
}
try {
DriverService service = plan.getDriverService();
serviceRef.set(service);
service.start();
return service.getUrl();
} catch (IOException e) {
throw new SessionNotCreatedException(e.getMessage(), e);
}
},
plan::writePayload,
() -> serviceRef.get().stop());
} else {
executor = new SpecCompliantExecutor(() -> remoteHost, plan::writePayload, () -> {});
}
return new RemoteWebDriver(executor, new ImmutableCapabilities());
}
@Test
public void throwIfRemoteEndReturnsNullFromFindChild() throws IOException {
CommandExecutor executor = prepareExecutorMock(echoCapabilities, nullResponder);
RemoteWebDriver driver = new RemoteWebDriver(executor, new ImmutableCapabilities());
RemoteWebElement element = new RemoteWebElement();
element.setParent(driver);
element.setId("unique");
assertThatExceptionOfType(NoSuchElementException.class)
.isThrownBy(() -> element.findElement(By.id("id")));
}
@Test
public void canHandleGetWindowSizeCommand() throws IOException {
CommandExecutor executor = prepareExecutorMock(
echoCapabilities,
valueResponder(ImmutableMap.of("width", 400, "height", 600)));
RemoteWebDriver driver = new RemoteWebDriver(executor, new ImmutableCapabilities());
Dimension size = driver.manage().window().getSize();
assertThat(size).isEqualTo(new Dimension(400, 600));
verifyCommands(
executor, driver.getSessionId(),
new CommandPayload(DriverCommand.GET_CURRENT_WINDOW_SIZE, emptyMap()));
}
@Test
public void canInitFirefoxOptionsWithCapabilities() {
FirefoxOptions options = new FirefoxOptions(new ImmutableCapabilities(
MARIONETTE, false,
PAGE_LOAD_STRATEGY, PageLoadStrategy.EAGER,
ACCEPT_INSECURE_CERTS, true));
assertThat(options.isLegacy()).isTrue();
assertThat(options.getCapability(PAGE_LOAD_STRATEGY)).isEqualTo(EAGER);
assertThat(options.getCapability(ACCEPT_INSECURE_CERTS)).isEqualTo(true);
}
@Test
public void canHandleSetWindowSizeCommand() throws IOException {
CommandExecutor executor = prepareExecutorMock(echoCapabilities, nullResponder);
RemoteWebDriver driver = new RemoteWebDriver(executor, new ImmutableCapabilities());
driver.manage().window().setSize(new Dimension(400, 600));
verifyCommands(
executor, driver.getSessionId(),
new CommandPayload(DriverCommand.SET_CURRENT_WINDOW_SIZE,
ImmutableMap.of("width", 400, "height", 600)));
}