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

Unified Diff: chrome/browser/chromeos/arc/fileapi/arc_file_system_operation_runner.cc

Issue 2715493002: mediaview: Support watchers in ArcFileSystemOperationRunner. (Closed)
Patch Set: Rebased to ToT. Created 3 years, 10 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
Index: chrome/browser/chromeos/arc/fileapi/arc_file_system_operation_runner.cc
diff --git a/chrome/browser/chromeos/arc/fileapi/arc_file_system_operation_runner.cc b/chrome/browser/chromeos/arc/fileapi/arc_file_system_operation_runner.cc
index 9e914c16f9b9ebc06ccca3ee45277ad827f8a7a1..161989d61b5d052c6bcd094bb28cc415edad721e 100644
--- a/chrome/browser/chromeos/arc/fileapi/arc_file_system_operation_runner.cc
+++ b/chrome/browser/chromeos/arc/fileapi/arc_file_system_operation_runner.cc
@@ -4,6 +4,8 @@
#include "chrome/browser/chromeos/arc/fileapi/arc_file_system_operation_runner.h"
+#include <utility>
+
#include "base/bind.h"
#include "base/location.h"
#include "base/memory/ptr_util.h"
@@ -18,6 +20,22 @@ using content::BrowserThread;
namespace arc {
+namespace {
+
+ArcFileSystemOperationRunner::ChangeType FromMojoChangeType(
+ mojom::ChangeType type) {
+ switch (type) {
+ case mojom::ChangeType::CHANGED:
+ return ArcFileSystemOperationRunner::ChangeType::CHANGED;
+ case mojom::ChangeType::DELETED:
+ return ArcFileSystemOperationRunner::ChangeType::DELETED;
dcheng 2017/02/28 06:56:32 Let's add a typemap for this.
Shuhei Takahashi 2017/03/01 09:10:08 Typemap sounds good and I tried adding one, but I
dcheng 2017/03/01 21:47:57 What's the error you're seeing?
Shuhei Takahashi 2017/03/02 02:05:01 Here's a WIP patch: https://codereview.chromium.or
+ }
+ NOTREACHED();
Luis Héctor Chávez 2017/03/06 17:10:48 nit: mention that the above switch is exhaustive,
+ return ArcFileSystemOperationRunner::ChangeType::CHANGED;
+}
+
+} // namespace
+
// static
const char ArcFileSystemOperationRunner::kArcServiceName[] =
"arc::ArcFileSystemOperationRunner";
@@ -42,27 +60,33 @@ ArcFileSystemOperationRunner::ArcFileSystemOperationRunner(
ArcFileSystemOperationRunner::ArcFileSystemOperationRunner(
ArcBridgeService* bridge_service,
const Profile* profile,
- bool observe_events)
+ bool set_should_defer_by_events)
: ArcService(bridge_service),
profile_(profile),
- observe_events_(observe_events),
+ set_should_defer_by_events_(set_should_defer_by_events),
+ binding_(this),
weak_ptr_factory_(this) {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
- if (observe_events_) {
- ArcSessionManager::Get()->AddObserver(this);
- arc_bridge_service()->file_system()->AddObserver(this);
- OnStateChanged();
- }
+ // We need to observe FileSystemInstance even in unit tests to call Init().
+ arc_bridge_service()->file_system()->AddObserver(this);
+
+ // ArcSessionManager may not exist in unit tests.
dcheng 2017/02/28 06:56:32 Nit: in many other parts of Chrome, null for testi
Shuhei Takahashi 2017/03/01 09:10:08 I totally agree checking null is not good, but we
+ auto* arc_session_manager = ArcSessionManager::Get();
+ if (arc_session_manager)
+ arc_session_manager->AddObserver(this);
+
+ OnStateChanged();
}
ArcFileSystemOperationRunner::~ArcFileSystemOperationRunner() {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
- if (observe_events_) {
- ArcSessionManager::Get()->RemoveObserver(this);
- arc_bridge_service()->file_system()->RemoveObserver(this);
- }
+ auto* arc_session_manager = ArcSessionManager::Get();
+ if (arc_session_manager)
+ arc_session_manager->AddObserver(this);
dcheng 2017/02/28 06:56:32 RemoveObserver?
Shuhei Takahashi 2017/03/01 09:10:08 Oops! Thanks for catching.
+
+ arc_bridge_service()->file_system()->RemoveObserver(this);
// On destruction, deferred operations are discarded.
}
@@ -150,6 +174,80 @@ void ArcFileSystemOperationRunner::GetChildDocuments(
callback);
}
+void ArcFileSystemOperationRunner::AddWatcher(
+ const std::string& authority,
+ const std::string& document_id,
+ const WatcherCallback& watcher_callback,
+ const AddWatcherCallback& callback) {
+ DCHECK_CURRENTLY_ON(BrowserThread::UI);
+ if (should_defer_) {
+ deferred_operations_.emplace_back(
+ base::Bind(&ArcFileSystemOperationRunner::AddWatcher,
+ weak_ptr_factory_.GetWeakPtr(), authority, document_id,
+ watcher_callback, callback));
+ return;
+ }
+ auto* file_system_instance = ARC_GET_INSTANCE_FOR_METHOD(
+ arc_bridge_service()->file_system(), AddWatcher);
+ if (!file_system_instance) {
+ base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE,
+ base::Bind(callback, -1));
+ return;
+ }
+ file_system_instance->AddWatcher(
+ authority, document_id,
+ base::Bind(&ArcFileSystemOperationRunner::OnWatcherAdded,
+ weak_ptr_factory_.GetWeakPtr(), watcher_callback, callback));
+}
+
+void ArcFileSystemOperationRunner::RemoveWatcher(
+ int64_t watcher_id,
+ const RemoveWatcherCallback& callback) {
+ DCHECK_CURRENTLY_ON(BrowserThread::UI);
+ // RemoveWatcher() is never deferred since watchers do not persist across
+ // container reboots.
+ if (should_defer_) {
+ base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE,
+ base::Bind(callback, false));
+ return;
+ }
+
+ // Unregister from |watcher_callbacks_| now because we will do it even if
+ // the remote method fails anyway. This is an implementation detail, so
+ // users must not assume registered callbacks are immediately invalidated.
+ auto iter = watcher_callbacks_.find(watcher_id);
+ if (iter == watcher_callbacks_.end()) {
+ base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE,
+ base::Bind(callback, false));
+ return;
+ }
+ watcher_callbacks_.erase(iter);
+
+ auto* file_system_instance = ARC_GET_INSTANCE_FOR_METHOD(
+ arc_bridge_service()->file_system(), AddWatcher);
+ if (!file_system_instance) {
+ base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE,
+ base::Bind(callback, false));
+ return;
+ }
+ file_system_instance->RemoveWatcher(watcher_id, callback);
+}
+
+void ArcFileSystemOperationRunner::OnDocumentChanged(int64_t watcher_id,
+ mojom::ChangeType type) {
+ DCHECK_CURRENTLY_ON(BrowserThread::UI);
+ auto iter = watcher_callbacks_.find(watcher_id);
+ if (iter == watcher_callbacks_.end()) {
+ // This may happen in a race condition with documents changes and
+ // RemoveWatcher().
+ return;
+ }
+ WatcherCallback watcher_callback = iter->second;
+ if (type == mojom::ChangeType::DELETED)
+ watcher_callbacks_.erase(watcher_id);
+ watcher_callback.Run(FromMojoChangeType(type));
+}
+
void ArcFileSystemOperationRunner::OnArcPlayStoreEnabledChanged(bool enabled) {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
OnStateChanged();
@@ -157,6 +255,10 @@ void ArcFileSystemOperationRunner::OnArcPlayStoreEnabledChanged(bool enabled) {
void ArcFileSystemOperationRunner::OnInstanceReady() {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
+ auto* file_system_instance =
+ ARC_GET_INSTANCE_FOR_METHOD(arc_bridge_service()->file_system(), Init);
+ if (file_system_instance)
+ file_system_instance->Init(binding_.CreateInterfacePtrAndBind());
OnStateChanged();
}
@@ -165,10 +267,26 @@ void ArcFileSystemOperationRunner::OnInstanceClosed() {
OnStateChanged();
}
+void ArcFileSystemOperationRunner::OnWatcherAdded(
+ const WatcherCallback& watcher_callback,
+ const AddWatcherCallback& callback,
+ int64_t watcher_id) {
+ DCHECK_CURRENTLY_ON(BrowserThread::UI);
+ if (watcher_id < 0) {
+ callback.Run(-1);
+ return;
+ }
+ DCHECK_EQ(0u, watcher_callbacks_.count(watcher_id));
dcheng 2017/02/28 06:56:32 As this is coming from a less-trusted container, w
Shuhei Takahashi 2017/03/01 09:10:08 Makes sense, done.
+ watcher_callbacks_.insert(std::make_pair(watcher_id, watcher_callback));
+ callback.Run(watcher_id);
+}
+
void ArcFileSystemOperationRunner::OnStateChanged() {
DCHECK_CURRENTLY_ON(BrowserThread::UI);
- SetShouldDefer(IsArcPlayStoreEnabledForProfile(profile_) &&
- !arc_bridge_service()->file_system()->has_instance());
+ if (set_should_defer_by_events_) {
+ SetShouldDefer(IsArcPlayStoreEnabledForProfile(profile_) &&
+ !arc_bridge_service()->file_system()->has_instance());
+ }
}
void ArcFileSystemOperationRunner::SetShouldDefer(bool should_defer) {

Powered by Google App Engine
This is Rietveld 408576698