From 54f66cc7a1e17155e90a1d3b5c33f627dbd0d50f Mon Sep 17 00:00:00 2001 From: Milian Wolff Date: Fri, 10 Jan 2014 14:21:05 +0100 Subject: Make the underlying transport mechanism of the webchannel pluggable. This enables us to optionally use navigator.qt instead of a WebSocket, which is nicer setup-wise and is also slightly faster: navigator.qt: 284.0 msecs per iteration (total: 2,840, iterations: 10) WebSocket: 295.8 msecs per iteration (total: 2,959, iterations: 10) The baseline is ca. 203 msecs, which would mean a performance boost of ca. 12.7%. Furthermore, this sets the fundation to eventually add a WebEngine transport mechanism. The WebViewTransport should also be removed and instead the WebView itself should directly implement the WebChannelTransportInterface. Change-Id: I368bb27e38ffa2f17ffeb7f5ae695690f6f5ad21 Reviewed-by: Simon Hausmann --- src/webchannel/qwebchannel.cpp | 75 +++++++++++++++++------------------------- 1 file changed, 30 insertions(+), 45 deletions(-) (limited to 'src/webchannel/qwebchannel.cpp') diff --git a/src/webchannel/qwebchannel.cpp b/src/webchannel/qwebchannel.cpp index b51a056..a080aae 100644 --- a/src/webchannel/qwebchannel.cpp +++ b/src/webchannel/qwebchannel.cpp @@ -43,7 +43,7 @@ #include "qwebchannel.h" #include "qwebchannel_p.h" #include "qmetaobjectpublisher_p.h" -#include "qwebchannelsocket_p.h" +#include "qwebchanneltransportinterface.h" #include #include @@ -52,6 +52,11 @@ QT_BEGIN_NAMESPACE void QWebChannelPrivate::sendJSONMessage(const QJsonValue &id, const QJsonValue &data, bool response) const { + if (transports.isEmpty()) { + qWarning("QWebChannel is not connected to any transports, cannot send messages."); + return; + } + QJsonObject obj; if (response) { obj[QStringLiteral("response")] = true; @@ -61,55 +66,27 @@ void QWebChannelPrivate::sendJSONMessage(const QJsonValue &id, const QJsonValue obj[QStringLiteral("data")] = data; } QJsonDocument doc(obj); - socket->sendMessage(doc.toJson(QJsonDocument::Compact)); + const QByteArray &message = doc.toJson(QJsonDocument::Compact); + + foreach (QWebChannelTransportInterface *transport, transports) { + transport->sendMessage(message); + } } QWebChannel::QWebChannel(QObject *parent) : QObject(parent) , d(new QWebChannelPrivate) { - d->socket = new QWebChannelSocket(this); - - connect(d->socket, SIGNAL(textDataReceived(QString)), - SIGNAL(rawMessageReceived(QString))); - connect(d->socket, SIGNAL(failed(QString)), - SIGNAL(failed(QString))); - connect(d->socket, SIGNAL(initialized()), - SIGNAL(initialized())); - connect(d->socket, SIGNAL(baseUrlChanged(QString)), - SIGNAL(baseUrlChanged(QString))); - connect(d->socket, SIGNAL(pongReceived()), - SIGNAL(pongReceived())); - - d->socket->initLater(); - d->publisher = new QMetaObjectPublisher(this); connect(d->publisher, SIGNAL(blockUpdatesChanged(bool)), SIGNAL(blockUpdatesChanged(bool))); - connect(d->socket, SIGNAL(textDataReceived(QString)), - d->publisher, SLOT(handleRawMessage(QString))); } QWebChannel::~QWebChannel() { -} - -QString QWebChannel::baseUrl() const -{ - return d->socket->m_baseUrl; -} - -void QWebChannel::setUseSecret(bool s) -{ - if (d->socket->m_useSecret == s) - return; - d->socket->m_useSecret = s; - d->socket->initLater(); -} - -bool QWebChannel::useSecret() const -{ - return d->socket->m_useSecret; + foreach (QWebChannelTransportInterface *transport, d->transports) { + transport->setMessageHandler(Q_NULLPTR); + } } void QWebChannel::registerObjects(const QHash< QString, QObject * > &objects) @@ -141,24 +118,32 @@ void QWebChannel::setBlockUpdates(bool block) d->publisher->setBlockUpdates(block); } -void QWebChannel::respond(const QJsonValue& messageId, const QJsonValue& data) const +void QWebChannel::connectTo(QWebChannelTransportInterface *transport) { - d->sendJSONMessage(messageId, data, true); + Q_ASSERT(transport); + if (!d->transports.contains(transport)) { + d->transports << transport; + transport->setMessageHandler(d->publisher); + } } -void QWebChannel::sendMessage(const QJsonValue& id, const QJsonValue& data) const +void QWebChannel::disconnectFrom(QWebChannelTransportInterface *transport) { - d->sendJSONMessage(id, data, false); + const int idx = d->transports.indexOf(transport); + if (idx != -1) { + transport->setMessageHandler(Q_NULLPTR); + d->transports.remove(idx); + } } -void QWebChannel::sendRawMessage(const QString& message) const +void QWebChannel::respond(const QJsonValue& messageId, const QJsonValue& data) const { - d->socket->sendMessage(message.toUtf8()); + d->sendJSONMessage(messageId, data, true); } -void QWebChannel::ping() const +void QWebChannel::sendMessage(const QJsonValue& id, const QJsonValue& data) const { - d->socket->ping(); + d->sendJSONMessage(id, data, false); } QT_END_NAMESPACE -- cgit v1.2.3