1b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)// Copyright 2013 The Chromium Authors. All rights reserved. 2b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 3b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)// found in the LICENSE file. 4b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) 5b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "chrome/browser/ui/webui/sync_file_system_internals/sync_file_system_internals_handler.h" 6b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) 7cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)#include <vector> 8cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) 9b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "base/bind.h" 10b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "base/bind_helpers.h" 11b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "base/values.h" 127d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "chrome/browser/drive/drive_notification_manager.h" 137d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "chrome/browser/drive/drive_notification_manager_factory.h" 14b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "chrome/browser/extensions/api/sync_file_system/sync_file_system_api_helpers.h" 15b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "chrome/browser/profiles/profile.h" 1690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include "chrome/browser/sync_file_system/logger.h" 17b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "chrome/browser/sync_file_system/sync_file_system_service.h" 18b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "chrome/browser/sync_file_system/sync_file_system_service_factory.h" 19b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "chrome/browser/sync_file_system/sync_service_state.h" 20b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "chrome/common/extensions/api/sync_file_system.h" 21b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "content/public/browser/storage_partition.h" 22b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "content/public/browser/web_ui.h" 23a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)#include "google_apis/drive/time_util.h" 24b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) 25eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdochusing drive::EventLogger; 26b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)using sync_file_system::SyncFileSystemServiceFactory; 27b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)using sync_file_system::SyncServiceState; 28b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) 29b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)namespace syncfs_internals { 30b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) 31b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)SyncFileSystemInternalsHandler::SyncFileSystemInternalsHandler(Profile* profile) 32cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) : profile_(profile), 33cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) observing_task_log_(false) { 345e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) sync_file_system::SyncFileSystemService* sync_service = 355e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) SyncFileSystemServiceFactory::GetForProfile(profile); 36effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (sync_service) 37effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch sync_service->AddSyncEventObserver(this); 385e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles)} 39b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) 405e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles)SyncFileSystemInternalsHandler::~SyncFileSystemInternalsHandler() { 415e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) sync_file_system::SyncFileSystemService* sync_service = 425e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) SyncFileSystemServiceFactory::GetForProfile(profile_); 43cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) if (!sync_service) 44cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) return; 45cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) sync_service->RemoveSyncEventObserver(this); 46cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) if (observing_task_log_) 47cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) sync_service->task_logger()->RemoveObserver(this); 485e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles)} 49b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) 50b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)void SyncFileSystemInternalsHandler::RegisterMessages() { 51b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) web_ui()->RegisterMessageCallback( 52b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) "getServiceStatus", 53b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) base::Bind(&SyncFileSystemInternalsHandler::GetServiceStatus, 54b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) base::Unretained(this))); 5590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) web_ui()->RegisterMessageCallback( 5690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) "getLog", 5790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) base::Bind(&SyncFileSystemInternalsHandler::GetLog, 5890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) base::Unretained(this))); 5990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) web_ui()->RegisterMessageCallback( 60a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles) "clearLogs", 61a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles) base::Bind(&SyncFileSystemInternalsHandler::ClearLogs, 62a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles) base::Unretained(this))); 63a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles) web_ui()->RegisterMessageCallback( 6490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) "getNotificationSource", 6590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) base::Bind(&SyncFileSystemInternalsHandler::GetNotificationSource, 6690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) base::Unretained(this))); 67cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) web_ui()->RegisterMessageCallback( 68cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) "observeTaskLog", 69cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) base::Bind(&SyncFileSystemInternalsHandler::ObserveTaskLog, 70cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) base::Unretained(this))); 71b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)} 72b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) 735e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles)void SyncFileSystemInternalsHandler::OnSyncStateUpdated( 745e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) const GURL& app_origin, 755e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) sync_file_system::SyncServiceState state, 765e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) const std::string& description) { 775e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) std::string state_string = extensions::api::sync_file_system::ToString( 785e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) extensions::SyncServiceStateToExtensionEnum(state)); 795e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) if (!description.empty()) 805e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) state_string += " (" + description + ")"; 815e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) 825e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) // TODO(calvinlo): OnSyncStateUpdated should be updated to also provide the 835e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) // notification mechanism (XMPP or Polling). 847d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) web_ui()->CallJavascriptFunction("SyncService.onGetServiceStatus", 855e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) base::StringValue(state_string)); 865e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles)} 875e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) 885e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles)void SyncFileSystemInternalsHandler::OnFileSynced( 8903b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) const storage::FileSystemURL& url, 905e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) sync_file_system::SyncFileStatus status, 915e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) sync_file_system::SyncAction action, 9203b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles) sync_file_system::SyncDirection direction) { 9303b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)} 945e3f23d412006dc4db4e659864679f29341e113fTorne (Richard Coles) 95cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)void SyncFileSystemInternalsHandler::OnLogRecorded( 96cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) const sync_file_system::TaskLogger::TaskLog& task_log) { 97cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) base::DictionaryValue dict; 98cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) int64 duration = (task_log.end_time - task_log.start_time).InMilliseconds(); 99cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) dict.SetInteger("duration", duration); 100cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) dict.SetString("task_description", task_log.task_description); 101cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) dict.SetString("result_description", task_log.result_description); 102cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) 103cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) scoped_ptr<base::ListValue> details(new base::ListValue); 104cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) details->AppendStrings(task_log.details); 105cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) dict.Set("details", details.release()); 10646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) web_ui()->CallJavascriptFunction("TaskLog.onTaskLogRecorded", dict); 107cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)} 108cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) 109b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)void SyncFileSystemInternalsHandler::GetServiceStatus( 110b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) const base::ListValue* args) { 111effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch SyncServiceState state_enum = sync_file_system::SYNC_SERVICE_DISABLED; 112effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch sync_file_system::SyncFileSystemService* sync_service = 113effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch SyncFileSystemServiceFactory::GetForProfile(profile_); 114effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (sync_service) 115effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch state_enum = sync_service->GetSyncServiceState(); 116effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch const std::string state_string = extensions::api::sync_file_system::ToString( 117b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) extensions::SyncServiceStateToExtensionEnum(state_enum)); 1187d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) web_ui()->CallJavascriptFunction("SyncService.onGetServiceStatus", 119b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) base::StringValue(state_string)); 120b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)} 121b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles) 12290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)void SyncFileSystemInternalsHandler::GetNotificationSource( 12390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) const base::ListValue* args) { 124eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch drive::DriveNotificationManager* drive_notification_manager = 125e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch drive::DriveNotificationManagerFactory::FindForBrowserContext(profile_); 126effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch if (!drive_notification_manager) 127effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch return; 12890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) bool xmpp_enabled = drive_notification_manager->push_notification_enabled(); 12990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) std::string notification_source = xmpp_enabled ? "XMPP" : "Polling"; 1307d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) web_ui()->CallJavascriptFunction("SyncService.onGetNotificationSource", 13190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) base::StringValue(notification_source)); 13290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)} 13390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) 13490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)void SyncFileSystemInternalsHandler::GetLog( 13590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) const base::ListValue* args) { 13690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) const std::vector<EventLogger::Event> log = 13790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) sync_file_system::util::GetLogHistory(); 13890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) 1397dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch int last_log_id_sent; 1407dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch if (!args->GetInteger(0, &last_log_id_sent)) 1417dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch last_log_id_sent = -1; 1427dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch 14390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) // Collate events which haven't been sent to WebUI yet. 14490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) base::ListValue list; 14590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) for (std::vector<EventLogger::Event>::const_iterator log_entry = log.begin(); 14690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) log_entry != log.end(); 14790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) ++log_entry) { 1487dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch if (log_entry->id <= last_log_id_sent) 14990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) continue; 15090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) 1515d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles) base::DictionaryValue* dict = new base::DictionaryValue; 1527dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch dict->SetInteger("id", log_entry->id); 15390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) dict->SetString("time", 15490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) google_apis::util::FormatTimeAsStringLocaltime(log_entry->when)); 15590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) dict->SetString("logEvent", log_entry->what); 15690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) list.Append(dict); 1577dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch last_log_id_sent = log_entry->id; 15890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) } 15990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) if (list.empty()) 16090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) return; 16190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) 1627d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) web_ui()->CallJavascriptFunction("SyncService.onGetLog", list); 16390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)} 16490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles) 165a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)void SyncFileSystemInternalsHandler::ClearLogs(const base::ListValue* args) { 166a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles) sync_file_system::util::ClearLog(); 167a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)} 168a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles) 169cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)void SyncFileSystemInternalsHandler::ObserveTaskLog( 170cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) const base::ListValue* args) { 171cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) sync_file_system::SyncFileSystemService* sync_service = 172cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) SyncFileSystemServiceFactory::GetForProfile(profile_); 173cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) if (!sync_service) 174cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) return; 175cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) if (!observing_task_log_) { 176cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) observing_task_log_ = true; 177cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) sync_service->task_logger()->AddObserver(this); 178cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) } 179cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) 18046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) DCHECK(sync_service->task_logger()); 181cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) const sync_file_system::TaskLogger::LogList& log = 182cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) sync_service->task_logger()->GetLog(); 18346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) 184cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) for (sync_file_system::TaskLogger::LogList::const_iterator itr = log.begin(); 185cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) itr != log.end(); ++itr) 186cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) OnLogRecorded(**itr); 187cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)} 188cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) 189b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)} // namespace syncfs_internals 190