Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(127)

Unified Diff: mojo/services/html_viewer/websockethandle_impl.cc

Issue 515923003: Mojo: Add a WebSocket/Client interface and hook it up to the HTML viewer. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: rebase Created 6 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « mojo/services/html_viewer/websockethandle_impl.h ('k') | mojo/services/network/BUILD.gn » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: mojo/services/html_viewer/websockethandle_impl.cc
diff --git a/mojo/services/html_viewer/websockethandle_impl.cc b/mojo/services/html_viewer/websockethandle_impl.cc
new file mode 100644
index 0000000000000000000000000000000000000000..e5d291a51ba381b6154e410adfc83e23a4103129
--- /dev/null
+++ b/mojo/services/html_viewer/websockethandle_impl.cc
@@ -0,0 +1,193 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "mojo/services/html_viewer/websockethandle_impl.h"
+
+#include <vector>
+
+#include "mojo/services/public/interfaces/network/network_service.mojom.h"
+#include "third_party/WebKit/public/platform/WebSerializedOrigin.h"
+#include "third_party/WebKit/public/platform/WebSocketHandleClient.h"
+#include "third_party/WebKit/public/platform/WebString.h"
+#include "third_party/WebKit/public/platform/WebURL.h"
+#include "third_party/WebKit/public/platform/WebVector.h"
+
+using blink::WebSerializedOrigin;
+using blink::WebSocketHandle;
+using blink::WebSocketHandleClient;
+using blink::WebString;
+using blink::WebURL;
+using blink::WebVector;
+
+namespace mojo {
+
+template<>
+struct TypeConverter<String, WebString> {
+ static String Convert(const WebString& str) {
+ return String(str.utf8());
+ }
+};
+template<>
+struct TypeConverter<WebString, String> {
+ static WebString Convert(const String& str) {
+ return WebString::fromUTF8(str.get());
+ }
+};
+
+template<typename T, typename U>
+struct TypeConverter<Array<T>, WebVector<U> > {
+ static Array<T> Convert(const WebVector<U>& vector) {
+ Array<T> array(vector.size());
+ for (size_t i = 0; i < vector.size(); ++i)
+ array[i] = TypeConverter<T, U>::Convert(vector[i]);
+ return array.Pass();
+ }
+};
+
+template<>
+struct TypeConverter<WebSocket::MessageType, WebSocketHandle::MessageType> {
+ static WebSocket::MessageType Convert(WebSocketHandle::MessageType type) {
+ DCHECK(type == WebSocketHandle::MessageTypeContinuation ||
+ type == WebSocketHandle::MessageTypeText ||
+ type == WebSocketHandle::MessageTypeBinary);
+ typedef WebSocket::MessageType MessageType;
+ COMPILE_ASSERT(
+ static_cast<MessageType>(WebSocketHandle::MessageTypeContinuation) ==
+ WebSocket::MESSAGE_TYPE_CONTINUATION,
+ enum_values_must_match_for_message_type);
+ COMPILE_ASSERT(
+ static_cast<MessageType>(WebSocketHandle::MessageTypeText) ==
+ WebSocket::MESSAGE_TYPE_TEXT,
+ enum_values_must_match_for_message_type);
+ COMPILE_ASSERT(
+ static_cast<MessageType>(WebSocketHandle::MessageTypeBinary) ==
+ WebSocket::MESSAGE_TYPE_BINARY,
+ enum_values_must_match_for_message_type);
+ return static_cast<WebSocket::MessageType>(type);
+ }
+};
+
+template<>
+struct TypeConverter<WebSocketHandle::MessageType, WebSocket::MessageType> {
+ static WebSocketHandle::MessageType Convert(WebSocket::MessageType type) {
+ DCHECK(type == WebSocket::MESSAGE_TYPE_CONTINUATION ||
+ type == WebSocket::MESSAGE_TYPE_TEXT ||
+ type == WebSocket::MESSAGE_TYPE_BINARY);
+ return static_cast<WebSocketHandle::MessageType>(type);
+ }
+};
+
+// This class forms a bridge from the mojo WebSocketClient interface and the
+// Blink WebSocketHandleClient interface.
+class WebSocketClientImpl : public InterfaceImpl<WebSocketClient> {
+ public:
+ explicit WebSocketClientImpl(WebSocketHandleImpl* handle,
+ blink::WebSocketHandleClient* client)
+ : handle_(handle), client_(client) {}
+ virtual ~WebSocketClientImpl() {}
+
+ private:
+ // WebSocketClient methods:
+ virtual void DidConnect(
+ bool fail,
+ const String& selected_subprotocol,
+ const String& extensions) OVERRIDE {
+ client_->didConnect(handle_,
+ fail,
+ selected_subprotocol.To<WebString>(),
+ extensions.To<WebString>());
+ }
+ virtual void DidReceiveData(bool fin,
+ WebSocket::MessageType type,
+ ScopedDataPipeConsumerHandle data_pipe) OVERRIDE {
+ uint32_t num_bytes;
+ ReadDataRaw(data_pipe.get(), NULL, &num_bytes, MOJO_READ_DATA_FLAG_QUERY);
+ std::vector<char> data(num_bytes);
+ ReadDataRaw(
+ data_pipe.get(), &data[0], &num_bytes, MOJO_READ_DATA_FLAG_NONE);
+ const char* data_ptr = data.empty() ? NULL : &data[0];
+ client_->didReceiveData(handle_,
+ fin,
+ ConvertTo<WebSocketHandle::MessageType>(type),
+ data_ptr,
+ data.size());
+ }
+
+ virtual void DidReceiveFlowControl(int64_t quota) OVERRIDE {
+ client_->didReceiveFlowControl(handle_, quota);
+ // |handle_| can be deleted here.
+ }
+
+ WebSocketHandleImpl* handle_;
+ blink::WebSocketHandleClient* client_;
+
+ DISALLOW_COPY_AND_ASSIGN(WebSocketClientImpl);
+};
+
+WebSocketHandleImpl::WebSocketHandleImpl(NetworkService* network_service)
+ : did_close_(false) {
+ network_service->CreateWebSocket(Get(&web_socket_));
+}
+
+WebSocketHandleImpl::~WebSocketHandleImpl() {
+ if (!did_close_) {
+ // The connection is abruptly disconnected by the renderer without
+ // closing handshake.
+ web_socket_->Close(WebSocket::kAbnormalCloseCode, String());
+ }
+}
+
+void WebSocketHandleImpl::connect(const WebURL& url,
+ const WebVector<WebString>& protocols,
+ const WebSerializedOrigin& origin,
+ WebSocketHandleClient* client) {
+ client_.reset(new WebSocketClientImpl(this, client));
+ WebSocketClientPtr client_ptr;
+ // TODO(mpcomplete): Is this the right ownership model? Or should mojo own
+ // |client_|?
+ WeakBindToProxy(client_.get(), &client_ptr);
+ web_socket_->Connect(url.string().utf8(),
+ Array<String>::From(protocols),
+ origin.string().utf8(),
+ client_ptr.Pass());
+}
+
+void WebSocketHandleImpl::send(bool fin,
+ WebSocketHandle::MessageType type,
+ const char* data,
+ size_t size) {
+ if (!client_)
+ return;
+
+ // TODO(mpcomplete): reuse the data pipe for subsequent sends.
+ uint32_t num_bytes = static_cast<uint32_t>(size);
+ MojoCreateDataPipeOptions options;
+ options.struct_size = sizeof(MojoCreateDataPipeOptions);
+ options.flags = MOJO_CREATE_DATA_PIPE_OPTIONS_FLAG_NONE;
+ options.element_num_bytes = 1;
+ options.capacity_num_bytes = num_bytes;
+ DataPipe data_pipe(options);
+ WriteDataRaw(data_pipe.producer_handle.get(),
+ data,
+ &num_bytes,
+ MOJO_WRITE_DATA_FLAG_ALL_OR_NONE);
+ web_socket_->Send(
+ fin,
+ ConvertTo<WebSocket::MessageType>(type),
+ data_pipe.consumer_handle.Pass());
+}
+
+void WebSocketHandleImpl::flowControl(int64_t quota) {
+ if (!client_)
+ return;
+
+ web_socket_->FlowControl(quota);
+}
+
+void WebSocketHandleImpl::close(unsigned short code, const WebString& reason) {
+ did_close_ = true;
+ web_socket_->Close(code, reason.utf8());
+}
+
+} // namespace mojo
« no previous file with comments | « mojo/services/html_viewer/websockethandle_impl.h ('k') | mojo/services/network/BUILD.gn » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698