Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 15 additions & 0 deletions Source/WebDriver/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,21 @@ set(WebDriver_SOURCES
)

if (ENABLE_WEBDRIVER_BIDI)
set(WebDriver_BIDI_PROTOCOL ${WebKit_DERIVED_SOURCES_DIR}/CombinedWebDriverBidiDomains.json)
set(WebDriver_BIDI_COMMAND_NAMES_HEADER ${WebDriver_DERIVED_SOURCES_DIR}/WebDriverBidiCommandNames.h)
add_custom_command(
OUTPUT ${WebDriver_BIDI_COMMAND_NAMES_HEADER}
MAIN_DEPENDENCY ${WEBKIT_DIR}/Scripts/generate-webdriver-bidi-command-names.py
DEPENDS ${WebDriver_BIDI_PROTOCOL}
COMMAND
${PYTHON_EXECUTABLE}
${WEBKIT_DIR}/Scripts/generate-webdriver-bidi-command-names.py
--output ${WebDriver_BIDI_COMMAND_NAMES_HEADER}
${WebDriver_BIDI_PROTOCOL}
VERBATIM
)

list(APPEND WebDriver_HEADERS ${WebDriver_BIDI_COMMAND_NAMES_HEADER})
list(APPEND WebDriver_SOURCES WebSocketServer.cpp)
endif ()

Expand Down
3 changes: 3 additions & 0 deletions Source/WebDriver/Capabilities.h
Original file line number Diff line number Diff line change
Expand Up @@ -85,6 +85,9 @@ struct Capabilities {
#endif
#if PLATFORM(GTK)
std::optional<bool> useOverlayScrollbars;
#endif
#if ENABLE(WEBDRIVER_BIDI)
std::optional<String> userAgent;
#endif
// https://w3c.github.io/webdriver-bidi/#websocket-url
std::optional<bool> webSocketURL;
Expand Down
18 changes: 15 additions & 3 deletions Source/WebDriver/Session.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -73,8 +73,9 @@ const String& Session::shadowRootIdentifier()
return shadowRootID;
}

Session::Session(Ref<SessionHost>&& host)
Session::Session(Ref<SessionHost>&& host, HasHTTPFlag hasHTTPFlag)
: m_host(WTF::move(host))
, m_hasHTTPFlag(hasHTTPFlag == HasHTTPFlag::Yes)
, m_scriptTimeout(defaultScriptTimeout)
, m_pageLoadTimeout(defaultPageLoadTimeout)
, m_implicitWaitTimeout(defaultImplicitWaitTimeout)
Expand All @@ -85,8 +86,8 @@ Session::Session(Ref<SessionHost>&& host)
}

#if ENABLE(WEBDRIVER_BIDI)
Session::Session(Ref<SessionHost>&& host, WeakPtr<WebSocketServer>&& bidiServer)
: Session(WTF::move(host))
Session::Session(Ref<SessionHost>&& host, WeakPtr<WebSocketServer>&& bidiServer, HasHTTPFlag hasHTTPFlag)
: Session(WTF::move(host), hasHTTPFlag)
{
m_bidiServer = WTF::move(bidiServer);
m_host->setBidiHandler(this);
Expand Down Expand Up @@ -264,6 +265,17 @@ void Session::createTopLevelBrowsingContext(Function<void(CommandResult&&)>&& co
return;
}

#if ENABLE(WEBDRIVER_BIDI)
if (hasBiDiEnabled()) {
auto userAgent = response.responseObject->getString("userAgent"_s);
if (userAgent.isEmpty()) {
completionHandler(CommandResult::fail(CommandResult::ErrorCode::UnknownError, "Could not retrieve user agent for the new browsing context"_s));
return;
}
m_host->setUserAgent(WTF::move(userAgent));
}
#endif

switchToTopLevelBrowsingContext(handle);
completionHandler(CommandResult::success());
});
Expand Down
16 changes: 10 additions & 6 deletions Source/WebDriver/Session.h
Original file line number Diff line number Diff line change
Expand Up @@ -58,21 +58,24 @@ public RefCounted<Session>
#endif
{
public:
static Ref<Session> create(Ref<SessionHost>&& host)
enum class HasHTTPFlag : bool { No, Yes };

static Ref<Session> create(Ref<SessionHost>&& host, HasHTTPFlag hasHTTPFlag)
{
return adoptRef(*new Session(WTF::move(host)));
return adoptRef(*new Session(WTF::move(host), hasHTTPFlag));
}
#if ENABLE(WEBDRIVER_BIDI)
static Ref<Session> create(Ref<SessionHost>&& host, WeakPtr<WebSocketServer> bidiServer)
static Ref<Session> create(Ref<SessionHost>&& host, WeakPtr<WebSocketServer> bidiServer, HasHTTPFlag hasHTTPFlag)
{
return adoptRef(*new Session(WTF::move(host), WTF::move(bidiServer)));
return adoptRef(*new Session(WTF::move(host), WTF::move(bidiServer), hasHTTPFlag));
}
#endif
virtual ~Session();

const String& id() const;
const Capabilities& capabilities() const;
bool isConnected() const;
bool hasHTTPFlag() const { return m_hasHTTPFlag; }
#if ENABLE(WEBDRIVER_BIDI)
bool hasBiDiEnabled() const { return m_hasBiDiEnabled; };
void setHasBiDiEnabled(bool flag) { m_hasBiDiEnabled = flag; }
Expand Down Expand Up @@ -166,9 +169,9 @@ public RefCounted<Session>
#endif

private:
Session(Ref<SessionHost>&&);
Session(Ref<SessionHost>&&, HasHTTPFlag);
#if ENABLE(WEBDRIVER_BIDI)
Session(Ref<SessionHost>&&, WeakPtr<WebSocketServer>&&);
Session(Ref<SessionHost>&&, WeakPtr<WebSocketServer>&&, HasHTTPFlag);
#endif

String uncheckedTopLevelBrowsingContext() const;
Expand Down Expand Up @@ -265,6 +268,7 @@ public RefCounted<Session>
InputSourceState& inputSourceState(const String& id);

RefPtr<SessionHost> m_host;
bool m_hasHTTPFlag;
double m_scriptTimeout;
double m_pageLoadTimeout;
double m_implicitWaitTimeout;
Expand Down
11 changes: 11 additions & 0 deletions Source/WebDriver/SessionHost.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -43,10 +43,21 @@ static WeakHashSet<SessionHost::BrowserTerminatedObserver>& browserTerminatedObs
}
#endif

void SessionHost::completeStartAutomationSession(bool capabilitiesDidMatch, std::optional<String> error)
{
if (!m_startSessionCompletionHandler)
return;

Ref protectedThis { *this };
m_startSessionCompletionHandler(capabilitiesDidMatch, WTF::move(error));
}

void SessionHost::inspectorDisconnected()
{
Ref<SessionHost> protectedThis(*this);

completeStartAutomationSession(false, "Browser disconnected while starting automation session"_s);

auto pendingRequestCount = m_commandRequests.size();
if (pendingRequestCount)
RELEASE_LOG_INFO(SessionHost, "Inspector disconnected; failing %u pending command(s)", pendingRequestCount);
Expand Down
19 changes: 16 additions & 3 deletions Source/WebDriver/SessionHost.h
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
#pragma once

#include "Capabilities.h"
#include <wtf/CompletionHandler.h>
#include <wtf/HashMap.h>
#include <wtf/JSONValues.h>
#include <wtf/Observer.h>
Expand Down Expand Up @@ -84,9 +85,20 @@ class SessionHost final

const String& sessionID() const LIFETIME_BOUND { return m_sessionID; }
const Capabilities& capabilities() const LIFETIME_BOUND { return m_capabilities; }
#if ENABLE(WEBDRIVER_BIDI)
void setUserAgent(String&& userAgent)
{
ASSERT(!userAgent.isEmpty());
ASSERT(!m_capabilities.userAgent);
m_capabilities.userAgent = WTF::move(userAgent);
}
#endif

void connectToBrowser(Function<void (std::optional<String> error)>&&);
void startAutomationSession(Function<void (bool, std::optional<String>)>&&);
void cancelSessionCreation();

using StartAutomationSessionCompletionHandler = CompletionHandler<void(bool, std::optional<String>)>;
void startAutomationSession(StartAutomationSessionCompletionHandler&&);

bool isRemoteBrowser() const;

Expand All @@ -113,6 +125,7 @@ class SessionHost final
bool paired { false };
};

void completeStartAutomationSession(bool capabilitiesDidMatch, std::optional<String> error);
void inspectorDisconnected();
void sendMessageToBackend(const String&);
void dispatchMessage(const String&);
Expand All @@ -125,6 +138,7 @@ class SessionHost final
enum class DisconnectReason {
BrowserDidCloseConnection,
AutomationTargetLost,
SessionCreationCancelled,
};

static const SocketConnection::MessageHandlers& messageHandlers();
Expand Down Expand Up @@ -165,14 +179,13 @@ class SessionHost final
String m_targetIp;
uint16_t m_targetPort { 0 };
bool m_isRemoteBrowser { false };
StartAutomationSessionCompletionHandler m_startSessionCompletionHandler;

#if USE(GLIB)
Function<void (bool, std::optional<String>)> m_startSessionCompletionHandler;
GRefPtr<GSubprocess> m_browser;
RefPtr<SocketConnection> m_socketConnection;
GRefPtr<GCancellable> m_cancellable;
#elif USE(INSPECTOR_SOCKET_SERVER)
Function<void(bool, std::optional<String>)> m_startSessionCompletionHandler;
std::optional<Inspector::ConnectionID> m_clientID;
#if PLATFORM(WIN)
WTF::Win32Handle m_browserHandle;
Expand Down
Loading