NaCl: Update revision in DEPS, r12770 -> r12773
[chromium-blink-merge.git] / chrome / browser / extensions / extension_crash_recovery_browsertest.cc
blobc91a4fc865d674107daf6746d1e8394cbc4282b1
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.
5 #include "chrome/browser/browser_process.h"
6 #include "chrome/browser/extensions/extension_browsertest.h"
7 #include "chrome/browser/extensions/extension_host.h"
8 #include "chrome/browser/extensions/extension_service.h"
9 #include "chrome/browser/notifications/balloon.h"
10 #include "chrome/browser/notifications/balloon_collection.h"
11 #include "chrome/browser/notifications/balloon_host.h"
12 #include "chrome/browser/notifications/notification.h"
13 #include "chrome/browser/notifications/notification_delegate.h"
14 #include "chrome/browser/profiles/profile.h"
15 #include "chrome/browser/ui/browser.h"
16 #include "chrome/browser/ui/browser_commands.h"
17 #include "chrome/browser/ui/tabs/tab_strip_model.h"
18 #include "chrome/test/base/ui_test_utils.h"
19 #include "content/public/browser/navigation_controller.h"
20 #include "content/public/browser/render_process_host.h"
21 #include "content/public/browser/render_view_host.h"
22 #include "content/public/browser/web_contents.h"
23 #include "content/public/common/result_codes.h"
24 #include "extensions/browser/extension_registry.h"
25 #include "extensions/browser/extension_system.h"
26 #include "extensions/browser/process_manager.h"
27 #include "extensions/browser/process_map.h"
28 #include "ui/message_center/message_center.h"
29 #include "ui/message_center/message_center_switches.h"
30 #include "ui/message_center/message_center_util.h"
31 #include "ui/message_center/notification_list.h"
33 #if defined(OS_CHROMEOS)
34 #include "chrome/browser/notifications/notification_ui_manager.h"
35 #else
36 #include "chrome/browser/notifications/balloon_notification_ui_manager.h"
37 #endif
39 using content::NavigationController;
40 using content::WebContents;
41 using extensions::Extension;
42 using extensions::ExtensionRegistry;
44 // Tests are timing out waiting for extension to crash.
45 // http://crbug.com/174705
46 #if defined(OS_MACOSX) || defined(USE_AURA) || defined(OS_LINUX)
47 #define MAYBE_ExtensionCrashRecoveryTest DISABLED_ExtensionCrashRecoveryTest
48 #else
49 #define MAYBE_ExtensionCrashRecoveryTest ExtensionCrashRecoveryTest
50 #endif // defined(OS_MACOSX) || defined(USE_AURA) || defined(OS_LINUX)
52 class ExtensionCrashRecoveryTestBase : public ExtensionBrowserTest {
53 protected:
54 virtual void AcceptNotification(size_t index) = 0;
55 virtual void CancelNotification(size_t index) = 0;
56 virtual size_t CountBalloons() = 0;
58 ExtensionService* GetExtensionService() {
59 return browser()->profile()->GetExtensionService();
62 extensions::ProcessManager* GetProcessManager() {
63 return extensions::ExtensionSystem::Get(browser()->profile())->
64 process_manager();
67 size_t GetEnabledExtensionCount() {
68 ExtensionRegistry* registry = ExtensionRegistry::Get(browser()->profile());
69 return registry->enabled_extensions().size();
72 size_t GetTerminatedExtensionCount() {
73 ExtensionRegistry* registry = ExtensionRegistry::Get(browser()->profile());
74 return registry->terminated_extensions().size();
77 void CrashExtension(std::string extension_id) {
78 const Extension* extension =
79 GetExtensionService()->GetExtensionById(extension_id, false);
80 ASSERT_TRUE(extension);
81 extensions::ExtensionHost* extension_host = GetProcessManager()->
82 GetBackgroundHostForExtension(extension_id);
83 ASSERT_TRUE(extension_host);
85 base::KillProcess(extension_host->render_process_host()->GetHandle(),
86 content::RESULT_CODE_KILLED, false);
87 ASSERT_TRUE(WaitForExtensionCrash(extension_id));
88 ASSERT_FALSE(GetProcessManager()->
89 GetBackgroundHostForExtension(extension_id));
91 // Wait for extension crash balloon to appear.
92 base::MessageLoop::current()->RunUntilIdle();
95 void CheckExtensionConsistency(std::string extension_id) {
96 const Extension* extension =
97 GetExtensionService()->extensions()->GetByID(extension_id);
98 ASSERT_TRUE(extension);
99 extensions::ExtensionHost* extension_host = GetProcessManager()->
100 GetBackgroundHostForExtension(extension_id);
101 ASSERT_TRUE(extension_host);
102 extensions::ProcessManager::ViewSet all_views =
103 GetProcessManager()->GetAllViews();
104 extensions::ProcessManager::ViewSet::const_iterator it =
105 all_views.find(extension_host->host_contents()->GetRenderViewHost());
106 ASSERT_FALSE(it == all_views.end());
107 ASSERT_TRUE(extension_host->IsRenderViewLive());
108 extensions::ProcessMap* process_map =
109 extensions::ProcessMap::Get(browser()->profile());
110 ASSERT_TRUE(process_map->Contains(
111 extension_id,
112 extension_host->render_view_host()->GetProcess()->GetID()));
115 void LoadTestExtension() {
116 ExtensionBrowserTest::SetUpInProcessBrowserTestFixture();
117 const Extension* extension = LoadExtension(
118 test_data_dir_.AppendASCII("common").AppendASCII("background_page"));
119 ASSERT_TRUE(extension);
120 first_extension_id_ = extension->id();
121 CheckExtensionConsistency(first_extension_id_);
124 void LoadSecondExtension() {
125 const Extension* extension = LoadExtension(
126 test_data_dir_.AppendASCII("install").AppendASCII("install"));
127 ASSERT_TRUE(extension);
128 second_extension_id_ = extension->id();
129 CheckExtensionConsistency(second_extension_id_);
132 std::string first_extension_id_;
133 std::string second_extension_id_;
136 class MAYBE_ExtensionCrashRecoveryTest
137 : public ExtensionCrashRecoveryTestBase {
138 protected:
139 virtual void AcceptNotification(size_t index) OVERRIDE {
140 if (message_center::IsRichNotificationEnabled()) {
141 message_center::MessageCenter* message_center =
142 message_center::MessageCenter::Get();
143 ASSERT_GT(message_center->NotificationCount(), index);
144 message_center::NotificationList::Notifications::reverse_iterator it =
145 message_center->GetVisibleNotifications().rbegin();
146 for (size_t i=0; i < index; ++i)
147 it++;
148 std::string id = (*it)->id();
149 message_center->ClickOnNotification(id);
150 #if !defined(OS_CHROMEOS)
151 } else {
152 Balloon* balloon = GetNotificationDelegate(index);
153 ASSERT_TRUE(balloon);
154 balloon->OnClick();
155 #endif
157 WaitForExtensionLoad();
160 virtual void CancelNotification(size_t index) OVERRIDE {
161 if (message_center::IsRichNotificationEnabled()) {
162 message_center::MessageCenter* message_center =
163 message_center::MessageCenter::Get();
164 ASSERT_GT(message_center->NotificationCount(), index);
165 message_center::NotificationList::Notifications::reverse_iterator it =
166 message_center->GetVisibleNotifications().rbegin();
167 for (size_t i=0; i < index; i++) { it++; }
168 ASSERT_TRUE(g_browser_process->notification_ui_manager()->
169 CancelById((*it)->id()));
170 #if !defined(OS_CHROMEOS)
171 } else {
172 Balloon* balloon = GetNotificationDelegate(index);
173 ASSERT_TRUE(balloon);
174 std::string id = balloon->notification().notification_id();
175 ASSERT_TRUE(g_browser_process->notification_ui_manager()->CancelById(id));
176 #endif
180 virtual size_t CountBalloons() OVERRIDE {
181 if (message_center::IsRichNotificationEnabled())
182 return message_center::MessageCenter::Get()->NotificationCount();
184 #if defined(OS_CHROMEOS)
185 CHECK(false);
186 return 0;
187 #else
188 return BalloonNotificationUIManager::GetInstanceForTesting()->
189 balloon_collection()->GetActiveBalloons().size();
190 #endif
193 private:
194 #if !defined(OS_CHROMEOS)
195 Balloon* GetNotificationDelegate(size_t index) {
196 BalloonNotificationUIManager* manager =
197 BalloonNotificationUIManager::GetInstanceForTesting();
198 BalloonCollection::Balloons balloons =
199 manager->balloon_collection()->GetActiveBalloons();
200 return index < balloons.size() ? balloons.at(index) : NULL;
202 #endif
205 // Flaky: http://crbug.com/242167.
206 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest, DISABLED_Basic) {
207 const size_t count_before = GetEnabledExtensionCount();
208 const size_t crash_count_before = GetTerminatedExtensionCount();
209 LoadTestExtension();
210 CrashExtension(first_extension_id_);
211 ASSERT_EQ(count_before, GetEnabledExtensionCount());
212 ASSERT_EQ(crash_count_before + 1, GetTerminatedExtensionCount());
213 ASSERT_NO_FATAL_FAILURE(AcceptNotification(0));
215 SCOPED_TRACE("after clicking the balloon");
216 CheckExtensionConsistency(first_extension_id_);
217 ASSERT_EQ(crash_count_before, GetTerminatedExtensionCount());
220 // Flaky, http://crbug.com/241191.
221 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
222 DISABLED_CloseAndReload) {
223 const size_t count_before = GetEnabledExtensionCount();
224 const size_t crash_count_before = GetTerminatedExtensionCount();
225 LoadTestExtension();
226 CrashExtension(first_extension_id_);
228 ASSERT_EQ(count_before, GetEnabledExtensionCount());
229 ASSERT_EQ(crash_count_before + 1, GetTerminatedExtensionCount());
231 ASSERT_NO_FATAL_FAILURE(CancelNotification(0));
232 ReloadExtension(first_extension_id_);
234 SCOPED_TRACE("after reloading");
235 CheckExtensionConsistency(first_extension_id_);
236 ASSERT_EQ(crash_count_before, GetTerminatedExtensionCount());
239 // Test is timing out on Windows http://crbug.com/174705.
240 #if defined(OS_WIN)
241 #define MAYBE_ReloadIndependently DISABLED_ReloadIndependently
242 #else
243 #define MAYBE_ReloadIndependently ReloadIndependently
244 #endif // defined(OS_WIN)
245 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
246 MAYBE_ReloadIndependently) {
247 const size_t count_before = GetEnabledExtensionCount();
248 LoadTestExtension();
249 CrashExtension(first_extension_id_);
250 ASSERT_EQ(count_before, GetEnabledExtensionCount());
252 ReloadExtension(first_extension_id_);
254 SCOPED_TRACE("after reloading");
255 CheckExtensionConsistency(first_extension_id_);
257 WebContents* current_tab =
258 browser()->tab_strip_model()->GetActiveWebContents();
259 ASSERT_TRUE(current_tab);
261 // The balloon should automatically hide after the extension is successfully
262 // reloaded.
263 ASSERT_EQ(0U, CountBalloons());
266 // Test is timing out on Windows http://crbug.com/174705.
267 #if defined(OS_WIN)
268 #define MAYBE_ReloadIndependentlyChangeTabs DISABLED_ReloadIndependentlyChangeTabs
269 #else
270 #define MAYBE_ReloadIndependentlyChangeTabs ReloadIndependentlyChangeTabs
271 #endif // defined(OS_WIN)
273 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
274 MAYBE_ReloadIndependentlyChangeTabs) {
275 const size_t count_before = GetEnabledExtensionCount();
276 LoadTestExtension();
277 CrashExtension(first_extension_id_);
278 ASSERT_EQ(count_before, GetEnabledExtensionCount());
280 WebContents* original_tab =
281 browser()->tab_strip_model()->GetActiveWebContents();
282 ASSERT_TRUE(original_tab);
283 ASSERT_EQ(1U, CountBalloons());
285 // Open a new tab, but the balloon will still be there.
286 chrome::NewTab(browser());
287 WebContents* new_current_tab =
288 browser()->tab_strip_model()->GetActiveWebContents();
289 ASSERT_TRUE(new_current_tab);
290 ASSERT_NE(new_current_tab, original_tab);
291 ASSERT_EQ(1U, CountBalloons());
293 ReloadExtension(first_extension_id_);
295 SCOPED_TRACE("after reloading");
296 CheckExtensionConsistency(first_extension_id_);
298 // The balloon should automatically hide after the extension is successfully
299 // reloaded.
300 ASSERT_EQ(0U, CountBalloons());
303 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
304 DISABLED_ReloadIndependentlyNavigatePage) {
305 const size_t count_before = GetEnabledExtensionCount();
306 LoadTestExtension();
307 CrashExtension(first_extension_id_);
308 ASSERT_EQ(count_before, GetEnabledExtensionCount());
310 WebContents* current_tab =
311 browser()->tab_strip_model()->GetActiveWebContents();
312 ASSERT_TRUE(current_tab);
313 ASSERT_EQ(1U, CountBalloons());
315 // Navigate to another page.
316 ui_test_utils::NavigateToURL(
317 browser(), ui_test_utils::GetTestUrl(
318 base::FilePath(base::FilePath::kCurrentDirectory),
319 base::FilePath(FILE_PATH_LITERAL("title1.html"))));
320 ASSERT_EQ(1U, CountBalloons());
322 ReloadExtension(first_extension_id_);
324 SCOPED_TRACE("after reloading");
325 CheckExtensionConsistency(first_extension_id_);
327 // The balloon should automatically hide after the extension is successfully
328 // reloaded.
329 ASSERT_EQ(0U, CountBalloons());
332 // Make sure that when we don't do anything about the crashed extension
333 // and close the browser, it doesn't crash. The browser is closed implicitly
334 // at the end of each browser test.
336 // http://crbug.com/84719
337 #if defined(OS_LINUX)
338 #define MAYBE_ShutdownWhileCrashed DISABLED_ShutdownWhileCrashed
339 #else
340 #define MAYBE_ShutdownWhileCrashed ShutdownWhileCrashed
341 #endif // defined(OS_LINUX)
343 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
344 MAYBE_ShutdownWhileCrashed) {
345 const size_t count_before = GetEnabledExtensionCount();
346 LoadTestExtension();
347 CrashExtension(first_extension_id_);
348 ASSERT_EQ(count_before, GetEnabledExtensionCount());
351 // Flaky, http://crbug.com/241245.
352 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
353 DISABLED_TwoExtensionsCrashFirst) {
354 const size_t count_before = GetEnabledExtensionCount();
355 LoadTestExtension();
356 LoadSecondExtension();
357 CrashExtension(first_extension_id_);
358 ASSERT_EQ(count_before + 1, GetEnabledExtensionCount());
359 ASSERT_NO_FATAL_FAILURE(AcceptNotification(0));
361 SCOPED_TRACE("after clicking the balloon");
362 CheckExtensionConsistency(first_extension_id_);
363 CheckExtensionConsistency(second_extension_id_);
366 // Flaky: http://crbug.com/242196
367 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
368 DISABLED_TwoExtensionsCrashSecond) {
369 const size_t count_before = GetEnabledExtensionCount();
370 LoadTestExtension();
371 LoadSecondExtension();
372 CrashExtension(second_extension_id_);
373 ASSERT_EQ(count_before + 1, GetEnabledExtensionCount());
374 ASSERT_NO_FATAL_FAILURE(AcceptNotification(0));
376 SCOPED_TRACE("after clicking the balloon");
377 CheckExtensionConsistency(first_extension_id_);
378 CheckExtensionConsistency(second_extension_id_);
381 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
382 TwoExtensionsCrashBothAtOnce) {
383 const size_t count_before = GetEnabledExtensionCount();
384 const size_t crash_count_before = GetTerminatedExtensionCount();
385 LoadTestExtension();
386 LoadSecondExtension();
387 CrashExtension(first_extension_id_);
388 ASSERT_EQ(count_before + 1, GetEnabledExtensionCount());
389 ASSERT_EQ(crash_count_before + 1, GetTerminatedExtensionCount());
390 CrashExtension(second_extension_id_);
391 ASSERT_EQ(count_before, GetEnabledExtensionCount());
392 ASSERT_EQ(crash_count_before + 2, GetTerminatedExtensionCount());
395 SCOPED_TRACE("first balloon");
396 ASSERT_NO_FATAL_FAILURE(AcceptNotification(0));
397 CheckExtensionConsistency(first_extension_id_);
401 SCOPED_TRACE("second balloon");
402 ASSERT_NO_FATAL_FAILURE(AcceptNotification(0));
403 CheckExtensionConsistency(first_extension_id_);
404 CheckExtensionConsistency(second_extension_id_);
408 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
409 TwoExtensionsOneByOne) {
410 const size_t count_before = GetEnabledExtensionCount();
411 LoadTestExtension();
412 CrashExtension(first_extension_id_);
413 ASSERT_EQ(count_before, GetEnabledExtensionCount());
414 LoadSecondExtension();
415 CrashExtension(second_extension_id_);
416 ASSERT_EQ(count_before, GetEnabledExtensionCount());
419 SCOPED_TRACE("first balloon");
420 ASSERT_NO_FATAL_FAILURE(AcceptNotification(0));
421 CheckExtensionConsistency(first_extension_id_);
425 SCOPED_TRACE("second balloon");
426 ASSERT_NO_FATAL_FAILURE(AcceptNotification(0));
427 CheckExtensionConsistency(first_extension_id_);
428 CheckExtensionConsistency(second_extension_id_);
432 // http://crbug.com/84719
433 #if defined(OS_LINUX)
434 #define MAYBE_TwoExtensionsShutdownWhileCrashed \
435 DISABLED_TwoExtensionsShutdownWhileCrashed
436 #else
437 #define MAYBE_TwoExtensionsShutdownWhileCrashed \
438 TwoExtensionsShutdownWhileCrashed
439 #endif // defined(OS_LINUX)
441 // Make sure that when we don't do anything about the crashed extensions
442 // and close the browser, it doesn't crash. The browser is closed implicitly
443 // at the end of each browser test.
444 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
445 MAYBE_TwoExtensionsShutdownWhileCrashed) {
446 const size_t count_before = GetEnabledExtensionCount();
447 LoadTestExtension();
448 CrashExtension(first_extension_id_);
449 ASSERT_EQ(count_before, GetEnabledExtensionCount());
450 LoadSecondExtension();
451 CrashExtension(second_extension_id_);
452 ASSERT_EQ(count_before, GetEnabledExtensionCount());
455 // Flaky, http://crbug.com/241573.
456 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
457 DISABLED_TwoExtensionsIgnoreFirst) {
458 const size_t count_before = GetEnabledExtensionCount();
459 LoadTestExtension();
460 LoadSecondExtension();
461 CrashExtension(first_extension_id_);
462 ASSERT_EQ(count_before + 1, GetEnabledExtensionCount());
463 CrashExtension(second_extension_id_);
464 ASSERT_EQ(count_before, GetEnabledExtensionCount());
466 // Accept notification 1 before canceling notification 0.
467 // Otherwise, on Linux and Windows, there is a race here, in which
468 // canceled notifications do not immediately go away.
469 ASSERT_NO_FATAL_FAILURE(AcceptNotification(1));
470 ASSERT_NO_FATAL_FAILURE(CancelNotification(0));
472 SCOPED_TRACE("balloons done");
473 ASSERT_EQ(count_before + 1, GetEnabledExtensionCount());
474 CheckExtensionConsistency(second_extension_id_);
477 // Flaky, http://crbug.com/241164.
478 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
479 DISABLED_TwoExtensionsReloadIndependently) {
480 const size_t count_before = GetEnabledExtensionCount();
481 LoadTestExtension();
482 LoadSecondExtension();
483 CrashExtension(first_extension_id_);
484 ASSERT_EQ(count_before + 1, GetEnabledExtensionCount());
485 CrashExtension(second_extension_id_);
486 ASSERT_EQ(count_before, GetEnabledExtensionCount());
489 SCOPED_TRACE("first: reload");
490 WebContents* current_tab =
491 browser()->tab_strip_model()->GetActiveWebContents();
492 ASSERT_TRUE(current_tab);
493 // At the beginning we should have one balloon displayed for each extension.
494 ASSERT_EQ(2U, CountBalloons());
495 ReloadExtension(first_extension_id_);
496 // One of the balloons should hide after the extension is reloaded.
497 ASSERT_EQ(1U, CountBalloons());
498 CheckExtensionConsistency(first_extension_id_);
502 SCOPED_TRACE("second: balloon");
503 ASSERT_NO_FATAL_FAILURE(AcceptNotification(0));
504 CheckExtensionConsistency(first_extension_id_);
505 CheckExtensionConsistency(second_extension_id_);
509 // http://crbug.com/243648
510 #if defined(OS_WIN)
511 #define MAYBE_CrashAndUninstall DISABLED_CrashAndUninstall
512 #else
513 #define MAYBE_CrashAndUninstall CrashAndUninstall
514 #endif
515 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
516 MAYBE_CrashAndUninstall) {
517 const size_t count_before = GetEnabledExtensionCount();
518 const size_t crash_count_before = GetTerminatedExtensionCount();
519 LoadTestExtension();
520 LoadSecondExtension();
521 CrashExtension(first_extension_id_);
522 ASSERT_EQ(count_before + 1, GetEnabledExtensionCount());
523 ASSERT_EQ(crash_count_before + 1, GetTerminatedExtensionCount());
525 ASSERT_EQ(1U, CountBalloons());
526 UninstallExtension(first_extension_id_);
527 base::MessageLoop::current()->RunUntilIdle();
529 SCOPED_TRACE("after uninstalling");
530 ASSERT_EQ(count_before + 1, GetEnabledExtensionCount());
531 ASSERT_EQ(crash_count_before, GetTerminatedExtensionCount());
532 ASSERT_EQ(0U, CountBalloons());
535 // http://crbug.com/84719
536 #if defined(OS_LINUX)
537 #define MAYBE_CrashAndUnloadAll DISABLED_CrashAndUnloadAll
538 #else
539 #define MAYBE_CrashAndUnloadAll CrashAndUnloadAll
540 #endif // defined(OS_LINUX)
542 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
543 MAYBE_CrashAndUnloadAll) {
544 const size_t count_before = GetEnabledExtensionCount();
545 const size_t crash_count_before = GetTerminatedExtensionCount();
546 LoadTestExtension();
547 LoadSecondExtension();
548 CrashExtension(first_extension_id_);
549 ASSERT_EQ(count_before + 1, GetEnabledExtensionCount());
550 ASSERT_EQ(crash_count_before + 1, GetTerminatedExtensionCount());
552 GetExtensionService()->UnloadAllExtensionsForTest();
553 ASSERT_EQ(crash_count_before, GetTerminatedExtensionCount());
556 // Fails a DCHECK on Aura and Linux: http://crbug.com/169622
557 // Failing on Windows: http://crbug.com/232340
558 #if defined(USE_AURA) || defined(OS_WIN) || defined(OS_LINUX)
559 #define MAYBE_ReloadTabsWithBackgroundPage DISABLED_ReloadTabsWithBackgroundPage
560 #else
561 #define MAYBE_ReloadTabsWithBackgroundPage ReloadTabsWithBackgroundPage
562 #endif
564 // Test that when an extension with a background page that has a tab open
565 // crashes, the tab stays open, and reloading it reloads the extension.
566 // Regression test for issue 71629.
567 IN_PROC_BROWSER_TEST_F(MAYBE_ExtensionCrashRecoveryTest,
568 MAYBE_ReloadTabsWithBackgroundPage) {
569 TabStripModel* tab_strip = browser()->tab_strip_model();
570 const size_t count_before = GetEnabledExtensionCount();
571 const size_t crash_count_before = GetTerminatedExtensionCount();
572 LoadTestExtension();
574 // Open a tab extension.
575 chrome::NewTab(browser());
576 ui_test_utils::NavigateToURL(
577 browser(),
578 GURL("chrome-extension://" + first_extension_id_ + "/background.html"));
580 const int tabs_before = tab_strip->count();
581 CrashExtension(first_extension_id_);
583 // Tab should still be open, and extension should be crashed.
584 EXPECT_EQ(tabs_before, tab_strip->count());
585 EXPECT_EQ(count_before, GetEnabledExtensionCount());
586 EXPECT_EQ(crash_count_before + 1, GetTerminatedExtensionCount());
589 content::WindowedNotificationObserver observer(
590 content::NOTIFICATION_LOAD_STOP,
591 content::Source<NavigationController>(
592 &browser()->tab_strip_model()->GetActiveWebContents()->
593 GetController()));
594 chrome::Reload(browser(), CURRENT_TAB);
595 observer.Wait();
597 // Extension should now be loaded.
598 SCOPED_TRACE("after reloading the tab");
599 CheckExtensionConsistency(first_extension_id_);
600 ASSERT_EQ(count_before + 1, GetEnabledExtensionCount());
601 ASSERT_EQ(0U, CountBalloons());