testing_automation_provider.cc revision eb525c5499e34cc9c4b825d6d9e75bb07cc06ace
12a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Copyright 2013 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/automation/testing_automation_provider.h"
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <map>
85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <set>
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <string>
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <vector>
115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/bind.h"
135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/bind_helpers.h"
145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/command_line.h"
152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "base/files/file_path.h"
165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/json/json_reader.h"
175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/json/json_writer.h"
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/json/string_escape.h"
195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/path_service.h"
202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "base/prefs/pref_service.h"
215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/process.h"
225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/process_util.h"
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/sequenced_task_runner.h"
24868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "base/strings/stringprintf.h"
25868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "base/strings/utf_string_conversions.h"
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/threading/thread_restrictions.h"
27eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch#include "base/time/time.h"
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/app/chrome_command_ids.h"
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/autocomplete/autocomplete_controller.h"
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/autocomplete/autocomplete_match.h"
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/autocomplete/autocomplete_result.h"
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/automation/automation_browser_tracker.h"
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/automation/automation_provider_json.h"
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/automation/automation_provider_list.h"
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/automation/automation_provider_observers.h"
365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/automation/automation_tab_tracker.h"
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/automation/automation_util.h"
385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/automation/automation_window_tracker.h"
395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/bookmarks/bookmark_model.h"
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/bookmarks/bookmark_model_factory.h"
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/bookmarks/bookmark_storage.h"
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/browser_process.h"
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/browser_shutdown.h"
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/content_settings/host_content_settings_map.h"
452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/devtools/devtools_window.h"
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/download/download_prefs.h"
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/download/download_service.h"
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/download/download_service_factory.h"
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/download/download_shelf.h"
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/download/save_package_file_picker.h"
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/browser_action_test_util.h"
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/crx_installer.h"
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/extension_action.h"
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/extension_action_manager.h"
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/extension_host.h"
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/extension_process_manager.h"
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/extension_service.h"
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/extension_system.h"
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/extension_tab_util.h"
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/unpacked_installer.h"
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/extensions/updater/extension_updater.h"
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/history/history_service_factory.h"
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/history/top_sites.h"
642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/infobars/confirm_infobar_delegate.h"
652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/infobars/infobar_service.h"
665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/lifetime/application_lifetime.h"
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/notifications/balloon.h"
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/notifications/balloon_collection.h"
692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/notifications/balloon_notification_ui_manager.h"
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/notifications/notification.h"
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/password_manager/password_store.h"
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/password_manager/password_store_change.h"
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/password_manager/password_store_factory.h"
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/platform_util.h"
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/plugins/plugin_prefs.h"
762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/printing/print_preview_dialog_controller.h"
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/profiles/profile.h"
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/profiles/profile_info_cache.h"
795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/profiles/profile_manager.h"
805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/search_engines/template_url.h"
815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/search_engines/template_url_service.h"
825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/search_engines/template_url_service_factory.h"
835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/sessions/session_service_factory.h"
845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/sessions/session_tab_helper.h"
855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/app_modal_dialogs/app_modal_dialog.h"
865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/app_modal_dialogs/app_modal_dialog_queue.h"
875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/app_modal_dialogs/javascript_app_modal_dialog.h"
885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/app_modal_dialogs/native_app_modal_dialog.h"
895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/bookmarks/bookmark_bar.h"
905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/browser_commands.h"
915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/browser_finder.h"
922a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/browser/ui/browser_iterator.h"
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/browser_list.h"
945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/browser_tabstrip.h"
955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/browser_window.h"
965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/extensions/application_launch.h"
975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/find_bar/find_bar.h"
985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/find_bar/find_bar_controller.h"
995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/fullscreen/fullscreen_controller.h"
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/fullscreen/fullscreen_exit_bubble_type.h"
1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/host_desktop.h"
1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/login/login_prompt.h"
1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/omnibox/location_bar.h"
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/omnibox/omnibox_edit_model.h"
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/omnibox/omnibox_view.h"
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/search_engines/keyword_editor_controller.h"
1075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/ui/startup/startup_types.h"
1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/automation_constants.h"
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/automation_id.h"
1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/automation_messages.h"
1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/chrome_constants.h"
1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/chrome_notification_types.h"
113eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch#include "chrome/common/chrome_paths.h"
1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/chrome_switches.h"
1152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/common/extensions/background_info.h"
1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/extensions/extension.h"
1172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "chrome/common/extensions/manifest_url_handler.h"
1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/extensions/permissions/permission_set.h"
11990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include "chrome/common/extensions/permissions/permissions_data.h"
1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/pref_names.h"
1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/common/render_messages.h"
1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/browser_child_process_host_iterator.h"
1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/child_process_data.h"
1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/favicon_status.h"
125b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)#include "content/public/browser/geolocation_provider.h"
1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/interstitial_page.h"
1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/interstitial_page_delegate.h"
1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/navigation_entry.h"
1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/notification_service.h"
1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/plugin_service.h"
1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/render_process_host.h"
1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/render_view_host.h"
1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/render_widget_host_view.h"
1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/browser/web_contents.h"
1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/common/child_process_host.h"
1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/common/common_param_traits.h"
137eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch#include "content/public/common/drop_data.h"
1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/common/geoposition.h"
1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "content/public/common/ssl_status.h"
140c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#include "extensions/browser/view_type_utils.h"
1412a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "extensions/common/url_pattern.h"
1422a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "extensions/common/url_pattern_set.h"
1435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/cookies/cookie_store.h"
1447d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "third_party/WebKit/public/web/WebInputEvent.h"
1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/base/events/event_constants.h"
1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/base/keycodes/keyboard_codes.h"
1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/base/ui_base_types.h"
1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "webkit/plugins/webplugininfo.h"
1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(ENABLE_CONFIGURATION_POLICY)
1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chrome/browser/policy/policy_service.h"
1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_CHROMEOS)
1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "chromeos/dbus/dbus_thread_manager.h"
1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
1575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_MACOSX)
159c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#include <mach/mach.h>
160c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#include <mach/mach_vm.h>
1615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
1625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if !defined(NO_TCMALLOC) && (defined(OS_LINUX) || defined(OS_CHROMEOS))
1645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "third_party/tcmalloc/chromium/src/gperftools/heap-profiler.h"
1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif  // !defined(NO_TCMALLOC) && (defined(OS_LINUX) || defined(OS_CHROMEOS))
1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using automation::Error;
1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using automation::ErrorCode;
1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using automation_util::SendErrorIfModalDialogActive;
1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::BrowserChildProcessHostIterator;
1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::BrowserContext;
1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::BrowserThread;
1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::ChildProcessHost;
1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::DownloadItem;
1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::DownloadManager;
1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::InterstitialPage;
1775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::NativeWebKeyboardEvent;
1785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::NavigationController;
1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::NavigationEntry;
1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::OpenURLParams;
1812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)using content::PluginService;
1825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::Referrer;
1835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::RenderViewHost;
1845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::SSLStatus;
1855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using content::WebContents;
1865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using extensions::Extension;
1875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using extensions::ExtensionActionManager;
1885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)using extensions::ExtensionList;
1892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)using extensions::Manifest;
1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace {
1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Helper to reply asynchronously if |automation| is still valid.
1945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SendSuccessReply(base::WeakPtr<AutomationProvider> automation,
1955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                      IPC::Message* reply_message) {
196868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  if (automation.get())
1975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(automation.get(), reply_message).SendSuccess(NULL);
1985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
1995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Helper to process the result of CanEnablePlugin.
2015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void DidEnablePlugin(base::WeakPtr<AutomationProvider> automation,
2025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     IPC::Message* reply_message,
2032a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                     const base::FilePath::StringType& path,
2045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     const std::string& error_msg,
2055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     bool did_enable) {
2065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (did_enable) {
2075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    SendSuccessReply(automation, reply_message);
2085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
209868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    if (automation.get()) {
210868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      AutomationJSONReply(automation.get(), reply_message)
211868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)          .SendError(base::StringPrintf(error_msg.c_str(), path.c_str()));
2125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
2135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
2145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Helper to resolve the overloading of PostTask.
2175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void PostTask(BrowserThread::ID id, const base::Closure& callback) {
2185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BrowserThread::PostTask(id, FROM_HERE, callback);
2195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class AutomationInterstitialPage : public content::InterstitialPageDelegate {
2225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
2235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationInterstitialPage(WebContents* tab,
2245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             const GURL& url,
2255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             const std::string& contents)
2265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      : contents_(contents) {
2275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    interstitial_page_ = InterstitialPage::Create(tab, true, url, this);
2285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    interstitial_page_->Show();
2295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
2305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  virtual std::string GetHTMLContents() OVERRIDE { return contents_; }
2325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private:
2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const std::string contents_;
2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  InterstitialPage* interstitial_page_;  // Owns us.
2365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DISALLOW_COPY_AND_ASSIGN(AutomationInterstitialPage);
2385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
2395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace
2415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)const int TestingAutomationProvider::kSynchronousCommands[] = {
2435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  IDC_HOME,
2445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  IDC_SELECT_NEXT_TAB,
2455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  IDC_SELECT_PREVIOUS_TAB,
2465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  IDC_SHOW_BOOKMARK_MANAGER,
2475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
2485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TestingAutomationProvider::TestingAutomationProvider(Profile* profile)
250eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch    : AutomationProvider(profile) {
2515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BrowserList::AddObserver(this);
2525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  registrar_.Add(this, chrome::NOTIFICATION_SESSION_END,
2535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                 content::NotificationService::AllSources());
2545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_CHROMEOS)
2555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AddChromeosObservers();
2565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)TestingAutomationProvider::~TestingAutomationProvider() {
2605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_CHROMEOS)
2615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RemoveChromeosObservers();
2625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
2635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BrowserList::RemoveObserver(this);
2645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)IPC::Channel::Mode TestingAutomationProvider::GetChannelMode(
2675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    bool use_named_interface) {
2685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (use_named_interface)
2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_POSIX)
2705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return IPC::Channel::MODE_OPEN_NAMED_SERVER;
2715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
2725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return IPC::Channel::MODE_NAMED_SERVER;
2735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
2745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  else
2755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return IPC::Channel::MODE_CLIENT;
2765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OnBrowserAdded(Browser* browser) {
2795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OnBrowserRemoved(Browser* browser) {
2825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if !defined(OS_CHROMEOS) && !defined(OS_MACOSX)
2835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // For backwards compatibility with the testing automation interface, we
2845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // want the automation provider (and hence the process) to go away when the
2855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // last browser goes away.
2862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // The automation layer doesn't support non-native desktops.
2872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (BrowserList::GetInstance(chrome::HOST_DESKTOP_TYPE_NATIVE)->empty() &&
2882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      !CommandLine::ForCurrentProcess()->HasSwitch(
2895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          switches::kKeepAliveForTest)) {
2905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // If you change this, update Observer for chrome::SESSION_END
2915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // below.
29290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    base::MessageLoop::current()->PostTask(
2935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        FROM_HERE,
2945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        base::Bind(&TestingAutomationProvider::OnRemoveProvider, this));
2955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
2965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif  // !defined(OS_CHROMEOS) && !defined(OS_MACOSX)
2975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
2985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
2995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::Observe(
3005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int type,
3015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const content::NotificationSource& source,
3025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const content::NotificationDetails& details) {
3035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK(type == chrome::NOTIFICATION_SESSION_END);
3045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // OnBrowserRemoved does a ReleaseLater. When session end is received we exit
3055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // before the task runs resulting in this object not being deleted. This
3065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Release balance out the Release scheduled by OnBrowserRemoved.
3075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Release();
3085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool TestingAutomationProvider::OnMessageReceived(
3115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const IPC::Message& message) {
3125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  base::ThreadRestrictions::ScopedAllowWait allow_wait;
3135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool handled = true;
3145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool deserialize_success = true;
3155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  IPC_BEGIN_MESSAGE_MAP_EX(TestingAutomationProvider,
3165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           message,
3175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           deserialize_success)
3185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(AutomationMsg_CloseBrowser, CloseBrowser)
3195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_ActivateTab, ActivateTab)
3205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(AutomationMsg_AppendTab, AppendTab)
3215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_GetMachPortCount, GetMachPortCount)
3225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_ActiveTabIndex, GetActiveTabIndex)
3235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(AutomationMsg_CloseTab, CloseTab)
3245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_GetCookies, GetCookies)
3255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(
3265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        AutomationMsg_NavigateToURLBlockUntilNavigationsComplete,
3275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        NavigateToURLBlockUntilNavigationsComplete)
3285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_NavigationAsync, NavigationAsync)
3295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(AutomationMsg_Reload, Reload)
3305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_BrowserWindowCount, GetBrowserWindowCount)
3315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_NormalBrowserWindowCount,
3325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        GetNormalBrowserWindowCount)
3335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_BrowserWindow, GetBrowserWindow)
3345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_WindowExecuteCommandAsync,
3355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        ExecuteBrowserCommandAsync)
3365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(AutomationMsg_WindowExecuteCommand,
3375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        ExecuteBrowserCommand)
3385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_TerminateSession, TerminateSession)
3395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_WindowViewBounds, WindowGetViewBounds)
3405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_SetWindowBounds, SetWindowBounds)
3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_TabCount, GetTabCount)
3425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_Type, GetType)
3435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_Tab, GetTab)
3445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_TabTitle, GetTabTitle)
3455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_TabIndex, GetTabIndex)
3465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_TabURL, GetTabURL)
3475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(AutomationMsg_DomOperation,
3485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                    ExecuteJavascript)
3495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(AutomationMsg_OpenNewBrowserWindowOfType,
3505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                    OpenNewBrowserWindowOfType)
3515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_WindowForBrowser, GetWindowForBrowser)
3525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_GetMetricEventDuration,
3535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        GetMetricEventDuration)
3545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_BringBrowserToFront, BringBrowserToFront)
3555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER(AutomationMsg_FindWindowVisibility,
3565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        GetFindWindowVisibility)
3575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(AutomationMsg_WaitForBookmarkModelToLoad,
3585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                    WaitForBookmarkModelToLoad)
3595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(
3605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        AutomationMsg_WaitForBrowserWindowCountToBecome,
3615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        WaitForBrowserWindowCountToBecome)
3625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(
3635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        AutomationMsg_GoBackBlockUntilNavigationsComplete,
3645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        GoBackBlockUntilNavigationsComplete)
3655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(
3665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        AutomationMsg_GoForwardBlockUntilNavigationsComplete,
3675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        GoForwardBlockUntilNavigationsComplete)
3685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(AutomationMsg_SendJSONRequest,
3695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                    SendJSONRequestWithBrowserIndex)
3705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(
3715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        AutomationMsg_SendJSONRequestWithBrowserHandle,
3725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        SendJSONRequestWithBrowserHandle)
3735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(AutomationMsg_WaitForTabCountToBecome,
3745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                    WaitForTabCountToBecome)
3755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(AutomationMsg_WaitForInfoBarCount,
3765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                    WaitForInfoBarCount)
3775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_HANDLER_DELAY_REPLY(
3785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        AutomationMsg_WaitForProcessLauncherThreadToGoIdle,
3795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        WaitForProcessLauncherThreadToGoIdle)
3805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC_MESSAGE_UNHANDLED(
3825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        handled = AutomationProvider::OnMessageReceived(message))
3835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  IPC_END_MESSAGE_MAP_EX()
3845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!deserialize_success)
3855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    OnMessageDeserializationFailure();
3865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return handled;
3875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OnChannelError() {
3905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!reinitialize_on_channel_error_ &&
3915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser_shutdown::GetShutdownType() == browser_shutdown::NOT_VALID) {
3922a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    chrome::AttemptExit();
3935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
3945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationProvider::OnChannelError();
3955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
3965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
3975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::CloseBrowser(int browser_handle,
3985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                             IPC::Message* reply_message) {
3995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!browser_tracker_->ContainsHandle(browser_handle))
4005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
4015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser = browser_tracker_->GetResource(browser_handle);
4035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new BrowserClosedNotificationObserver(browser, this, reply_message, false);
4045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser->window()->Close();
4055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ActivateTab(int handle,
4085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                            int at_index,
4095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                            int* status) {
4105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *status = -1;
4115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_tracker_->ContainsHandle(handle) && at_index > -1) {
4125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = browser_tracker_->GetResource(handle);
4132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    if (at_index >= 0 && at_index < browser->tab_strip_model()->count()) {
4142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->tab_strip_model()->ActivateTabAt(at_index, true);
4155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      *status = 0;
4165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
4175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
4185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::AppendTab(int handle,
4215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                          const GURL& url,
4225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                          IPC::Message* reply_message) {
4235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int append_tab_response = -1;  // -1 is the error code
4245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  TabAppendedNotificationObserver* observer = NULL;
4255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_tracker_->ContainsHandle(handle)) {
4275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = browser_tracker_->GetResource(handle);
4285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    observer = new TabAppendedNotificationObserver(browser, this,
4295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                   reply_message, false);
4302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    WebContents* contents =
4315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        chrome::AddSelectedTabWithURL(browser, url,
4325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                      content::PAGE_TRANSITION_TYPED);
4335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (contents) {
4345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      append_tab_response = GetIndexForNavigationController(
4352a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          &contents->GetController(), browser);
4365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
4375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
4385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (append_tab_response < 0) {
4405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Appending tab failed. Clean up and send failure response.
4415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (observer)
4435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      delete observer;
4445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationMsg_AppendTab::WriteReplyParams(reply_message,
4465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                              append_tab_response);
4475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Send(reply_message);
4485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
4495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetMachPortCount(int* port_count) {
4525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_MACOSX)
453c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  mach_port_name_array_t names;
454c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  mach_msg_type_number_t names_count;
455c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  mach_port_type_array_t types;
456c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  mach_msg_type_number_t types_count;
457c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)
458c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  mach_port_t port = mach_task_self();
459c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)
460c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  // A friendlier interface would allow NULL buffers to only get the counts.
461c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  kern_return_t kr = mach_port_names(port, &names, &names_count,
462c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)                                     &types, &types_count);
463c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  if (kr != KERN_SUCCESS) {
464c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)    *port_count = 0;
465c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)    return;
466c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  }
467c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)
468c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  // The documentation states this is an invariant.
469c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  DCHECK_EQ(names_count, types_count);
470c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  *port_count = names_count;
471c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)
472c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  mach_vm_deallocate(port, reinterpret_cast<mach_vm_address_t>(names),
473c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)      names_count * sizeof(mach_port_name_array_t));
474c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  mach_vm_deallocate(port, reinterpret_cast<mach_vm_address_t>(types),
475c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)      types_count * sizeof(mach_port_type_array_t));
4765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
4775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *port_count = 0;
4785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
4795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetActiveTabIndex(int handle,
4825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                  int* active_tab_index) {
4835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *active_tab_index = -1;  // -1 is the error code
4845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_tracker_->ContainsHandle(handle)) {
4855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = browser_tracker_->GetResource(handle);
4862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    *active_tab_index = browser->tab_strip_model()->active_index();
4875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
4885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
4895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
4905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::CloseTab(int tab_handle,
4915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                         bool wait_until_closed,
4925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                         IPC::Message* reply_message) {
4935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (tab_tracker_->ContainsHandle(tab_handle)) {
4945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NavigationController* controller = tab_tracker_->GetResource(tab_handle);
4952a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    Browser* browser = chrome::FindBrowserWithWebContents(
4965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        controller->GetWebContents());
4975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DCHECK(browser);
4985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    new TabClosedNotificationObserver(this, wait_until_closed, reply_message,
4995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                      false);
5002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    chrome::CloseWebContents(browser, controller->GetWebContents(), false);
5015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
5025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
5035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationMsg_CloseTab::WriteReplyParams(reply_message, false);
5055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Send(reply_message);
5065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetCookies(const GURL& url, int handle,
5095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                           int* value_size,
5105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                           std::string* value) {
5115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* contents = tab_tracker_->ContainsHandle(handle) ?
5125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      tab_tracker_->GetResource(handle)->GetWebContents() : NULL;
5135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  automation_util::GetCookies(url, contents, value_size, value);
5145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::NavigateToURLBlockUntilNavigationsComplete(
5175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int handle, const GURL& url, int number_of_navigations,
5185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
5195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (tab_tracker_->ContainsHandle(handle)) {
5205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NavigationController* tab = tab_tracker_->GetResource(handle);
5215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Simulate what a user would do. Activate the tab and then navigate.
5235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // We could allow navigating in a background tab in future.
5245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = FindAndActivateTab(tab);
5255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (browser) {
5275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new NavigationNotificationObserver(tab, this, reply_message,
5285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                         number_of_navigations, false, false);
5295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      // TODO(darin): avoid conversion to GURL.
5315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      OpenURLParams params(
5325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          url, Referrer(), CURRENT_TAB,
5335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          content::PageTransitionFromInt(
5345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)              content::PAGE_TRANSITION_TYPED |
5355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)              content::PAGE_TRANSITION_FROM_ADDRESS_BAR),
5365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          false);
5375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser->OpenURL(params);
5385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
5395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
5405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
5415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationMsg_NavigateToURLBlockUntilNavigationsComplete::WriteReplyParams(
5435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      reply_message, AUTOMATION_MSG_NAVIGATION_ERROR);
5445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Send(reply_message);
5455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::NavigationAsync(int handle,
5485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                const GURL& url,
5495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                bool* status) {
5505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *status = false;
5515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (tab_tracker_->ContainsHandle(handle)) {
5535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NavigationController* tab = tab_tracker_->GetResource(handle);
5545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Simulate what a user would do. Activate the tab and then navigate.
5565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // We could allow navigating in a background tab in future.
5575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = FindAndActivateTab(tab);
5585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (browser) {
5605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      // Don't add any listener unless a callback mechanism is desired.
5615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      // TODO(vibhor): Do this if such a requirement arises in future.
5625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      OpenURLParams params(
5635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          url, Referrer(), CURRENT_TAB,
5645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          content::PageTransitionFromInt(
5655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)              content::PAGE_TRANSITION_TYPED |
5665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)              content::PAGE_TRANSITION_FROM_ADDRESS_BAR),
5675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          false);
5685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser->OpenURL(params);
5695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      *status = true;
5705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
5715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
5725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::Reload(int handle,
5755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                       IPC::Message* reply_message) {
5765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (tab_tracker_->ContainsHandle(handle)) {
5775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NavigationController* tab = tab_tracker_->GetResource(handle);
5785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = FindAndActivateTab(tab);
5795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (chrome::IsCommandEnabled(browser, IDC_RELOAD)) {
5805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new NavigationNotificationObserver(
5815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          tab, this, reply_message, 1, false, false);
5825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      chrome::ExecuteCommand(browser, IDC_RELOAD);
5835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
5845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
5855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
5865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationMsg_Reload::WriteReplyParams(
5885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      reply_message, AUTOMATION_MSG_NAVIGATION_ERROR);
5895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Send(reply_message);
5905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetBrowserWindowCount(int* window_count) {
5932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // The automation layer doesn't support non-native desktops.
5942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  *window_count = static_cast<int>(BrowserList::GetInstance(
5952a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                      chrome::HOST_DESKTOP_TYPE_NATIVE)->size());
5965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
5985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetNormalBrowserWindowCount(int* window_count) {
5992a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  *window_count = static_cast<int>(chrome::GetTabbedBrowserCount(
6002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                      profile_, chrome::HOST_DESKTOP_TYPE_NATIVE));
6015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetBrowserWindow(int index, int* handle) {
6045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *handle = 0;
6055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser = automation_util::GetBrowserAt(index);
6065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser)
6075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *handle = browser_tracker_->Add(browser);
6085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ExecuteBrowserCommandAsync(int handle,
6115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                           int command,
6125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                           bool* success) {
6135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *success = false;
6145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!browser_tracker_->ContainsHandle(handle)) {
6155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    LOG(WARNING) << "Browser tracker does not contain handle: " << handle;
6165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
6175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
6185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser = browser_tracker_->GetResource(handle);
6195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!chrome::SupportsCommand(browser, command)) {
6205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    LOG(WARNING) << "Browser does not support command: " << command;
6215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
6225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
6235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!chrome::IsCommandEnabled(browser, command)) {
6245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    LOG(WARNING) << "Browser command not enabled: " << command;
6255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
6265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
6275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  chrome::ExecuteCommand(browser, command);
6285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *success = true;
6295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ExecuteBrowserCommand(
6325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int handle, int command, IPC::Message* reply_message) {
6335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_tracker_->ContainsHandle(handle)) {
6345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = browser_tracker_->GetResource(handle);
6355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (chrome::SupportsCommand(browser, command) &&
6365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        chrome::IsCommandEnabled(browser, command)) {
6375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      // First check if we can handle the command without using an observer.
6385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      for (size_t i = 0; i < arraysize(kSynchronousCommands); i++) {
6395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        if (command == kSynchronousCommands[i]) {
6405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          chrome::ExecuteCommand(browser, command);
6415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          AutomationMsg_WindowExecuteCommand::WriteReplyParams(reply_message,
6425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                               true);
6435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          Send(reply_message);
6445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          return;
6455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
6465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
6475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      // Use an observer if we have one, otherwise fail.
6495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (ExecuteBrowserCommandObserver::CreateAndRegisterObserver(
6505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          this, browser, command, reply_message, false)) {
6515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        chrome::ExecuteCommand(browser, command);
6525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
6535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
6545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
6555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
6565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationMsg_WindowExecuteCommand::WriteReplyParams(reply_message, false);
6575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Send(reply_message);
6585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
6595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WebkitMouseClick(DictionaryValue* args,
6615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                 IPC::Message* reply_message) {
6625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
6635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
6645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* view;
6665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
6675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetRenderViewFromJSONArgs(args, profile(), &view, &error)) {
6685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
6695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
6705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
6715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebKit::WebMouseEvent mouse_event;
6735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("x", &mouse_event.x) ||
6745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("y", &mouse_event.y)) {
6755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
6765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("(X,Y) coordinates missing or invalid");
6775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
6785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
6795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int button;
6815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("button", &button)) {
6825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
6835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("Mouse button missing or invalid");
6845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
6855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
6865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (button == automation::kLeftButton) {
6875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    mouse_event.button = WebKit::WebMouseEvent::ButtonLeft;
6885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (button == automation::kRightButton) {
6895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    mouse_event.button = WebKit::WebMouseEvent::ButtonRight;
6905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (button == automation::kMiddleButton) {
6915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    mouse_event.button = WebKit::WebMouseEvent::ButtonMiddle;
6925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
6935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
6945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("Invalid button press requested");
6955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
6965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
6975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
6985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseDown;
6995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.clickCount = 1;
7005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
7025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseUp;
7045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new InputEventAckNotificationObserver(this, reply_message, mouse_event.type,
7055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                        1);
7065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
7075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
7085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WebkitMouseMove(
7105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
7115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
7125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
7135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* view;
7155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
7165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetRenderViewFromJSONArgs(args, profile(), &view, &error)) {
7175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
7185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
7195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebKit::WebMouseEvent mouse_event;
7225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("x", &mouse_event.x) ||
7235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("y", &mouse_event.y)) {
7245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
7255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("(X,Y) coordinates missing or invalid");
7265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
7275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseMove;
7305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new InputEventAckNotificationObserver(this, reply_message, mouse_event.type,
7315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                        1);
7325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
7335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
7345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WebkitMouseDrag(DictionaryValue* args,
7365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                IPC::Message* reply_message) {
7375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
7385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
7395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* view;
7415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
7425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetRenderViewFromJSONArgs(args, profile(), &view, &error)) {
7435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
7445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
7455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebKit::WebMouseEvent mouse_event;
7485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int start_x, start_y, end_x, end_y;
7495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("start_x", &start_x) ||
7505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("start_y", &start_y) ||
7515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("end_x", &end_x) ||
7525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("end_y", &end_y)) {
7535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
7545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("Invalid start/end positions");
7555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
7565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseMove;
7595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Step 1- Move the mouse to the start position.
7605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.x = start_x;
7615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.y = start_y;
7625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
7635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Step 2- Left click mouse down, the mouse button is fixed.
7655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseDown;
7665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.button = WebKit::WebMouseEvent::ButtonLeft;
7675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.clickCount = 1;
7685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
7695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Step 3 - Move the mouse to the end position.
7715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseMove;
7725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.x = end_x;
7735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.y = end_y;
7745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.clickCount = 0;
7755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
7765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Step 4 - Release the left mouse button.
7785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseUp;
7795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.clickCount = 1;
7805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new InputEventAckNotificationObserver(this, reply_message, mouse_event.type,
7815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                        1);
7825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
7835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
7845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WebkitMouseButtonDown(
7865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
7875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
7885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
7895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* view;
7915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
7925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetRenderViewFromJSONArgs(args, profile(), &view, &error)) {
7935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
7945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
7955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
7965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
7975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebKit::WebMouseEvent mouse_event;
7985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("x", &mouse_event.x) ||
7995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("y", &mouse_event.y)) {
8005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
8015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("(X,Y) coordinates missing or invalid");
8025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
8035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
8045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseDown;
8065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.button = WebKit::WebMouseEvent::ButtonLeft;
8075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.clickCount = 1;
8085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new InputEventAckNotificationObserver(this, reply_message, mouse_event.type,
8095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                        1);
8105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
8115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
8125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WebkitMouseButtonUp(
8145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
8155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
8165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
8175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* view;
8195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
8205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetRenderViewFromJSONArgs(args, profile(), &view, &error)) {
8215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
8225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
8235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
8245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebKit::WebMouseEvent mouse_event;
8265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("x", &mouse_event.x) ||
8275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("y", &mouse_event.y)) {
8285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
8295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("(X,Y) coordinates missing or invalid");
8305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
8315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
8325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseUp;
8345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.button = WebKit::WebMouseEvent::ButtonLeft;
8355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.clickCount = 1;
8365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new InputEventAckNotificationObserver(this, reply_message, mouse_event.type,
8375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                        1);
8385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
8395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
8405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WebkitMouseDoubleClick(
8425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
8435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
8445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
8455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* view;
8475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
8485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetRenderViewFromJSONArgs(args, profile(), &view, &error)) {
8495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
8505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
8515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
8525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebKit::WebMouseEvent mouse_event;
8545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("x", &mouse_event.x) ||
8555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("y", &mouse_event.y)) {
8565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
8575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("(X,Y) coordinates missing or invalid");
8585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
8595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
8605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseDown;
8625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.button = WebKit::WebMouseEvent::ButtonLeft;
8635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.clickCount = 1;
8645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
8655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseUp;
8675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new InputEventAckNotificationObserver(this, reply_message, mouse_event.type,
8685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                        2);
8695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
8705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseDown;
8725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.clickCount = 2;
8735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
8745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  mouse_event.type = WebKit::WebInputEvent::MouseUp;
8765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardMouseEvent(mouse_event);
8775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
8785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::DragAndDropFilePaths(
8805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
8815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
8825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
8835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* view;
8855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
8865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetRenderViewFromJSONArgs(args, profile(), &view, &error)) {
8875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
8885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
8895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
8905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int x, y;
8925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("x", &x) || !args->GetInteger("y", &y)) {
8935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
8945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("(X,Y) coordinates missing or invalid");
8955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
8965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
8975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
8985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* paths = NULL;
8995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetList("paths", &paths)) {
9005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
9015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'paths' missing or invalid");
9025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
9035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
9045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Emulate drag and drop to set the file paths to the file upload control.
906eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  content::DropData drop_data;
9075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (size_t path_index = 0; path_index < paths->GetSize(); ++path_index) {
9085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    string16 path;
9095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!paths->GetString(path_index, &path)) {
9105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      AutomationJSONReply(this, reply_message)
9115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          .SendError("'paths' contains a non-string type");
9125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
9135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
9145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    drop_data.filenames.push_back(
916eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch        content::DropData::FileInfo(path, string16()));
9175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
9185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const gfx::Point client(x, y);
9205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // We don't set any values in screen variable because DragTarget*** ignore the
9215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // screen argument.
9225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const gfx::Point screen;
9235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int operations = 0;
9255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  operations |= WebKit::WebDragOperationCopy;
9265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  operations |= WebKit::WebDragOperationLink;
9275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  operations |= WebKit::WebDragOperationMove;
9285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->DragTargetDragEnter(
9305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      drop_data, client, screen,
9315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      static_cast<WebKit::WebDragOperationsMask>(operations), 0);
9325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new DragTargetDropAckNotificationObserver(this, reply_message);
9335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->DragTargetDrop(client, screen, 0);
9345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
9355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetTabCount(int handle, int* tab_count) {
9375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *tab_count = -1;  // -1 is the error code
9385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_tracker_->ContainsHandle(handle)) {
9405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = browser_tracker_->GetResource(handle);
9412a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    *tab_count = browser->tab_strip_model()->count();
9425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
9435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
9445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetType(int handle, int* type_as_int) {
9465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *type_as_int = -1;  // -1 is the error code
9475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_tracker_->ContainsHandle(handle)) {
9495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = browser_tracker_->GetResource(handle);
9505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *type_as_int = static_cast<int>(browser->type());
9515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
9525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
9535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetTab(int win_handle,
9555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                       int tab_index,
9565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                       int* tab_handle) {
9575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *tab_handle = 0;
9585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_tracker_->ContainsHandle(win_handle) && (tab_index >= 0)) {
9595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = browser_tracker_->GetResource(win_handle);
9602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    if (tab_index < browser->tab_strip_model()->count()) {
9612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      WebContents* web_contents =
9622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          browser->tab_strip_model()->GetWebContentsAt(tab_index);
9635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      *tab_handle = tab_tracker_->Add(&web_contents->GetController());
9645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
9655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
9665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
9675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetTabTitle(int handle,
9695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                            int* title_string_size,
9705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                            std::wstring* title) {
9715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *title_string_size = -1;  // -1 is the error code
9725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (tab_tracker_->ContainsHandle(handle)) {
9735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NavigationController* tab = tab_tracker_->GetResource(handle);
9745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NavigationEntry* entry = tab->GetActiveEntry();
9755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (entry != NULL) {
976c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)      *title = UTF16ToWideHack(entry->GetTitleForDisplay(std::string()));
9775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
9785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      *title = std::wstring();
9795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
9805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *title_string_size = static_cast<int>(title->size());
9815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
9825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
9835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetTabIndex(int handle, int* tabstrip_index) {
9855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *tabstrip_index = -1;  // -1 is the error code
9865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (tab_tracker_->ContainsHandle(handle)) {
9885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NavigationController* tab = tab_tracker_->GetResource(handle);
9892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    Browser* browser = chrome::FindBrowserWithWebContents(
9902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        tab->GetWebContents());
9912a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    *tabstrip_index = browser->tab_strip_model()->GetIndexOfWebContents(
9925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        tab->GetWebContents());
9935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
9945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
9955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
9965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetTabURL(int handle,
9975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                          bool* success,
9985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                          GURL* url) {
9995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *success = false;
10005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (tab_tracker_->ContainsHandle(handle)) {
10015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NavigationController* tab = tab_tracker_->GetResource(handle);
10025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Return what the user would see in the location bar.
10035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *url = tab->GetActiveEntry()->GetVirtualURL();
10045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *success = true;
10055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
10065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
10075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ExecuteJavascriptInRenderViewFrame(
10095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const string16& frame_xpath,
10105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const string16& script,
10115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message,
10125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    RenderViewHost* render_view_host) {
10135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Set the routing id of this message with the controller.
10145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This routing id needs to be remembered for the reverse
10155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // communication while sending back the response of
10165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // this javascript execution.
10175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  render_view_host->ExecuteJavascriptInWebFrame(
10185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      frame_xpath,
10195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      UTF8ToUTF16("window.domAutomationController.setAutomationId(0);"));
10205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  render_view_host->ExecuteJavascriptInWebFrame(
10215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      frame_xpath, script);
10225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
10235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ExecuteJavascript(
10255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int handle,
10265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const std::wstring& frame_xpath,
10275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const std::wstring& script,
10285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
10295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents = GetWebContentsForHandle(handle, NULL);
10305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!web_contents) {
10315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationMsg_DomOperation::WriteReplyParams(reply_message, std::string());
10325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Send(reply_message);
10335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
10345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
10355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new DomOperationMessageSender(this, reply_message, false);
10375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExecuteJavascriptInRenderViewFrame(WideToUTF16Hack(frame_xpath),
10385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                     WideToUTF16Hack(script), reply_message,
10395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                     web_contents->GetRenderViewHost());
10405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
10415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "OpenNewBrowserWindowWithNewProfile" }
10435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample output: {}
10445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OpenNewBrowserWindowWithNewProfile(
10455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args, IPC::Message* reply_message) {
10465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ProfileManager* profile_manager = g_browser_process->profile_manager();
10475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new BrowserOpenedWithNewProfileNotificationObserver(this, reply_message);
10485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  profile_manager->CreateMultiProfileAsync(
1049868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      string16(), string16(), ProfileManager::CreateCallback(), false);
10505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
10515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetMultiProfileInfo" }
10535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// See GetMultiProfileInfo() in pyauto.py for sample output.
10545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetMultiProfileInfo(
10555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args, IPC::Message* reply_message) {
10565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
10575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ProfileManager* profile_manager = g_browser_process->profile_manager();
10585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const ProfileInfoCache& profile_info_cache =
10595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      profile_manager->GetProfileInfoCache();
10605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->SetBoolean("enabled",
10615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      profile_manager->IsMultipleProfilesEnabled());
10625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* profiles = new ListValue;
10645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (size_t index = 0; index < profile_info_cache.GetNumberOfProfiles();
10655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)       ++index) {
10665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* item = new DictionaryValue;
10675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetString("name", profile_info_cache.GetNameOfProfileAtIndex(index));
10685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetString("path",
10695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                    profile_info_cache.GetPathOfProfileAtIndex(index).value());
10705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    profiles->Append(item);
10715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
10725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("profiles", profiles);
10735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(return_value.get());
10745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
10755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OpenNewBrowserWindowOfType(
10775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int type, bool show, IPC::Message* reply_message) {
10785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new BrowserOpenedNotificationObserver(this, reply_message, false);
10795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // We may have no current browser windows open so don't rely on
10805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // asking an existing browser to execute the IDC_NEWWINDOW command.
10815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser = new Browser(
10822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      Browser::CreateParams(static_cast<Browser::Type>(type), profile_,
10832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                            chrome::HOST_DESKTOP_TYPE_NATIVE));
10845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  chrome::AddBlankTabAt(browser, -1, true);
10855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (show)
10865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser->window()->Show();
10875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
10885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
10895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OpenNewBrowserWindow(
10905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
10915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
10925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool show;
10935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("show", &show)) {
10945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
10955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'show' missing or invalid.");
10965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
10975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
10985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new BrowserOpenedNotificationObserver(this, reply_message, true);
10995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser = new Browser(
11002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      Browser::CreateParams(Browser::TYPE_TABBED, profile_,
11012a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                            chrome::HOST_DESKTOP_TYPE_NATIVE));
11025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  chrome::AddBlankTabAt(browser, -1, true);
11035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (show)
11045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser->window()->Show();
11055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
11065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetBrowserWindowCountJSON(
11085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
11095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
11105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
11112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // The automation layer doesn't support non-native desktops.
11122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  dict.SetInteger("count",
11132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                  static_cast<int>(BrowserList::GetInstance(
11142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                      chrome::HOST_DESKTOP_TYPE_NATIVE)->size()));
11155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&dict);
11165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
11175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::CloseBrowserWindow(
11195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
11205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
11215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
11225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
11235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
11245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
11255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
11265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
11275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
11285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new BrowserClosedNotificationObserver(browser, this, reply_message, true);
11295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser->window()->Close();
11305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
11315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OpenProfileWindow(
11335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args, IPC::Message* reply_message) {
11345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ProfileManager* profile_manager = g_browser_process->profile_manager();
11352a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  base::FilePath::StringType path;
11365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("path", &path)) {
11375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
11385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Invalid or missing arg: 'path'");
11395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
11405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
11412a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  Profile* profile = profile_manager->GetProfileByPath(base::FilePath(path));
11425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!profile) {
11435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
11442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        base::StringPrintf("Invalid profile path: %s", path.c_str()));
11455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
11465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
11475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int num_loads;
11485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("num_loads", &num_loads)) {
11495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
11505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Invalid or missing arg: 'num_loads'");
11515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
11525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
11535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new BrowserOpenedWithExistingProfileNotificationObserver(
11545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this, reply_message, num_loads);
11555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ProfileManager::FindOrCreateNewWindowForProfile(
11565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      profile,
11575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      chrome::startup::IS_NOT_PROCESS_STARTUP,
11585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      chrome::startup::IS_NOT_FIRST_RUN,
11595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      chrome::HOST_DESKTOP_TYPE_NATIVE,
11605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      false);
11615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
11625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetWindowForBrowser(int browser_handle,
11645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                    bool* success,
11655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                    int* handle) {
11665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *success = false;
11675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *handle = 0;
11685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_tracker_->ContainsHandle(browser_handle)) {
11705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = browser_tracker_->GetResource(browser_handle);
11715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    gfx::NativeWindow win = browser->window()->GetNativeWindow();
11725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Add() returns the existing handle for the resource if any.
11735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *handle = window_tracker_->Add(win);
11745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *success = true;
11755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
11765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
11775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetMetricEventDuration(
11795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const std::string& event_name,
11805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int* duration_ms) {
11815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *duration_ms = metric_event_duration_observer_->GetEventDurationMs(
11825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      event_name);
11835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
11845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::BringBrowserToFront(int browser_handle,
11865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                    bool* success) {
11875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *success = false;
11885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_tracker_->ContainsHandle(browser_handle)) {
11895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = browser_tracker_->GetResource(browser_handle);
11905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser->window()->Activate();
11915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *success = true;
11925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
11935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
11945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
11955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetFindWindowVisibility(int handle,
11965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                        bool* visible) {
11975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  *visible = false;
11985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser = browser_tracker_->GetResource(handle);
11995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser) {
12005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    FindBarTesting* find_bar =
12015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        browser->GetFindBarController()->find_bar()->GetFindBarTesting();
12025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    find_bar->GetFindBarWindowInfo(NULL, visible);
12035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
12045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
12055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Bookmark bar visibility is based on the pref (e.g. is it in the toolbar).
12075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Presence in the NTP is signalled in |detached|.
12085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetBookmarkBarStatus(
12095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
12105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
12115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
12125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
12135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
12145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
12155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
12165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
12175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
12185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // browser->window()->IsBookmarkBarVisible() is not consistent across
12195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // platforms. bookmark_bar_state() also follows prefs::kShowBookmarkBar
12205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // and has a shared implementation on all platforms.
12215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
12225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("visible",
12235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  browser->bookmark_bar_state() == BookmarkBar::SHOW);
12245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("animating", browser->window()->IsBookmarkBarAnimating());
12255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("detached",
12265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  browser->bookmark_bar_state() == BookmarkBar::DETACHED);
12275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&dict);
12285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
12295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetBookmarksAsJSON(
12315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
12325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
12335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
12345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
12355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg, bookmarks_as_json;
12365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
12375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
12385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
12395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
12405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BookmarkModel* bookmark_model =
12415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BookmarkModelFactory::GetForProfile(browser->profile());
1242b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)  if (!bookmark_model->loaded()) {
12435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Bookmark model is not loaded");
12445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
12455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
12465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_refptr<BookmarkStorage> storage(
12475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new BookmarkStorage(browser->profile(),
12485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                          bookmark_model,
12497d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)                          browser->profile()->GetIOTaskRunner().get()));
12505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!storage->SerializeData(&bookmarks_as_json)) {
12515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Failed to serialize bookmarks");
12525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
12535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
12545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
12555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetString("bookmarks_as_json", bookmarks_as_json);
12565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&dict);
12575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
12585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WaitForBookmarkModelToLoad(
12605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int handle,
12615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
12625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_tracker_->ContainsHandle(handle)) {
12635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = browser_tracker_->GetResource(handle);
12645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    BookmarkModel* model =
12655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        BookmarkModelFactory::GetForProfile(browser->profile());
12665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationProviderBookmarkModelObserver* observer =
12675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        new AutomationProviderBookmarkModelObserver(this, reply_message,
12685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                    model, false);
1269b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)    if (model->loaded()) {
12705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      observer->ReleaseReply();
12715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      delete observer;
12725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      AutomationMsg_WaitForBookmarkModelToLoad::WriteReplyParams(
12735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          reply_message, true);
12745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      Send(reply_message);
12755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
12765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
12775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
12785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
12795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WaitForBookmarkModelToLoadJSON(
12805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
12815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
12825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
12835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg, bookmarks_as_json;
12845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
12855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error_msg);
12865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
12875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
12885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BookmarkModel* model =
12895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BookmarkModelFactory::GetForProfile(browser->profile());
12905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationProviderBookmarkModelObserver* observer =
12915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new AutomationProviderBookmarkModelObserver(this, reply_message, model,
12925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                  true);
1293b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)  if (model->loaded()) {
12945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    observer->ReleaseReply();
12955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    delete observer;
12965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendSuccess(NULL);
12975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
12985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
12995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
13005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::AddBookmark(
13025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
13035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
13045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
13055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
13065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg, url;
13075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 title;
13085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int parent_id, index;
13095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool folder;
13105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
13115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
13125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("is_folder", &folder)) {
13155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'is_folder' missing or invalid");
13165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!folder && !args->GetString("url", &url)) {
13195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'url' missing or invalid");
13205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("parent_id", &parent_id)) {
13235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'parent_id' missing or invalid");
13245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("index", &index)) {
13275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'index' missing or invalid");
13285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("title", &title)) {
13315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'title' missing or invalid");
13325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BookmarkModel* model =
13355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BookmarkModelFactory::GetForProfile(browser->profile());
1336b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)  if (!model->loaded()) {
13375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Bookmark model is not loaded");
13385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const BookmarkNode* parent = model->GetNodeByID(parent_id);
13415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!parent) {
13425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Failed to get parent bookmark node");
13435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const BookmarkNode* child;
13465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (folder) {
13475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    child = model->AddFolder(parent, index, title);
13485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
13495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    child = model->AddURL(parent, index, title, GURL(url));
13505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!child) {
13525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Failed to add bookmark");
13535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
13565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
13575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
13585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ReparentBookmark(DictionaryValue* args,
13595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                 IPC::Message* reply_message) {
13605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
13615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
13625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
13635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int new_parent_id, id, index;
13645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
13655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
13665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("id", &id)) {
13695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'id' missing or invalid");
13705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("new_parent_id", &new_parent_id)) {
13735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'new_parent_id' missing or invalid");
13745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("index", &index)) {
13775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'index' missing or invalid");
13785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BookmarkModel* model =
13815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BookmarkModelFactory::GetForProfile(browser->profile());
1382b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)  if (!model->loaded()) {
13835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Bookmark model is not loaded");
13845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const BookmarkNode* node = model->GetNodeByID(id);
13875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const BookmarkNode* new_parent = model->GetNodeByID(new_parent_id);
13885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!node) {
13895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Failed to get bookmark node");
13905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!new_parent) {
13935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Failed to get new parent bookmark node");
13945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
13955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
13965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  model->Move(node, new_parent, index);
13975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
13985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
13995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetBookmarkTitle(DictionaryValue* args,
14015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                 IPC::Message* reply_message) {
14025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
14035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
14045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
14055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 title;
14065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int id;
14075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
14085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
14095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("id", &id)) {
14125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'id' missing or invalid");
14135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("title", &title)) {
14165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'title' missing or invalid");
14175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BookmarkModel* model =
14205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BookmarkModelFactory::GetForProfile(browser->profile());
1421b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)  if (!model->loaded()) {
14225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Bookmark model is not loaded");
14235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const BookmarkNode* node = model->GetNodeByID(id);
14265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!node) {
14275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Failed to get bookmark node");
14285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  model->SetTitle(node, title);
14315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
14325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
14335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetBookmarkURL(DictionaryValue* args,
14355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                               IPC::Message* reply_message) {
14365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
14375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
14385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg, url;
14395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int id;
14405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
14415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
14425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("id", &id)) {
14455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'id' missing or invalid");
14465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("url", &url)) {
14495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'url' missing or invalid");
14505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BookmarkModel* model =
14535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BookmarkModelFactory::GetForProfile(browser->profile());
1454b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)  if (!model->loaded()) {
14555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Bookmark model is not loaded");
14565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const BookmarkNode* node = model->GetNodeByID(id);
14595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!node) {
14605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Failed to get bookmark node");
14615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  model->SetURL(node, GURL(url));
14645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
14655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
14665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
14675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::RemoveBookmark(DictionaryValue* args,
14685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                               IPC::Message* reply_message) {
14695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
14705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
14715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
14725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int id;
14735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
14745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
14755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("id", &id)) {
14785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'id' missing or invalid");
14795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BookmarkModel* model =
14825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BookmarkModelFactory::GetForProfile(browser->profile());
1483b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)  if (!model->loaded()) {
14845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Bookmark model is not loaded");
14855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const BookmarkNode* node = model->GetNodeByID(id);
14885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!node) {
14895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Failed to get bookmark node");
14905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const BookmarkNode* parent = node->parent();
14935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!parent) {
14945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Failed to get parent bookmark node");
14955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
14965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
14975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  model->Remove(parent, parent->GetIndexOf(node));
14985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
14995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
15005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WaitForBrowserWindowCountToBecome(
15025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int target_count,
15035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
15042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // The automation layer doesn't support non-native desktops.
15052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  int current_count = static_cast<int>(BrowserList::GetInstance(
15062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                          chrome::HOST_DESKTOP_TYPE_NATIVE)->size());
15072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (current_count == target_count) {
15085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationMsg_WaitForBrowserWindowCountToBecome::WriteReplyParams(
15095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        reply_message, true);
15105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Send(reply_message);
15115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
15125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
15135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Set up an observer (it will delete itself).
15155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new BrowserCountChangeNotificationObserver(target_count, this, reply_message);
15165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
15175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GoBackBlockUntilNavigationsComplete(
15195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int handle, int number_of_navigations, IPC::Message* reply_message) {
15205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (tab_tracker_->ContainsHandle(handle)) {
15215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NavigationController* tab = tab_tracker_->GetResource(handle);
15225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = FindAndActivateTab(tab);
15235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (chrome::IsCommandEnabled(browser, IDC_BACK)) {
15245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new NavigationNotificationObserver(tab, this, reply_message,
15255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                         number_of_navigations, false, false);
15265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      chrome::ExecuteCommand(browser, IDC_BACK);
15275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
15285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
15295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
15305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationMsg_GoBackBlockUntilNavigationsComplete::WriteReplyParams(
15325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      reply_message, AUTOMATION_MSG_NAVIGATION_ERROR);
15335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Send(reply_message);
15345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
15355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GoForwardBlockUntilNavigationsComplete(
15375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int handle, int number_of_navigations, IPC::Message* reply_message) {
15385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (tab_tracker_->ContainsHandle(handle)) {
15395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NavigationController* tab = tab_tracker_->GetResource(handle);
15405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = FindAndActivateTab(tab);
15415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (chrome::IsCommandEnabled(browser, IDC_FORWARD)) {
15425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new NavigationNotificationObserver(tab, this, reply_message,
15435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                         number_of_navigations, false, false);
15445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      chrome::ExecuteCommand(browser, IDC_FORWARD);
15455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
15465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
15475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
15485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationMsg_GoForwardBlockUntilNavigationsComplete::WriteReplyParams(
15505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      reply_message, AUTOMATION_MSG_NAVIGATION_ERROR);
15515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Send(reply_message);
15525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
15535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
15545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::BuildJSONHandlerMaps() {
15555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Map json commands to their handlers.
15565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ApplyAccelerator"] =
15575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ExecuteBrowserCommandAsyncJSON;
15585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["RunCommand"] =
15595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ExecuteBrowserCommandJSON;
15605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["IsMenuCommandEnabled"] =
15615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsMenuCommandEnabledJSON;
15625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ActivateTab"] =
15635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ActivateTabJSON;
15645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["BringBrowserToFront"] =
15655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::BringBrowserToFrontJSON;
15665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetIndicesFromTab"] =
15675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetIndicesFromTab;
15685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["NavigateToURL"] =
15695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::NavigateToURL;
15705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetActiveTabIndex"] =
15715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetActiveTabIndexJSON;
15725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["AppendTab"] =
15735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::AppendTabJSON;
15745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["OpenNewBrowserWindow"] =
15755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::OpenNewBrowserWindow;
15765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["CloseBrowserWindow"] =
15775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::CloseBrowserWindow;
15785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["WaitUntilNavigationCompletes"] =
15795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::WaitUntilNavigationCompletes;
15805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetLocalStatePrefsInfo"] =
15815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetLocalStatePrefsInfo;
15825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetLocalStatePrefs"] =
15835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetLocalStatePrefs;
15845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetPrefsInfo"] = &TestingAutomationProvider::GetPrefsInfo;
15855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetPrefs"] = &TestingAutomationProvider::SetPrefs;
15865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ExecuteJavascript"] =
15875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ExecuteJavascriptJSON;
15885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["AddDomEventObserver"] =
15895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::AddDomEventObserver;
15905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["RemoveEventObserver"] =
15915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::RemoveEventObserver;
15925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetNextEvent"] =
15935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetNextEvent;
15945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ClearEventQueue"] =
15955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ClearEventQueue;
15965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ExecuteJavascriptInRenderView"] =
15975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ExecuteJavascriptInRenderView;
15985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GoForward"] =
15995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GoForward;
16005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GoBack"] =
16015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GoBack;
16025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["Reload"] =
16035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ReloadJSON;
16045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["OpenFindInPage"] =
16055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::OpenFindInPage;
16065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["IsFindInPageVisible"] =
16075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsFindInPageVisible;
16085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetDownloadShelfVisible"] =
16095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetDownloadShelfVisibleJSON;
16105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["IsDownloadShelfVisible"] =
16115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsDownloadShelfVisibleJSON;
16125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetDownloadDirectory"] =
16135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetDownloadDirectoryJSON;
16145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetCookies"] =
16155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetCookiesJSON;
16165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["DeleteCookie"] =
16175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::DeleteCookieJSON;
16185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetCookie"] =
16195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetCookieJSON;
16205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetCookiesInBrowserContext"] =
16215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetCookiesInBrowserContext;
16225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["DeleteCookieInBrowserContext"] =
16235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::DeleteCookieInBrowserContext;
16245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetCookieInBrowserContext"] =
16255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetCookieInBrowserContext;
16265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["WaitForBookmarkModelToLoad"] =
16285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::WaitForBookmarkModelToLoadJSON;
16295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetBookmarksAsJSON"] =
16305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetBookmarksAsJSON;
16315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetBookmarkBarStatus"] =
16325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetBookmarkBarStatus;
16335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["AddBookmark"] =
16345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::AddBookmark;
16355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ReparentBookmark"] =
16365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ReparentBookmark;
16375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetBookmarkTitle"] =
16385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetBookmarkTitle;
16395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetBookmarkURL"] =
16405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetBookmarkURL;
16415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["RemoveBookmark"] =
16425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::RemoveBookmark;
16435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
16445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetTabIds"] =
16455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetTabIds;
16465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetViews"] =
16475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetViews;
16485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["IsTabIdValid"] =
16495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsTabIdValid;
16505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["DoesAutomationObjectExist"] =
16515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::DoesAutomationObjectExist;
16525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["CloseTab"] =
16535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::CloseTabJSON;
16545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetViewBounds"] =
16555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetViewBounds;
16565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["MaximizeView"] =
16575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::MaximizeView;
16585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["WebkitMouseMove"] =
16595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::WebkitMouseMove;
16605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["WebkitMouseClick"] =
16615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::WebkitMouseClick;
16625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["WebkitMouseDrag"] =
16635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::WebkitMouseDrag;
16645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["WebkitMouseButtonUp"] =
16655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::WebkitMouseButtonUp;
16665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["WebkitMouseButtonDown"] =
16675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::WebkitMouseButtonDown;
16685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["WebkitMouseDoubleClick"] =
16695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::WebkitMouseDoubleClick;
16705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["DragAndDropFilePaths"] =
16715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::DragAndDropFilePaths;
16725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SendWebkitKeyEvent"] =
16735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SendWebkitKeyEvent;
16745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ActivateTab"] =
16755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ActivateTabJSON;
16765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetAppModalDialogMessage"] =
16775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetAppModalDialogMessage;
16785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["AcceptOrDismissAppModalDialog"] =
16795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::AcceptOrDismissAppModalDialog;
16805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ActionOnSSLBlockingPage"] =
16815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ActionOnSSLBlockingPage;
16825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetSecurityState"] =
16835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetSecurityState;
16845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetChromeDriverAutomationVersion"] =
16855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetChromeDriverAutomationVersion;
16865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["IsPageActionVisible"] =
16875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsPageActionVisible;
16885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["CreateNewAutomationProvider"] =
16895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::CreateNewAutomationProvider;
16905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetBrowserWindowCount"] =
16915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetBrowserWindowCountJSON;
16925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetBrowserInfo"] =
16935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetBrowserInfo;
16945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetTabInfo"] =
16955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetTabInfo;
16965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetTabCount"] =
16975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetTabCountJSON;
16985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["OpenNewBrowserWindowWithNewProfile"] =
16995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::OpenNewBrowserWindowWithNewProfile;
17005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetMultiProfileInfo"] =
17015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetMultiProfileInfo;
17025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["OpenProfileWindow"] =
17035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::OpenProfileWindow;
17045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetProcessInfo"] =
17055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetProcessInfo;
17065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["RefreshPolicies"] =
17075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::RefreshPolicies;
17085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["InstallExtension"] =
17095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::InstallExtension;
17105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetExtensionsInfo"] =
17115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetExtensionsInfo;
17125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["UninstallExtensionById"] =
17135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::UninstallExtensionById;
17145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetExtensionStateById"] =
17155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetExtensionStateById;
17165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["TriggerPageActionById"] =
17175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::TriggerPageActionById;
17185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["TriggerBrowserActionById"] =
17195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::TriggerBrowserActionById;
17205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["UpdateExtensionsNow"] =
17215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::UpdateExtensionsNow;
17225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["OverrideGeoposition"] =
17235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::OverrideGeoposition;
17245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SimulateAsanMemoryBug"] =
17255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SimulateAsanMemoryBug;
17265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_CHROMEOS)
17285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["AcceptOOBENetworkScreen"] =
17295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::AcceptOOBENetworkScreen;
17305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["AcceptOOBEEula"] = &TestingAutomationProvider::AcceptOOBEEula;
17315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["CancelOOBEUpdate"] =
17325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::CancelOOBEUpdate;
17335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["PickUserImage"] = &TestingAutomationProvider::PickUserImage;
17345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SkipToLogin"] = &TestingAutomationProvider::SkipToLogin;
17355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetOOBEScreenInfo"] =
17365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetOOBEScreenInfo;
17375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetLoginInfo"] = &TestingAutomationProvider::GetLoginInfo;
17395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ShowCreateAccountUI"] =
17405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ShowCreateAccountUI;
17415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ExecuteJavascriptInOOBEWebUI"] =
17425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ExecuteJavascriptInOOBEWebUI;
17435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["LoginAsGuest"] = &TestingAutomationProvider::LoginAsGuest;
17445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SubmitLoginForm"] =
17455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SubmitLoginForm;
17465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["AddLoginEventObserver"] =
17475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::AddLoginEventObserver;
17485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SignOut"] = &TestingAutomationProvider::SignOut;
17495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["LockScreen"] = &TestingAutomationProvider::LockScreen;
17515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["UnlockScreen"] = &TestingAutomationProvider::UnlockScreen;
17525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SignoutInScreenLocker"] =
17535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SignoutInScreenLocker;
17545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetBatteryInfo"] = &TestingAutomationProvider::GetBatteryInfo;
17565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetNetworkInfo"] = &TestingAutomationProvider::GetNetworkInfo;
17585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["NetworkScan"] = &TestingAutomationProvider::NetworkScan;
17595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ToggleNetworkDevice"] =
17605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ToggleNetworkDevice;
17615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ConnectToCellularNetwork"] =
17625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ConnectToCellularNetwork;
17635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["DisconnectFromCellularNetwork"] =
17645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::DisconnectFromCellularNetwork;
17655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ConnectToWifiNetwork"] =
17665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ConnectToWifiNetwork;
17675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ConnectToHiddenWifiNetwork"] =
17685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ConnectToHiddenWifiNetwork;
17695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["DisconnectFromWifiNetwork"] =
17705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::DisconnectFromWifiNetwork;
17715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ForgetWifiNetwork"] =
17725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ForgetWifiNetwork;
17735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["AddPrivateNetwork"] =
17755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::AddPrivateNetwork;
17765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetPrivateNetworkInfo"] =
17775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetPrivateNetworkInfo;
17785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["ConnectToPrivateNetwork"] =
17795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::ConnectToPrivateNetwork;
17805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["DisconnectFromPrivateNetwork"] =
17815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::DisconnectFromPrivateNetwork;
17825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["EnableSpokenFeedback"] =
17845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::EnableSpokenFeedback;
17855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["IsSpokenFeedbackEnabled"] =
17865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsSpokenFeedbackEnabled;
17875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetTimeInfo"] = &TestingAutomationProvider::GetTimeInfo;
17895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetTimezone"] = &TestingAutomationProvider::SetTimezone;
17905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetUpdateInfo"] = &TestingAutomationProvider::GetUpdateInfo;
17925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["UpdateCheck"] = &TestingAutomationProvider::UpdateCheck;
17935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetReleaseTrack"] =
17945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetReleaseTrack;
17955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
17965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["GetVolumeInfo"] = &TestingAutomationProvider::GetVolumeInfo;
17975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetVolume"] = &TestingAutomationProvider::SetVolume;
17985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetMute"] = &TestingAutomationProvider::SetMute;
17995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["OpenCrosh"] = &TestingAutomationProvider::OpenCrosh;
18015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetProxySettings"] =
18025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetProxySettings;
18035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  handler_map_["SetSharedProxies"] =
18045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetSharedProxies;
18055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetTimeInfo"] =
18075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetTimeInfo;
18085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif  // defined(OS_CHROMEOS)
18095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["DisablePlugin"] =
18115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::DisablePlugin;
18125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["EnablePlugin"] =
18135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::EnablePlugin;
18145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetPluginsInfo"] =
18155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetPluginsInfo;
18165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetNavigationInfo"] =
18185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetNavigationInfo;
18195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["PerformActionOnInfobar"] =
18215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::PerformActionOnInfobar;
18225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetHistoryInfo"] =
18245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetHistoryInfo;
18255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetOmniboxInfo"] =
18275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetOmniboxInfo;
18285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["SetOmniboxText"] =
18295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetOmniboxText;
18305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["OmniboxAcceptInput"] =
18315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::OmniboxAcceptInput;
18325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["OmniboxMovePopupSelection"] =
18335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::OmniboxMovePopupSelection;
18345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["LoadSearchEngineInfo"] =
18365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::LoadSearchEngineInfo;
18375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetSearchEngineInfo"] =
18385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetSearchEngineInfo;
18395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["AddOrEditSearchEngine"] =
18405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::AddOrEditSearchEngine;
18415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["PerformActionOnSearchEngine"] =
18425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::PerformActionOnSearchEngine;
18435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["SetWindowDimensions"] =
18455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetWindowDimensions;
18465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetDownloadsInfo"] =
18485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetDownloadsInfo;
18495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["WaitForAllDownloadsToComplete"] =
18505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::WaitForAllDownloadsToComplete;
18515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["PerformActionOnDownload"] =
18525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::PerformActionOnDownload;
18535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetInitialLoadTimes"] =
18555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetInitialLoadTimes;
18565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["SaveTabContents"] =
18585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SaveTabContents;
18595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["AddSavedPassword"] =
18615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::AddSavedPassword;
18625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["RemoveSavedPassword"] =
18635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::RemoveSavedPassword;
18645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetSavedPasswords"] =
18655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetSavedPasswords;
18665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["FindInPage"] = &TestingAutomationProvider::FindInPage;
18685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetAllNotifications"] =
18705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetAllNotifications;
18715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["CloseNotification"] =
18725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::CloseNotification;
18735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["WaitForNotificationCount"] =
18745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::WaitForNotificationCount;
18755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetNTPInfo"] =
18775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetNTPInfo;
18785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["RemoveNTPMostVisitedThumbnail"] =
18795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::RemoveNTPMostVisitedThumbnail;
18805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["RestoreAllNTPMostVisitedThumbnails"] =
18815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::RestoreAllNTPMostVisitedThumbnails;
18825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["KillRendererProcess"] =
18845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::KillRendererProcess;
18855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["LaunchApp"] = &TestingAutomationProvider::LaunchApp;
18875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["SetAppLaunchType"] =
18885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::SetAppLaunchType;
18895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetV8HeapStats"] =
18915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetV8HeapStats;
18925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["GetFPS"] =
18935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::GetFPS;
18945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
18955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["IsFullscreenForBrowser"] =
18965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsFullscreenForBrowser;
18975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["IsFullscreenForTab"] =
18985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsFullscreenForTab;
18995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["IsMouseLocked"] =
19005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsMouseLocked;
19015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["IsMouseLockPermissionRequested"] =
19025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsMouseLockPermissionRequested;
19035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["IsFullscreenPermissionRequested"] =
19045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsFullscreenPermissionRequested;
19055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["IsFullscreenBubbleDisplayed"] =
19065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsFullscreenBubbleDisplayed;
19075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["IsFullscreenBubbleDisplayingButtons"] =
19085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::IsFullscreenBubbleDisplayingButtons;
19095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["AcceptCurrentFullscreenOrMouseLockRequest"] =
19105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::AcceptCurrentFullscreenOrMouseLockRequest;
19115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_handler_map_["DenyCurrentFullscreenOrMouseLockRequest"] =
19125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &TestingAutomationProvider::DenyCurrentFullscreenOrMouseLockRequest;
19135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
19145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)scoped_ptr<DictionaryValue> TestingAutomationProvider::ParseJSONRequestCommand(
19165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const std::string& json_request,
19175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    std::string* command,
19185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    std::string* error) {
19195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> dict_value;
19205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<Value> values(base::JSONReader::ReadAndReturnError(json_request,
19215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      base::JSON_ALLOW_TRAILING_COMMAS, NULL, error));
19225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (values.get()) {
19235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Make sure input is a dict with a string command.
19245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (values->GetType() != Value::TYPE_DICTIONARY) {
19255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      *error = "Command dictionary is not a dictionary.";
19265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
19275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      dict_value.reset(static_cast<DictionaryValue*>(values.release()));
19285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (!dict_value->GetStringASCII("command", command)) {
19295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        *error = "Command key string missing from dictionary.";
19305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        dict_value.reset(NULL);
19315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
19325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
19335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
19345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return dict_value.Pass();
19355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
19365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SendJSONRequestWithBrowserHandle(
19385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int handle,
19395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const std::string& json_request,
19405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
19415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser = NULL;
19425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_tracker_->ContainsHandle(handle))
19435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser = browser_tracker_->GetResource(handle);
19445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser || handle < 0) {
19455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    SendJSONRequest(browser, json_request, reply_message);
19465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
19475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
19485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "The browser window does not exist.");
19495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
19505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
19515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SendJSONRequestWithBrowserIndex(
19535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int index,
19545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const std::string& json_request,
19555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
19565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser = index < 0 ? NULL : automation_util::GetBrowserAt(index);
19575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!browser && index >= 0) {
19582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(base::StringPrintf(
19592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        "Browser window with index=%d does not exist.", index));
19605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
19615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    SendJSONRequest(browser, json_request, reply_message);
19625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
19635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
19645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SendJSONRequest(Browser* browser,
19665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                const std::string& json_request,
19675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                IPC::Message* reply_message) {
19685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string command, error_string;
19695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> dict_value(
19705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      ParseJSONRequestCommand(json_request, &command, &error_string));
19715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!dict_value.get() || command.empty()) {
19725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error_string);
19735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
19745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
19755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (handler_map_.empty() || browser_handler_map_.empty())
19775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    BuildJSONHandlerMaps();
19785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
19795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Look for command in handlers that take a Browser.
19805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_handler_map_.find(std::string(command)) !=
19815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser_handler_map_.end() && browser) {
19825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    (this->*browser_handler_map_[command])(browser, dict_value.get(),
19835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                           reply_message);
19845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Look for command in handlers that don't take a Browser.
19855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (handler_map_.find(std::string(command)) != handler_map_.end()) {
19865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    (this->*handler_map_[command])(dict_value.get(), reply_message);
19875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Command has no handler.
19885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
19892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    error_string = base::StringPrintf("Unknown command '%s'. Options: ",
19902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                      command.c_str());
19915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    for (std::map<std::string, JsonHandler>::const_iterator it =
19925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         handler_map_.begin(); it != handler_map_.end(); ++it) {
19935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      error_string += it->first + ", ";
19945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
19955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    for (std::map<std::string, BrowserJsonHandler>::const_iterator it =
19965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         browser_handler_map_.begin(); it != browser_handler_map_.end(); ++it) {
19975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      error_string += it->first + ", ";
19985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
19995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error_string);
20005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
20015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
20025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
20035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::BringBrowserToFrontJSON(
20045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
20055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
20065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
20075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
20085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
20095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
20105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
20115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
20125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
20135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser->window()->Activate();
20145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
20155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
20165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
20175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "SetWindowDimensions",
20185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "x": 20,         # optional
20195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "y": 20,         # optional
20205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "width": 800,    # optional
20215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "height": 600 }  # optional
20225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetWindowDimensions(
20235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
20245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
20255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
20265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  gfx::Rect rect = browser->window()->GetRestoredBounds();
20275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int x, y, width, height;
20285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (args->GetInteger("x", &x))
20295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    rect.set_x(x);
20305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (args->GetInteger("y", &y))
20315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    rect.set_y(y);
20325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (args->GetInteger("width", &width))
20335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    rect.set_width(width);
20345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (args->GetInteger("height", &height))
20355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    rect.set_height(height);
20365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser->window()->SetBounds(rect);
20375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(NULL);
20385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
20395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
20405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)ListValue* TestingAutomationProvider::GetInfobarsInfo(WebContents* wc) {
20415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Each infobar may have different properties depending on the type.
20425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* infobars = new ListValue;
20432a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  InfoBarService* infobar_service = InfoBarService::FromWebContents(wc);
2044c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  for (size_t i = 0; i < infobar_service->infobar_count(); ++i) {
20455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* infobar_item = new DictionaryValue;
2046c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)    InfoBarDelegate* infobar = infobar_service->infobar_at(i);
20475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    switch (infobar->GetInfoBarAutomationType()) {
20485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      case InfoBarDelegate::CONFIRM_INFOBAR:
20495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        infobar_item->SetString("type", "confirm_infobar");
20505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        break;
20515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      case InfoBarDelegate::PASSWORD_INFOBAR:
20525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        infobar_item->SetString("type", "password_infobar");
20535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        break;
20545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      case InfoBarDelegate::RPH_INFOBAR:
20555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        infobar_item->SetString("type", "rph_infobar");
20565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        break;
20575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      case InfoBarDelegate::UNKNOWN_INFOBAR:
20585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        infobar_item->SetString("type", "unknown_infobar");
20595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        break;
20605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
20615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (infobar->AsConfirmInfoBarDelegate()) {
20625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      // Also covers ThemeInstalledInfoBarDelegate.
20635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      ConfirmInfoBarDelegate* confirm_infobar =
20645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        infobar->AsConfirmInfoBarDelegate();
20655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      infobar_item->SetString("text", confirm_infobar->GetMessageText());
20665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      infobar_item->SetString("link_text", confirm_infobar->GetLinkText());
20675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      ListValue* buttons_list = new ListValue;
20685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      int buttons = confirm_infobar->GetButtons();
20695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (buttons & ConfirmInfoBarDelegate::BUTTON_OK) {
20705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        StringValue* button_label = new StringValue(
20715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            confirm_infobar->GetButtonLabel(
20725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)              ConfirmInfoBarDelegate::BUTTON_OK));
20735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        buttons_list->Append(button_label);
20745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
20755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (buttons & ConfirmInfoBarDelegate::BUTTON_CANCEL) {
20765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        StringValue* button_label = new StringValue(
20775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            confirm_infobar->GetButtonLabel(
20785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)              ConfirmInfoBarDelegate::BUTTON_CANCEL));
20795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        buttons_list->Append(button_label);
20805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
20815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      infobar_item->Set("buttons", buttons_list);
20825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else if (infobar->AsExtensionInfoBarDelegate()) {
20835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      infobar_item->SetString("type", "extension_infobar");
20845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
20855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      infobar_item->SetString("type", "unknown_infobar");
20865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
20875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    infobars->Append(infobar_item);
20885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
20895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return infobars;
20905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
20915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
20925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "PerformActionOnInfobar",
20935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "action": "dismiss",
20945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "infobar_index": 0,
20955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "tab_index": 0 }
20965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample output: {}
20975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::PerformActionOnInfobar(
20985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
20995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
21005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
21015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
21025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int tab_index;
21035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int infobar_index_int;
21045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string action;
21055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("tab_index", &tab_index) ||
21065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("infobar_index", &infobar_index_int) ||
21075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetString("action", &action)) {
21085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Invalid or missing args");
21095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
21105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
21115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  WebContents* web_contents =
21132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->tab_strip_model()->GetWebContentsAt(tab_index);
21145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!web_contents) {
21152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    reply.SendError(base::StringPrintf("No such tab at index %d", tab_index));
21165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
21175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
21182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  InfoBarService* infobar_service =
21192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      InfoBarService::FromWebContents(web_contents);
21205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  InfoBarDelegate* infobar = NULL;
21225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  size_t infobar_index = static_cast<size_t>(infobar_index_int);
2123c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  if (infobar_index >= infobar_service->infobar_count()) {
21242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    reply.SendError(base::StringPrintf("No such infobar at index %" PRIuS,
21252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                       infobar_index));
21265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
21275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
2128c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  infobar = infobar_service->infobar_at(infobar_index);
21295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if ("dismiss" == action) {
21315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    infobar->InfoBarDismissed();
21322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    infobar_service->RemoveInfoBar(infobar);
21335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendSuccess(NULL);
21345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
21355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
21365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if ("accept" == action || "cancel" == action) {
21375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ConfirmInfoBarDelegate* confirm_infobar;
21385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!(confirm_infobar = infobar->AsConfirmInfoBarDelegate())) {
21395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      reply.SendError("Not a confirm infobar");
21405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
21415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
21425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if ("accept" == action) {
21435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (confirm_infobar->Accept())
21442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        infobar_service->RemoveInfoBar(infobar);
21455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else if ("cancel" == action) {
21465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (confirm_infobar->Cancel())
21472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        infobar_service->RemoveInfoBar(infobar);
21485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
21495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendSuccess(NULL);
21505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
21515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
21525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendError("Invalid action");
21545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
21555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace {
21575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Gets info about BrowserChildProcessHost. Must run on IO thread to
21595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// honor the semantics of BrowserChildProcessHostIterator.
21605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Used by AutomationProvider::GetBrowserInfo().
21615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void GetChildProcessHostInfo(ListValue* child_processes) {
21625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (BrowserChildProcessHostIterator iter; !iter.Done(); ++iter) {
21635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Only add processes which are already started, since we need their handle.
21645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (iter.GetData().handle == base::kNullProcessHandle)
21655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      continue;
21665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* item = new DictionaryValue;
21675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetString("name", iter.GetData().name);
21682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    item->SetString(
21692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        "type",
21702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        content::GetProcessTypeNameInEnglish(iter.GetData().process_type));
21715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetInteger("pid", base::GetProcId(iter.GetData().handle));
21725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    child_processes->Append(item);
21735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
21745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
21755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace
21775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
21785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetBrowserInfo" }
21795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to GetBrowserInfo() in chrome/test/pyautolib/pyauto.py for
21805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// sample json output.
21815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetBrowserInfo(
21825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
21835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
21845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  base::ThreadRestrictions::ScopedAllowIO allow_io;  // needed for PathService
21855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue* properties = new DictionaryValue;
21865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetString("ChromeVersion", chrome::kChromeVersion);
21875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetString("BrowserProcessExecutableName",
21885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        chrome::kBrowserProcessExecutableName);
21895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetString("HelperProcessExecutableName",
21905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        chrome::kHelperProcessExecutableName);
21915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetString("BrowserProcessExecutablePath",
21925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        chrome::kBrowserProcessExecutablePath);
21935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetString("HelperProcessExecutablePath",
21945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                        chrome::kHelperProcessExecutablePath);
21955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetString("command_line_string",
21965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      CommandLine::ForCurrentProcess()->GetCommandLineString());
21972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  base::FilePath dumps_path;
2198eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  PathService::Get(chrome::DIR_CRASH_DUMPS, &dumps_path);
21995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetString("DIR_CRASH_DUMPS", dumps_path.value());
22005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(USE_AURA)
22015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetBoolean("aura", true);
22025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
22035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetBoolean("aura", false);
22045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
22055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string branding;
22075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(GOOGLE_CHROME_BUILD)
22085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  branding = "Google Chrome";
22095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#elif defined(CHROMIUM_BUILD)
22105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  branding = "Chromium";
22115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
22125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  branding = "Unknown Branding";
22135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
22145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetString("branding", branding);
22155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool is_official_build = false;
22175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OFFICIAL_BUILD)
22185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  is_official_build = true;
22195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
22205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetBoolean("is_official", is_official_build);
22215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
22235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("properties", properties);
22245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->SetInteger("browser_pid", base::GetCurrentProcId());
22265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Add info about all windows in a list of dictionaries, one dictionary
22275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // item per window.
22285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* windows = new ListValue;
22295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int windex = 0;
22302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
22312a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  for (chrome::BrowserIterator it; !it.done(); it.Next(), ++windex) {
22325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* browser_item = new DictionaryValue;
22335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser = *it;
22345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_item->SetInteger("index", windex);
22355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Window properties
22365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    gfx::Rect rect = browser->window()->GetRestoredBounds();
22375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_item->SetInteger("x", rect.x());
22385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_item->SetInteger("y", rect.y());
22395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_item->SetInteger("width", rect.width());
22405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_item->SetInteger("height", rect.height());
22415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_item->SetBoolean("fullscreen",
22425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             browser->window()->IsFullscreen());
22435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ListValue* visible_page_actions = new ListValue;
22445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Add info about all visible page actions. Skipped on panels, which do not
22455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // have a location bar.
22465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    LocationBar* loc_bar = browser->window()->GetLocationBar();
22475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (loc_bar) {
22485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      LocationBarTesting* loc_bar_test =
22495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          loc_bar->GetLocationBarForTesting();
22505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      size_t page_action_visible_count =
22515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          static_cast<size_t>(loc_bar_test->PageActionVisibleCount());
22525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      for (size_t i = 0; i < page_action_visible_count; ++i) {
22535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        StringValue* extension_id = new StringValue(
22545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            loc_bar_test->GetVisiblePageAction(i)->extension_id());
22555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        visible_page_actions->Append(extension_id);
22565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
22575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
22585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_item->Set("visible_page_actions", visible_page_actions);
22592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    browser_item->SetInteger("selected_tab",
22602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                             browser->tab_strip_model()->active_index());
22615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_item->SetBoolean("incognito",
22625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             browser->profile()->IsOffTheRecord());
22635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_item->SetString("profile_path",
22645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        browser->profile()->GetPath().BaseName().MaybeAsASCII());
22655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    std::string type;
22665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    switch (browser->type()) {
22675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      case Browser::TYPE_TABBED:
22685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        type = "tabbed";
22695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        break;
22705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      case Browser::TYPE_POPUP:
22715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        type = "popup";
22725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        break;
22735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      default:
22745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        type = "unknown";
22755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        break;
22765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
22775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_item->SetString("type", type);
22785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // For each window, add info about all tabs in a list of dictionaries,
22795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // one dictionary item per tab.
22805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ListValue* tabs = new ListValue;
22812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    for (int i = 0; i < browser->tab_strip_model()->count(); ++i) {
22822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      WebContents* wc = browser->tab_strip_model()->GetWebContentsAt(i);
22835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      DictionaryValue* tab = new DictionaryValue;
22845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      tab->SetInteger("index", i);
22855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      tab->SetString("url", wc->GetURL().spec());
22865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      tab->SetInteger("renderer_pid",
22875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                      base::GetProcId(wc->GetRenderProcessHost()->GetHandle()));
22885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      tab->Set("infobars", GetInfobarsInfo(wc));
22895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      tab->SetBoolean("pinned", browser->tab_strip_model()->IsTabPinned(i));
22905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      tabs->Append(tab);
22915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
22925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_item->Set("tabs", tabs);
22935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    windows->Append(browser_item);
22955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
22965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("windows", windows);
22975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
22985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_LINUX)
22995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int flags = ChildProcessHost::CHILD_ALLOW_SELF;
23005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
23015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int flags = ChildProcessHost::CHILD_NORMAL;
23025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
23035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
23045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Add all extension processes in a list of dictionaries, one dictionary
23055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // item per extension process.
23065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* extension_views = new ListValue;
23075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ProfileManager* profile_manager = g_browser_process->profile_manager();
23085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::vector<Profile*> profiles(profile_manager->GetLoadedProfiles());
23095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (size_t i = 0; i < profiles.size(); ++i) {
23105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ExtensionProcessManager* process_manager =
23115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        extensions::ExtensionSystem::Get(profiles[i])->process_manager();
23125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!process_manager)
23135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      continue;
23145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const ExtensionProcessManager::ViewSet view_set =
23155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        process_manager->GetAllViews();
23165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    for (ExtensionProcessManager::ViewSet::const_iterator jt =
23175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)             view_set.begin();
23185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         jt != view_set.end(); ++jt) {
23195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      content::RenderViewHost* render_view_host = *jt;
23205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      // Don't add dead extension processes.
23215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (!render_view_host->IsRenderViewLive())
23225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        continue;
23235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      // Don't add views for which we can't obtain an extension.
23245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      // TODO(benwells): work out why this happens. It only happens for one
23255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      // test, and only on the bots.
23265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      const Extension* extension =
23275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          process_manager->GetExtensionForRenderViewHost(render_view_host);
23285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (!extension)
23295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        continue;
23305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      DictionaryValue* item = new DictionaryValue;
23315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      item->SetString("name", extension->name());
23325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      item->SetString("extension_id", extension->id());
23335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      item->SetInteger(
23345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          "pid",
23355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          base::GetProcId(render_view_host->GetProcess()->GetHandle()));
23365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      DictionaryValue* view = new DictionaryValue;
23375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      view->SetInteger(
23385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          "render_process_id",
23395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          render_view_host->GetProcess()->GetID());
23405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      view->SetInteger(
23415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          "render_view_id",
23425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          render_view_host->GetRoutingID());
23435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      item->Set("view", view);
23445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      std::string type;
23455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      WebContents* web_contents =
23465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          WebContents::FromRenderViewHost(render_view_host);
2347c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)      extensions::ViewType view_type = extensions::GetViewType(web_contents);
23485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      switch (view_type) {
2349c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)        case extensions::VIEW_TYPE_EXTENSION_BACKGROUND_PAGE:
23505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          type = "EXTENSION_BACKGROUND_PAGE";
23515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          break;
2352c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)        case extensions::VIEW_TYPE_EXTENSION_POPUP:
23535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          type = "EXTENSION_POPUP";
23545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          break;
2355c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)        case extensions::VIEW_TYPE_EXTENSION_INFOBAR:
23565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          type = "EXTENSION_INFOBAR";
23575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          break;
2358c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)        case extensions::VIEW_TYPE_EXTENSION_DIALOG:
23595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          type = "EXTENSION_DIALOG";
23605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          break;
2361c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)        case extensions::VIEW_TYPE_APP_SHELL:
23625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          type = "APP_SHELL";
23635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          break;
2364c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)        case extensions::VIEW_TYPE_PANEL:
23655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          type = "PANEL";
23665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          break;
23675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        default:
23685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          type = "unknown";
23695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          break;
23705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
23715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      item->SetString("view_type", type);
23725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      item->SetString("url", web_contents->GetURL().spec());
23735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      item->SetBoolean("loaded", !render_view_host->IsLoading());
23745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      extension_views->Append(item);
23755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
23765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
23775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("extension_views", extension_views);
23785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
23795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->SetString("child_process_path",
23805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                          ChildProcessHost::GetChildPath(flags).value());
23815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Child processes are the processes for plugins and other workers.
23825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Add all child processes in a list of dictionaries, one dictionary item
23835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // per child process.
23845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* child_processes = new ListValue;
23855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("child_processes", child_processes);
23865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BrowserThread::PostTaskAndReply(
23875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BrowserThread::IO, FROM_HERE,
23885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      base::Bind(&GetChildProcessHostInfo, child_processes),
23895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      base::Bind(&AutomationJSONReply::SendSuccess,
23905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                 base::Owned(new AutomationJSONReply(this, reply_message)),
23915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                 base::Owned(return_value.release())));
23925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
23935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
23945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetProcessInfo" }
23955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to GetProcessInfo() in chrome/test/pyautolib/pyauto.py for
23965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// sample json output.
23975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetProcessInfo(
23985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
23995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
24005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_refptr<ProcessInfoObserver>
24015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      proc_observer(new ProcessInfoObserver(this, reply_message));
24025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // TODO(jamescook): Maybe this shouldn't update UMA stats?
24035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  proc_observer->StartFetch(MemoryDetails::UPDATE_USER_METRICS);
24045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
24055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
24065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetNavigationInfo" }
24075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to GetNavigationInfo() in chrome/test/pyautolib/pyauto.py for
24085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// sample json output.
24095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetNavigationInfo(
24105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
24115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
24125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
24135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
24145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int tab_index;
24155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents = NULL;
24165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("tab_index", &tab_index) ||
24172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      !(web_contents =
24182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)            browser->tab_strip_model()->GetWebContentsAt(tab_index))) {
24195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("tab_index missing or invalid.");
24205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
24215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
24225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
24235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const NavigationController& controller = web_contents->GetController();
24245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NavigationEntry* nav_entry = controller.GetActiveEntry();
24255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK(nav_entry);
24265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
24275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Security info.
24285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue* ssl = new DictionaryValue;
24295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::map<content::SecurityStyle, std::string> style_to_string;
24305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  style_to_string[content::SECURITY_STYLE_UNKNOWN] = "SECURITY_STYLE_UNKNOWN";
24315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  style_to_string[content::SECURITY_STYLE_UNAUTHENTICATED] =
24325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      "SECURITY_STYLE_UNAUTHENTICATED";
24335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  style_to_string[content::SECURITY_STYLE_AUTHENTICATION_BROKEN] =
24345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      "SECURITY_STYLE_AUTHENTICATION_BROKEN";
24355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  style_to_string[content::SECURITY_STYLE_AUTHENTICATED] =
24365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      "SECURITY_STYLE_AUTHENTICATED";
24375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
24385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  SSLStatus ssl_status = nav_entry->GetSSL();
24395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ssl->SetString("security_style",
24405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                 style_to_string[ssl_status.security_style]);
24415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ssl->SetBoolean("ran_insecure_content",
24425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !!(ssl_status.content_status & SSLStatus::RAN_INSECURE_CONTENT));
24435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ssl->SetBoolean("displayed_insecure_content",
24445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !!(ssl_status.content_status & SSLStatus::DISPLAYED_INSECURE_CONTENT));
24455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("ssl", ssl);
24465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
24475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Page type.
24485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::map<content::PageType, std::string> pagetype_to_string;
24495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pagetype_to_string[content::PAGE_TYPE_NORMAL] = "NORMAL_PAGE";
24505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pagetype_to_string[content::PAGE_TYPE_ERROR] = "ERROR_PAGE";
24515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  pagetype_to_string[content::PAGE_TYPE_INTERSTITIAL] =
24525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      "INTERSTITIAL_PAGE";
24535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->SetString("page_type",
24545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                          pagetype_to_string[nav_entry->GetPageType()]);
24555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
24565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->SetString("favicon_url", nav_entry->GetFavicon().url.spec());
24575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(return_value.get());
24585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
24595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
24605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetHistoryInfo",
24615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "search_text": "some text" }
24625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer chrome/test/pyautolib/history_info.py for sample json output.
24635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetHistoryInfo(Browser* browser,
24645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                               DictionaryValue* args,
24655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                               IPC::Message* reply_message) {
24665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  consumer_.CancelAllRequests();
24675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
24685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 search_text;
24695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  args->GetString("search_text", &search_text);
24705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
24715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Fetch history.
24725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  HistoryService* hs = HistoryServiceFactory::GetForProfile(
24735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser->profile(), Profile::EXPLICIT_ACCESS);
24745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  history::QueryOptions options;
24755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The observer owns itself.  It deletes itself after it fetches history.
24765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationProviderHistoryObserver* history_observer =
24775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new AutomationProviderHistoryObserver(this, reply_message);
24785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  hs->QueryHistory(
24795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      search_text,
24805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      options,
24815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      &consumer_,
24825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      base::Bind(&AutomationProviderHistoryObserver::HistoryQueryComplete,
24835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                 base::Unretained(history_observer)));
24845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
24855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
24865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetDownloadsInfo" }
24875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer chrome/test/pyautolib/download_info.py for sample json output.
24885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetDownloadsInfo(Browser* browser,
24895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                 DictionaryValue* args,
24905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                 IPC::Message* reply_message) {
24915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
24925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
24935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* list_of_downloads = new ListValue;
24945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
24955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DownloadService* download_service(
24965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      DownloadServiceFactory::GetForProfile(browser->profile()));
24975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
24985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (download_service->HasCreatedDownloadManager()) {
24995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    std::vector<DownloadItem*> downloads;
25005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    BrowserContext::GetDownloadManager(browser->profile())->GetAllDownloads(
25015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        &downloads);
25025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
25035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    for (std::vector<DownloadItem*>::iterator it = downloads.begin();
25045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         it != downloads.end();
25055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         it++) {  // Fill info about each download item.
25065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      list_of_downloads->Append(GetDictionaryFromDownloadItem(
25075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          *it, browser->profile()->IsOffTheRecord()));
25085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
25095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
25105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("downloads", list_of_downloads);
25115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(return_value.get());
25125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
25135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
25145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WaitForAllDownloadsToComplete(
25155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
25165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
25175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
25185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* pre_download_ids = NULL;
25195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
25205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetList("pre_download_ids", &pre_download_ids)) {
25215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
25222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        .SendError(
25232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)            base::StringPrintf("List of IDs of previous downloads required."));
25245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
25255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
25265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
25275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DownloadService* download_service =
25285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      DownloadServiceFactory::GetForProfile(browser->profile());
25295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!download_service->HasCreatedDownloadManager()) {
25305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // No download manager, so no downloads to wait for.
25315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendSuccess(NULL);
25325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
25335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
25345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
25355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This observer will delete itself.
25365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new AllDownloadsCompleteObserver(
25375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this, reply_message,
25385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BrowserContext::GetDownloadManager(browser->profile()),
25395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      pre_download_ids);
25405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
25415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
25425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// See PerformActionOnDownload() in chrome/test/pyautolib/pyauto.py for sample
25435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// json input and output.
25445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::PerformActionOnDownload(
25455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
25465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
25475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
25485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int id;
25495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string action;
25505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
25515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DownloadService* download_service =
25525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      DownloadServiceFactory::GetForProfile(browser->profile());
25535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!download_service->HasCreatedDownloadManager()) {
25545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError("No download manager.");
25555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
25565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
25575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("id", &id) || !args->GetString("action", &action)) {
25585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
25595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("Must include int id and string action.");
25605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
25615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
25625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
25635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DownloadManager* download_manager =
25645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BrowserContext::GetDownloadManager(browser->profile());
25655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DownloadItem* selected_item = download_manager->GetDownload(id);
25665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!selected_item) {
25675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
25682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        .SendError(base::StringPrintf("No download with an id of %d\n", id));
25695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
25705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
25715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
25727d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  DownloadItem::DownloadState download_state = selected_item->GetState();
25737d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
25745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // We need to be IN_PROGRESS for these actions.
25752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if ((action == "pause" || action == "resume" || action == "cancel") &&
25767d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      download_state != DownloadItem::IN_PROGRESS) {
25775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
25787d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)        .SendError(base::StringPrintf(
25797d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)            "Action '%s' called on download that is not in progress.",
25807d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)            action.c_str()));
25817d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    return;
25825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
25835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
25845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (action == "open") {
25855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    selected_item->AddObserver(
25865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        new AutomationProviderDownloadUpdatedObserver(
25875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            this, reply_message, true, browser->profile()->IsOffTheRecord()));
25885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    selected_item->OpenDownload();
25895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (action == "toggle_open_files_like_this") {
25905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DownloadPrefs* prefs =
25915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        DownloadPrefs::FromBrowserContext(selected_item->GetBrowserContext());
259290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    base::FilePath path = selected_item->GetTargetFilePath();
25935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!selected_item->ShouldOpenFileBasedOnExtension())
25945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      prefs->EnableAutoOpenBasedOnExtension(path);
25955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    else
25965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      prefs->DisableAutoOpenBasedOnExtension(path);
25975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendSuccess(NULL);
25985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (action == "remove") {
25995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    new AutomationProviderDownloadModelChangedObserver(
26005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        this, reply_message, download_manager);
26015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    selected_item->Remove();
26025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (action == "decline_dangerous_download") {
26035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    new AutomationProviderDownloadModelChangedObserver(
26045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        this, reply_message, download_manager);
2605868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    selected_item->Remove();
26065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (action == "save_dangerous_download") {
26075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    selected_item->AddObserver(new AutomationProviderDownloadUpdatedObserver(
26085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        this, reply_message, false, browser->profile()->IsOffTheRecord()));
2609868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    selected_item->ValidateDangerousDownload();
26102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  } else if (action == "pause") {
26117d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    if (selected_item->IsPaused()) {
26122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      // Action would be a no-op; respond right from here.  No-op implies
26132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      // the test is poorly written or failing, so make it an error return.
26147d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      AutomationJSONReply(this, reply_message)
26157d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)          .SendError("Action 'pause' called on already paused download.");
26162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    } else {
26172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      selected_item->AddObserver(new AutomationProviderDownloadUpdatedObserver(
26182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          this, reply_message, false, browser->profile()->IsOffTheRecord()));
26192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      selected_item->Pause();
26202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    }
26212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  } else if (action == "resume") {
26227d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    if (!selected_item->IsPaused()) {
26232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      // Action would be a no-op; respond right from here.  No-op implies
26242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      // the test is poorly written or failing, so make it an error return.
26257d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      AutomationJSONReply(this, reply_message)
26267d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)          .SendError("Action 'resume' called on unpaused download.");
26272a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    } else {
26282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      selected_item->AddObserver(new AutomationProviderDownloadUpdatedObserver(
26292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          this, reply_message, false, browser->profile()->IsOffTheRecord()));
26302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      selected_item->Resume();
26312a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    }
26325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (action == "cancel") {
26335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    selected_item->AddObserver(new AutomationProviderDownloadUpdatedObserver(
26345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        this, reply_message, false, browser->profile()->IsOffTheRecord()));
26355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    selected_item->Cancel(true);
26365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
26375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
26382a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        .SendError(
26392a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)            base::StringPrintf("Invalid action '%s' given.", action.c_str()));
26405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
26415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
26425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
26435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetDownloadShelfVisibleJSON(
26445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
26455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
26465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
26475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
26485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
26495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool is_visible;
26505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
26515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
26525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
26535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
26545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("is_visible", &is_visible)) {
26555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'is_visible' missing or invalid.");
26565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
26575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
26585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (is_visible) {
26595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser->window()->GetDownloadShelf()->Show();
26605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
2661c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)    browser->window()->GetDownloadShelf()->Close(DownloadShelf::AUTOMATIC);
26625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
26635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
26645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
26655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
26665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsDownloadShelfVisibleJSON(
26675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
26685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
26695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
26705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
26715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
26725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
26735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
26745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
26755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
26765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
26775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("is_visible", browser->window()->IsDownloadShelfVisible());
26785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&dict);
26795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
26805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
26815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetDownloadDirectoryJSON(
26825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
26835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
26845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
26855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
26865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
26875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetTabFromJSONArgs(args, &web_contents, &error)) {
26885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error);
26895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
26905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
26915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DownloadManager* dlm =
26925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BrowserContext::GetDownloadManager(
26935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          web_contents->GetController().GetBrowserContext());
26945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
26955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetString("path",
26965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      DownloadPrefs::FromDownloadManager(dlm)->DownloadPath().value());
26975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&dict);
26985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
26995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
27005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample JSON input { "command": "LoadSearchEngineInfo" }
27015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::LoadSearchEngineInfo(
27025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
27035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
27045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
27055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  TemplateURLService* url_model =
27065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      TemplateURLServiceFactory::GetForProfile(browser->profile());
27075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (url_model->loaded()) {
27085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendSuccess(NULL);
27095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
27105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
27115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  url_model->AddObserver(new AutomationProviderSearchEngineObserver(
27125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this, browser->profile(), reply_message));
27135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  url_model->Load();
27145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
27155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
27165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample JSON input { "command": "GetSearchEngineInfo" }
27175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to pyauto.py for sample output.
27185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetSearchEngineInfo(
27195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
27205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
27215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
27225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  TemplateURLService* url_model =
27235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      TemplateURLServiceFactory::GetForProfile(browser->profile());
27245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
27255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* search_engines = new ListValue;
27265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  TemplateURLService::TemplateURLVector template_urls =
27275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      url_model->GetTemplateURLs();
27285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (TemplateURLService::TemplateURLVector::const_iterator it =
27295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)       template_urls.begin(); it != template_urls.end(); ++it) {
27305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* search_engine = new DictionaryValue;
27315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    search_engine->SetString("short_name", UTF16ToUTF8((*it)->short_name()));
27325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    search_engine->SetString("keyword", UTF16ToUTF8((*it)->keyword()));
27335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    search_engine->SetBoolean("in_default_list", (*it)->ShowInDefaultList());
27345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    search_engine->SetBoolean("is_default",
27355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        (*it) == url_model->GetDefaultSearchProvider());
27365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    search_engine->SetBoolean("is_valid", (*it)->url_ref().IsValid());
27375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    search_engine->SetBoolean("supports_replacement",
27385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              (*it)->url_ref().SupportsReplacement());
27395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    search_engine->SetString("url", (*it)->url());
27405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    search_engine->SetString("host", (*it)->url_ref().GetHost());
27415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    search_engine->SetString("path", (*it)->url_ref().GetPath());
27425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    search_engine->SetString("display_url",
27435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                             UTF16ToUTF8((*it)->url_ref().DisplayURL()));
27445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    search_engines->Append(search_engine);
27455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
27465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("search_engines", search_engines);
27475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(return_value.get());
27485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
27495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
27505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to pyauto.py for sample JSON input.
27515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::AddOrEditSearchEngine(
27525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
27535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
27545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
27555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  TemplateURLService* url_model =
27565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      TemplateURLServiceFactory::GetForProfile(browser->profile());
27575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 new_title;
27585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 new_keyword;
27595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string new_url;
27605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string keyword;
27615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("new_title", &new_title) ||
27625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetString("new_keyword", &new_keyword) ||
27635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetString("new_url", &new_url)) {
27645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
27655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "One or more inputs invalid");
27665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
27675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
27685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string new_ref_url = TemplateURLRef::DisplayURLToURLRef(
27695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      UTF8ToUTF16(new_url));
27705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<KeywordEditorController> controller(
27715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new KeywordEditorController(browser->profile()));
27725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (args->GetString("keyword", &keyword)) {
27735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    TemplateURL* template_url =
27745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        url_model->GetTemplateURLForKeyword(UTF8ToUTF16(keyword));
27755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (template_url == NULL) {
27765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      AutomationJSONReply(this, reply_message).SendError(
27775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          "No match for keyword: " + keyword);
27785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
27795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
27805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    url_model->AddObserver(new AutomationProviderSearchEngineObserver(
27815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        this, browser->profile(), reply_message));
27825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    controller->ModifyTemplateURL(template_url, new_title, new_keyword,
27835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                  new_ref_url);
27845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
27855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    url_model->AddObserver(new AutomationProviderSearchEngineObserver(
27865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        this, browser->profile(), reply_message));
27875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    controller->AddTemplateURL(new_title, new_keyword, new_ref_url);
27885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
27895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
27905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
27915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "PerformActionOnSearchEngine",
27925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "keyword": keyword, "action": action }
27935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::PerformActionOnSearchEngine(
27945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
27955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
27965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
27975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  TemplateURLService* url_model =
27985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      TemplateURLServiceFactory::GetForProfile(browser->profile());
27995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string keyword;
28005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string action;
28015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("keyword", &keyword) ||
28025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetString("action", &action)) {
28035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
28045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "One or more inputs invalid");
28055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
28065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
28075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  TemplateURL* template_url =
28085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      url_model->GetTemplateURLForKeyword(UTF8ToUTF16(keyword));
28095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (template_url == NULL) {
28105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
28115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "No match for keyword: " + keyword);
28125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
28135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
28145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (action == "delete") {
28155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    url_model->AddObserver(new AutomationProviderSearchEngineObserver(
28165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this, browser->profile(), reply_message));
28175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    url_model->Remove(template_url);
28185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (action == "default") {
28195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    url_model->AddObserver(new AutomationProviderSearchEngineObserver(
28205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this, browser->profile(), reply_message));
28215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    url_model->SetDefaultSearchProvider(template_url);
28225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
28235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
28245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Invalid action: " + action);
28255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
28265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
28275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
28285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetLocalStatePrefsInfo" }
28295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer chrome/test/pyautolib/prefs_info.py for sample json output.
28305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetLocalStatePrefsInfo(
28315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
28325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
28335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue* items = g_browser_process->local_state()->
28345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      GetPreferenceValues();
28355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
28365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("prefs", items);  // return_value owns items.
28375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(return_value.get());
28385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
28395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
28405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "SetLocalStatePrefs", "path": path,
28415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "value": value }
28425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetLocalStatePrefs(
28435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
28445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
28455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string path;
28465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Value* val = NULL;
28475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
28485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (args->GetString("path", &path) && args->Get("value", &val)) {
28495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    PrefService* pref_service = g_browser_process->local_state();
28505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const PrefService::Preference* pref =
28515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        pref_service->FindPreference(path.c_str());
28525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!pref) {  // Not a registered pref.
28535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      reply.SendError("pref not registered.");
28545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
28555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else if (pref->IsManaged()) {  // Do not attempt to change a managed pref.
28565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      reply.SendError("pref is managed. cannot be changed.");
28575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
28585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {  // Set the pref.
28595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      pref_service->Set(path.c_str(), *val);
28605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
28615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
28625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("no pref path or value given.");
28635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
28645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
28655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
28665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
28675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
28685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
28695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetPrefsInfo", "windex": 0 }
28705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer chrome/test/pyautolib/prefs_info.py for sample json output.
28715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetPrefsInfo(DictionaryValue* args,
28725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                             IPC::Message* reply_message) {
28735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
28745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
28755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
28765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
28775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
28785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
28795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
28805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue* items = browser->profile()->GetPrefs()->
28815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      GetPreferenceValues();
28825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
28835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
28845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("prefs", items);  // return_value owns items.
28855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(return_value.get());
28865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
28875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
28885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input:
28895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// { "command": "SetPrefs",
28905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//   "windex": 0,
28915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//   "path": path,
28925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//   "value": value }
28935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetPrefs(DictionaryValue* args,
28945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                         IPC::Message* reply_message) {
28955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
28965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
28975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
28985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
28995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
29005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
29015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
29025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string path;
29035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Value* val = NULL;
29045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (args->GetString("path", &path) && args->Get("value", &val)) {
29055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    PrefService* pref_service = browser->profile()->GetPrefs();
29065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const PrefService::Preference* pref =
29075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        pref_service->FindPreference(path.c_str());
29085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!pref) {  // Not a registered pref.
29095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      reply.SendError("pref not registered.");
29105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
29115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else if (pref->IsManaged()) {  // Do not attempt to change a managed pref.
29125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      reply.SendError("pref is managed. cannot be changed.");
29135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
29145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {  // Set the pref.
29155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      pref_service->Set(path.c_str(), *val);
29165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
29175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
29185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("no pref path or value given.");
29195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
29205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
29215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
29225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
29235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
29245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
29255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetOmniboxInfo" }
29265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer chrome/test/pyautolib/omnibox_info.py for sample json output.
29275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetOmniboxInfo(Browser* browser,
29285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                               DictionaryValue* args,
29295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                               IPC::Message* reply_message) {
29305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
29315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
29325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
29335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  LocationBar* loc_bar = browser->window()->GetLocationBar();
29345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!loc_bar) {
29355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("The specified browser does not have a location bar.");
29365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
29375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
29385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const OmniboxView* omnibox_view = loc_bar->GetLocationEntry();
29395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const OmniboxEditModel* model = omnibox_view->model();
29405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
29415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Fill up matches.
29425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* matches = new ListValue;
29435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const AutocompleteResult& result = model->result();
29445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (AutocompleteResult::const_iterator i(result.begin()); i != result.end();
29455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)       ++i) {
29465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const AutocompleteMatch& match = *i;
29475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* item = new DictionaryValue;  // owned by return_value
294890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    item->SetString("type", AutocompleteMatchType::ToString(match.type));
29495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetBoolean("starred", match.starred);
29505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetString("destination_url", match.destination_url.spec());
29515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetString("contents", match.contents);
29525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetString("description", match.description);
29535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    matches->Append(item);
29545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
29555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("matches", matches);
29565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
29575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Fill up other properties.
29585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue* properties = new DictionaryValue;  // owned by return_value
29595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetBoolean("has_focus", model->has_focus());
29605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetBoolean("query_in_progress",
29615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         !model->autocomplete_controller()->done());
29625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetString("keyword", model->keyword());
29635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  properties->SetString("text", omnibox_view->GetText());
29645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("properties", properties);
29655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
29665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(return_value.get());
29675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
29685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
29695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "SetOmniboxText",
29705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "text": "goog" }
29715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetOmniboxText(Browser* browser,
29725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                               DictionaryValue* args,
29735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                               IPC::Message* reply_message) {
29745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 text;
29755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
29765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("text", &text)) {
29775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("text missing");
29785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
29795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
29805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  chrome::FocusLocationBar(browser);
29815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  LocationBar* loc_bar = browser->window()->GetLocationBar();
29825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!loc_bar) {
29835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("The specified browser does not have a location bar.");
29845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
29855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
29865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  OmniboxView* omnibox_view = loc_bar->GetLocationEntry();
29875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  omnibox_view->model()->OnSetFocus(false);
29885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  omnibox_view->SetUserText(text);
29895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
29905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
29915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
29925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "OmniboxMovePopupSelection",
29935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "count": 1 }
29945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Negative count implies up, positive implies down. Count values will be
29955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// capped by the size of the popup list.
29965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OmniboxMovePopupSelection(
29975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
29985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
29995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
30005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int count;
30015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
30025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("count", &count)) {
30035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("count missing");
30045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
30055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
30065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  LocationBar* loc_bar = browser->window()->GetLocationBar();
30075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!loc_bar) {
30085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("The specified browser does not have a location bar.");
30095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
30105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
30115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  loc_bar->GetLocationEntry()->model()->OnUpOrDownKeyPressed(count);
30125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
30135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
30145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
30155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "OmniboxAcceptInput" }
30165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OmniboxAcceptInput(
30175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
30185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
30195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
30205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NavigationController& controller =
30212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->tab_strip_model()->GetActiveWebContents()->GetController();
30225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  LocationBar* loc_bar = browser->window()->GetLocationBar();
30235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!loc_bar) {
30245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
30255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "The specified browser does not have a location bar.");
30265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
30275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
30285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new OmniboxAcceptNotificationObserver(&controller, this, reply_message);
30295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  loc_bar->AcceptInput();
30305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
30315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
30325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetInitialLoadTimes" }
30335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to InitialLoadObserver::GetTimingInformation() for sample output.
30345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetInitialLoadTimes(
30355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser*,
30365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue*,
30375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
30385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(
30395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      initial_load_observer_->GetTimingInformation());
30405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
30415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string json_return;
30425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  base::JSONWriter::Write(return_value.get(), &json_return);
30435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationMsg_SendJSONRequest::WriteReplyParams(
30445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      reply_message, json_return, true);
30455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Send(reply_message);
30465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
30475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
30485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetPluginsInfo" }
30495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer chrome/test/pyautolib/plugins_info.py for sample json output.
30505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetPluginsInfo(
30515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
30525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
30535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
30545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PluginService::GetInstance()->GetPlugins(
30555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      base::Bind(&TestingAutomationProvider::GetPluginsInfoCallback,
30565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          this, browser, args, reply_message));
30575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
30585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
30595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetPluginsInfoCallback(
30605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
30615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
30625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message,
30635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const std::vector<webkit::WebPluginInfo>& plugins) {
30647d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  PluginPrefs* plugin_prefs =
30657d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      PluginPrefs::GetForProfile(browser->profile()).get();
30665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* items = new ListValue;
30675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (std::vector<webkit::WebPluginInfo>::const_iterator it =
30685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           plugins.begin();
30695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)       it != plugins.end();
30705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)       ++it) {
30715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* item = new DictionaryValue;
30725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetString("name", it->name);
30735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetString("path", it->path.value());
30745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetString("version", it->version);
30755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetString("desc", it->desc);
30765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->SetBoolean("enabled", plugin_prefs->IsPluginEnabled(*it));
30775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // Add info about mime types.
30785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ListValue* mime_types = new ListValue();
30795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    for (std::vector<webkit::WebPluginMimeType>::const_iterator type_it =
30805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)             it->mime_types.begin();
30815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         type_it != it->mime_types.end();
30825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         ++type_it) {
30835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      DictionaryValue* mime_type = new DictionaryValue();
30845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      mime_type->SetString("mimeType", type_it->mime_type);
30855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      mime_type->SetString("description", type_it->description);
30865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
30875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      ListValue* file_extensions = new ListValue();
30885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      for (std::vector<std::string>::const_iterator ext_it =
30895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)               type_it->file_extensions.begin();
30905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           ext_it != type_it->file_extensions.end();
30915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)           ++ext_it) {
30925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        file_extensions->Append(new StringValue(*ext_it));
30935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
30945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      mime_type->Set("fileExtensions", file_extensions);
30955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
30965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      mime_types->Append(mime_type);
30975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
30985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    item->Set("mimeTypes", mime_types);
30995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    items->Append(item);
31005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
31015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
31025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("plugins", items);  // return_value owns items.
31035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
31045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(return_value.get());
31055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
31065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
31075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input:
31085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//    { "command": "EnablePlugin",
31095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//      "path": "/Library/Internet Plug-Ins/Flash Player.plugin" }
31105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::EnablePlugin(Browser* browser,
31115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                             DictionaryValue* args,
31125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                             IPC::Message* reply_message) {
31132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  base::FilePath::StringType path;
31145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("path", &path)) {
31155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError("path not specified.");
31165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
31175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
31187d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  PluginPrefs* plugin_prefs =
31197d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      PluginPrefs::GetForProfile(browser->profile()).get();
31207d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  plugin_prefs->EnablePlugin(
31217d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      true,
31227d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      base::FilePath(path),
31237d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      base::Bind(&DidEnablePlugin,
31247d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)                 AsWeakPtr(),
31257d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)                 reply_message,
31267d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)                 path,
31277d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)                 "Could not enable plugin for path %s."));
31285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
31295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
31305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input:
31315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//    { "command": "DisablePlugin",
31325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//      "path": "/Library/Internet Plug-Ins/Flash Player.plugin" }
31335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::DisablePlugin(Browser* browser,
31345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                              DictionaryValue* args,
31355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                              IPC::Message* reply_message) {
31362a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  base::FilePath::StringType path;
31375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("path", &path)) {
31385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError("path not specified.");
31395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
31405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
31417d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  PluginPrefs* plugin_prefs =
31427d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      PluginPrefs::GetForProfile(browser->profile()).get();
31437d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  plugin_prefs->EnablePlugin(
31447d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      false,
31457d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      base::FilePath(path),
31467d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      base::Bind(&DidEnablePlugin,
31477d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)                 AsWeakPtr(),
31487d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)                 reply_message,
31497d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)                 path,
31507d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)                 "Could not disable plugin for path %s."));
31515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
31525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
31535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input:
31545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//    { "command": "SaveTabContents",
31555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//      "tab_index": 0,
31565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//      "filename": <a full pathname> }
31575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json output:
31585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//    {}
31595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SaveTabContents(
31605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
31615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
31625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
31635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int tab_index = 0;
31642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  base::FilePath::StringType filename;
31652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  base::FilePath::StringType parent_directory;
31665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents = NULL;
31675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
31685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("tab_index", &tab_index) ||
31695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetString("filename", &filename)) {
31705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
31715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("tab_index or filename param missing");
31725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
31735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
31742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    web_contents = browser->tab_strip_model()->GetWebContentsAt(tab_index);
31755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!web_contents) {
31765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      AutomationJSONReply(this, reply_message).SendError("no tab at tab_index");
31775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
31785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
31795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
31805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // We're doing a SAVE_AS_ONLY_HTML so the the directory path isn't
31815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // used.  Nevertheless, SavePackage requires it be valid.  Sigh.
31822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  parent_directory = base::FilePath(filename).DirName().value();
31835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!web_contents->SavePage(
31842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          base::FilePath(filename),
31852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          base::FilePath(parent_directory),
31865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          content::SAVE_PAGE_TYPE_AS_ONLY_HTML)) {
31875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
31885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Could not initiate SavePage");
31895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
31905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
31915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The observer will delete itself when done.
31925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new SavePackageNotificationObserver(
31935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      BrowserContext::GetDownloadManager(browser->profile()),
31945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this, reply_message);
31955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
31965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
31975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace {
31985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
31995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Translates a dictionary password to a PasswordForm struct.
32005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)content::PasswordForm GetPasswordFormFromDict(
32015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const DictionaryValue& password_dict) {
32025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // If the time is specified, change time to the specified time.
32045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  base::Time time = base::Time::Now();
32055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int it;
32065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  double dt;
32075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (password_dict.GetInteger("time", &it))
32085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    time = base::Time::FromTimeT(it);
32095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  else if (password_dict.GetDouble("time", &dt))
32105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    time = base::Time::FromDoubleT(dt);
32115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string signon_realm;
32135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 username_value;
32145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 password_value;
32155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 origin_url_text;
32165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 username_element;
32175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 password_element;
32185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 submit_element;
32195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 action_target_text;
32205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool blacklist;
32215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 old_password_element;
32225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 old_password_value;
32235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // We don't care if any of these fail - they are either optional or checked
32255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // before this function is called.
32265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_dict.GetString("signon_realm", &signon_realm);
32275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_dict.GetString("username_value", &username_value);
32285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_dict.GetString("password_value", &password_value);
32295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_dict.GetString("origin_url", &origin_url_text);
32305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_dict.GetString("username_element", &username_element);
32315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_dict.GetString("password_element", &password_element);
32325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_dict.GetString("submit_element", &submit_element);
32335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_dict.GetString("action_target", &action_target_text);
32345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!password_dict.GetBoolean("blacklist", &blacklist))
32355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    blacklist = false;
32365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  GURL origin_gurl(origin_url_text);
32385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  GURL action_target(action_target_text);
32395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  content::PasswordForm password_form;
32415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_form.signon_realm = signon_realm;
32425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_form.username_value = username_value;
32435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_form.password_value = password_value;
32445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_form.origin = origin_gurl;
32455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_form.username_element = username_element;
32465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_form.password_element = password_element;
32475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_form.submit_element = submit_element;
32485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_form.action = action_target;
32495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_form.blacklisted_by_user = blacklist;
32505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_form.date_created = time;
32515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return password_form;
32535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
32545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace
32565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// See AddSavedPassword() in chrome/test/functional/pyauto.py for sample json
32585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// input.
32595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json output: { "password_added": true }
32605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::AddSavedPassword(
32615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
32625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
32635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
32645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue* password_dict = NULL;
32655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetDictionary("password", &password_dict)) {
32665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
32675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Must specify a password dictionary.");
32685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
32695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
32705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The "signon realm" is effectively the primary key and must be included.
32725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Check here before calling GetPasswordFormFromDict.
32735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!password_dict->HasKey("signon_realm")) {
32745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
32755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Password must include a value for 'signon_realm.'");
32765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
32775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
32785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  content::PasswordForm new_password =
32805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      GetPasswordFormFromDict(*password_dict);
32815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Use IMPLICIT_ACCESS since new passwords aren't added in incognito mode.
32835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PasswordStore* password_store = PasswordStoreFactory::GetForProfile(
32847d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      browser->profile(), Profile::IMPLICIT_ACCESS).get();
32855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The password store does not exist for an incognito window.
32875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (password_store == NULL) {
32885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
32895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return_value->SetBoolean("password_added", false);
32905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendSuccess(return_value.get());
32915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
32925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
32935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
32945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This observer will delete itself.
32955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PasswordStoreLoginsChangedObserver* observer =
32965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new PasswordStoreLoginsChangedObserver(this, reply_message,
32975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                             PasswordStoreChange::ADD,
32985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                             "password_added");
32995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  observer->Init();
33005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_store->AddLogin(new_password);
33015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
33025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// See RemoveSavedPassword() in chrome/test/functional/pyauto.py for sample
33045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// json input.
33055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json output: {}
33065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::RemoveSavedPassword(
33075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
33085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
33095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
33105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue* password_dict = NULL;
33115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetDictionary("password", &password_dict)) {
33135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
33145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Must specify a password dictionary.");
33155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
33165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
33175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The "signon realm" is effectively the primary key and must be included.
33195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Check here before calling GetPasswordFormFromDict.
33205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!password_dict->HasKey("signon_realm")) {
33215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
33225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Password must include a value for 'signon_realm.'");
33235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
33245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
33255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  content::PasswordForm to_remove =
33265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      GetPasswordFormFromDict(*password_dict);
33275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Use EXPLICIT_ACCESS since passwords can be removed in incognito mode.
33295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PasswordStore* password_store = PasswordStoreFactory::GetForProfile(
33307d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      browser->profile(), Profile::EXPLICIT_ACCESS).get();
33315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (password_store == NULL) {
33325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
33335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Unable to get password store.");
33345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
33355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
33365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This observer will delete itself.
33385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PasswordStoreLoginsChangedObserver* observer =
33395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new PasswordStoreLoginsChangedObserver(
3340c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)          this, reply_message, PasswordStoreChange::REMOVE, std::string());
33415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  observer->Init();
33425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_store->RemoveLogin(to_remove);
33445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
33455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetSavedPasswords" }
33475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to GetSavedPasswords() in chrome/test/pyautolib/pyauto.py for sample
33485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// json output.
33495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetSavedPasswords(
33505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
33515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
33525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
33535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Use EXPLICIT_ACCESS since saved passwords can be retrieved in
33545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // incognito mode.
33555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PasswordStore* password_store = PasswordStoreFactory::GetForProfile(
33567d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      browser->profile(), Profile::EXPLICIT_ACCESS).get();
33575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (password_store == NULL) {
33595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply reply(this, reply_message);
33605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Unable to get password store.");
33615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
33625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
33635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  password_store->GetAutofillableLogins(
33645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new AutomationProviderGetPasswordsObserver(this, reply_message));
33655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Observer deletes itself after sending the result.
33665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
33675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace {
33695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Get the WebContents from a dictionary of arguments.
33712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)WebContents* GetWebContentsFromDict(const Browser* browser,
33725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                    const DictionaryValue* args,
33735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                    std::string* error_message) {
33745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int tab_index;
33755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("tab_index", &tab_index)) {
33765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *error_message = "Must include tab_index.";
33775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return NULL;
33785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
33795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  WebContents* web_contents =
33812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->tab_strip_model()->GetWebContentsAt(tab_index);
33822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (!web_contents) {
33832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    *error_message = base::StringPrintf("No tab at index %d.", tab_index);
33845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return NULL;
33855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
33862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  return web_contents;
33875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
33885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace
33905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
33915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::FindInPage(
33925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
33935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
33945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
33955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_message;
33962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  WebContents* web_contents =
33972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      GetWebContentsFromDict(browser, args, &error_message);
33982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (!web_contents) {
33995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error_message);
34005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
34015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
34025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 search_string;
34035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool forward;
34045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool match_case;
34055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool find_next;
34065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("search_string", &search_string)) {
34075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).
34085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        SendError("Must include search_string string.");
34095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
34105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
34115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("forward", &forward)) {
34125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).
34135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        SendError("Must include forward boolean.");
34145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
34155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
34165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("match_case", &match_case)) {
34175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).
34185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        SendError("Must include match_case boolean.");
34195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
34205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
34215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("find_next", &find_next)) {
34225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).
34235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        SendError("Must include find_next boolean.");
34245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
34255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
34262a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  SendFindRequest(web_contents,
34275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  true,
34285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  search_string,
34295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  forward,
34305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  match_case,
34315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  find_next,
34325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  reply_message);
34335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
34345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
34355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OpenFindInPage(
34365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
34375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
34385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
34395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
34405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
34415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
34425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
34435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
34445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
34455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  chrome::FindInPage(browser, false, false);
34465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
34475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
34485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
34495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsFindInPageVisible(
34505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
34515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
34525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
34535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool visible;
34545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
34555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
34565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
34575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
34585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
34595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
34605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  FindBarTesting* find_bar =
34615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser->GetFindBarController()->find_bar()->GetFindBarTesting();
34625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  find_bar->GetFindBarWindowInfo(NULL, &visible);
34635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
34645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("is_visible", visible);
34655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&dict);
34665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
34675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
34685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::InstallExtension(
34695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
34702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  base::FilePath::StringType path_string;
34715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool with_ui;
34725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool from_webstore = false;
34735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
34745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  content::WebContents* tab;
34755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
34765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserAndTabFromJSONArgs(args, &browser, &tab, &error_msg)) {
34775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error_msg);
34785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
34795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
34805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("path", &path_string)) {
34815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
34825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Missing or invalid 'path'");
34835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
34845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
34855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("with_ui", &with_ui)) {
34865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
34875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Missing or invalid 'with_ui'");
34885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
34895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
34905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  args->GetBoolean("from_webstore", &from_webstore);
34915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
34922a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ExtensionService* service = extensions::ExtensionSystem::Get(
34932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->profile())->extension_service();
34945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExtensionProcessManager* manager =
34955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      extensions::ExtensionSystem::Get(browser->profile())->process_manager();
34965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (service && manager) {
34975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // The observer will delete itself when done.
34985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    new ExtensionReadyNotificationObserver(
34995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        manager,
35005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        service,
35015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        this,
35025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        reply_message);
35035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
35042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    base::FilePath extension_path(path_string);
35055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // If the given path has a 'crx' extension, assume it is a packed extension
35065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // and install it. Otherwise load it as an unpacked extension.
35075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (extension_path.MatchesExtension(FILE_PATH_LITERAL(".crx"))) {
35085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      ExtensionInstallPrompt* client = (with_ui ?
35095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          new ExtensionInstallPrompt(tab) :
35105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          NULL);
35115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      scoped_refptr<extensions::CrxInstaller> installer(
35125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          extensions::CrxInstaller::Create(service, client));
35135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (!with_ui)
35145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        installer->set_allow_silent_install(true);
35155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      installer->set_install_cause(extension_misc::INSTALL_CAUSE_AUTOMATION);
35165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (from_webstore)
35175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        installer->set_creation_flags(Extension::FROM_WEBSTORE);
35185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      installer->InstallCrx(extension_path);
35195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
35205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      scoped_refptr<extensions::UnpackedInstaller> installer(
35215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          extensions::UnpackedInstaller::Create(service));
35225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      installer->set_prompt_for_plugins(with_ui);
35235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      installer->Load(extension_path);
35245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
35255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
35265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
35275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Extensions service/process manager is not available");
35285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
35295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
35305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
35315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace {
35325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
35335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)ListValue* GetHostPermissions(const Extension* ext, bool effective_perm) {
35342a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  extensions::URLPatternSet pattern_set;
353590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  if (effective_perm) {
353690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    pattern_set =
353790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        extensions::PermissionsData::GetEffectiveHostPermissions(ext);
353890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else {
35395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    pattern_set = ext->GetActivePermissions()->explicit_hosts();
354090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  }
35415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
35425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* permissions = new ListValue;
35432a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  for (extensions::URLPatternSet::const_iterator perm = pattern_set.begin();
35445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)       perm != pattern_set.end(); ++perm) {
35455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    permissions->Append(new StringValue(perm->GetAsString()));
35465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
35475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
35485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return permissions;
35495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
35505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
35515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)ListValue* GetAPIPermissions(const Extension* ext) {
35525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* permissions = new ListValue;
35535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::set<std::string> perm_list =
35545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      ext->GetActivePermissions()->GetAPIsAsStrings();
35555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (std::set<std::string>::const_iterator perm = perm_list.begin();
35565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)       perm != perm_list.end(); ++perm) {
35575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    permissions->Append(new StringValue(perm->c_str()));
35585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
35595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return permissions;
35605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
35615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
35625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace
35635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
35645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetExtensionsInfo" }
35655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// See GetExtensionsInfo() in chrome/test/pyautolib/pyauto.py for sample json
35665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// output.
35675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetExtensionsInfo(DictionaryValue* args,
35685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                  IPC::Message* reply_message) {
35695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
35705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
35715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
35725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
35735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
35745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
35755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
35762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ExtensionService* service = extensions::ExtensionSystem::Get(
35772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->profile())->extension_service();
35785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!service) {
35795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("No extensions service.");
35805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
35815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
35825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
35835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* extensions_values = new ListValue;
35845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const ExtensionSet* extensions = service->extensions();
35855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const ExtensionSet* disabled_extensions = service->disabled_extensions();
35865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExtensionList all;
35875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  all.insert(all.end(),
35885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)             extensions->begin(),
35895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)             extensions->end());
35905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  all.insert(all.end(),
35915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)             disabled_extensions->begin(),
35925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)             disabled_extensions->end());
35935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExtensionActionManager* extension_action_manager =
35945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      ExtensionActionManager::Get(browser->profile());
35955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (ExtensionList::const_iterator it = all.begin();
35965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)       it != all.end(); ++it) {
3597868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    const Extension* extension = it->get();
35985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    std::string id = extension->id();
35995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* extension_value = new DictionaryValue;
36005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetString("id", id);
36015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetString("version", extension->VersionString());
36025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetString("name", extension->name());
36035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetString("public_key", extension->public_key());
36045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetString("description", extension->description());
36052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    extension_value->SetString(
36062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        "background_url",
36072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        extensions::BackgroundInfo::GetBackgroundURL(extension).spec());
36085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetString("options_url",
36092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        extensions::ManifestURL::GetOptionsPage(extension).spec());
36105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->Set("host_permissions",
36115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         GetHostPermissions(extension, false));
36125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->Set("effective_host_permissions",
36135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         GetHostPermissions(extension, true));
36145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->Set("api_permissions", GetAPIPermissions(extension));
36152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    Manifest::Location location = extension->location();
36165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetBoolean("is_component",
36172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                location == Manifest::COMPONENT);
36185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetBoolean("is_internal",
36192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                location == Manifest::INTERNAL);
36205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetBoolean("is_user_installed",
36212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        location == Manifest::INTERNAL ||
36222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        Manifest::IsUnpackedLocation(location));
36235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetBoolean("is_enabled", service->IsExtensionEnabled(id));
36245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetBoolean("allowed_in_incognito",
36255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                service->IsIncognitoEnabled(id));
36265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extension_value->SetBoolean(
36275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "has_page_action",
36285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        extension_action_manager->GetPageAction(*extension) != NULL);
36295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    extensions_values->Append(extension_value);
36305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
36315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->Set("extensions", extensions_values);
36325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(return_value.get());
36335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
36345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
36355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// See UninstallExtensionById() in chrome/test/pyautolib/pyauto.py for sample
36365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// json input.
36375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json output: {}
36385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::UninstallExtensionById(
36395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
36405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
36415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const Extension* extension;
36425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
36435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
36445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error)) {
36455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
36465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
36475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
36485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetExtensionFromJSONArgs(
36495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          args, "id", browser->profile(), &extension, &error)) {
36505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
36515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
36525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
36532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ExtensionService* service = extensions::ExtensionSystem::Get(
36542a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->profile())->extension_service();
36555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!service) {
36565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
36575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "No extensions service.");
36585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
36595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
36605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
36615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Wait for a notification indicating that the extension with the given ID
36625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // has been uninstalled.  This observer will delete itself.
36635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new ExtensionUninstallObserver(this, reply_message, extension->id());
36645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  service->UninstallExtension(extension->id(), false, NULL);
36655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
36665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
36675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// See SetExtensionStateById() in chrome/test/pyautolib/pyauto.py
36685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// for sample json input.
36695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetExtensionStateById(
36705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
36715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
36725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const Extension* extension;
36735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
36745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
36755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error)) {
36765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
36775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
36785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
36795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetExtensionFromJSONArgs(
36805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          args, "id", browser->profile(), &extension, &error)) {
36815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
36825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
36835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
36845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
36855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool enable;
36865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("enable", &enable)) {
36875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
36885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("Missing or invalid key: enable");
36895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
36905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
36915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
36925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool allow_in_incognito;
36935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("allow_in_incognito", &allow_in_incognito)) {
36945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
36955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("Missing or invalid key: allow_in_incognito");
36965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
36975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
36985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
36995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (allow_in_incognito && !enable) {
37005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
37015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("Invalid state: Disabled extension "
37025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                    "cannot be allowed in incognito mode.");
37035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
37045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
37055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
37062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ExtensionService* service = extensions::ExtensionSystem::Get(
37072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->profile())->extension_service();
37085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExtensionProcessManager* manager =
37095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      extensions::ExtensionSystem::Get(browser->profile())->process_manager();
37105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!service) {
37115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
37125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("No extensions service or process manager.");
37135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
37145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
37155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
37165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (enable) {
37175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!service->IsExtensionEnabled(extension->id())) {
37185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new ExtensionReadyNotificationObserver(
37195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          manager,
37205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          service,
37215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          this,
37225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          reply_message);
37235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      service->EnableExtension(extension->id());
37245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    } else {
37255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      AutomationJSONReply(this, reply_message).SendSuccess(NULL);
37265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
37275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
37285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    service->DisableExtension(extension->id(),
37295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                              Extension::DISABLE_USER_ACTION);
37305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendSuccess(NULL);
37315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
37325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
37335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  service->SetIsIncognitoEnabled(extension->id(), allow_in_incognito);
37345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
37355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
37365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// See TriggerPageActionById() in chrome/test/pyautolib/pyauto.py
37375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// for sample json input.
37385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::TriggerPageActionById(
37395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
37405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
37415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
37425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
37435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* tab;
37445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserAndTabFromJSONArgs(args, &browser, &tab, &error)) {
37455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
37465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
37475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
37485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const Extension* extension;
37495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetEnabledExtensionFromJSONArgs(
37505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          args, "id", browser->profile(), &extension, &error)) {
37515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
37525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
37535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
37545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExtensionAction* page_action =
37555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      ExtensionActionManager::Get(browser->profile())->
37565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      GetPageAction(*extension);
37575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!page_action) {
37585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
37595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Extension doesn't have any page action.");
37605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
37615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
37625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EnsureTabSelected(browser, tab);
37635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
37645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool pressed = false;
37655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  LocationBarTesting* loc_bar =
37665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser->window()->GetLocationBar()->GetLocationBarForTesting();
37675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  size_t page_action_visible_count =
37685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      static_cast<size_t>(loc_bar->PageActionVisibleCount());
37695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (size_t i = 0; i < page_action_visible_count; ++i) {
37705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (loc_bar->GetVisiblePageAction(i) == page_action) {
37715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      loc_bar->TestPageActionPressed(i);
37725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      pressed = true;
37735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      break;
37745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
37755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
37765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!pressed) {
37775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
37785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Extension's page action is not visible.");
37795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
37805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
37815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
37825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (page_action->HasPopup(ExtensionTabUtil::GetTabId(tab))) {
37835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // This observer will delete itself.
37845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    new ExtensionPopupObserver(
37855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        this, reply_message, extension->id());
37865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
37875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendSuccess(NULL);
37885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
37895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
37905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
37915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// See TriggerBrowserActionById() in chrome/test/pyautolib/pyauto.py
37925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// for sample json input.
37935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::TriggerBrowserActionById(
37945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
37955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
37965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
37975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
37985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* tab;
37995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserAndTabFromJSONArgs(args, &browser, &tab, &error)) {
38005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
38015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
38025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
38035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const Extension* extension;
38045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetEnabledExtensionFromJSONArgs(
38055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          args, "id", browser->profile(), &extension, &error)) {
38065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
38075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
38085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
38095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExtensionAction* action = ExtensionActionManager::Get(browser->profile())->
38105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      GetBrowserAction(*extension);
38115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!action) {
38125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
38135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Extension doesn't have any browser action.");
38145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
38155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
38165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EnsureTabSelected(browser, tab);
38175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
38185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BrowserActionTestUtil browser_actions(browser);
38195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int num_browser_actions = browser_actions.NumberOfBrowserActions();
38205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int action_index = -1;
38215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(TOOLKIT_VIEWS)
38225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (int i = 0; i < num_browser_actions; ++i) {
38235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (extension->id() == browser_actions.GetExtensionId(i)) {
38245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      action_index = i;
38255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      break;
38265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
38275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
38285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
38295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // TODO(kkania): Implement the platform-specific GetExtensionId() in
38305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // BrowserActionTestUtil.
38315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (num_browser_actions != 1) {
38322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(base::StringPrintf(
38335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Found %d browser actions. Only one browser action must be active.",
38345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        num_browser_actions));
38355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
38365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
38375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This extension has a browser action, and there's only one action, so this
38385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // must be the first one.
38395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  action_index = 0;
38405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
38415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (action_index == -1) {
38425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
38435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Extension's browser action is not visible.");
38445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
38455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
38465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_actions.Press(action_index);
38475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
38485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (action->HasPopup(ExtensionTabUtil::GetTabId(tab))) {
38495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    // This observer will delete itself.
38505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    new ExtensionPopupObserver(
38515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        this, reply_message, extension->id());
38525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
38535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendSuccess(NULL);
38545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
38555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
38565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
38575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ActionOnSSLBlockingPage(
38585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
38595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
38605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
38615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool proceed;
38625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
38635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetTabFromJSONArgs(args, &web_contents, &error)) {
38645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
38655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
38665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
38675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("proceed", &proceed)) {
38685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
38695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "'proceed' is missing or invalid");
38705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
38715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
38725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NavigationController& controller = web_contents->GetController();
38735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NavigationEntry* entry = controller.GetActiveEntry();
38745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (entry->GetPageType() == content::PAGE_TYPE_INTERSTITIAL) {
38755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    InterstitialPage* ssl_blocking_page =
38765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        InterstitialPage::GetInterstitialPage(web_contents);
38775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (ssl_blocking_page) {
38785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (proceed) {
38795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        new NavigationNotificationObserver(&controller, this, reply_message, 1,
38805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                           false, true);
38815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        ssl_blocking_page->Proceed();
38825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
38835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
38845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      ssl_blocking_page->DontProceed();
38855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      AutomationJSONReply(this, reply_message).SendSuccess(NULL);
38865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
38875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
38885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
38895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendError(error);
38905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
38915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
38925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetSecurityState(DictionaryValue* args,
38935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                 IPC::Message* reply_message) {
38945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
38955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
38965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
38975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetTabFromJSONArgs(args, &web_contents, &error)) {
38985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error);
38995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
39005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
39015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NavigationEntry* entry = web_contents->GetController().GetActiveEntry();
39025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
39035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetInteger("security_style",
39045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  static_cast<int>(entry->GetSSL().security_style));
39055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetInteger("ssl_cert_status",
39065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  static_cast<int>(entry->GetSSL().cert_status));
39075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetInteger("insecure_content_status",
39085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  static_cast<int>(entry->GetSSL().content_status));
39095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&dict);
39105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
39115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
39125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "UpdateExtensionsNow" }
39135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json output: {}
39145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::UpdateExtensionsNow(
39155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
39165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
39175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
39185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
39195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error)) {
39205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
39215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
39225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
39232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ExtensionService* service = extensions::ExtensionSystem::Get(
39242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->profile())->extension_service();
39255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!service) {
39265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
39275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "No extensions service.");
39285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
39295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
39305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
39315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  extensions::ExtensionUpdater* updater = service->updater();
39325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!updater) {
39335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
39345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "No updater for extensions service.");
39355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
39365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
39375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
39385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExtensionProcessManager* manager =
39395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      extensions::ExtensionSystem::Get(browser->profile())->process_manager();
39405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!manager) {
39415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
39425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "No extension process manager.");
39435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
39445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
39455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
39465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Create a new observer that waits until the extensions have been fully
39475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // updated (we should not send the reply until after all extensions have
39485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // been updated).  This observer will delete itself.
39492a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ExtensionsUpdatedObserver* observer = new ExtensionsUpdatedObserver(
39502a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      manager, this, reply_message);
39512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  extensions::ExtensionUpdater::CheckParams params;
39522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  params.install_immediately = true;
39532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  params.callback = base::Bind(&ExtensionsUpdatedObserver::UpdateCheckFinished,
39542a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                               base::Unretained(observer));
39552a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  updater->CheckNow(params);
39565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
39575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
39585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace {
39595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
39605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void SendSuccessIfAlive(
39615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::WeakPtr<AutomationProvider> provider,
39625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
3963868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  if (provider.get())
39645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(provider.get(), reply_message).SendSuccess(NULL);
39655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
39665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
39675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace
39685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
39695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OverrideGeoposition(
39705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
39715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
39725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  double latitude, longitude, altitude;
39735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetDouble("latitude", &latitude) ||
39745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetDouble("longitude", &longitude) ||
39755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetDouble("altitude", &altitude)) {
39765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
39775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Missing or invalid geolocation parameters");
39785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
39795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
39805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  content::Geoposition position;
39815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  position.latitude = latitude;
39825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  position.longitude = longitude;
39835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  position.altitude = altitude;
39845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  position.accuracy = 0.;
39855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  position.timestamp = base::Time::Now();
3986b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)
3987b2df76ea8fec9e32f6f3718986dba0d95315b29cTorne (Richard Coles)  content::GeolocationProvider::OverrideLocationForTesting(
39885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      position,
39895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      base::Bind(&SendSuccessIfAlive, AsWeakPtr(), reply_message));
39905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
39915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
39925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to GetAllNotifications() in chrome/test/pyautolib/pyauto.py for
39935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// sample json input/output.
39945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetAllNotifications(
39955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
39965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
39975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
39985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new GetAllNotificationsObserver(this, reply_message);
39995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
40005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
40015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to CloseNotification() in chrome/test/pyautolib/pyauto.py for
40025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// sample json input.
40035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Returns empty json message.
40045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::CloseNotification(
40055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
40065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
40075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
40085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int index;
40095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("index", &index)) {
40105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
40115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'index' missing or invalid.");
40125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
40135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
40142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  BalloonNotificationUIManager* manager =
40152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      BalloonNotificationUIManager::GetInstanceForTesting();
40165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BalloonCollection* collection = manager->balloon_collection();
40175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const BalloonCollection::Balloons& balloons = collection->GetActiveBalloons();
40185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int balloon_count = static_cast<int>(balloons.size());
40195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (index < 0 || index >= balloon_count) {
40205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
40212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        .SendError(base::StringPrintf("No notification at index %d", index));
40225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
40235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
40245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::vector<const Notification*> queued_notes;
40255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  manager->GetQueuedNotificationsForTesting(&queued_notes);
40265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (queued_notes.empty()) {
40275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    new OnNotificationBalloonCountObserver(
40285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        this, reply_message, balloon_count - 1);
40295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
40305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    new NewNotificationBalloonObserver(this, reply_message);
40315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
40325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  manager->CancelById(balloons[index]->notification().notification_id());
40335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
40345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
40355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to WaitForNotificationCount() in chrome/test/pyautolib/pyauto.py for
40365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// sample json input.
40375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Returns empty json message.
40385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WaitForNotificationCount(
40395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
40405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
40415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
40425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int count;
40435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("count", &count)) {
40445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
40455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'count' missing or invalid.");
40465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
40475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
40485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This will delete itself when finished.
40495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new OnNotificationBalloonCountObserver(this, reply_message, count);
40505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
40515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
40525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample JSON input: { "command": "GetNTPInfo" }
40535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// For output, refer to chrome/test/pyautolib/ntp_model.py.
40545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetNTPInfo(
40555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
40565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
40575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
40585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This observer will delete itself.
40595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new NTPInfoObserver(this, reply_message);
40605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
40615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
40625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::RemoveNTPMostVisitedThumbnail(
40635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
40645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
40655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
40665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
40675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string url;
40685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("url", &url)) {
40695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Missing or invalid 'url' key.");
40705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
40715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
40725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  history::TopSites* top_sites = browser->profile()->GetTopSites();
40735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!top_sites) {
40745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("TopSites service is not initialized.");
40755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
40765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
40775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  top_sites->AddBlacklistedURL(GURL(url));
40785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
40795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
40805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
40815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::RestoreAllNTPMostVisitedThumbnails(
40825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
40835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
40845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
40855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
40865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  history::TopSites* top_sites = browser->profile()->GetTopSites();
40875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!top_sites) {
40885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("TopSites service is not initialized.");
40895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
40905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
40915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  top_sites->ClearBlacklistedURLs();
40925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
40935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
40945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
40955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::KillRendererProcess(
40965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
40975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
40985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
40995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int pid;
4100c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  uint32 kAccessFlags = base::kProcessAccessTerminate |
4101c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)                        base::kProcessAccessWaitForTermination |
4102c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)                        base::kProcessAccessQueryInformation;
4103c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)
41045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("pid", &pid)) {
41055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
41065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'pid' key missing or invalid.");
41075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
41085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
41095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  base::ProcessHandle process;
4110c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)  if (!base::OpenProcessHandleWithAccess(static_cast<base::ProcessId>(pid),
4111c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)                                         kAccessFlags,
4112c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)                                         &process)) {
41135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(base::StringPrintf(
41145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Failed to open process handle for pid %d", pid));
41155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
41165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
41175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new RendererProcessClosedObserver(this, reply_message);
41185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  base::KillProcess(process, 0, false);
41195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  base::CloseProcessHandle(process);
41205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
41215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
41225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool TestingAutomationProvider::BuildWebKeyEventFromArgs(
41235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
41245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    std::string* error,
41255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NativeWebKeyboardEvent* event) {
41265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int type, modifiers;
41275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool is_system_key;
41285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 unmodified_text, text;
41295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string key_identifier;
41305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("type", &type)) {
41315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *error = "'type' missing or invalid.";
41325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
41335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
41345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("isSystemKey", &is_system_key)) {
41355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *error = "'isSystemKey' missing or invalid.";
41365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
41375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
41385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("unmodifiedText", &unmodified_text)) {
41395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *error = "'unmodifiedText' missing or invalid.";
41405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
41415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
41425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("text", &text)) {
41435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *error = "'text' missing or invalid.";
41445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
41455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
41465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("nativeKeyCode", &event->nativeKeyCode)) {
41475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *error = "'nativeKeyCode' missing or invalid.";
41485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
41495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
41505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("windowsKeyCode", &event->windowsKeyCode)) {
41515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *error = "'windowsKeyCode' missing or invalid.";
41525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
41535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
41545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("modifiers", &modifiers)) {
41555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *error = "'modifiers' missing or invalid.";
41565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
41575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
41585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (args->GetString("keyIdentifier", &key_identifier)) {
41595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::strlcpy(event->keyIdentifier,
41605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  key_identifier.c_str(),
41615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  WebKit::WebKeyboardEvent::keyIdentifierLengthCap);
41625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
41635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    event->setKeyIdentifierFromWindowsKeyCode();
41645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
41655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
41665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (type == automation::kRawKeyDownType) {
41675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    event->type = WebKit::WebInputEvent::RawKeyDown;
41685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (type == automation::kKeyDownType) {
41695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    event->type = WebKit::WebInputEvent::KeyDown;
41705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (type == automation::kKeyUpType) {
41715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    event->type = WebKit::WebInputEvent::KeyUp;
41725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (type == automation::kCharType) {
41735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    event->type = WebKit::WebInputEvent::Char;
41745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
41755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *error = "'type' refers to an unrecognized keyboard event type";
41765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return false;
41775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
41785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
41795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 unmodified_text_truncated = unmodified_text.substr(
41805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      0, WebKit::WebKeyboardEvent::textLengthCap - 1);
41815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  memcpy(event->unmodifiedText,
41825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         unmodified_text_truncated.c_str(),
41835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)         unmodified_text_truncated.length() + 1);
41845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 text_truncated = text.substr(
41855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      0, WebKit::WebKeyboardEvent::textLengthCap - 1);
41865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  memcpy(event->text, text_truncated.c_str(), text_truncated.length() + 1);
41875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
41885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->modifiers = 0;
41895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (modifiers & automation::kShiftKeyMask)
41905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    event->modifiers |= WebKit::WebInputEvent::ShiftKey;
41915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (modifiers & automation::kControlKeyMask)
41925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    event->modifiers |= WebKit::WebInputEvent::ControlKey;
41935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (modifiers & automation::kAltKeyMask)
41945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    event->modifiers |= WebKit::WebInputEvent::AltKey;
41955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (modifiers & automation::kMetaKeyMask)
41965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    event->modifiers |= WebKit::WebInputEvent::MetaKey;
41975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
41985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->isSystemKey = is_system_key;
41995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->timeStampSeconds = base::Time::Now().ToDoubleT();
42005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->skip_in_browser = true;
42015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return true;
42025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
42035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::BuildSimpleWebKeyEvent(
42055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    WebKit::WebInputEvent::Type type,
42065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int windows_key_code,
42075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NativeWebKeyboardEvent* event) {
42085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->nativeKeyCode = 0;
42095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->windowsKeyCode = windows_key_code;
42105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->setKeyIdentifierFromWindowsKeyCode();
42115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->type = type;
42125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->modifiers = 0;
42135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->isSystemKey = false;
42145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->timeStampSeconds = base::Time::Now().ToDoubleT();
42155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  event->skip_in_browser = true;
42165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
42175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SendWebKeyPressEventAsync(
42195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int key_code,
42205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    WebContents* web_contents) {
42215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Create and send a "key down" event for the specified key code.
42225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NativeWebKeyboardEvent event_down;
42235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BuildSimpleWebKeyEvent(WebKit::WebInputEvent::RawKeyDown, key_code,
42245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                         &event_down);
42255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  web_contents->GetRenderViewHost()->ForwardKeyboardEvent(event_down);
42265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Create and send a corresponding "key up" event.
42285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NativeWebKeyboardEvent event_up;
42295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BuildSimpleWebKeyEvent(WebKit::WebInputEvent::KeyUp, key_code, &event_up);
42305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  web_contents->GetRenderViewHost()->ForwardKeyboardEvent(event_up);
42315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
42325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SendWebkitKeyEvent(
42345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
42355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
42365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
42375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
42385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NativeWebKeyboardEvent event;
42405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // In the event of an error, BuildWebKeyEventFromArgs handles telling what
42415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // went wrong and sending the reply message; if it fails, we just have to
42425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // stop here.
42435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
42445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!BuildWebKeyEventFromArgs(args, &error, &event)) {
42455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
42465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
42475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
42485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* view;
42505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetRenderViewFromJSONArgs(args, profile(), &view, &error)) {
42515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
42525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
42535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
42545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new InputEventAckNotificationObserver(this, reply_message, event.type, 1);
42555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ForwardKeyboardEvent(event);
42565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
42575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace {
42595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Gets the active JavaScript modal dialog, or NULL if none.
42615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)JavaScriptAppModalDialog* GetActiveJavaScriptModalDialog(
42625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    ErrorCode* error_code) {
42635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AppModalDialogQueue* dialog_queue = AppModalDialogQueue::GetInstance();
42645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!dialog_queue->HasActiveDialog() ||
42655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !dialog_queue->active_dialog()->IsJavaScriptModalDialog()) {
42665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    *error_code = automation::kNoJavaScriptModalDialogOpen;
42675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return NULL;
42685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
42695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return static_cast<JavaScriptAppModalDialog*>(dialog_queue->active_dialog());
42705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
42715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace
42735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetAppModalDialogMessage(
42755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
42765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
42775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ErrorCode code;
42785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  JavaScriptAppModalDialog* dialog = GetActiveJavaScriptModalDialog(&code);
42795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!dialog) {
42805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendErrorCode(code);
42815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
42825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
42835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue result_dict;
42845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  result_dict.SetString("message", UTF16ToUTF8(dialog->message_text()));
42855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&result_dict);
42865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
42875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::AcceptOrDismissAppModalDialog(
42895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
42905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
42915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool accept;
42925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("accept", &accept)) {
42935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Missing or invalid 'accept'");
42945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
42955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
42965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
42975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ErrorCode code;
42985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  JavaScriptAppModalDialog* dialog = GetActiveJavaScriptModalDialog(&code);
42995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!dialog) {
43005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendErrorCode(code);
43015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
43025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
43035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (accept) {
43045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    std::string prompt_text;
43055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (args->GetString("prompt_text", &prompt_text))
43065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      dialog->SetOverridePromptText(UTF8ToUTF16(prompt_text));
43075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    dialog->native_dialog()->AcceptAppModalDialog();
43085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
43095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    dialog->native_dialog()->CancelAppModalDialog();
43105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
43115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
43125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
43135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
43145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample JSON input: { "command": "LaunchApp",
43155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "id": "ahfgeienlihckogmohjhadlkjgocpleb" }
43165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample JSON output: {}
43175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::LaunchApp(
43185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
43195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
43205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
43215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string id;
43225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("id", &id)) {
43235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
43245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Must include string id.");
43255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
43265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
43275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
43282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ExtensionService* service = extensions::ExtensionSystem::Get(
43292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->profile())->extension_service();
43305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!service) {
43315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
43325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "No extensions service.");
43335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
43345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
43355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
43365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const Extension* extension = service->GetExtensionById(
43375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      id, false  /* do not include disabled extensions */);
43385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!extension) {
43395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
43402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        base::StringPrintf(
43412a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)            "Extension with ID '%s' doesn't exist or is disabled.",
43422a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)            id.c_str()));
43435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
43445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
43455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
43462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  WebContents* old_contents =
43472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->tab_strip_model()->GetActiveWebContents();
43485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!old_contents) {
43495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
43505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Cannot identify selected tab contents.");
43515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
43525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
43535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
43542a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  chrome::AppLaunchParams launch_params(profile(), extension, CURRENT_TAB);
43555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This observer will delete itself.
43565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new AppLaunchObserver(&old_contents->GetController(), this, reply_message,
43572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                        launch_params.container);
43582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  chrome::OpenApplication(launch_params);
43595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
43605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
43615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample JSON input: { "command": "SetAppLaunchType",
43625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "id": "ahfgeienlihckogmohjhadlkjgocpleb",
43635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "launch_type": "pinned" }
43645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample JSON output: {}
43655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetAppLaunchType(
43665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
43675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
43685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
43695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
43705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
43715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string id;
43725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("id", &id)) {
43735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Must include string id.");
43745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
43755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
43765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
43775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string launch_type_str;
43785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("launch_type", &launch_type_str)) {
43795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Must specify app launch type.");
43805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
43815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
43825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
43832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ExtensionService* service = extensions::ExtensionSystem::Get(
43842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      browser->profile())->extension_service();
43855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!service) {
43865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("No extensions service.");
43875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
43885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
43895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
43905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const Extension* extension = service->GetExtensionById(
43915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      id, true  /* include disabled extensions */);
43925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!extension) {
43932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    reply.SendError(base::StringPrintf(
43942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        "Extension with ID '%s' doesn't exist.", id.c_str()));
43955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
43965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
43975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
43985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  extensions::ExtensionPrefs::LaunchType launch_type;
43995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (launch_type_str == "pinned") {
44005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    launch_type = extensions::ExtensionPrefs::LAUNCH_PINNED;
44015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (launch_type_str == "regular") {
44025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    launch_type = extensions::ExtensionPrefs::LAUNCH_REGULAR;
44035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (launch_type_str == "fullscreen") {
44045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    launch_type = extensions::ExtensionPrefs::LAUNCH_FULLSCREEN;
44055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (launch_type_str == "window") {
44065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    launch_type = extensions::ExtensionPrefs::LAUNCH_WINDOW;
44075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
44082a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    reply.SendError(base::StringPrintf(
44092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        "Unexpected launch type '%s'.", launch_type_str.c_str()));
44105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
44115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
44125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  service->extension_prefs()->SetLaunchType(extension->id(), launch_type);
44145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
44155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
44165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetV8HeapStats",
44185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "tab_index": 0 }
44195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to GetV8HeapStats() in chrome/test/pyautolib/pyauto.py for
44205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// sample json output.
44215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetV8HeapStats(
44225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
44235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
44245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
44255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
44265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int tab_index;
44275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
44285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("tab_index", &tab_index)) {
44305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
44315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Missing 'tab_index' argument.");
44325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
44335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
44345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44352a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  web_contents = browser->tab_strip_model()->GetWebContentsAt(tab_index);
44365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!web_contents) {
44372a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(base::StringPrintf(
44382a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        "Could not get WebContents at tab index %d", tab_index));
44395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
44405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
44415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* render_view = web_contents->GetRenderViewHost();
44435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This observer will delete itself.
44455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new V8HeapStatsObserver(
44465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this, reply_message,
44475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      base::GetProcId(render_view->GetProcess()->GetHandle()));
44485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  render_view->Send(new ChromeViewMsg_GetV8HeapStats);
44495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
44505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Sample json input: { "command": "GetFPS",
44525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//                      "tab_index": 0 }
44535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Refer to GetFPS() in chrome/test/pyautolib/pyauto.py for
44545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// sample json output.
44555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetFPS(
44565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
44575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
44585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
44595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
44605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int tab_index;
44615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
44625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("tab_index", &tab_index)) {
44645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
44655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Missing 'tab_index' argument.");
44665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
44675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
44685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  web_contents = browser->tab_strip_model()->GetWebContentsAt(tab_index);
44705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!web_contents) {
44712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(base::StringPrintf(
44722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        "Could not get WebContents at tab index %d", tab_index));
44735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
44745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
44755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* render_view = web_contents->GetRenderViewHost();
44775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int routing_id = render_view->GetRoutingID();
44785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This observer will delete itself.
44805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new FPSObserver(
44815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this, reply_message,
44825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      base::GetProcId(render_view->GetProcess()->GetHandle()),
44835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      routing_id);
44845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  render_view->Send(new ChromeViewMsg_GetFPS(routing_id));
44855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
44865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsFullscreenForBrowser(Browser* browser,
44885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
44895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
44905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
44915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("result",
44925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  browser->fullscreen_controller()->IsFullscreenForBrowser());
44935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&dict);
44945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
44955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
44965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsFullscreenForTab(Browser* browser,
44975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
44985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
44995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
45005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("result",
45015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser->fullscreen_controller()->IsFullscreenForTabOrPending());
45025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&dict);
45035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
45045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
45055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsMouseLocked(Browser* browser,
45065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
45075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
45085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
45092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  dict.SetBoolean("result", browser->tab_strip_model()->GetActiveWebContents()->
45105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      GetRenderViewHost()->GetView()->IsMouseLocked());
45115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&dict);
45125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
45135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
45145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsMouseLockPermissionRequested(
45155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
45165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
45175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
45185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  FullscreenExitBubbleType type =
45195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser->fullscreen_controller()->GetFullscreenExitBubbleType();
45205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool mouse_lock = false;
45215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  fullscreen_bubble::PermissionRequestedByType(type, NULL, &mouse_lock);
45225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
45235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("result", mouse_lock);
45245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&dict);
45255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
45265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
45275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsFullscreenPermissionRequested(
45285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
45295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
45305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
45315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  FullscreenExitBubbleType type =
45325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser->fullscreen_controller()->GetFullscreenExitBubbleType();
45335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool fullscreen = false;
45345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  fullscreen_bubble::PermissionRequestedByType(type, &fullscreen, NULL);
45355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
45365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("result", fullscreen);
45375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&dict);
45385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
45395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
45405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsFullscreenBubbleDisplayed(Browser* browser,
45415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
45425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
45435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  FullscreenExitBubbleType type =
45445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser->fullscreen_controller()->GetFullscreenExitBubbleType();
45455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
45465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("result",
45475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  type != FEB_TYPE_BROWSER_FULLSCREEN_EXIT_INSTRUCTION);
45485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&dict);
45495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
45505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
45515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsFullscreenBubbleDisplayingButtons(
45525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
45535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
45545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
45555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  FullscreenExitBubbleType type =
45565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser->fullscreen_controller()->GetFullscreenExitBubbleType();
45575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
45585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("result", fullscreen_bubble::ShowButtonsForType(type));
45595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&dict);
45605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
45615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
45625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::AcceptCurrentFullscreenOrMouseLockRequest(
45635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
45645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
45655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
45662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  browser->fullscreen_controller()->OnAcceptFullscreenPermission();
45675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(NULL);
45685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
45695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
45705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::DenyCurrentFullscreenOrMouseLockRequest(
45715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Browser* browser,
45725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
45735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
45742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  browser->fullscreen_controller()->OnDenyFullscreenPermission();
45755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(NULL);
45765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
45775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
45785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WaitForTabToBeRestored(
45795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
45805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
45815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
45825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
45835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetTabFromJSONArgs(args, &web_contents, &error)) {
45845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
45855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
45865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
45875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NavigationController& controller = web_contents->GetController();
45885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new NavigationControllerRestoredObserver(this, &controller, reply_message);
45895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
45905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
45915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::RefreshPolicies(
45925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
45935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
45945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if !defined(ENABLE_CONFIGURATION_POLICY)
45955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendError(
45965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      "Configuration Policy disabled");
45975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else
45985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Some policies (e.g. URLBlacklist) post tasks to other message loops
45995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // before they start enforcing updated policy values; make sure those tasks
46005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // have finished after a policy update.
46015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Updates of the URLBlacklist are done on IO, after building the blacklist
46025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // on FILE, which is initiated from IO.
46035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  base::Closure reply =
46045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      base::Bind(SendSuccessReply, AsWeakPtr(), reply_message);
46055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  g_browser_process->policy_service()->RefreshPolicies(
46065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      base::Bind(PostTask, BrowserThread::IO,
46075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          base::Bind(PostTask, BrowserThread::FILE,
46085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)              base::Bind(PostTask, BrowserThread::IO,
46095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                  base::Bind(PostTask, BrowserThread::UI, reply)))));
46105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif
46115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
46125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
46135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)static int AccessArray(const volatile int arr[], const volatile int *index) {
46145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return arr[*index];
46155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
46165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
46175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SimulateAsanMemoryBug(
46185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args, IPC::Message* reply_message) {
46195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // This array is volatile not to let compiler optimize us out.
46205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  volatile int testarray[3] = {0, 0, 0};
46215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
46225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Send the reply while we can.
46235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(NULL);
46245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
46255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Cause Address Sanitizer to abort this process.
46265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  volatile int index = 5;
46275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AccessArray(testarray, &index);
46285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
46295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
46305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetIndicesFromTab(
46315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
46325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
46335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
46345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int id_or_handle = 0;
46355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool has_id = args->HasKey("tab_id");
46365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool has_handle = args->HasKey("tab_handle");
46375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (has_id && has_handle) {
46385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(
46395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "Both 'tab_id' and 'tab_handle' were specified. Only one is allowed");
46405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
46415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else if (!has_id && !has_handle) {
46425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Either 'tab_id' or 'tab_handle' must be specified");
46435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
46445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
46455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (has_id && !args->GetInteger("tab_id", &id_or_handle)) {
46465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'tab_id' is invalid");
46475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
46485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
46495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (has_handle && (!args->GetInteger("tab_handle", &id_or_handle) ||
46505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                     !tab_tracker_->ContainsHandle(id_or_handle))) {
46515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'tab_handle' is invalid");
46525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
46535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
46545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int id = id_or_handle;
46555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (has_handle) {
46565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    SessionTabHelper* session_tab_helper =
46575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        SessionTabHelper::FromWebContents(
46585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            tab_tracker_->GetResource(id_or_handle)->GetWebContents());
46595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    id = session_tab_helper->session_id().id();
46605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
46612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  chrome::BrowserIterator it;
46625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int browser_index = 0;
46632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  for (; !it.done(); it.Next(), ++browser_index) {
46642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    Browser* browser = *it;
46652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    for (int tab_index = 0;
46662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)         tab_index < browser->tab_strip_model()->count();
46672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)         ++tab_index) {
46682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      WebContents* tab =
46692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          browser->tab_strip_model()->GetWebContentsAt(tab_index);
46705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      SessionTabHelper* session_tab_helper =
46715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          SessionTabHelper::FromWebContents(tab);
46725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (session_tab_helper->session_id().id() == id) {
46735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        DictionaryValue dict;
46745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        dict.SetInteger("windex", browser_index);
46755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        dict.SetInteger("tab_index", tab_index);
46765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        reply.SendSuccess(&dict);
46775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        return;
46785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
46795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
46805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
46815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendError("Could not find tab among current browser windows");
46825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
46835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
46845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::NavigateToURL(
46855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
46865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
46875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
46885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
46895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
46905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int navigation_count;
46915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string url, error;
46925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
46935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
46945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserAndTabFromJSONArgs(args, &browser, &web_contents, &error)) {
46955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
46965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
46975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
46985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("url", &url)) {
46995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
47005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'url' missing or invalid");
47015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
47025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
47035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("navigation_count", &navigation_count)) {
47045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
47055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'navigation_count' missing or invalid");
47065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
47075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
47085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (navigation_count > 0) {
47095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    new NavigationNotificationObserver(
47105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        &web_contents->GetController(), this, reply_message,
47115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        navigation_count, false, true);
47125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
47135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendSuccess(NULL);
47145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
47155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  OpenURLParams params(
47165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      GURL(url), content::Referrer(), CURRENT_TAB,
47175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      content::PageTransitionFromInt(
47185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          content::PAGE_TRANSITION_TYPED |
47195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          content::PAGE_TRANSITION_FROM_ADDRESS_BAR),
47205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      false);
47215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser->OpenURLFromTab(web_contents, params);
47225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
47235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
47245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetActiveTabIndexJSON(
47255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
47265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
47275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
47285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
47295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
47305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
47315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
47325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
47335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
47342a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  int tab_index = browser->tab_strip_model()->active_index();
47355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
47365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->SetInteger("tab_index", tab_index);
47375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(return_value.get());
47385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
47395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
47405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::AppendTabJSON(DictionaryValue* args,
47415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                              IPC::Message* reply_message) {
47425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  TabAppendedNotificationObserver* observer = NULL;
47435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int append_tab_response = -1;
47445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
47455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg, url;
47465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error_msg)) {
47475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error_msg);
47485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
47495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
47505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("url", &url)) {
47515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
47525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'url' missing or invalid");
47535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
47545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
47555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  observer = new TabAppendedNotificationObserver(browser, this, reply_message,
47565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                 true);
47572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  WebContents* contents =
47585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      chrome::AddSelectedTabWithURL(browser, GURL(url),
47595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                    content::PAGE_TRANSITION_TYPED);
47605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (contents) {
47615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    append_tab_response = GetIndexForNavigationController(
47622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        &contents->GetController(), browser);
47635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
47645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
47655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!contents || append_tab_response < 0) {
47665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (observer) {
47675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      observer->ReleaseReply();
47685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      delete observer;
47695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
47705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError("Failed to append tab.");
47715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
47725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
47735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
47745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WaitUntilNavigationCompletes(
47755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
47765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
47775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
47785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
47795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
47805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
47815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
47825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
47835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserAndTabFromJSONArgs(args, &browser, &web_contents, &error)) {
47845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
47855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
47865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
47875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NavigationNotificationObserver* observer =
47885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new NavigationNotificationObserver(&web_contents->GetController(), this,
47895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                         reply_message, 1, true, true);
47905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!web_contents->IsLoading()) {
47915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    observer->ConditionMet(AUTOMATION_MSG_NAVIGATION_SUCCESS);
47925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
47935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
47945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
47955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
47965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ExecuteJavascriptJSON(
47975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
47985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
47995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
48005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
48025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 frame_xpath, javascript;
48035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
48045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* render_view;
48055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetRenderViewFromJSONArgs(args, profile(), &render_view, &error)) {
48065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
48075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        Error(automation::kInvalidId, error));
48085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
48105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("frame_xpath", &frame_xpath)) {
48115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
48125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'frame_xpath' missing or invalid");
48135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
48155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("javascript", &javascript)) {
48165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
48175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'javascript' missing or invalid");
48185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
48205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
48215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new DomOperationMessageSender(this, reply_message, true);
48225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExecuteJavascriptInRenderViewFrame(frame_xpath, javascript, reply_message,
48235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                     render_view);
48245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
48255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
48265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ExecuteJavascriptInRenderView(
48275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
48285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
48295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  string16 frame_xpath, javascript, extension_id, url_text;
48305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
48315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int render_process_id, render_view_id;
48325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("frame_xpath", &frame_xpath)) {
48335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
48345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'frame_xpath' missing or invalid");
48355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
48375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("javascript", &javascript)) {
48385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
48395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'javascript' missing or invalid");
48405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
48425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("view.render_process_id", &render_process_id)) {
48435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
48445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'view.render_process_id' missing or invalid");
48455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
48475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("view.render_view_id", &render_view_id)) {
48485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
48495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError("'view.render_view_id' missing or invalid");
48505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
48525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
48535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* rvh = RenderViewHost::FromID(render_process_id,
48545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                               render_view_id);
48555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!rvh) {
48565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
48575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)            "A RenderViewHost object was not found with the given view ID.");
48585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
48605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
48615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new DomOperationMessageSender(this, reply_message, true);
48625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExecuteJavascriptInRenderViewFrame(frame_xpath, javascript, reply_message,
48635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                     rvh);
48645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
48655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
48665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::AddDomEventObserver(
48675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
48685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
48695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
48705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
48725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
48735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string event_name;
48745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int automation_id;
48755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool recurring;
48765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("event_name", &event_name)) {
48775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'event_name' missing or invalid");
48785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
48805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("automation_id", &automation_id)) {
48815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'automation_id' missing or invalid");
48825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
48845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("recurring", &recurring)) {
48855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'recurring' missing or invalid");
48865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
48875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
48885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
48895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!automation_event_queue_.get())
48905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    automation_event_queue_.reset(new AutomationEventQueue);
48915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
48925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int observer_id = automation_event_queue_->AddObserver(
48935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new DomEventObserver(automation_event_queue_.get(), event_name,
48945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                           automation_id, recurring));
48955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<DictionaryValue> return_value(new DictionaryValue);
48965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  return_value->SetInteger("observer_id", observer_id);
48975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(return_value.get());
48985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
48995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
49005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::RemoveEventObserver(
49015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
49025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
49035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
49045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int observer_id;
49055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("observer_id", &observer_id) ||
49065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !automation_event_queue_.get()) {
49075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'observer_id' missing or invalid");
49085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
49105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (automation_event_queue_->RemoveObserver(observer_id)) {
49115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendSuccess(NULL);
49125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
49145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendError("Invalid observer id.");
49155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
49165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
49175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ClearEventQueue(
49185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
49195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
49205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  automation_event_queue_.reset();
49215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(NULL);
49225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
49235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
49245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetNextEvent(
49255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
49265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
49275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  scoped_ptr<AutomationJSONReply> reply(
49285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new AutomationJSONReply(this, reply_message));
49295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int observer_id;
49305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool blocking;
49315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("observer_id", &observer_id)) {
49325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply->SendError("'observer_id' missing or invalid");
49335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
49355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetBoolean("blocking", &blocking)) {
49365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply->SendError("'blocking' missing or invalid");
49375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
49395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!automation_event_queue_.get()) {
49405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply->SendError(
49415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "No observers are attached to the queue. Did you create any?");
49425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
49445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
49455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The reply will be freed once a matching event is added to the queue.
49465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  automation_event_queue_->GetNextEvent(reply.release(), observer_id, blocking);
49475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
49485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
49495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GoForward(
49505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
49515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
49525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
49535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
49555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
49565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
49575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetTabFromJSONArgs(args, &web_contents, &error)) {
49585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
49595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
49615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NavigationController& controller = web_contents->GetController();
49625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!controller.CanGoForward()) {
49635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue dict;
49645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    dict.SetBoolean("did_go_forward", false);
49655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendSuccess(&dict);
49665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
49685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new NavigationNotificationObserver(&controller, this, reply_message,
49695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                     1, false, true);
49705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  controller.GoForward();
49715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
49725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
49735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ExecuteBrowserCommandAsyncJSON(
49745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
49755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
49765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
49775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int command;
49785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
49795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
49805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error)) {
49815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error);
49825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
49845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("accelerator", &command)) {
49855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'accelerator' missing or invalid.");
49865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
49885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!chrome::SupportsCommand(browser, command)) {
49892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    reply.SendError(base::StringPrintf("Browser does not support command=%d.",
49902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                                       command));
49915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
49935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!chrome::IsCommandEnabled(browser, command)) {
49942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    reply.SendError(base::StringPrintf(
49952a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        "Browser command=%d not enabled.", command));
49965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
49975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
49985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  chrome::ExecuteCommand(browser, command);
49995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
50005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
50015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
50025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ExecuteBrowserCommandJSON(
50035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
50045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
50055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int command;
50065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
50075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
50085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error)) {
50095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
50105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
50115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
50125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("accelerator", &command)) {
50135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
50145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "'accelerator' missing or invalid.");
50155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
50165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
50175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!chrome::SupportsCommand(browser, command)) {
50185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
50192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        base::StringPrintf("Browser does not support command=%d.", command));
50205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
50215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
50225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!chrome::IsCommandEnabled(browser, command)) {
50235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
50242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        base::StringPrintf("Browser command=%d not enabled.", command));
50255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
50265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
50275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // First check if we can handle the command without using an observer.
50285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (size_t i = 0; i < arraysize(kSynchronousCommands); i++) {
50295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (command == kSynchronousCommands[i]) {
50305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      chrome::ExecuteCommand(browser, command);
50315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      AutomationJSONReply(this, reply_message).SendSuccess(NULL);
50325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
50335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
50345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
50355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Use an observer if we have one, otherwise fail.
50365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (ExecuteBrowserCommandObserver::CreateAndRegisterObserver(
50375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      this, browser, command, reply_message, true)) {
50385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    chrome::ExecuteCommand(browser, command);
50395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
50405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
50412a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  AutomationJSONReply(this, reply_message).SendError(base::StringPrintf(
50422a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      "Unable to register observer for browser command=%d.", command));
50435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
50445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
50455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsMenuCommandEnabledJSON(
50465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
50475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
50485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int command;
50495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
50505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
50515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error)) {
50525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
50535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
50545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
50555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("accelerator", &command)) {
50565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(
50575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        "'accelerator' missing or invalid.");
50585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
50595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
50605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
50615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("enabled", chrome::IsCommandEnabled(browser, command));
50625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&dict);
50635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
50645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
50655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetTabInfo(
50665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
50675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
50685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
50695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
50705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* tab;
50715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
50725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (GetBrowserAndTabFromJSONArgs(args, &browser, &tab, &error)) {
50735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    NavigationEntry* entry = tab->GetController().GetActiveEntry();
50745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!entry) {
50755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      reply.SendError("Unable to get active navigation entry");
50765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      return;
50775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
50785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue dict;
5079c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)    dict.SetString("title", entry->GetTitleForDisplay(std::string()));
50805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    dict.SetString("url", entry->GetVirtualURL().spec());
50815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendSuccess(&dict);
50825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  } else {
50835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error);
50845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
50855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
50865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
50875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetTabCountJSON(
50885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
50895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
50905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
50915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
50925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
50935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error)) {
50945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error);
50955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
50965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
50975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
50982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  dict.SetInteger("tab_count", browser->tab_strip_model()->count());
50995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&dict);
51005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
51015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
51025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GoBack(
51035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
51045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
51055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
51065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
51075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
51085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
51095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
51105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetTabFromJSONArgs(args, &web_contents, &error)) {
51115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
51125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
51135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
51145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NavigationController& controller = web_contents->GetController();
51155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!controller.CanGoBack()) {
51165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue dict;
51175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    dict.SetBoolean("did_go_back", false);
51185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendSuccess(&dict);
51195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
51205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
51215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new NavigationNotificationObserver(&controller, this, reply_message,
51225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                     1, false, true);
51235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  controller.GoBack();
51245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
51255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
51265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ReloadJSON(
51275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
51285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
51295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
51305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
51315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
51325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
51335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
51345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetTabFromJSONArgs(args, &web_contents, &error)) {
51355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
51365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
51375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
51385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NavigationController& controller = web_contents->GetController();
51395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new NavigationNotificationObserver(&controller, this, reply_message,
51405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                     1, false, true);
51415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  controller.Reload(false);
51425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
51435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
51445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetCookiesJSON(
51455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
51465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  automation_util::GetCookiesJSON(this, args, reply_message);
51475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
51485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
51495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::DeleteCookieJSON(
51505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
51515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  automation_util::DeleteCookieJSON(this, args, reply_message);
51525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
51535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
51545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetCookieJSON(
51555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
51565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  automation_util::SetCookieJSON(this, args, reply_message);
51575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
51585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
51595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetCookiesInBrowserContext(
51605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
51615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
51625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
51635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
51645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string value, url_string;
51655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int windex, value_size;
51665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("windex", &windex)) {
51675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'windex' missing or invalid.");
51685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
51695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
51705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  web_contents = automation_util::GetWebContentsAt(windex, 0);
51715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!web_contents) {
51725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'windex' does not refer to a browser window.");
51735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
51745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
51755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("url", &url_string)) {
51765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'url' missing or invalid.");
51775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
51785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
51795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  GURL url(url_string);
51805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!url.is_valid()) {
51815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Invalid url.");
51825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
51835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
51845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  automation_util::GetCookies(url, web_contents, &value_size, &value);
51855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (value_size == -1) {
51865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(
51872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        base::StringPrintf("Unable to retrieve cookies for url=%s.",
51882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                           url_string.c_str()));
51895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
51905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
51915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
51925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetString("cookies", value);
51935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&dict);
51945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
51955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
51965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::DeleteCookieInBrowserContext(
51975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
51985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
51995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
52005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
52015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string cookie_name, error, url_string;
52025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int windex;
52035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool success = false;
52045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("windex", &windex)) {
52055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'windex' missing or invalid.");
52065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  web_contents = automation_util::GetWebContentsAt(windex, 0);
52095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!web_contents) {
52105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'windex' does not refer to a browser window.");
52115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("cookie_name", &cookie_name)) {
52145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'cookie_name' missing or invalid.");
52155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("url", &url_string)) {
52185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'url' missing or invalid.");
52195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  GURL url(url_string);
52225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!url.is_valid()) {
52235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Invalid url.");
52245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  automation_util::DeleteCookie(url, cookie_name, web_contents, &success);
52275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!success) {
52285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(
52292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        base::StringPrintf("Failed to delete cookie with name=%s for url=%s.",
52302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                           cookie_name.c_str(), url_string.c_str()));
52315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
52345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
52355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
52365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetCookieInBrowserContext(
52375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
52385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
52395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
52405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
52415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string value, error, url_string;
52425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int windex, response_value = -1;
52435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("windex", &windex)) {
52445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'windex' missing or invalid.");
52455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  web_contents = automation_util::GetWebContentsAt(windex, 0);
52485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!web_contents) {
52495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'windex' does not refer to a browser window.");
52505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("value", &value)) {
52535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'value' missing or invalid.");
52545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("url", &url_string)) {
52575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'url' missing or invalid.");
52585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  GURL url(url_string);
52615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!url.is_valid()) {
52625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Invalid url.");
52635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  automation_util::SetCookie(url, value, web_contents, &response_value);
52665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (response_value != 1) {
52672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    reply.SendError(base::StringPrintf(
52682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        "Unable set cookie for url=%s.", url_string.c_str()));
52695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
52705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
52725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
52735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
52745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetTabIds(
52755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
52765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* id_list = new ListValue();
52772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  for (chrome::BrowserIterator it; !it.done(); it.Next()) {
52782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    Browser* browser = *it;
52792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    for (int i = 0; i < browser->tab_strip_model()->count(); ++i) {
52805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      int id = SessionTabHelper::FromWebContents(
52812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          browser->tab_strip_model()->GetWebContentsAt(i))->session_id().id();
52825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      id_list->Append(Value::CreateIntegerValue(id));
52835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
52845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
52855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
52865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.Set("ids", id_list);
52875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&dict);
52885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
52895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
52905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetViews(
52915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
52925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ListValue* view_list = new ListValue();
52932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  printing::PrintPreviewDialogController* preview_controller =
52942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      printing::PrintPreviewDialogController::GetInstance();
52952a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  for (chrome::BrowserIterator it; !it.done(); it.Next()) {
52962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    Browser* browser = *it;
52972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    for (int i = 0; i < browser->tab_strip_model()->count(); ++i) {
52982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      WebContents* contents = browser->tab_strip_model()->GetWebContentsAt(i);
52995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      DictionaryValue* dict = new DictionaryValue();
53002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      AutomationId id = automation_util::GetIdForTab(contents);
53015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      dict->Set("auto_id", id.ToValue());
53025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      view_list->Append(dict);
53035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (preview_controller) {
53042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        WebContents* preview_dialog =
53052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)            preview_controller->GetPrintPreviewForContents(contents);
53062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)        if (preview_dialog) {
53075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          DictionaryValue* dict = new DictionaryValue();
53082a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)          AutomationId id = automation_util::GetIdForTab(preview_dialog);
53095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          dict->Set("auto_id", id.ToValue());
53105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          view_list->Append(dict);
53115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        }
53125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
53135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
53145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
53155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
53165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExtensionProcessManager* extension_mgr =
53175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      extensions::ExtensionSystem::Get(profile())->process_manager();
53185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const ExtensionProcessManager::ViewSet all_views =
53195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      extension_mgr->GetAllViews();
53205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExtensionProcessManager::ViewSet::const_iterator iter;
53215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (iter = all_views.begin(); iter != all_views.end(); ++iter) {
53225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    content::RenderViewHost* host = (*iter);
53235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationId id = automation_util::GetIdForExtensionView(host);
53245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!id.is_valid())
53255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      continue;
53265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    const Extension* extension =
53275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        extension_mgr->GetExtensionForRenderViewHost(host);
53285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* dict = new DictionaryValue();
53295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    dict->Set("auto_id", id.ToValue());
53305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    dict->SetString("extension_id", extension->id());
53315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    view_list->Append(dict);
53325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
53335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
53345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.Set("views", view_list);
53355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&dict);
53365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
53375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
53385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsTabIdValid(
53395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
53405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
53415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int id;
53425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("id", &id)) {
53435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'id' missing or invalid");
53445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
53455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
53465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool is_valid = false;
53472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  for (chrome::BrowserIterator it; !it.done(); it.Next()) {
53482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    Browser* browser = *it;
53492a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    for (int i = 0; i < browser->tab_strip_model()->count(); ++i) {
53502a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      WebContents* tab = browser->tab_strip_model()->GetWebContentsAt(i);
53515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      SessionTabHelper* session_tab_helper =
53525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          SessionTabHelper::FromWebContents(tab);
53535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      if (session_tab_helper->session_id().id() == id) {
53545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        is_valid = true;
53555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        break;
53565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      }
53575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
53585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
53595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
53605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("is_valid", is_valid);
53615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&dict);
53625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
53635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
53645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::DoesAutomationObjectExist(
53655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
53665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
53675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationId id;
53685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error_msg;
53695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetAutomationIdFromJSONArgs(args, "auto_id", &id, &error_msg)) {
53705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error_msg);
53715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
53725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
53735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
53745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean(
53755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      "does_exist",
53765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      automation_util::DoesObjectWithIdExist(id, profile()));
53775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&dict);
53785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
53795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
53805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::CloseTabJSON(
53815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args, IPC::Message* reply_message) {
53825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
53835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* tab;
53845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
53855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool wait_until_closed = false;  // ChromeDriver does not use this.
53865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  args->GetBoolean("wait_until_closed", &wait_until_closed);
53875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Close tabs synchronously.
53885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (GetBrowserAndTabFromJSONArgs(args, &browser, &tab, &error)) {
53895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (wait_until_closed) {
53905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      new TabClosedNotificationObserver(this, wait_until_closed, reply_message,
53915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                        true);
53925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
53932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    chrome::CloseWebContents(browser, tab, false);
53945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (!wait_until_closed)
53955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      AutomationJSONReply(this, reply_message).SendSuccess(NULL);
53965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
53975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
53985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Close other types of views asynchronously.
53995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RenderViewHost* view;
54005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetRenderViewFromJSONArgs(args, profile(), &view, &error)) {
54015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message).SendError(error);
54025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
54035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
54045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  view->ClosePage();
54055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(NULL);
54065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
54075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
54085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::SetViewBounds(
54095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
54105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
54115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
54125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  int x, y, width, height;
54135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetInteger("bounds.x", &x) ||
54145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("bounds.y", &y) ||
54155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("bounds.width", &width) ||
54165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      !args->GetInteger("bounds.height", &height)) {
54175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Missing or invalid 'bounds'");
54185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
54195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
54205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
54215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
54225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error)) {
54235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(Error(automation::kInvalidId, error));
54245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
54255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
54265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  BrowserWindow* browser_window = browser->window();
54275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (browser_window->IsMaximized()) {
54285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    browser_window->Restore();
54295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
54305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser_window->SetBounds(gfx::Rect(x, y, width, height));
54315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
54325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
54335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
54345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::MaximizeView(
54355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
54365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
54375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
54385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
54395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserFromJSONArgs(args, &browser, &error)) {
54405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationJSONReply(this, reply_message)
54415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)        .SendError(Error(automation::kInvalidId, error));
54425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
54435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
54445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
54455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_LINUX)
54465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Maximization on Linux is asynchronous, so create an observer object to be
54475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // notified upon maximization completion.
54485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new WindowMaximizedObserver(this, reply_message);
54495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif  // defined(OS_LINUX)
54505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
54515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  browser->window()->Maximize();
54525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
54535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if !defined(OS_LINUX)
54545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Send success reply right away for OS's with synchronous maximize command.
54555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(NULL);
54565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif  // !defined(OS_LINUX)
54575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
54585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
54595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::ActivateTabJSON(
54605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
54615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
54625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (SendErrorIfModalDialogActive(this, reply_message))
54635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
54645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
54655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
54665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser;
54675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* web_contents;
54685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
54695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetBrowserAndTabFromJSONArgs(args, &browser, &web_contents, &error)) {
54705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error);
54715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
54725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
54732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  TabStripModel* tab_strip = browser->tab_strip_model();
54742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  tab_strip->ActivateTabAt(tab_strip->GetIndexOfWebContents(web_contents),
54752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                           true);
54765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
54775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
54785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
54795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::IsPageActionVisible(
54805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    base::DictionaryValue* args,
54815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
54825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
54835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
54845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebContents* tab;
54855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string error;
54865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetTabFromJSONArgs(args, &tab, &error)) {
54875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error);
54885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
54895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
54905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser = automation_util::GetBrowserForTab(tab);
54915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  const Extension* extension;
54925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!GetEnabledExtensionFromJSONArgs(
54935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          args, "extension_id", browser->profile(), &extension, &error)) {
54945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError(error);
54955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
54965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
54975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!browser) {
54985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Tab does not belong to an open browser");
54995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
55005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
55015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ExtensionAction* page_action =
55025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      ExtensionActionManager::Get(browser->profile())->
55035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      GetPageAction(*extension);
55045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!page_action) {
55055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Extension doesn't have any page action");
55065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
55075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
55085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  EnsureTabSelected(browser, tab);
55095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  bool is_visible = false;
55115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  LocationBarTesting* loc_bar =
55125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      browser->window()->GetLocationBar()->GetLocationBarForTesting();
55135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  size_t page_action_visible_count =
55145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      static_cast<size_t>(loc_bar->PageActionVisibleCount());
55155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  for (size_t i = 0; i < page_action_visible_count; ++i) {
55165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    if (loc_bar->GetVisiblePageAction(i) == page_action) {
55175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      is_visible = true;
55185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      break;
55195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    }
55205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
55215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue dict;
55225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  dict.SetBoolean("is_visible", is_visible);
55235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(&dict);
55245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
55255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::GetChromeDriverAutomationVersion(
55275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
55285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
55295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DictionaryValue reply_dict;
55305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply_dict.SetInteger("version", automation::kChromeDriverAutomationVersion);
55315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply(this, reply_message).SendSuccess(&reply_dict);
55325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
55335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::CreateNewAutomationProvider(
55355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    DictionaryValue* args,
55365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
55375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationJSONReply reply(this, reply_message);
55385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  std::string channel_id;
55395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!args->GetString("channel_id", &channel_id)) {
55405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("'channel_id' missing or invalid");
55415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
55425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
55435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  AutomationProvider* provider = new TestingAutomationProvider(profile_);
55455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  provider->DisableInitialLoadObservers();
55465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // TODO(kkania): Remove this when crbug.com/91311 is fixed.
55475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // Named server channels should ideally be created and closed on the file
55485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // thread, within the IPC channel code.
55495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  base::ThreadRestrictions::ScopedAllowIO allow_io;
55505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!provider->InitializeChannel(
55515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          automation::kNamedInterfacePrefix + channel_id)) {
55525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    reply.SendError("Failed to initialize channel: " + channel_id);
55535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
55545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
55555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DCHECK(g_browser_process);
55565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  g_browser_process->GetAutomationProviderList()->AddProvider(provider);
55575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  reply.SendSuccess(NULL);
55585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
55595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WaitForTabCountToBecome(
55615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int browser_handle,
55625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int target_tab_count,
55635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
55645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!browser_tracker_->ContainsHandle(browser_handle)) {
55655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationMsg_WaitForTabCountToBecome::WriteReplyParams(reply_message,
55665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                            false);
55675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Send(reply_message);
55685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
55695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
55705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  Browser* browser = browser_tracker_->GetResource(browser_handle);
55725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The observer will delete itself.
55745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new TabCountChangeObserver(this, browser, reply_message, target_tab_count);
55755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
55765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WaitForInfoBarCount(
55785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    int tab_handle,
55795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    size_t target_count,
55805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
55815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!tab_tracker_->ContainsHandle(tab_handle)) {
55825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationMsg_WaitForInfoBarCount::WriteReplyParams(reply_message_, false);
55835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Send(reply_message_);
55845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
55855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
55865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  NavigationController* controller = tab_tracker_->GetResource(tab_handle);
55885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (!controller) {
55895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    AutomationMsg_WaitForInfoBarCount::WriteReplyParams(reply_message_, false);
55905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    Send(reply_message_);
55915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    return;
55925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  }
55935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  // The delegate will delete itself.
55955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new InfoBarCountObserver(this, reply_message,
55962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)                           controller->GetWebContents(), target_count);
55975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
55985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::WaitForProcessLauncherThreadToGoIdle(
56005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    IPC::Message* reply_message) {
56015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  new WaitForProcessLauncherThreadToGoIdleObserver(this, reply_message);
56025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
56035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
56045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::OnRemoveProvider() {
56055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  if (g_browser_process)
56065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    g_browser_process->GetAutomationProviderList()->RemoveProvider(this);
56075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
56085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
56095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestingAutomationProvider::EnsureTabSelected(Browser* browser,
56105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)                                                  WebContents* tab) {
56112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  TabStripModel* tab_strip = browser->tab_strip_model();
56122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  if (tab_strip->GetActiveWebContents() != tab)
56132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    tab_strip->ActivateTabAt(tab_strip->GetIndexOfWebContents(tab), true);
56145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}
5615