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

Unified Diff: mojo/service_manager/service_manager.cc

Issue 423963004: First cut at "content handling" support in Mojo. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Addressed Dave's comments, plus added a --content-handlers switch Created 6 years, 4 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/service_manager/service_manager.h ('k') | mojo/service_manager/service_manager_unittest.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: mojo/service_manager/service_manager.cc
diff --git a/mojo/service_manager/service_manager.cc b/mojo/service_manager/service_manager.cc
index 0f13cfde6b375231d69db0fdd336a8d5a1f18788..6676cc6679f4b0cade83e74483eb6c80df7b2106 100644
--- a/mojo/service_manager/service_manager.cc
+++ b/mojo/service_manager/service_manager.cc
@@ -2,16 +2,18 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
-#include <stdio.h>
-
#include "mojo/service_manager/service_manager.h"
+#include <stdio.h>
+
+#include "base/bind.h"
#include "base/lazy_instance.h"
#include "base/logging.h"
#include "base/macros.h"
#include "base/stl_util.h"
#include "mojo/common/common_type_converters.h"
#include "mojo/service_manager/service_loader.h"
+#include "mojo/services/public/interfaces/content_handler/content_handler.mojom.h"
namespace mojo {
@@ -31,7 +33,54 @@ class StubServiceProvider : public InterfaceImpl<ServiceProvider> {
ScopedMessagePipeHandle client_handle) MOJO_OVERRIDE {}
};
-}
+} // namespace
+
+class ServiceManager::LoadServiceCallbacksImpl
+ : public ServiceLoader::LoadServiceCallbacks {
+ public:
+ LoadServiceCallbacksImpl(base::WeakPtr<ServiceManager> manager,
+ const GURL& requested_url,
+ const GURL& requestor_url,
+ ServiceProviderPtr service_provider)
+ : manager_(manager),
+ requested_url_(requested_url),
+ requestor_url_(requestor_url),
+ service_provider_(service_provider.Pass()) {
+ }
+
+ private:
+ virtual ~LoadServiceCallbacksImpl() {
+ }
+
+ // LoadServiceCallbacks implementation
+ virtual ScopedMessagePipeHandle RegisterApplication() OVERRIDE {
+ ScopedMessagePipeHandle shell_handle;
+ if (manager_) {
+ manager_->RegisterLoadedApplication(requested_url_,
+ requestor_url_,
+ service_provider_.Pass(),
+ &shell_handle);
+ }
+ return shell_handle.Pass();
+ }
+
+ virtual void LoadWithContentHandler(
+ const GURL& content_handler_url,
+ URLResponsePtr content) OVERRIDE {
+ if (manager_) {
+ manager_->LoadWithContentHandler(requested_url_,
+ requestor_url_,
+ content_handler_url,
+ content.Pass(),
+ service_provider_.Pass());
+ }
+ }
+
+ base::WeakPtr<ServiceManager> manager_;
+ GURL requested_url_;
+ GURL requestor_url_;
+ ServiceProviderPtr service_provider_;
+};
class ServiceManager::ShellImpl : public InterfaceImpl<Shell> {
public:
@@ -74,6 +123,24 @@ class ServiceManager::ShellImpl : public InterfaceImpl<Shell> {
DISALLOW_COPY_AND_ASSIGN(ShellImpl);
};
+struct ServiceManager::ContentHandlerConnection {
+ ContentHandlerConnection(ServiceManager* manager,
+ const GURL& content_handler_url) {
+ ServiceProviderPtr service_provider;
+ BindToProxy(&service_provider_impl, &service_provider);
+ manager->ConnectToApplication(content_handler_url,
+ GURL(),
+ service_provider.Pass());
+ MessagePipe pipe;
+ content_handler.Bind(pipe.handle0.Pass());
+ service_provider_impl.client()->ConnectToService(ContentHandler::Name_,
+ pipe.handle1.Pass());
+ }
+
+ StubServiceProvider service_provider_impl;
+ ContentHandlerPtr content_handler;
+};
+
// static
ServiceManager::TestAPI::TestAPI(ServiceManager* manager) : manager_(manager) {
}
@@ -90,10 +157,13 @@ bool ServiceManager::TestAPI::HasFactoryForURL(const GURL& url) const {
manager_->url_to_shell_impl_.end();
}
-ServiceManager::ServiceManager() : interceptor_(NULL) {
+ServiceManager::ServiceManager()
+ : interceptor_(NULL),
+ weak_ptr_factory_(this) {
}
ServiceManager::~ServiceManager() {
+ STLDeleteValues(&url_to_content_handler_);
tim (not reviewing) 2014/08/05 20:45:55 Are connections you're adding here for content han
Aaron Boodman 2014/08/05 22:45:34 Yes, content handlers are also normal mojo applica
TerminateShellConnections();
STLDeleteValues(&url_to_loader_);
STLDeleteValues(&scheme_to_loader_);
@@ -115,15 +185,24 @@ void ServiceManager::ConnectToApplication(const GURL& url,
const GURL& requestor_url,
ServiceProviderPtr service_provider) {
URLToShellImplMap::const_iterator shell_it = url_to_shell_impl_.find(url);
- ShellImpl* shell_impl;
if (shell_it != url_to_shell_impl_.end()) {
- shell_impl = shell_it->second;
- } else {
- MessagePipe pipe;
- GetLoaderForURL(url)->LoadService(this, url, pipe.handle0.Pass());
- shell_impl = WeakBindToPipe(new ShellImpl(this, url), pipe.handle1.Pass());
- url_to_shell_impl_[url] = shell_impl;
+ ConnectToClient(shell_it->second, url, requestor_url,
+ service_provider.Pass());
+ return;
}
+
+ scoped_refptr<LoadServiceCallbacksImpl> callbacks(
+ new LoadServiceCallbacksImpl(weak_ptr_factory_.GetWeakPtr(),
+ url,
+ requestor_url,
+ service_provider.Pass()));
+ GetLoaderForURL(url)->LoadService(this, url, callbacks);
+}
+
+void ServiceManager::ConnectToClient(ShellImpl* shell_impl,
+ const GURL& url,
+ const GURL& requestor_url,
+ ServiceProviderPtr service_provider) {
if (interceptor_) {
shell_impl->ConnectToClient(
requestor_url,
@@ -133,6 +212,48 @@ void ServiceManager::ConnectToApplication(const GURL& url,
}
}
+void ServiceManager::RegisterLoadedApplication(
+ const GURL& url,
+ const GURL& requestor_url,
+ ServiceProviderPtr service_provider,
+ ScopedMessagePipeHandle* shell_handle) {
+ ShellImpl* shell_impl = NULL;
+ URLToShellImplMap::iterator iter = url_to_shell_impl_.find(url);
+ if (iter != url_to_shell_impl_.end()) {
+ // This can happen because services are loaded asynchronously. So if we get
+ // two requests for the same service close to each other, we might get here
+ // and find that we already have it.
+ shell_impl = iter->second;
+ } else {
+ MessagePipe pipe;
+ shell_impl = WeakBindToPipe(new ShellImpl(this, url), pipe.handle1.Pass());
+ url_to_shell_impl_[url] = shell_impl;
+ *shell_handle = pipe.handle0.Pass();
+ }
+
+ ConnectToClient(shell_impl, url, requestor_url, service_provider.Pass());
+}
+
+void ServiceManager::LoadWithContentHandler(
+ const GURL& content_url,
+ const GURL& requestor_url,
+ const GURL& content_handler_url,
+ URLResponsePtr content,
+ ServiceProviderPtr service_provider) {
+ ContentHandlerConnection* connection = NULL;
+ URLToContentHandlerMap::iterator iter =
+ url_to_content_handler_.find(content_handler_url);
+ if (iter != url_to_content_handler_.end()) {
+ connection = iter->second;
+ } else {
+ connection = new ContentHandlerConnection(this, content_handler_url);
+ url_to_content_handler_[content_handler_url] = connection;
+ }
+ connection->content_handler->OnConnect(content_url.spec(),
+ content.Pass(),
+ service_provider.Pass());
+}
+
void ServiceManager::SetLoaderForURL(scoped_ptr<ServiceLoader> loader,
const GURL& url) {
URLToLoaderMap::iterator it = url_to_loader_.find(url);
« no previous file with comments | « mojo/service_manager/service_manager.h ('k') | mojo/service_manager/service_manager_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698