1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "base/command_line.h"
6 #include "base/path_service.h"
7 #include "base/run_loop.h"
8 #include "base/strings/utf_string_conversions.h"
9 #include "chrome/browser/extensions/extension_browsertest.h"
10 #include "chrome/browser/profiles/profile.h"
11 #include "chrome/browser/ui/app_list/app_list_controller_delegate.h"
12 #include "chrome/browser/ui/app_list/app_list_service.h"
13 #include "chrome/browser/ui/app_list/test/chrome_app_list_test_support.h"
14 #include "chrome/browser/ui/browser.h"
15 #include "chrome/browser/ui/browser_finder.h"
16 #include "chrome/browser/ui/host_desktop.h"
17 #include "chrome/common/chrome_paths.h"
18 #include "chrome/common/chrome_switches.h"
19 #include "chrome/test/base/in_process_browser_test.h"
20 #include "chrome/test/base/testing_profile.h"
21 #include "ui/app_list/app_list_model.h"
22 #include "ui/app_list/app_list_switches.h"
23 #include "ui/app_list/search_box_model.h"
24 #include "ui/app_list/search_result.h"
25 #include "ui/app_list/search_result_observer.h"
26 #include "ui/base/models/list_model_observer.h"
28 #if defined(OS_CHROMEOS)
29 #include "chromeos/chromeos_switches.h"
30 #include "chromeos/login/user_names.h"
31 #endif // defined(OS_CHROMEOS)
33 // Browser Test for AppListController that runs on all platforms supporting
35 typedef InProcessBrowserTest AppListControllerBrowserTest
;
37 // Test the CreateNewWindow function of the controller delegate.
38 IN_PROC_BROWSER_TEST_F(AppListControllerBrowserTest
, CreateNewWindow
) {
39 const chrome::HostDesktopType desktop
= chrome::GetActiveDesktop();
40 AppListService
* service
= test::GetAppListService();
41 AppListControllerDelegate
* controller(service
->GetControllerDelegate());
42 ASSERT_TRUE(controller
);
44 EXPECT_EQ(1U, chrome::GetBrowserCount(browser()->profile(), desktop
));
45 EXPECT_EQ(0U, chrome::GetBrowserCount(
46 browser()->profile()->GetOffTheRecordProfile(), desktop
));
48 controller
->CreateNewWindow(browser()->profile(), false);
49 EXPECT_EQ(2U, chrome::GetBrowserCount(browser()->profile(), desktop
));
51 controller
->CreateNewWindow(browser()->profile(), true);
52 EXPECT_EQ(1U, chrome::GetBrowserCount(
53 browser()->profile()->GetOffTheRecordProfile(), desktop
));
56 // Test creating the app list for an incognito version of the current profile.
57 IN_PROC_BROWSER_TEST_F(AppListControllerBrowserTest
, RegularThenIncognito
) {
58 AppListService
* service
= test::GetAppListService();
59 // On Ash, the app list always has a profile.
60 if (chrome::GetActiveDesktop() == chrome::HOST_DESKTOP_TYPE_ASH
)
61 EXPECT_TRUE(service
->GetCurrentAppListProfile());
63 EXPECT_FALSE(service
->GetCurrentAppListProfile());
65 service
->ShowForProfile(browser()->profile());
66 EXPECT_EQ(browser()->profile(), service
->GetCurrentAppListProfile());
68 AppListControllerDelegate
* controller
= service
->GetControllerDelegate();
69 service
->ShowForProfile(browser()->profile()->GetOffTheRecordProfile());
71 // Should be showing the same profile.
72 EXPECT_EQ(browser()->profile(), service
->GetCurrentAppListProfile());
74 // Should not have been reconstructed.
75 EXPECT_EQ(controller
, service
->GetControllerDelegate());
77 // Same set of tests using ShowForAppInstall, which the webstore uses and was
78 // traditionally where issues with incognito-mode app launchers started. Pass
79 // true for start_discovery_tracking to emulate what the webstore does on the
80 // first app install, to cover AppListServiceImpl::CreateForProfile().
81 service
->ShowForAppInstall(
82 browser()->profile()->GetOffTheRecordProfile(), "", true);
83 EXPECT_EQ(browser()->profile(), service
->GetCurrentAppListProfile());
84 EXPECT_EQ(controller
, service
->GetControllerDelegate());
87 // Test creating the initial app list for incognito profile.
88 IN_PROC_BROWSER_TEST_F(AppListControllerBrowserTest
, Incognito
) {
89 AppListService
* service
= test::GetAppListService();
90 if (chrome::GetActiveDesktop() == chrome::HOST_DESKTOP_TYPE_ASH
)
91 EXPECT_TRUE(service
->GetCurrentAppListProfile());
93 EXPECT_FALSE(service
->GetCurrentAppListProfile());
95 service
->ShowForProfile(browser()->profile()->GetOffTheRecordProfile());
96 // Initial load should have picked the non-incongito profile.
97 EXPECT_EQ(browser()->profile(), service
->GetCurrentAppListProfile());
100 // Browser Test for AppListController that observes search result changes.
101 class AppListControllerSearchResultsBrowserTest
102 : public ExtensionBrowserTest
,
103 public app_list::SearchResultObserver
,
104 public ui::ListModelObserver
{
106 AppListControllerSearchResultsBrowserTest()
107 : observed_result_(NULL
),
108 observed_results_list_(NULL
) {}
110 void WatchResultsLookingForItem(
111 app_list::AppListModel::SearchResults
* search_results
,
112 const std::string
& extension_name
) {
113 EXPECT_FALSE(observed_results_list_
);
114 observed_results_list_
= search_results
;
115 observed_results_list_
->AddObserver(this);
116 item_to_observe_
= base::ASCIIToUTF16(extension_name
);
119 void StopWatchingResults() {
120 EXPECT_TRUE(observed_results_list_
);
121 observed_results_list_
->RemoveObserver(this);
125 void AttemptToLocateItem() {
126 if (observed_result_
) {
127 observed_result_
->RemoveObserver(this);
128 observed_result_
= NULL
;
131 for (size_t i
= 0; i
< observed_results_list_
->item_count(); ++i
) {
132 if (observed_results_list_
->GetItemAt(i
)->title() != item_to_observe_
)
135 // Ensure there is at most one.
136 EXPECT_FALSE(observed_result_
);
137 observed_result_
= observed_results_list_
->GetItemAt(i
);
140 if (observed_result_
)
141 observed_result_
->AddObserver(this);
144 // Overridden from SearchResultObserver:
145 void OnIconChanged() override
{}
146 void OnActionsChanged() override
{}
147 void OnIsInstallingChanged() override
{}
148 void OnPercentDownloadedChanged() override
{}
149 void OnItemInstalled() override
{}
151 // Overridden from ui::ListModelObserver:
152 void ListItemsAdded(size_t start
, size_t count
) override
{
153 AttemptToLocateItem();
155 void ListItemsRemoved(size_t start
, size_t count
) override
{
156 AttemptToLocateItem();
158 void ListItemMoved(size_t index
, size_t target_index
) override
{}
159 void ListItemsChanged(size_t start
, size_t count
) override
{}
161 app_list::SearchResult
* observed_result_
;
164 base::string16 item_to_observe_
;
165 app_list::AppListModel::SearchResults
* observed_results_list_
;
167 DISALLOW_COPY_AND_ASSIGN(AppListControllerSearchResultsBrowserTest
);
171 // Flaky on Mac. https://crbug.com/415264
172 #if defined(OS_MACOSX)
173 #define MAYBE_UninstallSearchResult DISABLED_UninstallSearchResult
175 #define MAYBE_UninstallSearchResult UninstallSearchResult
177 // Test showing search results, and uninstalling one of them while displayed.
178 IN_PROC_BROWSER_TEST_F(AppListControllerSearchResultsBrowserTest
,
179 MAYBE_UninstallSearchResult
) {
180 base::FilePath test_extension_path
;
181 ASSERT_TRUE(PathService::Get(chrome::DIR_TEST_DATA
, &test_extension_path
));
182 test_extension_path
= test_extension_path
.AppendASCII("extensions")
183 .AppendASCII("platform_apps")
184 .AppendASCII("minimal");
185 const extensions::Extension
* extension
=
186 InstallExtension(test_extension_path
,
187 1 /* expected_change: new install */);
188 ASSERT_TRUE(extension
);
190 AppListService
* service
= test::GetAppListService();
191 ASSERT_TRUE(service
);
192 service
->ShowForProfile(browser()->profile());
194 app_list::AppListModel
* model
= test::GetAppListModel(service
);
196 WatchResultsLookingForItem(model
->results(), extension
->name());
198 // Ensure a search finds the extension.
199 EXPECT_FALSE(observed_result_
);
200 model
->search_box()->SetText(base::ASCIIToUTF16("minimal"));
201 EXPECT_TRUE(observed_result_
);
203 // Ensure the UI is updated. This is via PostTask in views.
204 base::RunLoop().RunUntilIdle();
206 // Now uninstall and ensure this browser test observes it.
207 UninstallExtension(extension
->id());
209 // Allow async AppSearchProvider::UpdateResults to run.
210 base::RunLoop().RunUntilIdle();
212 EXPECT_FALSE(observed_result_
);
213 StopWatchingResults();
214 service
->DismissAppList();
217 #if defined(OS_CHROMEOS)
219 class AppListControllerGuestModeBrowserTest
: public InProcessBrowserTest
{
221 AppListControllerGuestModeBrowserTest() {}
224 void SetUpCommandLine(base::CommandLine
* command_line
) override
;
227 DISALLOW_COPY_AND_ASSIGN(AppListControllerGuestModeBrowserTest
);
230 void AppListControllerGuestModeBrowserTest::SetUpCommandLine(
231 base::CommandLine
* command_line
) {
232 command_line
->AppendSwitch(chromeos::switches::kGuestSession
);
233 command_line
->AppendSwitchASCII(chromeos::switches::kLoginUser
,
234 chromeos::login::kGuestUserName
);
235 command_line
->AppendSwitchASCII(chromeos::switches::kLoginProfile
,
236 TestingProfile::kTestUserProfileDir
);
237 command_line
->AppendSwitch(switches::kIncognito
);
240 // Test creating the initial app list in guest mode.
241 IN_PROC_BROWSER_TEST_F(AppListControllerGuestModeBrowserTest
, Incognito
) {
242 AppListService
* service
= test::GetAppListService();
243 EXPECT_TRUE(service
->GetCurrentAppListProfile());
245 service
->ShowForProfile(browser()->profile());
246 EXPECT_EQ(browser()->profile(), service
->GetCurrentAppListProfile());
249 #endif // defined(OS_CHROMEOS)