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 <deque> 6 #include <string> 7 8 #include "base/bind.h" 9 #include "base/callback.h" 10 #include "base/command_line.h" 11 #include "base/compiler_specific.h" 12 #include "base/memory/ref_counted.h" 13 #include "base/run_loop.h" 14 #include "base/strings/stringprintf.h" 15 #include "base/strings/utf_string_conversions.h" 16 #include "chrome/browser/browser_process.h" 17 #include "chrome/browser/chrome_notification_types.h" 18 #include "chrome/browser/infobars/confirm_infobar_delegate.h" 19 #include "chrome/browser/infobars/infobar.h" 20 #include "chrome/browser/infobars/infobar_service.h" 21 #include "chrome/browser/notifications/balloon.h" 22 #include "chrome/browser/notifications/balloon_collection.h" 23 #include "chrome/browser/notifications/balloon_host.h" 24 #include "chrome/browser/notifications/balloon_notification_ui_manager.h" 25 #include "chrome/browser/notifications/desktop_notification_service.h" 26 #include "chrome/browser/notifications/desktop_notification_service_factory.h" 27 #include "chrome/browser/notifications/notification.h" 28 #include "chrome/browser/profiles/profile.h" 29 #include "chrome/browser/ui/browser.h" 30 #include "chrome/browser/ui/browser_tabstrip.h" 31 #include "chrome/browser/ui/browser_window.h" 32 #include "chrome/browser/ui/tabs/tab_strip_model.h" 33 #include "chrome/common/content_settings.h" 34 #include "chrome/common/content_settings_pattern.h" 35 #include "chrome/test/base/in_process_browser_test.h" 36 #include "chrome/test/base/ui_test_utils.h" 37 #include "content/public/browser/notification_service.h" 38 #include "content/public/browser/notification_source.h" 39 #include "content/public/browser/notification_types.h" 40 #include "content/public/browser/render_view_host.h" 41 #include "content/public/browser/web_contents.h" 42 #include "content/public/test/browser_test_utils.h" 43 #include "content/public/test/test_utils.h" 44 #include "net/base/net_util.h" 45 #include "net/test/embedded_test_server/embedded_test_server.h" 46 #include "testing/gtest/include/gtest/gtest.h" 47 #include "ui/base/window_open_disposition.h" 48 #include "ui/message_center/message_center.h" 49 #include "ui/message_center/message_center_observer.h" 50 #include "ui/message_center/message_center_switches.h" 51 #include "ui/message_center/message_center_util.h" 52 #include "url/gurl.h" 53 54 namespace { 55 56 const char kExpectedIconUrl[] = "/notifications/no_such_file.png"; 57 58 enum InfobarAction { 59 DISMISS = 0, 60 ALLOW, 61 DENY, 62 }; 63 64 class NotificationChangeObserver { 65 public: 66 virtual ~NotificationChangeObserver() {} 67 virtual bool Wait() = 0; 68 }; 69 70 class MessageCenterChangeObserver 71 : public message_center::MessageCenterObserver, 72 public NotificationChangeObserver { 73 public: 74 MessageCenterChangeObserver() 75 : notification_received_(false) { 76 message_center::MessageCenter::Get()->AddObserver(this); 77 } 78 79 virtual ~MessageCenterChangeObserver() { 80 message_center::MessageCenter::Get()->RemoveObserver(this); 81 } 82 83 // NotificationChangeObserver: 84 virtual bool Wait() OVERRIDE { 85 if (notification_received_) 86 return true; 87 88 message_loop_runner_ = new content::MessageLoopRunner; 89 message_loop_runner_->Run(); 90 return notification_received_; 91 } 92 93 // message_center::MessageCenterObserver: 94 virtual void OnNotificationAdded( 95 const std::string& notification_id) OVERRIDE { 96 OnMessageCenterChanged(); 97 } 98 99 virtual void OnNotificationRemoved(const std::string& notification_id, 100 bool by_user) OVERRIDE { 101 OnMessageCenterChanged(); 102 } 103 104 virtual void OnNotificationUpdated( 105 const std::string& notification_id) OVERRIDE { 106 OnMessageCenterChanged(); 107 } 108 109 void OnMessageCenterChanged() { 110 notification_received_ = true; 111 if (message_loop_runner_.get()) 112 message_loop_runner_->Quit(); 113 } 114 115 bool notification_received_; 116 scoped_refptr<content::MessageLoopRunner> message_loop_runner_; 117 118 DISALLOW_COPY_AND_ASSIGN(MessageCenterChangeObserver); 119 }; 120 121 class NotificationBalloonChangeObserver 122 : public content::NotificationObserver, 123 public NotificationChangeObserver { 124 public: 125 NotificationBalloonChangeObserver() 126 : collection_(BalloonNotificationUIManager::GetInstanceForTesting()-> 127 balloon_collection()), 128 collection_changed_(false), 129 notification_received_(false), 130 running_(false), 131 done_(false) { 132 registrar_.Add(this, chrome::NOTIFICATION_NOTIFY_BALLOON_CONNECTED, 133 content::NotificationService::AllSources()); 134 registrar_.Add(this, chrome::NOTIFICATION_NOTIFY_BALLOON_DISCONNECTED, 135 content::NotificationService::AllSources()); 136 collection_->set_on_collection_changed_callback( 137 base::Bind(&NotificationBalloonChangeObserver::OnCollectionChanged, 138 base::Unretained(this))); 139 } 140 141 virtual ~NotificationBalloonChangeObserver() { 142 collection_->set_on_collection_changed_callback(base::Closure()); 143 } 144 145 // NotificationChangeObserver: 146 virtual bool Wait() OVERRIDE { 147 if (!Check()) { 148 running_ = true; 149 message_loop_runner_ = new content::MessageLoopRunner; 150 message_loop_runner_->Run(); 151 EXPECT_TRUE(done_); 152 } 153 return done_; 154 } 155 156 bool Check() { 157 if (done_) 158 return true; 159 160 if (collection_changed_ && notification_received_) { 161 done_ = true; 162 if (running_) { 163 message_loop_runner_->Quit(); 164 running_ = false; 165 } 166 } 167 return done_; 168 } 169 170 void OnCollectionChanged() { 171 collection_changed_ = true; 172 Check(); 173 } 174 175 // content::NotificationObserver: 176 virtual void Observe(int type, 177 const content::NotificationSource& source, 178 const content::NotificationDetails& details) OVERRIDE { 179 DCHECK(type == chrome::NOTIFICATION_NOTIFY_BALLOON_DISCONNECTED || 180 type == chrome::NOTIFICATION_NOTIFY_BALLOON_CONNECTED); 181 notification_received_ = true; 182 Check(); 183 } 184 185 private: 186 content::NotificationRegistrar registrar_; 187 BalloonCollection* collection_; 188 189 bool collection_changed_; 190 bool notification_received_; 191 bool running_; 192 bool done_; 193 scoped_refptr<content::MessageLoopRunner> message_loop_runner_; 194 195 DISALLOW_COPY_AND_ASSIGN(NotificationBalloonChangeObserver); 196 }; 197 198 } // namespace 199 200 class NotificationsTest : public InProcessBrowserTest { 201 public: 202 NotificationsTest() {} 203 204 protected: 205 int GetNotificationCount(); 206 207 NotificationChangeObserver* CreateObserver(); 208 209 void CloseBrowserWindow(Browser* browser); 210 void CrashTab(Browser* browser, int index); 211 const std::deque<Balloon*>& GetActiveBalloons(); 212 void CrashNotification(Balloon* balloon); 213 bool CloseNotificationAndWait(const Notification& notification); 214 215 void SetDefaultPermissionSetting(ContentSetting setting); 216 void DenyOrigin(const GURL& origin); 217 void AllowOrigin(const GURL& origin); 218 void AllowAllOrigins(); 219 220 void VerifyInfoBar(const Browser* browser, int index); 221 std::string CreateNotification(Browser* browser, 222 bool wait_for_new_balloon, 223 const char* icon, 224 const char* title, 225 const char* body, 226 const char* replace_id); 227 std::string CreateSimpleNotification(Browser* browser, 228 bool wait_for_new_balloon); 229 bool RequestPermissionAndWait(Browser* browser); 230 bool CancelNotification(const char* notification_id, Browser* browser); 231 bool PerformActionOnInfoBar(Browser* browser, 232 InfobarAction action, 233 size_t infobar_index, 234 int tab_index); 235 void GetPrefsByContentSetting(ContentSetting setting, 236 ContentSettingsForOneType* settings); 237 bool CheckOriginInSetting(const ContentSettingsForOneType& settings, 238 const GURL& origin); 239 240 GURL GetTestPageURL() const { 241 return embedded_test_server()->GetURL( 242 "/notifications/notification_tester.html"); 243 } 244 245 private: 246 void DropOriginPreference(const GURL& origin); 247 DesktopNotificationService* GetDesktopNotificationService(); 248 }; 249 250 int NotificationsTest::GetNotificationCount() { 251 if (message_center::IsRichNotificationEnabled()) { 252 return message_center::MessageCenter::Get()->NotificationCount(); 253 } else { 254 return BalloonNotificationUIManager::GetInstanceForTesting()-> 255 balloon_collection()->GetActiveBalloons().size(); 256 } 257 } 258 259 NotificationChangeObserver* NotificationsTest::CreateObserver() { 260 if (message_center::IsRichNotificationEnabled()) 261 return new MessageCenterChangeObserver(); 262 else 263 return new NotificationBalloonChangeObserver(); 264 } 265 266 void NotificationsTest::CloseBrowserWindow(Browser* browser) { 267 content::WindowedNotificationObserver observer( 268 chrome::NOTIFICATION_BROWSER_CLOSED, 269 content::Source<Browser>(browser)); 270 browser->window()->Close(); 271 observer.Wait(); 272 } 273 274 void NotificationsTest::CrashTab(Browser* browser, int index) { 275 content::CrashTab(browser->tab_strip_model()->GetWebContentsAt(index)); 276 } 277 278 const std::deque<Balloon*>& NotificationsTest::GetActiveBalloons() { 279 return BalloonNotificationUIManager::GetInstanceForTesting()-> 280 balloon_collection()->GetActiveBalloons(); 281 } 282 283 void NotificationsTest::CrashNotification(Balloon* balloon) { 284 content::CrashTab(balloon->balloon_view()->GetHost()->web_contents()); 285 } 286 287 bool NotificationsTest::CloseNotificationAndWait( 288 const Notification& notification) { 289 scoped_ptr<NotificationChangeObserver> observer(CreateObserver()); 290 bool success = g_browser_process->notification_ui_manager()-> 291 CancelById(notification.notification_id()); 292 if (success) 293 return observer->Wait(); 294 return false; 295 } 296 297 void NotificationsTest::SetDefaultPermissionSetting(ContentSetting setting) { 298 DesktopNotificationService* service = GetDesktopNotificationService(); 299 service->SetDefaultContentSetting(setting); 300 } 301 302 void NotificationsTest::DenyOrigin(const GURL& origin) { 303 DropOriginPreference(origin); 304 GetDesktopNotificationService()->DenyPermission(origin); 305 } 306 307 void NotificationsTest::AllowOrigin(const GURL& origin) { 308 DropOriginPreference(origin); 309 GetDesktopNotificationService()->GrantPermission(origin); 310 } 311 312 void NotificationsTest::AllowAllOrigins() { 313 GetDesktopNotificationService()->ResetAllOrigins(); 314 GetDesktopNotificationService()->SetDefaultContentSetting( 315 CONTENT_SETTING_ALLOW); 316 } 317 318 void NotificationsTest::VerifyInfoBar(const Browser* browser, int index) { 319 InfoBarService* infobar_service = InfoBarService::FromWebContents( 320 browser->tab_strip_model()->GetWebContentsAt(index)); 321 322 ASSERT_EQ(1U, infobar_service->infobar_count()); 323 ConfirmInfoBarDelegate* confirm_infobar = 324 infobar_service->infobar_at(0)->delegate()->AsConfirmInfoBarDelegate(); 325 ASSERT_TRUE(confirm_infobar); 326 int buttons = confirm_infobar->GetButtons(); 327 EXPECT_TRUE(buttons & ConfirmInfoBarDelegate::BUTTON_OK); 328 EXPECT_TRUE(buttons & ConfirmInfoBarDelegate::BUTTON_CANCEL); 329 } 330 331 std::string NotificationsTest::CreateNotification( 332 Browser* browser, 333 bool wait_for_new_balloon, 334 const char* icon, 335 const char* title, 336 const char* body, 337 const char* replace_id) { 338 std::string script = base::StringPrintf( 339 "createNotification('%s', '%s', '%s', '%s');", 340 icon, title, body, replace_id); 341 342 scoped_ptr<NotificationChangeObserver> observer(CreateObserver()); 343 std::string result; 344 bool success = content::ExecuteScriptAndExtractString( 345 browser->tab_strip_model()->GetActiveWebContents(), 346 script, 347 &result); 348 if (success && result != "-1" && wait_for_new_balloon) 349 success = observer->Wait(); 350 EXPECT_TRUE(success); 351 352 return result; 353 } 354 355 std::string NotificationsTest::CreateSimpleNotification( 356 Browser* browser, 357 bool wait_for_new_balloon) { 358 return CreateNotification( 359 browser, wait_for_new_balloon, 360 "no_such_file.png", "My Title", "My Body", ""); 361 } 362 363 bool NotificationsTest::RequestPermissionAndWait(Browser* browser) { 364 InfoBarService* infobar_service = InfoBarService::FromWebContents( 365 browser->tab_strip_model()->GetActiveWebContents()); 366 content::WindowedNotificationObserver observer( 367 chrome::NOTIFICATION_TAB_CONTENTS_INFOBAR_ADDED, 368 content::Source<InfoBarService>(infobar_service)); 369 std::string result; 370 bool success = content::ExecuteScriptAndExtractString( 371 browser->tab_strip_model()->GetActiveWebContents(), 372 "requestPermission();", 373 &result); 374 if (!success || result != "1") 375 return false; 376 observer.Wait(); 377 return true; 378 } 379 380 bool NotificationsTest::CancelNotification( 381 const char* notification_id, 382 Browser* browser) { 383 std::string script = base::StringPrintf( 384 "cancelNotification('%s');", 385 notification_id); 386 387 scoped_ptr<NotificationChangeObserver> observer(CreateObserver()); 388 std::string result; 389 bool success = content::ExecuteScriptAndExtractString( 390 browser->tab_strip_model()->GetActiveWebContents(), 391 script, 392 &result); 393 if (!success || result != "1") 394 return false; 395 return observer->Wait(); 396 } 397 398 bool NotificationsTest::PerformActionOnInfoBar( 399 Browser* browser, 400 InfobarAction action, 401 size_t infobar_index, 402 int tab_index) { 403 InfoBarService* infobar_service = InfoBarService::FromWebContents( 404 browser->tab_strip_model()->GetWebContentsAt(tab_index)); 405 if (infobar_index >= infobar_service->infobar_count()) { 406 ADD_FAILURE(); 407 return false; 408 } 409 410 InfoBar* infobar = infobar_service->infobar_at(infobar_index); 411 InfoBarDelegate* infobar_delegate = infobar->delegate(); 412 switch (action) { 413 case DISMISS: 414 infobar_delegate->InfoBarDismissed(); 415 infobar_service->RemoveInfoBar(infobar); 416 return true; 417 418 case ALLOW: { 419 ConfirmInfoBarDelegate* confirm_infobar_delegate = 420 infobar_delegate->AsConfirmInfoBarDelegate(); 421 if (!confirm_infobar_delegate) { 422 ADD_FAILURE(); 423 } else if (confirm_infobar_delegate->Accept()) { 424 infobar_service->RemoveInfoBar(infobar); 425 return true; 426 } 427 } 428 429 case DENY: { 430 ConfirmInfoBarDelegate* confirm_infobar_delegate = 431 infobar_delegate->AsConfirmInfoBarDelegate(); 432 if (!confirm_infobar_delegate) { 433 ADD_FAILURE(); 434 } else if (confirm_infobar_delegate->Cancel()) { 435 infobar_service->RemoveInfoBar(infobar); 436 return true; 437 } 438 } 439 } 440 441 return false; 442 } 443 444 void NotificationsTest::GetPrefsByContentSetting( 445 ContentSetting setting, 446 ContentSettingsForOneType* settings) { 447 DesktopNotificationService* service = GetDesktopNotificationService(); 448 service->GetNotificationsSettings(settings); 449 for (ContentSettingsForOneType::iterator it = settings->begin(); 450 it != settings->end(); ) { 451 if (it->setting != setting || it->source.compare("preference") != 0) 452 it = settings->erase(it); 453 else 454 ++it; 455 } 456 } 457 458 bool NotificationsTest::CheckOriginInSetting( 459 const ContentSettingsForOneType& settings, 460 const GURL& origin) { 461 ContentSettingsPattern pattern = 462 ContentSettingsPattern::FromURLNoWildcard(origin); 463 for (ContentSettingsForOneType::const_iterator it = settings.begin(); 464 it != settings.end(); ++it) { 465 if (it->primary_pattern == pattern) 466 return true; 467 } 468 return false; 469 } 470 471 void NotificationsTest::DropOriginPreference(const GURL& origin) { 472 GetDesktopNotificationService()->ClearSetting( 473 ContentSettingsPattern::FromURLNoWildcard(origin)); 474 } 475 476 DesktopNotificationService* NotificationsTest::GetDesktopNotificationService() { 477 Profile* profile = browser()->profile(); 478 return DesktopNotificationServiceFactory::GetForProfile(profile); 479 } 480 481 // If this flakes, use http://crbug.com/62311 and http://crbug.com/74428. 482 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestUserGestureInfobar) { 483 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 484 485 ui_test_utils::NavigateToURL( 486 browser(), 487 embedded_test_server()->GetURL( 488 "/notifications/notifications_request_function.html")); 489 490 // Request permission by calling request() while eval'ing an inline script; 491 // That's considered a user gesture to webkit, and should produce an infobar. 492 bool result; 493 ASSERT_TRUE(content::ExecuteScriptAndExtractBool( 494 browser()->tab_strip_model()->GetActiveWebContents(), 495 "window.domAutomationController.send(request());", 496 &result)); 497 EXPECT_TRUE(result); 498 499 EXPECT_EQ(1U, InfoBarService::FromWebContents( 500 browser()->tab_strip_model()->GetWebContentsAt(0))->infobar_count()); 501 } 502 503 // If this flakes, use http://crbug.com/62311. 504 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestNoUserGestureInfobar) { 505 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 506 507 // Load a page which just does a request; no user gesture should result 508 // in no infobar. 509 ui_test_utils::NavigateToURL( 510 browser(), 511 embedded_test_server()->GetURL( 512 "/notifications/notifications_request_inline.html")); 513 514 EXPECT_EQ(0U, InfoBarService::FromWebContents( 515 browser()->tab_strip_model()->GetWebContentsAt(0))->infobar_count()); 516 } 517 518 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestCreateSimpleNotification) { 519 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 520 521 // Creates a simple notification. 522 AllowAllOrigins(); 523 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 524 525 std::string result = CreateSimpleNotification(browser(), true); 526 EXPECT_NE("-1", result); 527 528 GURL EXPECTED_ICON_URL = embedded_test_server()->GetURL(kExpectedIconUrl); 529 ASSERT_EQ(1, GetNotificationCount()); 530 if (message_center::IsRichNotificationEnabled()) { 531 message_center::NotificationList::Notifications notifications = 532 message_center::MessageCenter::Get()->GetVisibleNotifications(); 533 EXPECT_EQ(ASCIIToUTF16("My Title"), (*notifications.rbegin())->title()); 534 EXPECT_EQ(ASCIIToUTF16("My Body"), (*notifications.rbegin())->message()); 535 } else { 536 const std::deque<Balloon*>& balloons = GetActiveBalloons(); 537 ASSERT_EQ(1U, balloons.size()); 538 Balloon* balloon = balloons[0]; 539 const Notification& notification = balloon->notification(); 540 EXPECT_EQ(EXPECTED_ICON_URL, notification.icon_url()); 541 EXPECT_EQ(ASCIIToUTF16("My Title"), notification.title()); 542 EXPECT_EQ(ASCIIToUTF16("My Body"), notification.message()); 543 } 544 } 545 546 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestCloseNotification) { 547 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 548 549 // Creates a notification and closes it. 550 AllowAllOrigins(); 551 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 552 553 std::string result = CreateSimpleNotification(browser(), true); 554 EXPECT_NE("-1", result); 555 ASSERT_EQ(1, GetNotificationCount()); 556 557 if (message_center::IsRichNotificationEnabled()) { 558 message_center::NotificationList::Notifications notifications = 559 message_center::MessageCenter::Get()->GetVisibleNotifications(); 560 message_center::MessageCenter::Get()->RemoveNotification( 561 (*notifications.rbegin())->id(), 562 true); // by_user 563 } else { 564 const std::deque<Balloon*>& balloons = GetActiveBalloons(); 565 EXPECT_TRUE(CloseNotificationAndWait(balloons[0]->notification())); 566 } 567 568 ASSERT_EQ(0, GetNotificationCount()); 569 } 570 571 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestCancelNotification) { 572 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 573 574 // Creates a notification and cancels it in the origin page. 575 AllowAllOrigins(); 576 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 577 578 std::string note_id = CreateSimpleNotification(browser(), true); 579 EXPECT_NE(note_id, "-1"); 580 581 ASSERT_EQ(1, GetNotificationCount()); 582 ASSERT_TRUE(CancelNotification(note_id.c_str(), browser())); 583 ASSERT_EQ(0, GetNotificationCount()); 584 } 585 586 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestPermissionInfobarAppears) { 587 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 588 589 // Requests notification privileges and verifies the infobar appears. 590 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 591 ASSERT_TRUE(RequestPermissionAndWait(browser())); 592 593 ASSERT_EQ(0, GetNotificationCount()); 594 ASSERT_NO_FATAL_FAILURE(VerifyInfoBar(browser(), 0)); 595 } 596 597 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestAllowOnPermissionInfobar) { 598 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 599 600 // Tries to create a notification and clicks allow on the infobar. 601 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 602 // This notification should not be shown because we do not have permission. 603 CreateSimpleNotification(browser(), false); 604 ASSERT_EQ(0, GetNotificationCount()); 605 606 ASSERT_TRUE(RequestPermissionAndWait(browser())); 607 ASSERT_TRUE(PerformActionOnInfoBar(browser(), ALLOW, 0, 0)); 608 609 CreateSimpleNotification(browser(), true); 610 EXPECT_EQ(1, GetNotificationCount()); 611 } 612 613 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestDenyOnPermissionInfobar) { 614 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 615 616 // Test that no notification is created 617 // when Deny is chosen from permission infobar. 618 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 619 ASSERT_TRUE(RequestPermissionAndWait(browser())); 620 PerformActionOnInfoBar(browser(), DENY, 0, 0); 621 CreateSimpleNotification(browser(), false); 622 ASSERT_EQ(0, GetNotificationCount()); 623 ContentSettingsForOneType settings; 624 GetPrefsByContentSetting(CONTENT_SETTING_BLOCK, &settings); 625 EXPECT_TRUE(CheckOriginInSetting(settings, GetTestPageURL())); 626 } 627 628 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestClosePermissionInfobar) { 629 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 630 631 // Test that no notification is created when permission infobar is dismissed. 632 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 633 ASSERT_TRUE(RequestPermissionAndWait(browser())); 634 PerformActionOnInfoBar(browser(), DISMISS, 0, 0); 635 CreateSimpleNotification(browser(), false); 636 ASSERT_EQ(0, GetNotificationCount()); 637 ContentSettingsForOneType settings; 638 GetPrefsByContentSetting(CONTENT_SETTING_BLOCK, &settings); 639 EXPECT_EQ(0U, settings.size()); 640 } 641 642 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestAllowNotificationsFromAllSites) { 643 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 644 645 // Verify that all domains can be allowed to show notifications. 646 SetDefaultPermissionSetting(CONTENT_SETTING_ALLOW); 647 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 648 649 std::string result = CreateSimpleNotification(browser(), true); 650 EXPECT_NE("-1", result); 651 652 ASSERT_EQ(1, GetNotificationCount()); 653 EXPECT_EQ(0U, InfoBarService::FromWebContents( 654 browser()->tab_strip_model()->GetWebContentsAt(0))->infobar_count()); 655 } 656 657 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestDenyNotificationsFromAllSites) { 658 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 659 660 // Verify that no domain can show notifications. 661 SetDefaultPermissionSetting(CONTENT_SETTING_BLOCK); 662 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 663 664 std::string result = CreateSimpleNotification(browser(), false); 665 EXPECT_EQ("-1", result); 666 667 ASSERT_EQ(0, GetNotificationCount()); 668 } 669 670 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestDenyDomainAndAllowAll) { 671 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 672 673 // Verify that denying a domain and allowing all shouldn't show 674 // notifications from the denied domain. 675 DenyOrigin(GetTestPageURL().GetOrigin()); 676 SetDefaultPermissionSetting(CONTENT_SETTING_ALLOW); 677 678 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 679 680 std::string result = CreateSimpleNotification(browser(), false); 681 EXPECT_EQ("-1", result); 682 683 ASSERT_EQ(0, GetNotificationCount()); 684 } 685 686 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestAllowDomainAndDenyAll) { 687 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 688 689 // Verify that allowing a domain and denying all others should show 690 // notifications from the allowed domain. 691 AllowOrigin(GetTestPageURL().GetOrigin()); 692 SetDefaultPermissionSetting(CONTENT_SETTING_BLOCK); 693 694 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 695 696 std::string result = CreateSimpleNotification(browser(), true); 697 EXPECT_NE("-1", result); 698 699 ASSERT_EQ(1, GetNotificationCount()); 700 } 701 702 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestDenyAndThenAllowDomain) { 703 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 704 705 // Verify that denying and again allowing should show notifications. 706 DenyOrigin(GetTestPageURL().GetOrigin()); 707 708 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 709 710 std::string result = CreateSimpleNotification(browser(), false); 711 EXPECT_EQ("-1", result); 712 713 ASSERT_EQ(0, GetNotificationCount()); 714 715 AllowOrigin(GetTestPageURL().GetOrigin()); 716 result = CreateSimpleNotification(browser(), true); 717 EXPECT_NE("-1", result); 718 719 ASSERT_EQ(1, GetNotificationCount()); 720 EXPECT_EQ(0U, InfoBarService::FromWebContents( 721 browser()->tab_strip_model()->GetWebContentsAt(0))->infobar_count()); 722 } 723 724 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestCreateDenyCloseNotifications) { 725 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 726 727 // Verify able to create, deny, and close the notification. 728 AllowAllOrigins(); 729 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 730 CreateSimpleNotification(browser(), true); 731 ASSERT_EQ(1, GetNotificationCount()); 732 733 DenyOrigin(GetTestPageURL().GetOrigin()); 734 ContentSettingsForOneType settings; 735 GetPrefsByContentSetting(CONTENT_SETTING_BLOCK, &settings); 736 ASSERT_TRUE(CheckOriginInSetting(settings, GetTestPageURL().GetOrigin())); 737 738 EXPECT_EQ(1, GetNotificationCount()); 739 if (message_center::IsRichNotificationEnabled()) { 740 message_center::NotificationList::Notifications notifications = 741 message_center::MessageCenter::Get()->GetVisibleNotifications(); 742 message_center::MessageCenter::Get()->RemoveNotification( 743 (*notifications.rbegin())->id(), 744 true); // by_user 745 } else { 746 const std::deque<Balloon*>& balloons = GetActiveBalloons(); 747 ASSERT_TRUE(CloseNotificationAndWait(balloons[0]->notification())); 748 } 749 ASSERT_EQ(0, GetNotificationCount()); 750 } 751 752 // Crashes on Linux/Win. See http://crbug.com/160657. 753 IN_PROC_BROWSER_TEST_F( 754 NotificationsTest, 755 DISABLED_TestOriginPrefsNotSavedInIncognito) { 756 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 757 758 // Verify that allow/deny origin preferences are not saved in incognito. 759 Browser* incognito = CreateIncognitoBrowser(); 760 ui_test_utils::NavigateToURL(incognito, GetTestPageURL()); 761 ASSERT_TRUE(RequestPermissionAndWait(incognito)); 762 PerformActionOnInfoBar(incognito, DENY, 0, 0); 763 CloseBrowserWindow(incognito); 764 765 incognito = CreateIncognitoBrowser(); 766 ui_test_utils::NavigateToURL(incognito, GetTestPageURL()); 767 ASSERT_TRUE(RequestPermissionAndWait(incognito)); 768 PerformActionOnInfoBar(incognito, ALLOW, 0, 0); 769 CreateSimpleNotification(incognito, true); 770 ASSERT_EQ(1, GetNotificationCount()); 771 CloseBrowserWindow(incognito); 772 773 incognito = CreateIncognitoBrowser(); 774 ui_test_utils::NavigateToURL(incognito, GetTestPageURL()); 775 ASSERT_TRUE(RequestPermissionAndWait(incognito)); 776 777 ContentSettingsForOneType settings; 778 GetPrefsByContentSetting(CONTENT_SETTING_BLOCK, &settings); 779 EXPECT_EQ(0U, settings.size()); 780 GetPrefsByContentSetting(CONTENT_SETTING_ALLOW, &settings); 781 EXPECT_EQ(0U, settings.size()); 782 } 783 784 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestExitBrowserWithInfobar) { 785 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 786 787 // Exit the browser window, when the infobar appears. 788 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 789 ASSERT_TRUE(RequestPermissionAndWait(browser())); 790 } 791 792 // Times out on Windows and Linux. http://crbug.com/168976 793 #if defined(OS_WIN) || defined(OS_LINUX) 794 #define MAYBE_TestCrashTabWithPermissionInfobar \ 795 DISABLED_TestCrashTabWithPermissionInfobar 796 #else 797 #define MAYBE_TestCrashTabWithPermissionInfobar \ 798 TestCrashTabWithPermissionInfobar 799 #endif 800 IN_PROC_BROWSER_TEST_F(NotificationsTest, 801 MAYBE_TestCrashTabWithPermissionInfobar) { 802 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 803 804 // Test crashing the tab with permission infobar doesn't crash Chrome. 805 ui_test_utils::NavigateToURLWithDisposition( 806 browser(), 807 embedded_test_server()->GetURL("/empty.html"), 808 NEW_BACKGROUND_TAB, 809 ui_test_utils::BROWSER_TEST_WAIT_FOR_TAB); 810 browser()->tab_strip_model()->ActivateTabAt(0, true); 811 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 812 ASSERT_TRUE(RequestPermissionAndWait(browser())); 813 CrashTab(browser(), 0); 814 } 815 816 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestKillNotificationProcess) { 817 // Notifications don't have their own process with the message center. 818 if (message_center::IsRichNotificationEnabled()) 819 return; 820 821 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 822 823 // Test killing a notification doesn't crash Chrome. 824 AllowAllOrigins(); 825 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 826 CreateSimpleNotification(browser(), true); 827 ASSERT_EQ(1, GetNotificationCount()); 828 829 const std::deque<Balloon*>& balloons = GetActiveBalloons(); 830 ASSERT_EQ(1U, balloons.size()); 831 CrashNotification(balloons[0]); 832 ASSERT_EQ(0, GetNotificationCount()); 833 } 834 835 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestIncognitoNotification) { 836 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 837 838 // Test notifications in incognito window. 839 Browser* browser = CreateIncognitoBrowser(); 840 ui_test_utils::NavigateToURL(browser, GetTestPageURL()); 841 browser->tab_strip_model()->ActivateTabAt(0, true); 842 ASSERT_TRUE(RequestPermissionAndWait(browser)); 843 PerformActionOnInfoBar(browser, ALLOW, 0, 0); 844 CreateSimpleNotification(browser, true); 845 ASSERT_EQ(1, GetNotificationCount()); 846 } 847 848 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestCloseTabWithPermissionInfobar) { 849 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 850 851 // Test that user can close tab when infobar present. 852 ui_test_utils::NavigateToURLWithDisposition( 853 browser(), 854 GURL("about:blank"), 855 NEW_BACKGROUND_TAB, 856 ui_test_utils::BROWSER_TEST_WAIT_FOR_TAB); 857 browser()->tab_strip_model()->ActivateTabAt(0, true); 858 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 859 ASSERT_TRUE(RequestPermissionAndWait(browser())); 860 content::WebContentsDestroyedWatcher destroyed_watcher( 861 browser()->tab_strip_model()->GetWebContentsAt(0)); 862 browser()->tab_strip_model()->CloseWebContentsAt(0, 863 TabStripModel::CLOSE_NONE); 864 destroyed_watcher.Wait(); 865 } 866 867 IN_PROC_BROWSER_TEST_F( 868 NotificationsTest, 869 TestNavigateAwayWithPermissionInfobar) { 870 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 871 872 // Test navigating away when an infobar is present, 873 // then trying to create a notification from the same page. 874 ui_test_utils::NavigateToURLWithDisposition( 875 browser(), 876 GURL("about:blank"), 877 NEW_BACKGROUND_TAB, 878 ui_test_utils::BROWSER_TEST_WAIT_FOR_TAB); 879 browser()->tab_strip_model()->ActivateTabAt(0, true); 880 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 881 ASSERT_TRUE(RequestPermissionAndWait(browser())); 882 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 883 ASSERT_TRUE(RequestPermissionAndWait(browser())); 884 PerformActionOnInfoBar(browser(), ALLOW, 0, 0); 885 CreateSimpleNotification(browser(), true); 886 ASSERT_EQ(1, GetNotificationCount()); 887 } 888 889 // See crbug.com/248470 890 #if defined(OS_LINUX) 891 #define MAYBE_TestCrashRendererNotificationRemain \ 892 DISABLED_TestCrashRendererNotificationRemain 893 #else 894 #define MAYBE_TestCrashRendererNotificationRemain \ 895 TestCrashRendererNotificationRemain 896 #endif 897 898 IN_PROC_BROWSER_TEST_F(NotificationsTest, 899 MAYBE_TestCrashRendererNotificationRemain) { 900 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 901 902 // Test crashing renderer does not close or crash notification. 903 AllowAllOrigins(); 904 ui_test_utils::NavigateToURLWithDisposition( 905 browser(), 906 GURL("about:blank"), 907 NEW_BACKGROUND_TAB, 908 ui_test_utils::BROWSER_TEST_WAIT_FOR_TAB); 909 browser()->tab_strip_model()->ActivateTabAt(0, true); 910 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 911 CreateSimpleNotification(browser(), true); 912 ASSERT_EQ(1, GetNotificationCount()); 913 CrashTab(browser(), 0); 914 ASSERT_EQ(1, GetNotificationCount()); 915 } 916 917 IN_PROC_BROWSER_TEST_F(NotificationsTest, TestNotificationReplacement) { 918 ASSERT_TRUE(embedded_test_server()->InitializeAndWaitUntilReady()); 919 920 // Test that we can replace a notification using the replaceId. 921 AllowAllOrigins(); 922 923 ui_test_utils::NavigateToURL(browser(), GetTestPageURL()); 924 925 std::string result = CreateNotification( 926 browser(), true, "abc.png", "Title1", "Body1", "chat"); 927 EXPECT_NE("-1", result); 928 929 ASSERT_EQ(1, GetNotificationCount()); 930 931 result = CreateNotification( 932 browser(), false, "no_such_file.png", "Title2", "Body2", "chat"); 933 EXPECT_NE("-1", result); 934 935 if (message_center::IsRichNotificationEnabled()) { 936 ASSERT_EQ(1, GetNotificationCount()); 937 message_center::NotificationList::Notifications notifications = 938 message_center::MessageCenter::Get()->GetVisibleNotifications(); 939 EXPECT_EQ(ASCIIToUTF16("Title2"), (*notifications.rbegin())->title()); 940 EXPECT_EQ(ASCIIToUTF16("Body2"), (*notifications.rbegin())->message()); 941 } else { 942 const std::deque<Balloon*>& balloons = GetActiveBalloons(); 943 ASSERT_EQ(1U, balloons.size()); 944 Balloon* balloon = balloons[0]; 945 const Notification& notification = balloon->notification(); 946 GURL EXPECTED_ICON_URL = embedded_test_server()->GetURL(kExpectedIconUrl); 947 EXPECT_EQ(EXPECTED_ICON_URL, notification.icon_url()); 948 EXPECT_EQ(ASCIIToUTF16("Title2"), notification.title()); 949 EXPECT_EQ(ASCIIToUTF16("Body2"), notification.message()); 950 } 951 } 952