// Copyright 2014 The Chromium Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #include "base/command_line.h" #include "base/message_loop/message_loop.h" #include "base/strings/utf_string_conversions.h" #include "chrome/browser/ui/website_settings/mock_permission_bubble_request.h" #include "chrome/browser/ui/website_settings/permission_bubble_manager.h" #include "chrome/browser/ui/website_settings/permission_bubble_request.h" #include "chrome/browser/ui/website_settings/permission_bubble_view.h" #include "chrome/common/chrome_switches.h" #include "chrome/test/base/chrome_render_view_host_test_harness.h" #include "testing/gtest/include/gtest/gtest.h" namespace { class MockView : public PermissionBubbleView { public: MockView() : shown_(false), can_accept_updates_(true), delegate_(NULL) {} virtual ~MockView() {} void Clear() { shown_ = false; can_accept_updates_ = true; delegate_ = NULL; permission_requests_.clear(); permission_states_.clear(); } // PermissionBubbleView: virtual void SetDelegate(Delegate* delegate) OVERRIDE { delegate_ = delegate; } virtual void Show( const std::vector<PermissionBubbleRequest*>& requests, const std::vector<bool>& accept_state, bool customization_state_) OVERRIDE { shown_ = true; permission_requests_ = requests; permission_states_ = accept_state; } virtual void Hide() OVERRIDE { shown_ = false; } virtual bool CanAcceptRequestUpdate() OVERRIDE { return can_accept_updates_; } virtual bool IsVisible() OVERRIDE { return shown_; } bool shown_; bool can_accept_updates_; Delegate* delegate_; std::vector<PermissionBubbleRequest*> permission_requests_; std::vector<bool> permission_states_; }; } // namespace class PermissionBubbleManagerTest : public ChromeRenderViewHostTestHarness { public: PermissionBubbleManagerTest() : ChromeRenderViewHostTestHarness(), request1_("test1"), request2_("test2"), iframe_request_same_domain_("iframe", GURL("http://www.google.com/some/url")), iframe_request_other_domain_("iframe", GURL("http://www.youtube.com")) {} virtual ~PermissionBubbleManagerTest() {} virtual void SetUp() OVERRIDE { ChromeRenderViewHostTestHarness::SetUp(); SetContents(CreateTestWebContents()); NavigateAndCommit(GURL("http://www.google.com")); manager_.reset(new PermissionBubbleManager(web_contents())); } virtual void TearDown() OVERRIDE { manager_.reset(); ChromeRenderViewHostTestHarness::TearDown(); } void ToggleAccept(int index, bool value) { manager_->ToggleAccept(index, value); } void Accept() { manager_->Accept(); } void Closing() { manager_->Closing(); } void WaitForFrameLoad() { // PermissionBubbleManager ignores all parameters. Yay? manager_->DocumentLoadedInFrame(NULL); base::MessageLoop::current()->RunUntilIdle(); } void WaitForCoalescing() { manager_->DocumentOnLoadCompletedInMainFrame(); base::MessageLoop::current()->RunUntilIdle(); } virtual void NavigationEntryCommitted( const content::LoadCommittedDetails& details) { manager_->NavigationEntryCommitted(details); } protected: MockPermissionBubbleRequest request1_; MockPermissionBubbleRequest request2_; MockPermissionBubbleRequest iframe_request_same_domain_; MockPermissionBubbleRequest iframe_request_other_domain_; MockView view_; scoped_ptr<PermissionBubbleManager> manager_; }; TEST_F(PermissionBubbleManagerTest, TestFlag) { EXPECT_FALSE(PermissionBubbleManager::Enabled()); CommandLine::ForCurrentProcess()->AppendSwitch( switches::kEnablePermissionsBubbles); EXPECT_TRUE(PermissionBubbleManager::Enabled()); } TEST_F(PermissionBubbleManagerTest, SingleRequest) { manager_->AddRequest(&request1_); manager_->SetView(&view_); WaitForCoalescing(); EXPECT_TRUE(view_.delegate_ == manager_.get()); EXPECT_TRUE(view_.shown_); ASSERT_EQ(static_cast<size_t>(1), view_.permission_requests_.size()); EXPECT_EQ(&request1_, view_.permission_requests_[0]); ToggleAccept(0, true); Accept(); EXPECT_TRUE(request1_.granted()); } TEST_F(PermissionBubbleManagerTest, SingleRequestViewFirst) { manager_->SetView(&view_); manager_->AddRequest(&request1_); WaitForCoalescing(); EXPECT_TRUE(view_.delegate_ == manager_.get()); EXPECT_TRUE(view_.shown_); ASSERT_EQ(static_cast<size_t>(1), view_.permission_requests_.size()); EXPECT_EQ(&request1_, view_.permission_requests_[0]); ToggleAccept(0, true); Accept(); EXPECT_TRUE(request1_.granted()); } TEST_F(PermissionBubbleManagerTest, TwoRequests) { manager_->AddRequest(&request1_); manager_->AddRequest(&request2_); manager_->SetView(&view_); WaitForCoalescing(); EXPECT_TRUE(view_.delegate_ == manager_.get()); EXPECT_TRUE(view_.shown_); ASSERT_EQ(static_cast<size_t>(2), view_.permission_requests_.size()); EXPECT_EQ(&request1_, view_.permission_requests_[0]); EXPECT_EQ(&request2_, view_.permission_requests_[1]); ToggleAccept(0, true); ToggleAccept(1, false); Accept(); EXPECT_TRUE(request1_.granted()); EXPECT_FALSE(request2_.granted()); } TEST_F(PermissionBubbleManagerTest, TwoRequestsTabSwitch) { manager_->AddRequest(&request1_); manager_->AddRequest(&request2_); manager_->SetView(&view_); WaitForCoalescing(); EXPECT_TRUE(view_.delegate_ == manager_.get()); EXPECT_TRUE(view_.shown_); ASSERT_EQ(static_cast<size_t>(2), view_.permission_requests_.size()); EXPECT_EQ(&request1_, view_.permission_requests_[0]); EXPECT_EQ(&request2_, view_.permission_requests_[1]); ToggleAccept(0, true); ToggleAccept(1, false); manager_->SetView(NULL); EXPECT_FALSE(view_.shown_); EXPECT_TRUE(view_.delegate_ == NULL); view_.Clear(); manager_->SetView(&view_); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); ASSERT_EQ(static_cast<size_t>(2), view_.permission_requests_.size()); EXPECT_EQ(&request1_, view_.permission_requests_[0]); EXPECT_EQ(&request2_, view_.permission_requests_[1]); EXPECT_TRUE(view_.permission_states_[0]); EXPECT_FALSE(view_.permission_states_[1]); Accept(); EXPECT_TRUE(request1_.granted()); EXPECT_FALSE(request2_.granted()); } TEST_F(PermissionBubbleManagerTest, NoRequests) { manager_->SetView(&view_); WaitForCoalescing(); EXPECT_FALSE(view_.shown_); } TEST_F(PermissionBubbleManagerTest, NoView) { manager_->AddRequest(&request1_); WaitForCoalescing(); EXPECT_FALSE(view_.shown_); } TEST_F(PermissionBubbleManagerTest, TwoRequestsCoalesce) { manager_->SetView(&view_); manager_->AddRequest(&request1_); manager_->AddRequest(&request2_); EXPECT_FALSE(view_.shown_); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); EXPECT_EQ(2u, view_.permission_requests_.size()); } TEST_F(PermissionBubbleManagerTest, TwoRequestsDoNotCoalesce) { manager_->SetView(&view_); manager_->AddRequest(&request1_); WaitForCoalescing(); manager_->AddRequest(&request2_); EXPECT_TRUE(view_.shown_); EXPECT_EQ(1u, view_.permission_requests_.size()); } TEST_F(PermissionBubbleManagerTest, TwoRequestsShownInTwoBubbles) { manager_->SetView(&view_); manager_->AddRequest(&request1_); WaitForCoalescing(); manager_->AddRequest(&request2_); EXPECT_TRUE(view_.shown_); ASSERT_EQ(1u, view_.permission_requests_.size()); EXPECT_EQ(&request1_, view_.permission_requests_[0]); view_.Hide(); Accept(); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); ASSERT_EQ(1u, view_.permission_requests_.size()); EXPECT_EQ(&request2_, view_.permission_requests_[0]); } TEST_F(PermissionBubbleManagerTest, TestAddDuplicateRequest) { manager_->SetView(&view_); manager_->AddRequest(&request1_); manager_->AddRequest(&request2_); manager_->AddRequest(&request1_); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); ASSERT_EQ(2u, view_.permission_requests_.size()); EXPECT_EQ(&request1_, view_.permission_requests_[0]); EXPECT_EQ(&request2_, view_.permission_requests_[1]); } TEST_F(PermissionBubbleManagerTest, SequentialRequests) { manager_->SetView(&view_); manager_->AddRequest(&request1_); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); Accept(); EXPECT_TRUE(request1_.granted()); EXPECT_FALSE(view_.shown_); manager_->AddRequest(&request2_); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); Accept(); EXPECT_FALSE(view_.shown_); EXPECT_TRUE(request2_.granted()); } TEST_F(PermissionBubbleManagerTest, SameRequestRejected) { manager_->SetView(&view_); manager_->AddRequest(&request1_); manager_->AddRequest(&request1_); EXPECT_FALSE(request1_.finished()); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); ASSERT_EQ(1u, view_.permission_requests_.size()); EXPECT_EQ(&request1_, view_.permission_requests_[0]); } TEST_F(PermissionBubbleManagerTest, DuplicateRequestRejected) { manager_->SetView(&view_); manager_->AddRequest(&request1_); MockPermissionBubbleRequest dupe_request("test1"); manager_->AddRequest(&dupe_request); EXPECT_TRUE(dupe_request.finished()); EXPECT_FALSE(request1_.finished()); } TEST_F(PermissionBubbleManagerTest, DuplicateQueuedRequest) { manager_->SetView(&view_); manager_->AddRequest(&request1_); WaitForCoalescing(); manager_->AddRequest(&request2_); MockPermissionBubbleRequest dupe_request("test1"); manager_->AddRequest(&dupe_request); EXPECT_TRUE(dupe_request.finished()); EXPECT_FALSE(request1_.finished()); MockPermissionBubbleRequest dupe_request2("test1"); manager_->AddRequest(&dupe_request2); EXPECT_TRUE(dupe_request2.finished()); EXPECT_FALSE(request2_.finished()); } TEST_F(PermissionBubbleManagerTest, ForgetRequestsOnPageNavigation) { manager_->SetView(&view_); manager_->AddRequest(&request1_); WaitForCoalescing(); manager_->AddRequest(&request2_); manager_->AddRequest(&iframe_request_other_domain_); EXPECT_TRUE(view_.shown_); ASSERT_EQ(1u, view_.permission_requests_.size()); NavigateAndCommit(GURL("http://www2.google.com/")); WaitForCoalescing(); EXPECT_FALSE(view_.shown_); EXPECT_TRUE(request1_.finished()); EXPECT_TRUE(request2_.finished()); EXPECT_TRUE(iframe_request_other_domain_.finished()); } TEST_F(PermissionBubbleManagerTest, TestCancel) { manager_->SetView(NULL); manager_->AddRequest(&request1_); WaitForCoalescing(); manager_->CancelRequest(&request1_); EXPECT_TRUE(request1_.finished()); manager_->SetView(&view_); EXPECT_FALSE(view_.shown_); manager_->AddRequest(&request2_); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); } TEST_F(PermissionBubbleManagerTest, TestCancelWhileDialogShown) { manager_->SetView(&view_); manager_->AddRequest(&request1_); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); EXPECT_FALSE(request1_.finished()); manager_->CancelRequest(&request1_); EXPECT_TRUE(request1_.finished()); } TEST_F(PermissionBubbleManagerTest, TestCancelWhileDialogShownNoUpdate) { manager_->SetView(&view_); view_.can_accept_updates_ = false; manager_->AddRequest(&request1_); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); EXPECT_FALSE(request1_.finished()); manager_->CancelRequest(&request1_); EXPECT_TRUE(request1_.finished()); Closing(); } TEST_F(PermissionBubbleManagerTest, TestCancelPendingRequest) { manager_->SetView(&view_); manager_->AddRequest(&request1_); WaitForCoalescing(); manager_->AddRequest(&request2_); EXPECT_TRUE(view_.shown_); EXPECT_EQ(1u, view_.permission_requests_.size()); manager_->CancelRequest(&request2_); EXPECT_TRUE(view_.shown_); EXPECT_FALSE(request1_.finished()); EXPECT_TRUE(request2_.finished()); } TEST_F(PermissionBubbleManagerTest, MainFrameNoRequestIFrameRequest) { manager_->SetView(&view_); manager_->AddRequest(&iframe_request_same_domain_); WaitForCoalescing(); WaitForFrameLoad(); EXPECT_TRUE(view_.shown_); Closing(); EXPECT_TRUE(iframe_request_same_domain_.finished()); } TEST_F(PermissionBubbleManagerTest, MainFrameAndIFrameRequestSameDomain) { manager_->SetView(&view_); manager_->AddRequest(&request1_); manager_->AddRequest(&iframe_request_same_domain_); WaitForFrameLoad(); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); EXPECT_EQ(2u, view_.permission_requests_.size()); Closing(); EXPECT_TRUE(request1_.finished()); EXPECT_TRUE(iframe_request_same_domain_.finished()); EXPECT_FALSE(view_.shown_); } TEST_F(PermissionBubbleManagerTest, MainFrameAndIFrameRequestOtherDomain) { manager_->SetView(&view_); manager_->AddRequest(&request1_); manager_->AddRequest(&iframe_request_other_domain_); WaitForFrameLoad(); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); Closing(); EXPECT_TRUE(request1_.finished()); EXPECT_FALSE(iframe_request_other_domain_.finished()); EXPECT_TRUE(view_.shown_); Closing(); EXPECT_TRUE(iframe_request_other_domain_.finished()); } TEST_F(PermissionBubbleManagerTest, IFrameRequestWhenMainRequestVisible) { manager_->SetView(&view_); manager_->AddRequest(&request1_); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); manager_->AddRequest(&iframe_request_same_domain_); WaitForFrameLoad(); EXPECT_EQ(1u, view_.permission_requests_.size()); Closing(); EXPECT_TRUE(request1_.finished()); EXPECT_FALSE(iframe_request_same_domain_.finished()); EXPECT_TRUE(view_.shown_); EXPECT_EQ(1u, view_.permission_requests_.size()); Closing(); EXPECT_TRUE(iframe_request_same_domain_.finished()); } TEST_F(PermissionBubbleManagerTest, IFrameRequestOtherDomainWhenMainRequestVisible) { manager_->SetView(&view_); manager_->AddRequest(&request1_); WaitForCoalescing(); EXPECT_TRUE(view_.shown_); manager_->AddRequest(&iframe_request_other_domain_); WaitForFrameLoad(); Closing(); EXPECT_TRUE(request1_.finished()); EXPECT_FALSE(iframe_request_other_domain_.finished()); EXPECT_TRUE(view_.shown_); Closing(); EXPECT_TRUE(iframe_request_other_domain_.finished()); } TEST_F(PermissionBubbleManagerTest, IFrameUserGestureRequest) { iframe_request_other_domain_.SetHasUserGesture(); manager_->SetView(&view_); manager_->AddRequest(&request1_); manager_->AddRequest(&iframe_request_other_domain_); WaitForFrameLoad(); WaitForCoalescing(); manager_->AddRequest(&request2_); EXPECT_TRUE(view_.shown_); Closing(); EXPECT_TRUE(request1_.finished()); EXPECT_FALSE(iframe_request_other_domain_.finished()); EXPECT_FALSE(request2_.finished()); EXPECT_TRUE(view_.shown_); Closing(); EXPECT_TRUE(iframe_request_other_domain_.finished()); EXPECT_FALSE(request2_.finished()); } TEST_F(PermissionBubbleManagerTest, AllUserGestureRequests) { iframe_request_other_domain_.SetHasUserGesture(); request2_.SetHasUserGesture(); manager_->SetView(&view_); manager_->AddRequest(&request1_); manager_->AddRequest(&iframe_request_other_domain_); WaitForCoalescing(); WaitForFrameLoad(); manager_->AddRequest(&request2_); EXPECT_TRUE(view_.shown_); Closing(); EXPECT_TRUE(request1_.finished()); EXPECT_FALSE(request2_.finished()); EXPECT_FALSE(iframe_request_other_domain_.finished()); EXPECT_TRUE(view_.shown_); Closing(); EXPECT_TRUE(request2_.finished()); EXPECT_FALSE(iframe_request_other_domain_.finished()); Closing(); EXPECT_TRUE(iframe_request_other_domain_.finished()); EXPECT_FALSE(view_.shown_); }