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

Side by Side Diff: chrome/browser/chromeos/extensions/file_browser_private_api.cc

Issue 10834383: Chrome OS "open with" picker allowing Web Intents (Closed) Base URL: http://git.chromium.org/chromium/src.git@master
Patch Set: some fixes, haven't approached JS yet Created 8 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 unified diff | Download patch
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/chromeos/extensions/file_browser_private_api.h" 5 #include "chrome/browser/chromeos/extensions/file_browser_private_api.h"
6 6
7 #include <sys/statvfs.h> 7 #include <sys/statvfs.h>
8 #include <utility> 8 #include <utility>
9 9
10 #include "base/base64.h" 10 #include "base/base64.h"
11 #include "base/bind.h" 11 #include "base/bind.h"
12 #include "base/file_path.h"
13 #include "base/file_util.h"
14 #include "base/i18n/case_conversion.h"
12 #include "base/json/json_writer.h" 15 #include "base/json/json_writer.h"
13 #include "base/logging.h" 16 #include "base/logging.h"
14 #include "base/memory/scoped_vector.h" 17 #include "base/memory/scoped_vector.h"
15 #include "base/memory/singleton.h" 18 #include "base/memory/singleton.h"
16 #include "base/string_split.h" 19 #include "base/string_split.h"
17 #include "base/stringprintf.h" 20 #include "base/stringprintf.h"
18 #include "base/time.h" 21 #include "base/time.h"
19 #include "base/values.h" 22 #include "base/values.h"
23 #include "base/utf_string_conversions.h"
20 #include "chrome/browser/chromeos/cros/cros_library.h" 24 #include "chrome/browser/chromeos/cros/cros_library.h"
21 #include "chrome/browser/chromeos/cros/network_library.h" 25 #include "chrome/browser/chromeos/cros/network_library.h"
22 #include "chrome/browser/chromeos/extensions/file_handler_util.h" 26 #include "chrome/browser/chromeos/extensions/file_handler_util.h"
23 #include "chrome/browser/chromeos/extensions/file_manager_util.h" 27 #include "chrome/browser/chromeos/extensions/file_manager_util.h"
24 #include "chrome/browser/chromeos/gdata/drive.pb.h" 28 #include "chrome/browser/chromeos/gdata/drive.pb.h"
25 #include "chrome/browser/chromeos/gdata/drive_file_system_util.h" 29 #include "chrome/browser/chromeos/gdata/drive_file_system_util.h"
26 #include "chrome/browser/chromeos/gdata/drive_service_interface.h" 30 #include "chrome/browser/chromeos/gdata/drive_service_interface.h"
27 #include "chrome/browser/chromeos/gdata/drive_system_service.h" 31 #include "chrome/browser/chromeos/gdata/drive_system_service.h"
28 #include "chrome/browser/chromeos/gdata/drive_webapps_registry.h" 32 #include "chrome/browser/chromeos/gdata/drive_webapps_registry.h"
29 #include "chrome/browser/chromeos/gdata/gdata_util.h" 33 #include "chrome/browser/chromeos/gdata/gdata_util.h"
30 #include "chrome/browser/chromeos/gdata/gdata_wapi_parser.h" 34 #include "chrome/browser/chromeos/gdata/gdata_wapi_parser.h"
31 #include "chrome/browser/chromeos/system/statistics_provider.h" 35 #include "chrome/browser/chromeos/system/statistics_provider.h"
32 #include "chrome/browser/extensions/extension_function_dispatcher.h" 36 #include "chrome/browser/extensions/extension_function_dispatcher.h"
33 #include "chrome/browser/extensions/extension_process_manager.h" 37 #include "chrome/browser/extensions/extension_process_manager.h"
34 #include "chrome/browser/extensions/extension_service.h" 38 #include "chrome/browser/extensions/extension_service.h"
35 #include "chrome/browser/extensions/extension_tab_util.h" 39 #include "chrome/browser/extensions/extension_tab_util.h"
36 #include "chrome/browser/extensions/process_map.h" 40 #include "chrome/browser/extensions/process_map.h"
41 #include "chrome/browser/intents/web_intents_util.h"
37 #include "chrome/browser/google_apis/operation_registry.h" 42 #include "chrome/browser/google_apis/operation_registry.h"
38 #include "chrome/browser/profiles/profile.h" 43 #include "chrome/browser/profiles/profile.h"
39 #include "chrome/browser/ui/browser.h" 44 #include "chrome/browser/ui/browser.h"
40 #include "chrome/browser/ui/browser_window.h" 45 #include "chrome/browser/ui/browser_window.h"
41 #include "chrome/browser/ui/views/select_file_dialog_extension.h" 46 #include "chrome/browser/ui/views/select_file_dialog_extension.h"
42 #include "chrome/browser/ui/webui/extensions/extension_icon_source.h" 47 #include "chrome/browser/ui/webui/extensions/extension_icon_source.h"
43 #include "chrome/common/chrome_version_info.h" 48 #include "chrome/common/chrome_version_info.h"
44 #include "chrome/common/extensions/extension.h" 49 #include "chrome/common/extensions/extension.h"
45 #include "chrome/common/extensions/extension_constants.h" 50 #include "chrome/common/extensions/extension_constants.h"
46 #include "chrome/common/extensions/extension_icon_set.h" 51 #include "chrome/common/extensions/extension_icon_set.h"
47 #include "chrome/common/extensions/file_browser_handler.h" 52 #include "chrome/common/extensions/file_browser_handler.h"
48 #include "chrome/common/pref_names.h" 53 #include "chrome/common/pref_names.h"
49 #include "chromeos/disks/disk_mount_manager.h" 54 #include "chromeos/disks/disk_mount_manager.h"
50 #include "content/public/browser/child_process_security_policy.h" 55 #include "content/public/browser/child_process_security_policy.h"
51 #include "content/public/browser/render_process_host.h" 56 #include "content/public/browser/render_process_host.h"
52 #include "content/public/browser/render_view_host.h" 57 #include "content/public/browser/render_view_host.h"
53 #include "googleurl/src/gurl.h" 58 #include "googleurl/src/gurl.h"
54 #include "grit/generated_resources.h" 59 #include "grit/generated_resources.h"
55 #include "grit/platform_locale_settings.h" 60 #include "grit/platform_locale_settings.h"
56 #include "net/base/escape.h" 61 #include "net/base/escape.h"
62 #include "net/base/mime_util.h"
57 #include "ui/base/dialogs/selected_file_info.h" 63 #include "ui/base/dialogs/selected_file_info.h"
58 #include "ui/base/l10n/l10n_util.h" 64 #include "ui/base/l10n/l10n_util.h"
59 #include "webkit/chromeos/fileapi/cros_mount_point_provider.h" 65 #include "webkit/chromeos/fileapi/cros_mount_point_provider.h"
60 #include "webkit/fileapi/file_system_context.h" 66 #include "webkit/fileapi/file_system_context.h"
61 #include "webkit/fileapi/file_system_file_util.h" 67 #include "webkit/fileapi/file_system_file_util.h"
62 #include "webkit/fileapi/file_system_operation_context.h" 68 #include "webkit/fileapi/file_system_operation_context.h"
63 #include "webkit/fileapi/file_system_types.h" 69 #include "webkit/fileapi/file_system_types.h"
64 #include "webkit/fileapi/file_system_url.h" 70 #include "webkit/fileapi/file_system_url.h"
65 #include "webkit/fileapi/file_system_util.h" 71 #include "webkit/fileapi/file_system_util.h"
72 #include "webkit/glue/web_intent_service_data.h"
66 73
67 using chromeos::disks::DiskMountManager; 74 using chromeos::disks::DiskMountManager;
68 using content::BrowserContext; 75 using content::BrowserContext;
69 using content::BrowserThread; 76 using content::BrowserThread;
70 using content::ChildProcessSecurityPolicy; 77 using content::ChildProcessSecurityPolicy;
71 using content::SiteInstance; 78 using content::SiteInstance;
72 using content::WebContents; 79 using content::WebContents;
73 using extensions::Extension; 80 using extensions::Extension;
74 using file_handler_util::FileTaskExecutor; 81 using file_handler_util::FileTaskExecutor;
75 using gdata::InstalledApp; 82 using gdata::InstalledApp;
76 using gdata::OperationRegistry; 83 using gdata::OperationRegistry;
77 84
78 namespace { 85 namespace {
79 86
80 // Default icon path for drive docs. 87 // Default icon path for drive docs.
81 const char kDefaultDriveIcon[] = "images/filetype_generic.png"; 88 const char kDefaultIcon[] = "images/filetype_generic.png";
82 const int kPreferredIconSize = 16; 89 const int kPreferredIconSize = 16;
83 90
84 // Error messages. 91 // Error messages.
85 const char kFileError[] = "File error %d"; 92 const char kFileError[] = "File error %d";
86 const char kInvalidFileUrl[] = "Invalid file URL"; 93 const char kInvalidFileUrl[] = "Invalid file URL";
87 const char kVolumeDevicePathNotFound[] = "Device path not found"; 94 const char kVolumeDevicePathNotFound[] = "Device path not found";
88 95
89 // Unescape rules used for parsing query parameters. 96 // Unescape rules used for parsing query parameters.
90 const net::UnescapeRule::Type kUnescapeRuleForQueryParameters = 97 const net::UnescapeRule::Type kUnescapeRuleForQueryParameters =
91 net::UnescapeRule::SPACES | 98 net::UnescapeRule::SPACES |
(...skipping 136 matching lines...) Expand 10 before | Expand all | Expand 10 after
228 if (icons.empty()) 235 if (icons.empty())
229 return result; 236 return result;
230 result = icons.rbegin()->second; 237 result = icons.rbegin()->second;
231 for (InstalledApp::IconList::const_reverse_iterator iter = icons.rbegin(); 238 for (InstalledApp::IconList::const_reverse_iterator iter = icons.rbegin();
232 iter != icons.rend() && iter->first >= preferred_size; ++iter) { 239 iter != icons.rend() && iter->first >= preferred_size; ++iter) {
233 result = iter->second; 240 result = iter->second;
234 } 241 }
235 return result; 242 return result;
236 } 243 }
237 244
245 // Finds the title of the given Web Intents |action|, if the passed extension
246 // supports this action for all specified |mime_types|. Returns true and
247 // provides the |title| as output on success.
248 bool FindTitleForActionWithTypes(
249 const Extension* extension,
250 const std::string& action,
251 const std::set<std::string>& mime_types,
252 std::string* title) {
253 DCHECK(!mime_types.empty());
254 std::set<std::string> pending(mime_types.begin(), mime_types.end());
255 std::string found_title;
256
257 for (std::vector<webkit_glue::WebIntentServiceData>::const_iterator data =
258 extension->intents_services().begin();
259 data != extension->intents_services().end(); ++data) {
260 if (pending.empty())
261 break;
262
263 if (UTF16ToUTF8(data->action) != action)
264 continue;
265
266 std::set<std::string>::iterator pending_iter = pending.begin();
267 while (pending_iter != pending.end()) {
268 std::set<std::string>::iterator current = pending_iter++;
269 if (net::MatchesMimeType(UTF16ToUTF8(data->type), *pending_iter))
270 pending.erase(current);
271 }
272 if (found_title.empty())
273 found_title = UTF16ToUTF8(data->title);
274 }
275
276 if (!pending.empty())
277 return false; // we haven't found all mime-types
tbarzic 2012/09/16 04:26:11 nit: I'm more used to seeing comments before if li
thorogood 2012/09/18 02:13:02 Done (and I've removed the "we" form, since appare
278
279 *title = found_title;
280 return true;
281 }
282
238 // Retrieves total and remaining available size on |mount_path|. 283 // Retrieves total and remaining available size on |mount_path|.
239 void GetSizeStatsOnFileThread(const std::string& mount_path, 284 void GetSizeStatsOnFileThread(const std::string& mount_path,
240 size_t* total_size_kb, 285 size_t* total_size_kb,
241 size_t* remaining_size_kb) { 286 size_t* remaining_size_kb) {
242 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE)); 287 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE));
243 288
244 uint64_t total_size_in_bytes = 0; 289 uint64_t total_size_in_bytes = 0;
245 uint64_t remaining_size_in_bytes = 0; 290 uint64_t remaining_size_in_bytes = 0;
246 291
247 struct statvfs stat = {}; // Zero-clear 292 struct statvfs stat = {}; // Zero-clear
(...skipping 346 matching lines...) Expand 10 before | Expand all | Expand 10 after
594 file_iter->mime_type, &info); 639 file_iter->mime_type, &info);
595 std::vector<gdata::DriveWebAppInfo*> info_ptrs; 640 std::vector<gdata::DriveWebAppInfo*> info_ptrs;
596 info.release(&info_ptrs); // so they don't go away prematurely. 641 info.release(&info_ptrs); // so they don't go away prematurely.
597 std::set<std::string> tasks_for_this_file; 642 std::set<std::string> tasks_for_this_file;
598 for (std::vector<gdata::DriveWebAppInfo*>::iterator 643 for (std::vector<gdata::DriveWebAppInfo*>::iterator
599 apps = info_ptrs.begin(); apps != info_ptrs.end(); ++apps) { 644 apps = info_ptrs.begin(); apps != info_ptrs.end(); ++apps) {
600 std::pair<WebAppInfoMap::iterator, bool> insert_result = 645 std::pair<WebAppInfoMap::iterator, bool> insert_result =
601 app_info->insert(std::make_pair((*apps)->app_id, *apps)); 646 app_info->insert(std::make_pair((*apps)->app_id, *apps));
602 // TODO(gspencer): For now, the action id is always "open-with", but we 647 // TODO(gspencer): For now, the action id is always "open-with", but we
603 // could add any actions that the drive app supports. 648 // could add any actions that the drive app supports.
604 std::string task_id = 649 std::string task_id = file_handler_util::MakeTaskID(
605 file_handler_util::MakeDriveTaskID((*apps)->app_id, "open-with"); 650 (*apps)->app_id, file_handler_util::TASK_DRIVE, "open-with");
606 tasks_for_this_file.insert(task_id); 651 tasks_for_this_file.insert(task_id);
607 // If we failed to insert a task_id because there was a duplicate, then we 652 // If we failed to insert a task_id because there was a duplicate, then we
608 // must delete it (since we own it). 653 // must delete it (since we own it).
609 if (!insert_result.second) 654 if (!insert_result.second)
610 delete *apps; 655 delete *apps;
611 } 656 }
612 if (file_iter == file_info_list.begin()) { 657 if (file_iter == file_info_list.begin()) {
613 *available_tasks = tasks_for_this_file; 658 *available_tasks = tasks_for_this_file;
614 } else { 659 } else {
615 std::set<std::string> intersection; 660 std::set<std::string> intersection;
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
648 const std::set<std::string>& available_tasks, 693 const std::set<std::string>& available_tasks,
649 const std::set<std::string>& default_tasks, 694 const std::set<std::string>& default_tasks,
650 ListValue* result_list, 695 ListValue* result_list,
651 bool* default_already_set) { 696 bool* default_already_set) {
652 *default_already_set = false; 697 *default_already_set = false;
653 // OK, now we traverse the intersection of available applications for this 698 // OK, now we traverse the intersection of available applications for this
654 // list of files, adding a task for each one that is found. 699 // list of files, adding a task for each one that is found.
655 for (std::set<std::string>::const_iterator app_iter = available_tasks.begin(); 700 for (std::set<std::string>::const_iterator app_iter = available_tasks.begin();
656 app_iter != available_tasks.end(); ++app_iter) { 701 app_iter != available_tasks.end(); ++app_iter) {
657 std::string app_id; 702 std::string app_id;
658 bool result = file_handler_util::CrackDriveTaskID(*app_iter, &app_id, NULL); 703 file_handler_util::TaskType task_type;
704 bool result = file_handler_util::CrackTaskID(
705 *app_iter, &app_id, &task_type, NULL);
659 DCHECK(result) << "Unable to parse Drive task id: " << *app_iter; 706 DCHECK(result) << "Unable to parse Drive task id: " << *app_iter;
660 if (!result) 707 DCHECK_EQ(task_type, file_handler_util::TASK_DRIVE);
661 continue; 708
662 WebAppInfoMap::const_iterator info_iter = app_info.find(app_id); 709 WebAppInfoMap::const_iterator info_iter = app_info.find(app_id);
663 DCHECK(info_iter != app_info.end()); 710 DCHECK(info_iter != app_info.end());
664 gdata::DriveWebAppInfo* info = info_iter->second; 711 gdata::DriveWebAppInfo* info = info_iter->second;
665 DictionaryValue* task = new DictionaryValue; 712 DictionaryValue* task = new DictionaryValue;
666 713
667 task->SetString("taskId", *app_iter); 714 task->SetString("taskId", *app_iter);
668 task->SetString("title", info->app_name); 715 task->SetString("title", info->app_name);
669 716
670 GURL best_icon = FindPreferredIcon(info->app_icons, 717 GURL best_icon = FindPreferredIcon(info->app_icons,
671 kPreferredIconSize); 718 kPreferredIconSize);
(...skipping 27 matching lines...) Expand all
699 return true; 746 return true;
700 747
701 gdata::DriveSystemService* system_service = 748 gdata::DriveSystemService* system_service =
702 gdata::DriveSystemServiceFactory::GetForProfile(profile_); 749 gdata::DriveSystemServiceFactory::GetForProfile(profile_);
703 // |system_service| is NULL if incognito window / guest login. We return true 750 // |system_service| is NULL if incognito window / guest login. We return true
704 // in this case because there might be other extension tasks, even if we don't 751 // in this case because there might be other extension tasks, even if we don't
705 // have any to add. 752 // have any to add.
706 if (!system_service || !system_service->webapps_registry()) 753 if (!system_service || !system_service->webapps_registry())
707 return true; 754 return true;
708 755
709
710 gdata::DriveWebAppsRegistry* registry = system_service->webapps_registry(); 756 gdata::DriveWebAppsRegistry* registry = system_service->webapps_registry();
711 757
712 // Map of app_id to DriveWebAppInfo so we can look up the apps we've found 758 // Map of app_id to DriveWebAppInfo so we can look up the apps we've found
713 // after taking the intersection of available apps. 759 // after taking the intersection of available apps.
714 std::map<std::string, gdata::DriveWebAppInfo*> app_info; 760 std::map<std::string, gdata::DriveWebAppInfo*> app_info;
715 // Set of application IDs. This will end up with the intersection of the 761 // Set of application IDs. This will end up with the intersection of the
716 // application IDs that apply to the paths in |file_paths|. 762 // application IDs that apply to the paths in |file_paths|.
717 std::set<std::string> available_tasks; 763 std::set<std::string> available_tasks;
718 764
719 IntersectAvailableDriveTasks(registry, file_info_list, 765 IntersectAvailableDriveTasks(registry, file_info_list,
720 &app_info, &available_tasks); 766 &app_info, &available_tasks);
721 std::set<std::string> default_tasks; 767 std::set<std::string> default_tasks;
722 FindDefaultDriveTasks(file_info_list, available_tasks, &default_tasks); 768 FindDefaultDriveTasks(file_info_list, available_tasks, &default_tasks);
723 CreateDriveTasks(registry, app_info, available_tasks, default_tasks, 769 CreateDriveTasks(registry, app_info, available_tasks, default_tasks,
724 result_list, default_already_set); 770 result_list, default_already_set);
725 771
726 // We own the pointers in |app_info|, so we need to delete them. 772 // We own the pointers in |app_info|, so we need to delete them.
727 STLDeleteContainerPairSecondPointers(app_info.begin(), app_info.end()); 773 STLDeleteContainerPairSecondPointers(app_info.begin(), app_info.end());
728 return true; 774 return true;
729 } 775 }
730 776
777 // Find Web Intent platform apps that support the View task, and add them to
778 // the |result_list|. These will be marked as TASK_WEBINTENT.
779 bool GetFileTasksFileBrowserFunction::FindWebIntentTasks(
780 const std::vector<GURL>& file_urls,
781 ListValue* result_list) {
782 DCHECK(!file_urls.empty());
783 ExtensionService* service = profile_->GetExtensionService();
784 if (!service)
785 return false;
786
787 std::set<std::string> mime_types;
788 for (std::vector<GURL>::const_iterator iter = file_urls.begin();
789 iter != file_urls.end(); ++iter) {
790 const FilePath file = FilePath(GURL(iter->spec()).ExtractFileName());
791 const FilePath::StringType file_extension =
792 StringToLowerASCII(file.Extension());
793
794 // TODO(thorogood): Rearchitect this call so it can run on the File thread;
795 // GetMimeTypeFromFile requires this on Linux. Right now, we use
796 // Chrome-level knowledge only.
797 std::string mime_type;
798 if (file_extension.empty() || !net::GetWellKnownMimeTypeFromExtension(
799 file_extension.substr(1), &mime_type)) {
800 // If the file doesn't have an extension or its mime-type cannot be
801 // determined, then indicate that it has the empty mime-type. This will
802 // only be matched if the Web Intents accepts "*" or "*/*".
803 mime_types.insert("");
804 } else {
805 mime_types.insert(mime_type);
806 }
807 }
808
809 for (ExtensionSet::const_iterator iter = service->extensions()->begin();
810 iter != service->extensions()->end();
811 ++iter) {
812 const Extension* extension = *iter;
813
814 // We don't support using hosted apps to open files.
815 if (!extension->is_platform_app())
816 continue;
817
818 if (profile_->IsOffTheRecord() &&
819 !service->IsIncognitoEnabled(extension->id()))
820 continue;
821
822 std::string title;
823 if (!FindTitleForActionWithTypes(
824 extension, web_intents::kActionView, mime_types, &title))
825 continue;
826
827 DictionaryValue* task = new DictionaryValue;
828 std::string task_id = file_handler_util::MakeTaskID(extension->id(),
829 file_handler_util::TASK_WEBINTENT, web_intents::kActionView);
830 task->SetString("taskId", task_id);
831 task->SetString("title", title);
832 task->SetBoolean("isDefault", false);
833
834 GURL best_icon = extension->GetIconURL(kPreferredIconSize,
835 ExtensionIconSet::MATCH_BIGGER);
836 if (!best_icon.is_empty())
837 task->SetString("iconUrl", best_icon.spec());
838 else
839 task->SetString("iconUrl", kDefaultIcon);
840
841 task->SetBoolean("driveApp", false);
842 result_list->Append(task);
843 }
844
845 return true;
846 }
847
731 bool GetFileTasksFileBrowserFunction::RunImpl() { 848 bool GetFileTasksFileBrowserFunction::RunImpl() {
732 // First argument is the list of files to get tasks for. 849 // First argument is the list of files to get tasks for.
733 ListValue* files_list = NULL; 850 ListValue* files_list = NULL;
734 if (!args_->GetList(0, &files_list)) 851 if (!args_->GetList(0, &files_list))
735 return false; 852 return false;
736 853
737 // Second argument is the list of mime types of each of the files in the list. 854 // Second argument is the list of mime types of each of the files in the list.
738 ListValue* mime_types_list = NULL; 855 ListValue* mime_types_list = NULL;
739 if (!args_->GetList(1, &mime_types_list)) 856 if (!args_->GetList(1, &mime_types_list))
740 return false; 857 return false;
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
790 ExtensionService* service = profile_->GetExtensionService(); 907 ExtensionService* service = profile_->GetExtensionService();
791 for (std::set<const FileBrowserHandler*>::const_iterator iter = 908 for (std::set<const FileBrowserHandler*>::const_iterator iter =
792 common_tasks.begin(); 909 common_tasks.begin();
793 iter != common_tasks.end(); 910 iter != common_tasks.end();
794 ++iter) { 911 ++iter) {
795 const FileBrowserHandler* handler = *iter; 912 const FileBrowserHandler* handler = *iter;
796 const std::string extension_id = handler->extension_id(); 913 const std::string extension_id = handler->extension_id();
797 const Extension* extension = service->GetExtensionById(extension_id, false); 914 const Extension* extension = service->GetExtensionById(extension_id, false);
798 CHECK(extension); 915 CHECK(extension);
799 DictionaryValue* task = new DictionaryValue; 916 DictionaryValue* task = new DictionaryValue;
800 task->SetString("taskId", 917 task->SetString("taskId", file_handler_util::MakeTaskID(
801 file_handler_util::MakeTaskID(extension_id, handler->id())); 918 extension_id, file_handler_util::TASK_FILE, handler->id()));
802 task->SetString("title", handler->title()); 919 task->SetString("title", handler->title());
803 // TODO(zelidrag): Figure out how to expose icon URL that task defined in 920 // TODO(zelidrag): Figure out how to expose icon URL that task defined in
804 // manifest instead of the default extension icon. 921 // manifest instead of the default extension icon.
805 GURL icon = 922 GURL icon =
806 ExtensionIconSource::GetIconURL(extension, 923 ExtensionIconSource::GetIconURL(extension,
807 extension_misc::EXTENSION_ICON_BITTY, 924 extension_misc::EXTENSION_ICON_BITTY,
808 ExtensionIconSet::MATCH_BIGGER, 925 ExtensionIconSet::MATCH_BIGGER,
809 false, NULL); // grayscale 926 false, NULL); // grayscale
810 task->SetString("iconUrl", icon.spec()); 927 task->SetString("iconUrl", icon.spec());
811 task->SetBoolean("driveApp", false); 928 task->SetBoolean("driveApp", false);
812 929
813 // Only set the default if there isn't already a default set. 930 // Only set the default if there isn't already a default set.
814 if (!default_already_set && 931 if (!default_already_set &&
815 default_tasks.find(*iter) != default_tasks.end()) { 932 default_tasks.find(*iter) != default_tasks.end()) {
816 task->SetBoolean("isDefault", true); 933 task->SetBoolean("isDefault", true);
817 default_already_set = true; 934 default_already_set = true;
818 } else { 935 } else {
819 task->SetBoolean("isDefault", false); 936 task->SetBoolean("isDefault", false);
820 } 937 }
821 938
822 result_list->Append(task); 939 result_list->Append(task);
823 } 940 }
824 941
942 // Take the union of Web Intents (that platform apps may accept) and all
943 // previous Drive and extension tasks. As above, we know there aren't
944 // duplicates because they're entirely different kinds of tasks.
945 if (!FindWebIntentTasks(file_urls, result_list))
946 return false;
947
825 if (VLOG_IS_ON(1)) { 948 if (VLOG_IS_ON(1)) {
826 std::string result_json; 949 std::string result_json;
827 base::JSONWriter::WriteWithOptions( 950 base::JSONWriter::WriteWithOptions(
828 result_list, 951 result_list,
829 base::JSONWriter::OPTIONS_DO_NOT_ESCAPE | 952 base::JSONWriter::OPTIONS_DO_NOT_ESCAPE |
830 base::JSONWriter::OPTIONS_PRETTY_PRINT, 953 base::JSONWriter::OPTIONS_PRETTY_PRINT,
831 &result_json); 954 &result_json);
832 VLOG(1) << "GetFileTasks result:\n" << result_json; 955 VLOG(1) << "GetFileTasks result:\n" << result_json;
833 } 956 }
834 957
835 // TODO(zelidrag, serya): Add intent content tasks to result_list once we
836 // implement that API.
837 SendResponse(true); 958 SendResponse(true);
838 return true; 959 return true;
839 } 960 }
840 961
841 ExecuteTasksFileBrowserFunction::ExecuteTasksFileBrowserFunction() {} 962 ExecuteTasksFileBrowserFunction::ExecuteTasksFileBrowserFunction() {}
842 963
843 void ExecuteTasksFileBrowserFunction::OnTaskExecuted(bool success) { 964 void ExecuteTasksFileBrowserFunction::OnTaskExecuted(bool success) {
844 SendResponse(success); 965 SendResponse(success);
845 } 966 }
846 967
847 ExecuteTasksFileBrowserFunction::~ExecuteTasksFileBrowserFunction() {} 968 ExecuteTasksFileBrowserFunction::~ExecuteTasksFileBrowserFunction() {}
848 969
849 bool ExecuteTasksFileBrowserFunction::RunImpl() { 970 bool ExecuteTasksFileBrowserFunction::RunImpl() {
850 // First param is task id that was to the extension with getFileTasks call. 971 // First param is task id that was to the extension with getFileTasks call.
851 std::string task_id; 972 std::string task_id;
852 if (!args_->GetString(0, &task_id) || !task_id.size()) 973 if (!args_->GetString(0, &task_id) || !task_id.size())
853 return false; 974 return false;
854 975
855 // TODO(kaznacheev): Crack the task_id here, store it in the Executor 976 // TODO(kaznacheev): Crack the task_id here, store it in the Executor
856 // and avoid passing it around. 977 // and avoid passing it around.
857 978
858 // The second param is the list of files that need to be executed with this 979 // The second param is the list of files that need to be executed with this
859 // task. 980 // task.
860 ListValue* files_list = NULL; 981 ListValue* files_list = NULL;
861 if (!args_->GetList(1, &files_list)) 982 if (!args_->GetList(1, &files_list))
862 return false; 983 return false;
863 984
864 std::string extension_id; 985 std::string extension_id;
986 file_handler_util::TaskType task_type;
865 std::string action_id; 987 std::string action_id;
866 if (!file_handler_util::CrackTaskID(task_id, &extension_id, &action_id)) { 988 if (!file_handler_util::CrackTaskID(
989 task_id, &extension_id, &task_type, &action_id)) {
867 LOG(WARNING) << "Invalid task " << task_id; 990 LOG(WARNING) << "Invalid task " << task_id;
868 return false; 991 return false;
869 } 992 }
870 993
871 if (!files_list->GetSize()) 994 if (!files_list->GetSize())
872 return true; 995 return true;
873 996
874 std::vector<GURL> file_urls; 997 std::vector<GURL> file_urls;
875 for (size_t i = 0; i < files_list->GetSize(); i++) { 998 for (size_t i = 0; i < files_list->GetSize(); i++) {
876 std::string origin_file_url; 999 std::string origin_file_url;
877 if (!files_list->GetString(i, &origin_file_url)) { 1000 if (!files_list->GetString(i, &origin_file_url)) {
878 error_ = kInvalidFileUrl; 1001 error_ = kInvalidFileUrl;
879 return false; 1002 return false;
880 } 1003 }
881 file_urls.push_back(GURL(origin_file_url)); 1004 file_urls.push_back(GURL(origin_file_url));
882 } 1005 }
883 1006
884 scoped_refptr<FileTaskExecutor> executor( 1007 scoped_refptr<FileTaskExecutor> executor(
885 FileTaskExecutor::Create(profile(), 1008 FileTaskExecutor::Create(profile(),
886 source_url(), 1009 source_url(),
887 extension_id, 1010 extension_id,
1011 task_type,
888 action_id)); 1012 action_id));
889 1013
890 if (!executor->ExecuteAndNotify( 1014 if (!executor->ExecuteAndNotify(
891 file_urls, 1015 file_urls,
892 base::Bind(&ExecuteTasksFileBrowserFunction::OnTaskExecuted, this))) 1016 base::Bind(&ExecuteTasksFileBrowserFunction::OnTaskExecuted, this)))
893 return false; 1017 return false;
894 1018
895 SetResult(new base::FundamentalValue(true)); 1019 SetResult(new base::FundamentalValue(true));
896 return true; 1020 return true;
897 } 1021 }
(...skipping 1116 matching lines...) Expand 10 before | Expand all | Expand 10 after
2014 // Get drive WebApps that can accept this file. 2138 // Get drive WebApps that can accept this file.
2015 ScopedVector<gdata::DriveWebAppInfo> web_apps; 2139 ScopedVector<gdata::DriveWebAppInfo> web_apps;
2016 system_service->webapps_registry()->GetWebAppsForFile( 2140 system_service->webapps_registry()->GetWebAppsForFile(
2017 file_path, file_specific_info.content_mime_type(), &web_apps); 2141 file_path, file_specific_info.content_mime_type(), &web_apps);
2018 if (!web_apps.empty()) { 2142 if (!web_apps.empty()) {
2019 std::string default_task_id = file_handler_util::GetDefaultTaskIdFromPrefs( 2143 std::string default_task_id = file_handler_util::GetDefaultTaskIdFromPrefs(
2020 profile_, 2144 profile_,
2021 file_specific_info.content_mime_type(), 2145 file_specific_info.content_mime_type(),
2022 file_path.Extension()); 2146 file_path.Extension());
2023 std::string default_app_id; 2147 std::string default_app_id;
2024 file_handler_util::CrackDriveTaskID(default_task_id, &default_app_id, NULL); 2148 file_handler_util::CrackTaskID(
2149 default_task_id, &default_app_id, NULL, NULL);
2025 2150
2026 ListValue* apps = new ListValue(); 2151 ListValue* apps = new ListValue();
2027 property_dict->Set("driveApps", apps); 2152 property_dict->Set("driveApps", apps);
2028 for (ScopedVector<gdata::DriveWebAppInfo>::const_iterator it = 2153 for (ScopedVector<gdata::DriveWebAppInfo>::const_iterator it =
2029 web_apps.begin(); 2154 web_apps.begin();
2030 it != web_apps.end(); ++it) { 2155 it != web_apps.end(); ++it) {
2031 const gdata::DriveWebAppInfo* webapp_info = *it; 2156 const gdata::DriveWebAppInfo* webapp_info = *it;
2032 DictionaryValue* app = new DictionaryValue(); 2157 DictionaryValue* app = new DictionaryValue();
2033 app->SetString("appId", webapp_info->app_id); 2158 app->SetString("appId", webapp_info->app_id);
2034 app->SetString("appName", webapp_info->app_name); 2159 app->SetString("appName", webapp_info->app_name);
(...skipping 567 matching lines...) Expand 10 before | Expand all | Expand 10 after
2602 gdata::DriveSystemService* system_service = 2727 gdata::DriveSystemService* system_service =
2603 gdata::DriveSystemServiceFactory::GetForProfile(profile_); 2728 gdata::DriveSystemServiceFactory::GetForProfile(profile_);
2604 if (!system_service || !system_service->file_system()) 2729 if (!system_service || !system_service->file_system())
2605 return false; 2730 return false;
2606 2731
2607 FilePath directory_path = GetVirtualPathFromURL(GURL(file_url_as_string)); 2732 FilePath directory_path = GetVirtualPathFromURL(GURL(file_url_as_string));
2608 system_service->file_system()->RequestDirectoryRefresh(directory_path); 2733 system_service->file_system()->RequestDirectoryRefresh(directory_path);
2609 2734
2610 return true; 2735 return true;
2611 } 2736 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698