desktop_notification_service_unittest.cc revision c407dc5cd9bdc5668497f21b26b09d988ab439de
1// Copyright (c) 2010 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/browser/notifications/desktop_notification_service.h" 6 7#include "base/ref_counted.h" 8#include "base/waitable_event.h" 9#include "chrome/browser/notifications/notifications_prefs_cache.h" 10#include "chrome/browser/pref_service.h" 11#include "chrome/browser/renderer_host/test/test_render_view_host.h" 12#include "chrome/browser/scoped_pref_update.h" 13#include "chrome/common/pref_names.h" 14#include "chrome/test/testing_profile.h" 15#include "grit/generated_resources.h" 16#include "testing/gtest/include/gtest/gtest.h" 17#include "third_party/WebKit/WebKit/chromium/public/WebNotificationPresenter.h" 18 19namespace { 20 21// NotificationsPrefsCache wants to be called on the IO thread. This class 22// routes calls to the cache on the IO thread. 23class ThreadProxy : public base::RefCountedThreadSafe<ThreadProxy> { 24 public: 25 ThreadProxy() 26 : io_event_(false, false), 27 ui_event_(false, false) { 28 // The current message loop was already initalized by the test superclass. 29 ui_thread_.reset( 30 new ChromeThread(ChromeThread::UI, MessageLoop::current())); 31 32 // Create IO thread, start its message loop. 33 io_thread_.reset(new ChromeThread(ChromeThread::IO)); 34 io_thread_->Start(); 35 36 // Calling PauseIOThread() here isn't safe, because the runnable method 37 // could complete before the constructor is done, deleting |this|. 38 } 39 40 int CacheHasPermission(NotificationsPrefsCache* cache, const GURL& url) { 41 DCHECK(ChromeThread::CurrentlyOn(ChromeThread::UI)); 42 ChromeThread::PostTask(ChromeThread::IO, FROM_HERE, 43 NewRunnableMethod(this, &ThreadProxy::CacheHasPermissionIO, 44 cache, url)); 45 io_event_.Signal(); 46 ui_event_.Wait(); // Wait for IO thread to be done. 47 ChromeThread::PostTask(ChromeThread::IO, FROM_HERE, 48 NewRunnableMethod(this, &ThreadProxy::PauseIOThreadIO)); 49 50 return permission_; 51 } 52 53 void PauseIOThread() { 54 ChromeThread::PostTask(ChromeThread::IO, FROM_HERE, 55 NewRunnableMethod(this, &ThreadProxy::PauseIOThreadIO)); 56 } 57 58 void DrainIOThread() { 59 DCHECK(ChromeThread::CurrentlyOn(ChromeThread::UI)); 60 io_event_.Signal(); 61 io_thread_->Stop(); 62 } 63 64 private: 65 friend class base::RefCountedThreadSafe<ThreadProxy>; 66 ~ThreadProxy() { 67 DrainIOThread(); 68 } 69 70 void PauseIOThreadIO() { 71 DCHECK(ChromeThread::CurrentlyOn(ChromeThread::IO)); 72 io_event_.Wait(); 73 } 74 75 void CacheHasPermissionIO(NotificationsPrefsCache* cache, const GURL& url) { 76 DCHECK(ChromeThread::CurrentlyOn(ChromeThread::IO)); 77 permission_ = cache->HasPermission(url); 78 ui_event_.Signal(); 79 } 80 81 base::WaitableEvent io_event_; 82 base::WaitableEvent ui_event_; 83 scoped_ptr<ChromeThread> ui_thread_; 84 scoped_ptr<ChromeThread> io_thread_; 85 86 int permission_; 87}; 88 89 90class DesktopNotificationServiceTest : public RenderViewHostTestHarness { 91 public: 92 DesktopNotificationServiceTest() { 93 } 94 95 virtual void SetUp() { 96 RenderViewHostTestHarness::SetUp(); 97 proxy_ = new ThreadProxy; 98 proxy_->PauseIOThread(); 99 100 // Creates the service, calls InitPrefs() on it which loads data from the 101 // profile into the cache and then puts the cache in io thread mode. 102 service_ = profile()->GetDesktopNotificationService(); 103 cache_ = service_->prefs_cache(); 104 } 105 106 virtual void TearDown() { 107 // The io thread's waiting on the io_event_ might hold a ref to |proxy_|, 108 // preventing its destruction. Clear that ref. 109 proxy_->DrainIOThread(); 110 RenderViewHostTestHarness::TearDown(); 111 } 112 113 DesktopNotificationService* service_; 114 NotificationsPrefsCache* cache_; 115 scoped_refptr<ThreadProxy> proxy_; 116}; 117 118TEST_F(DesktopNotificationServiceTest, DefaultContentSettingSentToCache) { 119 // The default pref registered in DesktopNotificationService is "ask", 120 // and that's what sent to the cache. 121 EXPECT_EQ(CONTENT_SETTING_ASK, cache_->CachedDefaultContentSetting()); 122 123 // Change the default content setting. This will post a task on the IO thread 124 // to update the cache. 125 service_->SetDefaultContentSetting(CONTENT_SETTING_BLOCK); 126 127 // The updated pref shouldn't be sent to the cache immediately. 128 EXPECT_EQ(CONTENT_SETTING_ASK, cache_->CachedDefaultContentSetting()); 129 130 // Run IO thread tasks. 131 proxy_->DrainIOThread(); 132 133 // Now that IO thread events have been processed, it should be there. 134 EXPECT_EQ(CONTENT_SETTING_BLOCK, cache_->CachedDefaultContentSetting()); 135} 136 137TEST_F(DesktopNotificationServiceTest, GrantPermissionSentToCache) { 138 GURL url("http://allowed.com"); 139 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionNotAllowed, 140 proxy_->CacheHasPermission(cache_, url)); 141 142 service_->GrantPermission(url); 143 144 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionAllowed, 145 proxy_->CacheHasPermission(cache_, url)); 146} 147 148TEST_F(DesktopNotificationServiceTest, DenyPermissionSentToCache) { 149 GURL url("http://denied.com"); 150 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionNotAllowed, 151 proxy_->CacheHasPermission(cache_, url)); 152 153 service_->DenyPermission(url); 154 155 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionDenied, 156 proxy_->CacheHasPermission(cache_, url)); 157} 158 159TEST_F(DesktopNotificationServiceTest, PrefChangesSentToCache) { 160 PrefService* prefs = profile()->GetPrefs(); 161 162 ListValue* allowed_sites = 163 prefs->GetMutableList(prefs::kDesktopNotificationAllowedOrigins); 164 { 165 allowed_sites->Append(new StringValue(GURL("http://allowed.com").spec())); 166 ScopedPrefUpdate updateAllowed( 167 prefs, prefs::kDesktopNotificationAllowedOrigins); 168 } 169 170 ListValue* denied_sites = 171 prefs->GetMutableList(prefs::kDesktopNotificationDeniedOrigins); 172 { 173 denied_sites->Append(new StringValue(GURL("http://denied.com").spec())); 174 ScopedPrefUpdate updateDenied( 175 prefs, prefs::kDesktopNotificationDeniedOrigins); 176 } 177 178 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionAllowed, 179 proxy_->CacheHasPermission(cache_, GURL("http://allowed.com"))); 180 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionDenied, 181 proxy_->CacheHasPermission(cache_, GURL("http://denied.com"))); 182} 183 184TEST_F(DesktopNotificationServiceTest, GetAllowedOrigins) { 185 service_->GrantPermission(GURL("http://allowed2.com")); 186 service_->GrantPermission(GURL("http://allowed.com")); 187 188 std::vector<GURL> allowed_origins(service_->GetAllowedOrigins()); 189 ASSERT_EQ(2u, allowed_origins.size()); 190 EXPECT_EQ(GURL("http://allowed2.com"), allowed_origins[0]); 191 EXPECT_EQ(GURL("http://allowed.com"), allowed_origins[1]); 192} 193 194TEST_F(DesktopNotificationServiceTest, GetBlockedOrigins) { 195 service_->DenyPermission(GURL("http://denied2.com")); 196 service_->DenyPermission(GURL("http://denied.com")); 197 198 std::vector<GURL> denied_origins(service_->GetBlockedOrigins()); 199 ASSERT_EQ(2u, denied_origins.size()); 200 EXPECT_EQ(GURL("http://denied2.com"), denied_origins[0]); 201 EXPECT_EQ(GURL("http://denied.com"), denied_origins[1]); 202} 203 204TEST_F(DesktopNotificationServiceTest, ResetAllSentToCache) { 205 GURL allowed_url("http://allowed.com"); 206 service_->GrantPermission(allowed_url); 207 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionAllowed, 208 proxy_->CacheHasPermission(cache_, allowed_url)); 209 GURL denied_url("http://denied.com"); 210 service_->DenyPermission(denied_url); 211 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionDenied, 212 proxy_->CacheHasPermission(cache_, denied_url)); 213 214 service_->ResetAllOrigins(); 215 216 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionNotAllowed, 217 proxy_->CacheHasPermission(cache_, allowed_url)); 218 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionNotAllowed, 219 proxy_->CacheHasPermission(cache_, denied_url)); 220} 221 222TEST_F(DesktopNotificationServiceTest, ResetAllowedSentToCache) { 223 GURL allowed_url("http://allowed.com"); 224 service_->GrantPermission(allowed_url); 225 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionAllowed, 226 proxy_->CacheHasPermission(cache_, allowed_url)); 227 228 service_->ResetAllowedOrigin(allowed_url); 229 230 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionNotAllowed, 231 proxy_->CacheHasPermission(cache_, allowed_url)); 232} 233 234TEST_F(DesktopNotificationServiceTest, ResetBlockedSentToCache) { 235 GURL denied_url("http://denied.com"); 236 service_->DenyPermission(denied_url); 237 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionDenied, 238 proxy_->CacheHasPermission(cache_, denied_url)); 239 240 service_->ResetBlockedOrigin(denied_url); 241 242 EXPECT_EQ(WebKit::WebNotificationPresenter::PermissionNotAllowed, 243 proxy_->CacheHasPermission(cache_, denied_url)); 244} 245 246} // namespace 247