Upstream version 8.37.180.0
[platform/framework/web/crosswalk.git] / src / chrome / test / base / browser_with_test_window_test.cc
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "chrome/test/base/browser_with_test_window_test.h"
6
7 #include "base/run_loop.h"
8 #include "chrome/browser/profiles/profile_destroyer.h"
9 #include "chrome/browser/ui/browser.h"
10 #include "chrome/browser/ui/browser_navigator.h"
11 #include "chrome/browser/ui/tabs/tab_strip_model.h"
12 #include "chrome/common/render_messages.h"
13 #include "chrome/test/base/testing_profile.h"
14 #include "content/public/browser/navigation_controller.h"
15 #include "content/public/browser/navigation_entry.h"
16 #include "content/public/browser/web_contents.h"
17 #include "content/public/common/page_transition_types.h"
18 #include "content/public/test/test_renderer_host.h"
19
20 #if defined(USE_AURA)
21 #include "ui/aura/test/aura_test_helper.h"
22 #include "ui/compositor/compositor.h"
23 #include "ui/compositor/test/context_factories_for_test.h"
24 #include "ui/wm/core/default_activation_client.h"
25 #endif
26
27 #if defined(USE_ASH)
28 #include "ash/test/ash_test_helper.h"
29 #include "ash/test/ash_test_views_delegate.h"
30 #endif
31
32 #if defined(TOOLKIT_VIEWS)
33 #include "ui/views/test/test_views_delegate.h"
34 #endif
35
36 using content::NavigationController;
37 using content::RenderViewHost;
38 using content::RenderViewHostTester;
39 using content::WebContents;
40
41 BrowserWithTestWindowTest::BrowserWithTestWindowTest()
42     : browser_type_(Browser::TYPE_TABBED),
43       host_desktop_type_(chrome::HOST_DESKTOP_TYPE_NATIVE),
44       hosted_app_(false) {
45 }
46
47 BrowserWithTestWindowTest::BrowserWithTestWindowTest(
48     Browser::Type browser_type,
49     chrome::HostDesktopType host_desktop_type,
50     bool hosted_app)
51     : browser_type_(browser_type),
52       host_desktop_type_(host_desktop_type),
53       hosted_app_(hosted_app) {
54 }
55
56 BrowserWithTestWindowTest::~BrowserWithTestWindowTest() {
57 }
58
59 void BrowserWithTestWindowTest::SetUp() {
60   testing::Test::SetUp();
61 #if defined(OS_CHROMEOS)
62   // TODO(jamescook): Windows Ash support. This will require refactoring
63   // AshTestHelper and AuraTestHelper so they can be used at the same time,
64   // perhaps by AshTestHelper owning an AuraTestHelper. Also, need to cleanup
65   // CreateViewsDelegate() below when cleanup done.
66   ash_test_helper_.reset(new ash::test::AshTestHelper(
67       base::MessageLoopForUI::current()));
68   ash_test_helper_->SetUp(true);
69 #elif defined(USE_AURA)
70   // The ContextFactory must exist before any Compositors are created.
71   bool enable_pixel_output = false;
72   ui::ContextFactory* context_factory =
73       ui::InitializeContextFactoryForTests(enable_pixel_output);
74
75   aura_test_helper_.reset(new aura::test::AuraTestHelper(
76       base::MessageLoopForUI::current()));
77   aura_test_helper_->SetUp(context_factory);
78   new wm::DefaultActivationClient(aura_test_helper_->root_window());
79 #endif  // USE_AURA
80 #if !defined(OS_CHROMEOS) && defined(TOOLKIT_VIEWS)
81   views_delegate_.reset(CreateViewsDelegate());
82 #endif
83
84   // Subclasses can provide their own Profile.
85   profile_ = CreateProfile();
86   // Subclasses can provide their own test BrowserWindow. If they return NULL
87   // then Browser will create the a production BrowserWindow and the subclass
88   // is responsible for cleaning it up (usually by NativeWidget destruction).
89   window_.reset(CreateBrowserWindow());
90
91   browser_.reset(CreateBrowser(profile(), browser_type_, hosted_app_,
92                                host_desktop_type_, window_.get()));
93 }
94
95 void BrowserWithTestWindowTest::TearDown() {
96   // Some tests end up posting tasks to the DB thread that must be completed
97   // before the profile can be destroyed and the test safely shut down.
98   base::RunLoop().RunUntilIdle();
99
100   // Reset the profile here because some profile keyed services (like the
101   // audio service) depend on test stubs that the helpers below will remove.
102   DestroyBrowserAndProfile();
103
104 #if defined(OS_CHROMEOS)
105   ash_test_helper_->TearDown();
106 #elif defined(USE_AURA)
107   aura_test_helper_->TearDown();
108   ui::TerminateContextFactoryForTests();
109 #endif
110   testing::Test::TearDown();
111
112   // A Task is leaked if we don't destroy everything, then run the message
113   // loop.
114   base::MessageLoop::current()->PostTask(FROM_HERE,
115                                          base::MessageLoop::QuitClosure());
116   base::MessageLoop::current()->Run();
117
118 #if defined(TOOLKIT_VIEWS)
119   views_delegate_.reset(NULL);
120 #endif
121 }
122
123 void BrowserWithTestWindowTest::AddTab(Browser* browser, const GURL& url) {
124   chrome::NavigateParams params(browser, url, content::PAGE_TRANSITION_TYPED);
125   params.tabstrip_index = 0;
126   params.disposition = NEW_FOREGROUND_TAB;
127   chrome::Navigate(&params);
128   CommitPendingLoad(&params.target_contents->GetController());
129 }
130
131 void BrowserWithTestWindowTest::CommitPendingLoad(
132   NavigationController* controller) {
133   if (!controller->GetPendingEntry())
134     return;  // Nothing to commit.
135
136   RenderViewHost* old_rvh =
137       controller->GetWebContents()->GetRenderViewHost();
138
139   RenderViewHost* pending_rvh = RenderViewHostTester::GetPendingForController(
140       controller);
141   if (pending_rvh) {
142     // Simulate the BeforeUnload_ACK that is received from the current renderer
143     // for a cross-site navigation.
144     DCHECK_NE(old_rvh, pending_rvh);
145     RenderViewHostTester::For(old_rvh)->SendBeforeUnloadACK(true);
146   }
147   // Commit on the pending_rvh, if one exists.
148   RenderViewHost* test_rvh = pending_rvh ? pending_rvh : old_rvh;
149   RenderViewHostTester* test_rvh_tester = RenderViewHostTester::For(test_rvh);
150
151   // Simulate a SwapOut_ACK before the navigation commits.
152   if (pending_rvh)
153     RenderViewHostTester::For(old_rvh)->SimulateSwapOutACK();
154
155   // For new navigations, we need to send a larger page ID. For renavigations,
156   // we need to send the preexisting page ID. We can tell these apart because
157   // renavigations will have a pending_entry_index while new ones won't (they'll
158   // just have a standalong pending_entry that isn't in the list already).
159   if (controller->GetPendingEntryIndex() >= 0) {
160     test_rvh_tester->SendNavigateWithTransition(
161         controller->GetPendingEntry()->GetPageID(),
162         controller->GetPendingEntry()->GetURL(),
163         controller->GetPendingEntry()->GetTransitionType());
164   } else {
165     test_rvh_tester->SendNavigateWithTransition(
166         controller->GetWebContents()->
167             GetMaxPageIDForSiteInstance(test_rvh->GetSiteInstance()) + 1,
168         controller->GetPendingEntry()->GetURL(),
169         controller->GetPendingEntry()->GetTransitionType());
170   }
171 }
172
173 void BrowserWithTestWindowTest::NavigateAndCommit(
174     NavigationController* controller,
175     const GURL& url) {
176   controller->LoadURL(
177       url, content::Referrer(), content::PAGE_TRANSITION_LINK, std::string());
178   CommitPendingLoad(controller);
179 }
180
181 void BrowserWithTestWindowTest::NavigateAndCommitActiveTab(const GURL& url) {
182   NavigateAndCommit(&browser()->tab_strip_model()->GetActiveWebContents()->
183                         GetController(),
184                     url);
185 }
186
187 void BrowserWithTestWindowTest::NavigateAndCommitActiveTabWithTitle(
188     Browser* navigating_browser,
189     const GURL& url,
190     const base::string16& title) {
191   NavigationController* controller = &navigating_browser->tab_strip_model()->
192       GetActiveWebContents()->GetController();
193   NavigateAndCommit(controller, url);
194   controller->GetActiveEntry()->SetTitle(title);
195 }
196
197 void BrowserWithTestWindowTest::DestroyBrowserAndProfile() {
198   if (browser_.get()) {
199     // Make sure we close all tabs, otherwise Browser isn't happy in its
200     // destructor.
201     browser()->tab_strip_model()->CloseAllTabs();
202     browser_.reset(NULL);
203   }
204   window_.reset(NULL);
205   // Destroy the profile here - otherwise, if the profile is freed in the
206   // destructor, and a test subclass owns a resource that the profile depends
207   // on (such as g_browser_process()->local_state()) there's no way for the
208   // subclass to free it after the profile.
209   if (profile_)
210     DestroyProfile(profile_);
211   profile_ = NULL;
212 }
213
214 TestingProfile* BrowserWithTestWindowTest::CreateProfile() {
215   return new TestingProfile();
216 }
217
218 void BrowserWithTestWindowTest::DestroyProfile(TestingProfile* profile) {
219   delete profile;
220 }
221
222 BrowserWindow* BrowserWithTestWindowTest::CreateBrowserWindow() {
223   return new TestBrowserWindow();
224 }
225
226 Browser* BrowserWithTestWindowTest::CreateBrowser(
227     Profile* profile,
228     Browser::Type browser_type,
229     bool hosted_app,
230     chrome::HostDesktopType host_desktop_type,
231     BrowserWindow* browser_window) {
232   Browser::CreateParams params(profile, host_desktop_type);
233   if (hosted_app) {
234     params = Browser::CreateParams::CreateForApp("Test",
235                                                  true /* trusted_source */,
236                                                  gfx::Rect(),
237                                                  profile,
238                                                  host_desktop_type);
239   } else {
240     params.type = browser_type;
241   }
242   params.window = browser_window;
243   return new Browser(params);
244 }
245
246 #if !defined(OS_CHROMEOS) && defined(TOOLKIT_VIEWS)
247 views::ViewsDelegate* BrowserWithTestWindowTest::CreateViewsDelegate() {
248 #if defined(USE_ASH)
249   return new ash::test::AshTestViewsDelegate;
250 #else
251   return new views::TestViewsDelegate;
252 #endif
253 }
254 #endif