diff options
author | phajdan.jr@chromium.org <phajdan.jr@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-02-10 19:26:59 +0000 |
---|---|---|
committer | phajdan.jr@chromium.org <phajdan.jr@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-02-10 19:26:59 +0000 |
commit | bf73f0bc6e83da6c7b4f9353be5b382ea91e6906 (patch) | |
tree | 474e26033ecc422393c79a02a8e7a7f8db83dee8 /chrome/browser | |
parent | 5c60cd093c8df908383b143a2c946670a1d08d44 (diff) | |
download | chromium_src-bf73f0bc6e83da6c7b4f9353be5b382ea91e6906.zip chromium_src-bf73f0bc6e83da6c7b4f9353be5b382ea91e6906.tar.gz chromium_src-bf73f0bc6e83da6c7b4f9353be5b382ea91e6906.tar.bz2 |
Make sure that ResourceQueue is shut down before destruction.
Rewrite UserScriptListener unit test to not use ResourceDispatcherHost.
Share more code with ExtensionsServiceTest.
TEST=Covered by unit_tests.
BUG=none
Review URL: http://codereview.chromium.org/601005
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@38648 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser')
5 files changed, 314 insertions, 375 deletions
diff --git a/chrome/browser/extensions/extensions_service_unittest.cc b/chrome/browser/extensions/extensions_service_unittest.cc index c68f808..1b29541 100644 --- a/chrome/browser/extensions/extensions_service_unittest.cc +++ b/chrome/browser/extensions/extensions_service_unittest.cc @@ -2,6 +2,8 @@ // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. +#include "chrome/browser/extensions/extensions_service_unittest.h" + #include <algorithm> #include <vector> @@ -10,7 +12,6 @@ #include "base/json/json_reader.h" #include "base/message_loop.h" #include "base/path_service.h" -#include "base/scoped_temp_dir.h" #include "base/string_util.h" #include "chrome/browser/extensions/crx_installer.h" #include "chrome/browser/extensions/extension_creator.h" @@ -195,13 +196,107 @@ class MockProviderVisitor : public ExternalExtensionProvider::Visitor { DISALLOW_COPY_AND_ASSIGN(MockProviderVisitor); }; +class ExtensionTestingProfile : public TestingProfile { + public: + ExtensionTestingProfile() { + } + + void set_extensions_service(ExtensionsService* service) { + service_ = service; + } + virtual ExtensionsService* GetExtensionsService() { return service_; } + + private: + ExtensionsService* service_; +}; + +// Our message loop may be used in tests which require it to be an IO loop. +ExtensionsServiceTestBase::ExtensionsServiceTestBase() + : loop_(MessageLoop::TYPE_IO), + ui_thread_(ChromeThread::UI, &loop_), + file_thread_(ChromeThread::FILE, &loop_) { +} + +ExtensionsServiceTestBase::~ExtensionsServiceTestBase() { + // Drop our reference to ExtensionsService now, so that it can be destroyed + // while ChromeThreads and MessageLoop are still around (they are used + // in the ExtensionsService destruction process). + service_ = NULL; + MessageLoop::current()->RunAllPending(); +} + +void ExtensionsServiceTestBase::InitializeExtensionsService( + const FilePath& pref_file, const FilePath& extensions_install_dir) { + ExtensionTestingProfile* profile = new ExtensionTestingProfile(); + prefs_.reset(new PrefService(pref_file)); + profile_.reset(profile); + + CommandLine::ForCurrentProcess()->AppendSwitch( + switches::kEnableExtensionToolstrips); + service_ = new ExtensionsService(profile_.get(), + CommandLine::ForCurrentProcess(), + prefs_.get(), + extensions_install_dir, + false); + service_->set_extensions_enabled(true); + service_->set_show_extensions_prompts(false); + profile->set_extensions_service(service_.get()); + + // When we start up, we want to make sure there is no external provider, + // since the ExtensionService on Windows will use the Registry as a default + // provider and if there is something already registered there then it will + // interfere with the tests. Those tests that need an external provider + // will register one specifically. + service_->ClearProvidersForTesting(); + + total_successes_ = 0; +} + +void ExtensionsServiceTestBase::InitializeInstalledExtensionsService( + const FilePath& prefs_file, const FilePath& source_install_dir) { + ASSERT_TRUE(temp_dir_.CreateUniqueTempDir()); + FilePath path_ = temp_dir_.path(); + path_ = path_.Append(FILE_PATH_LITERAL("TestingExtensionsPath")); + file_util::Delete(path_, true); + file_util::CreateDirectory(path_); + FilePath temp_prefs = path_.Append(FILE_PATH_LITERAL("Preferences")); + file_util::CopyFile(prefs_file, temp_prefs); + + extensions_install_dir_ = path_.Append(FILE_PATH_LITERAL("Extensions")); + file_util::Delete(extensions_install_dir_, true); + file_util::CopyDirectory(source_install_dir, extensions_install_dir_, true); + + InitializeExtensionsService(temp_prefs, extensions_install_dir_); +} + +void ExtensionsServiceTestBase::InitializeEmptyExtensionsService() { + ASSERT_TRUE(temp_dir_.CreateUniqueTempDir()); + FilePath path_ = temp_dir_.path(); + path_ = path_.Append(FILE_PATH_LITERAL("TestingExtensionsPath")); + file_util::Delete(path_, true); + file_util::CreateDirectory(path_); + FilePath prefs_filename = path_ + .Append(FILE_PATH_LITERAL("TestPreferences")); + extensions_install_dir_ = path_.Append(FILE_PATH_LITERAL("Extensions")); + file_util::Delete(extensions_install_dir_, true); + file_util::CreateDirectory(extensions_install_dir_); + + InitializeExtensionsService(prefs_filename, extensions_install_dir_); +} + +// static +void ExtensionsServiceTestBase::SetUpTestCase() { + ExtensionErrorReporter::Init(false); // no noisy errors +} + +void ExtensionsServiceTestBase::SetUp() { + ExtensionErrorReporter::GetInstance()->ClearErrors(); +} + class ExtensionsServiceTest - : public testing::Test, public NotificationObserver { + : public ExtensionsServiceTestBase, public NotificationObserver { public: - ExtensionsServiceTest() - : ui_thread_(ChromeThread::UI, &loop_), - file_thread_(ChromeThread::FILE, &loop_), - installed_(NULL) { + ExtensionsServiceTest() : installed_(NULL) { registrar_.Add(this, NotificationType::EXTENSION_LOADED, NotificationService::AllSources()); registrar_.Add(this, NotificationType::EXTENSION_UNLOADED, @@ -212,78 +307,6 @@ class ExtensionsServiceTest NotificationService::AllSources()); } - ~ExtensionsServiceTest() { - // Drop our reference to ExtensionsService now, so that it can be destroyed - // while ChromeThreads and MessageLoop are still around (they are used - // in the ExtensionsService destruction process). - service_ = NULL; - } - - virtual void InitializeExtensionsService(const FilePath& pref_file, - const FilePath& extensions_install_dir) { - prefs_.reset(new PrefService(pref_file)); - profile_.reset(new TestingProfile()); - - CommandLine::ForCurrentProcess()->AppendSwitch( - switches::kEnableExtensionToolstrips); - service_ = new ExtensionsService(profile_.get(), - CommandLine::ForCurrentProcess(), - prefs_.get(), - extensions_install_dir, - false); - service_->set_extensions_enabled(true); - service_->set_show_extensions_prompts(false); - - // When we start up, we want to make sure there is no external provider, - // since the ExtensionService on Windows will use the Registry as a default - // provider and if there is something already registered there then it will - // interfere with the tests. Those tests that need an external provider - // will register one specifically. - service_->ClearProvidersForTesting(); - - total_successes_ = 0; - } - - virtual void InitializeInstalledExtensionsService(const FilePath& prefs_file, - const FilePath& source_install_dir) { - ASSERT_TRUE(temp_dir_.CreateUniqueTempDir()); - FilePath path_ = temp_dir_.path(); - path_ = path_.Append(FILE_PATH_LITERAL("TestingExtensionsPath")); - file_util::Delete(path_, true); - file_util::CreateDirectory(path_); - FilePath temp_prefs = path_.Append(FILE_PATH_LITERAL("Preferences")); - file_util::CopyFile(prefs_file, temp_prefs); - - extensions_install_dir_ = path_.Append(FILE_PATH_LITERAL("Extensions")); - file_util::Delete(extensions_install_dir_, true); - file_util::CopyDirectory(source_install_dir, extensions_install_dir_, true); - - InitializeExtensionsService(temp_prefs, extensions_install_dir_); - } - - virtual void InitializeEmptyExtensionsService() { - ASSERT_TRUE(temp_dir_.CreateUniqueTempDir()); - FilePath path_ = temp_dir_.path(); - path_ = path_.Append(FILE_PATH_LITERAL("TestingExtensionsPath")); - file_util::Delete(path_, true); - file_util::CreateDirectory(path_); - FilePath prefs_filename = path_ - .Append(FILE_PATH_LITERAL("TestPreferences")); - extensions_install_dir_ = path_.Append(FILE_PATH_LITERAL("Extensions")); - file_util::Delete(extensions_install_dir_, true); - file_util::CreateDirectory(extensions_install_dir_); - - InitializeExtensionsService(prefs_filename, extensions_install_dir_); - } - - static void SetUpTestCase() { - ExtensionErrorReporter::Init(false); // no noisy errors - } - - virtual void SetUp() { - ExtensionErrorReporter::GetInstance()->ClearErrors(); - } - virtual void Observe(NotificationType type, const NotificationSource& source, const NotificationDetails& details) { @@ -319,10 +342,6 @@ class ExtensionsServiceTest } } - void set_extensions_enabled(bool enabled) { - service_->set_extensions_enabled(enabled); - } - void SetMockExternalProvider(Extension::Location location, ExternalExtensionProvider* provider) { service_->SetProviderForTesting(location, provider); @@ -501,15 +520,6 @@ class ExtensionsServiceTest } protected: - ScopedTempDir temp_dir_; - scoped_ptr<PrefService> prefs_; - scoped_ptr<Profile> profile_; - FilePath extensions_install_dir_; - scoped_refptr<ExtensionsService> service_; - size_t total_successes_; - MessageLoop loop_; - ChromeThread ui_thread_; - ChromeThread file_thread_; ExtensionList loaded_; std::string unloaded_id_; Extension* installed_; diff --git a/chrome/browser/extensions/extensions_service_unittest.h b/chrome/browser/extensions/extensions_service_unittest.h new file mode 100644 index 0000000..1f24fed --- /dev/null +++ b/chrome/browser/extensions/extensions_service_unittest.h @@ -0,0 +1,50 @@ +// Copyright (c) 2010 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. + +#ifndef CHROME_BROWSER_EXTENSIONS_EXTENSIONS_SERVICE_UNITTEST_H_ +#define CHROME_BROWSER_EXTENSIONS_EXTENSIONS_SERVICE_UNITTEST_H_ + +#include "base/file_path.h" +#include "base/message_loop.h" +#include "base/ref_counted.h" +#include "base/scoped_ptr.h" +#include "base/scoped_temp_dir.h" +#include "chrome/browser/chrome_thread.h" +#include "chrome/browser/extensions/extensions_service.h" +#include "testing/gtest/include/gtest/gtest.h" + +class ExtensionsServiceTestBase : public testing::Test { + public: + ExtensionsServiceTestBase(); + ~ExtensionsServiceTestBase(); + + virtual void InitializeExtensionsService( + const FilePath& pref_file, const FilePath& extensions_install_dir); + + virtual void InitializeInstalledExtensionsService( + const FilePath& prefs_file, const FilePath& source_install_dir); + + virtual void InitializeEmptyExtensionsService(); + + static void SetUpTestCase(); + + virtual void SetUp(); + + void set_extensions_enabled(bool enabled) { + service_->set_extensions_enabled(enabled); + } + + protected: + ScopedTempDir temp_dir_; + scoped_ptr<PrefService> prefs_; + scoped_ptr<Profile> profile_; + FilePath extensions_install_dir_; + scoped_refptr<ExtensionsService> service_; + size_t total_successes_; + MessageLoop loop_; + ChromeThread ui_thread_; + ChromeThread file_thread_; +}; + +#endif // CHROME_BROWSER_EXTENSIONS_EXTENSIONS_SERVICE_UNITTEST_H_ diff --git a/chrome/browser/extensions/user_script_listener_unittest.cc b/chrome/browser/extensions/user_script_listener_unittest.cc index 4d08553..546c734 100644 --- a/chrome/browser/extensions/user_script_listener_unittest.cc +++ b/chrome/browser/extensions/user_script_listener_unittest.cc @@ -1,350 +1,228 @@ -// Copyright (c) 2009 The Chromium Authors. All rights reserved. +// Copyright (c) 2010 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 <algorithm> -#include <vector> - #include "base/message_loop.h" #include "base/thread.h" -#include "chrome/browser/chrome_thread.h" -#include "chrome/browser/extensions/extensions_service.h" -#include "chrome/browser/extensions/user_script_master.h" -#include "chrome/browser/renderer_host/resource_dispatcher_host.h" +#include "chrome/browser/extensions/extension_file_util.h" +#include "chrome/browser/extensions/extensions_service_unittest.h" +#include "chrome/browser/extensions/user_script_listener.h" +#include "chrome/browser/renderer_host/global_request_id.h" +#include "chrome/browser/renderer_host/resource_dispatcher_host_request_info.h" +#include "chrome/browser/renderer_host/resource_handler.h" +#include "chrome/browser/renderer_host/resource_queue.h" #include "chrome/common/chrome_paths.h" -#include "chrome/common/chrome_plugin_lib.h" #include "chrome/common/notification_service.h" -#include "chrome/common/render_messages.h" -#include "chrome/test/testing_profile.h" -#include "ipc/ipc_message.h" +#include "chrome/common/notification_type.h" #include "net/url_request/url_request.h" #include "net/url_request/url_request_test_job.h" +#include "net/url_request/url_request_unittest.h" #include "testing/gtest/include/gtest/gtest.h" -#include "webkit/appcache/appcache_interfaces.h" -// A simple test URLRequestJob. We don't care what it does, only that whether it -// starts and finishes. -class SimpleTestJob : public URLRequestTestJob { - public: - explicit SimpleTestJob(URLRequest* request) - : URLRequestTestJob(request, test_headers(), test_data_1(), true) {} - private: - ~SimpleTestJob() {} -}; +class Profile; + +namespace { -class MockUserScriptMaster : public UserScriptMaster { +const char kMatchingUrl[] = "http://google.com/"; +const char kNotMatchingUrl[] = "http://example.com/"; +const char kTestData[] = "Hello, World!"; + +// Dummy ResourceHandler required for ResourceDispatcherHostRequestInfo. +class DummyResourceHandler : public ResourceHandler { public: - explicit MockUserScriptMaster(const FilePath& script_dir, Profile* profile) - : UserScriptMaster(script_dir, profile) {} + DummyResourceHandler() { + } + + virtual bool OnRequestRedirected(int request_id, const GURL& url, + ResourceResponse* response, + bool* defer) { + NOTREACHED(); + return true; + } - virtual void StartScan() { - // Do nothing. We want to manually control when scans occur. + virtual bool OnResponseStarted(int request_id, + ResourceResponse* response) { + NOTREACHED(); + return true; } - void TestStartScan() { - UserScriptMaster::StartScan(); + + virtual bool OnWillRead(int request_id, + net::IOBuffer** buf, + int* buf_size, + int min_size) { + NOTREACHED(); + return true; + } + + virtual bool OnReadCompleted(int request_id, int* bytes_read) { + NOTREACHED(); + return true; + } + + virtual bool OnResponseCompleted(int request_id, + const URLRequestStatus& status, + const std::string& security_info) { + NOTREACHED(); + return true; } private: - ~MockUserScriptMaster() {} + DISALLOW_COPY_AND_ASSIGN(DummyResourceHandler); }; -class MockIOThread : public ChromeThread { - public: - MockIOThread() : ChromeThread(ChromeThread::IO) {} - virtual ~MockIOThread() { Stop(); } +ResourceDispatcherHostRequestInfo* CreateRequestInfo(int request_id) { + return new ResourceDispatcherHostRequestInfo( + new DummyResourceHandler(), ChildProcessInfo::RENDER_PROCESS, 0, 0, + request_id, "null", "null", ResourceType::MAIN_FRAME, + 0, false, false, -1, -1); +} +// A simple test URLRequestJob. We don't care what it does, only that whether it +// starts and finishes. +class SimpleTestJob : public URLRequestTestJob { + public: + explicit SimpleTestJob(URLRequest* request) + : URLRequestTestJob(request, test_headers(), kTestData, true) {} private: - virtual void Init() { - service_.reset(new NotificationService()); - } - virtual void CleanUp() { - ChromePluginLib::UnloadAllPlugins(); - service_.reset(); - } - - scoped_ptr<NotificationService> service_; + ~SimpleTestJob() {} }; -// A class to help with making and handling resource requests. -class ResourceDispatcherHostTester - : public ResourceDispatcherHost::Receiver, - public URLRequest::Interceptor, - public base::RefCountedThreadSafe<ResourceDispatcherHostTester> { +class UserScriptListenerTest + : public ExtensionsServiceTestBase, + public URLRequest::Interceptor { public: - explicit ResourceDispatcherHostTester() - : Receiver(ChildProcessInfo::RENDER_PROCESS, -1) { + UserScriptListenerTest() + : mock_io_thread_(ChromeThread::IO, MessageLoop::current()) { URLRequest::RegisterRequestInterceptor(this); } - virtual ~ResourceDispatcherHostTester() { + + ~UserScriptListenerTest() { URLRequest::UnregisterRequestInterceptor(this); } - void MakeTestRequest(int request_id, const GURL& url) { - ChromeThread::PostTask( - ChromeThread::IO, FROM_HERE, - NewRunnableMethod( - this, &ResourceDispatcherHostTester::MakeTestRequestOnIOThread, - request_id, url)); - MessageLoop::current()->Run(); // wait for Quit from IO thread - } + virtual void SetUp() { + ExtensionsServiceTestBase::SetUp(); - void WaitForScan(MockUserScriptMaster* master) { - master->TestStartScan(); - MessageLoop::current()->RunAllPending(); // run the scan - ChromeThread::PostTask( - ChromeThread::IO, FROM_HERE, - NewRunnableMethod(this, &ResourceDispatcherHostTester::RunPending)); - MessageLoop::current()->Run(); // wait for Quit from IO thread - } + InitializeEmptyExtensionsService(); + service_->Init(); + MessageLoop::current()->RunAllPending(); + + listener_ = new UserScriptListener(&resource_queue_); - bool IsRequestStarted(int request_id) { - return std::find(started_requests_.begin(), started_requests_.end(), - request_id) != started_requests_.end(); + ResourceQueue::DelegateSet delegates; + delegates.insert(listener_.get()); + resource_queue_.Initialize(delegates); } - bool IsRequestComplete(int request_id) { - return std::find(completed_requests_.begin(), completed_requests_.end(), - request_id) != completed_requests_.end(); + virtual void TearDown() { + resource_queue_.Shutdown(); + listener_ = NULL; + MessageLoop::current()->RunAllPending(); } - private: // URLRequest::Interceptor virtual URLRequestJob* MaybeIntercept(URLRequest* request) { return new SimpleTestJob(request); } - // ResourceDispatcherHost::Receiver implementation - virtual bool Send(IPC::Message* msg) { - IPC_BEGIN_MESSAGE_MAP(ResourceDispatcherHostTester, *msg) - IPC_MESSAGE_HANDLER(ViewMsg_Resource_ReceivedResponse, OnReceivedResponse) - IPC_MESSAGE_HANDLER(ViewMsg_Resource_RequestComplete, OnRequestComplete) - IPC_END_MESSAGE_MAP() - delete msg; - return true; - } - - URLRequestContext* GetRequestContext( - uint32 request_id, - const ViewHostMsg_Resource_Request& request_data) { - return NULL; - } - - // TODO(mpcomplete): Some of this stuff is copied from - // resource_dispatcher_host_unittest.cc. Consider sharing. - static ViewHostMsg_Resource_Request CreateResourceRequest(const char* method, - const GURL& url) { - ViewHostMsg_Resource_Request request; - request.method = std::string(method); - request.url = url; - request.first_party_for_cookies = url; // bypass third-party cookie - // blocking - request.resource_type = ResourceType::MAIN_FRAME; - request.load_flags = 0; - // init the rest to default values to prevent getting UMR. - request.frame_origin = "null"; - request.main_frame_origin = "null"; - request.origin_child_id = 0; - request.request_context = 0; - request.appcache_host_id = appcache::kNoHostId; + protected: + TestURLRequest* StartTestRequest(URLRequest::Delegate* delegate, + const std::string& url) { + TestURLRequest* request = new TestURLRequest(GURL(url), delegate); + scoped_ptr<ResourceDispatcherHostRequestInfo> rdh_info( + CreateRequestInfo(0)); + resource_queue_.AddRequest(request, *rdh_info.get()); return request; } - void RunPending() { - MessageLoop::current()->SetNestableTasksAllowed(true); - MessageLoop::current()->RunAllPending(); - MessageLoop::current()->SetNestableTasksAllowed(false); - - // return control to UI thread. - ChromeThread::PostTask( - ChromeThread::UI, FROM_HERE, new MessageLoop::QuitTask()); + void LoadTestExtension() { + FilePath test_dir; + ASSERT_TRUE(PathService::Get(chrome::DIR_TEST_DATA, &test_dir)); + FilePath extension_path = test_dir + .AppendASCII("extensions") + .AppendASCII("good") + .AppendASCII("Extensions") + .AppendASCII("behllobkkfkfnphdnhnkndlbkcpglgmj") + .AppendASCII("1.0.0.0"); + service_->LoadExtension(extension_path); } - void MakeTestRequestOnIOThread(int request_id, const GURL& url) { - ViewHostMsg_Resource_Request request = CreateResourceRequest("GET", url); - ViewHostMsg_RequestResource msg(0, request_id, request); - bool msg_was_ok; - host_.OnMessageReceived(msg, this, &msg_was_ok); - RunPending(); + void UnloadTestExtension() { + ASSERT_FALSE(service_->extensions()->empty()); + service_->UnloadExtension(service_->extensions()->at(0)->id()); } - void OnReceivedResponse(int request_id, - const ResourceResponseHead& response_head) { - started_requests_.push_back(request_id); - } + scoped_refptr<UserScriptListener> listener_; - void OnRequestComplete(int request_id, - const URLRequestStatus& status, - const std::string& security_info) { - completed_requests_.push_back(request_id); - } - - ResourceDispatcherHost host_; + private: + ChromeThread mock_io_thread_; - // Note: these variables are accessed on both threads, but since we only - // one thread executes at a time, they are safe. - std::vector<int> started_requests_; - std::vector<int> completed_requests_; + ResourceQueue resource_queue_; }; -class ExtensionTestingProfile : public TestingProfile { - public: - ExtensionTestingProfile() { - } +TEST_F(UserScriptListenerTest, DelayAndUpdate) { + LoadTestExtension(); + MessageLoop::current()->RunAllPending(); - FilePath GetExtensionsInstallDir() { - return GetPath().AppendASCII(ExtensionsService::kInstallDirectoryName); - } + TestDelegate delegate; + scoped_ptr<TestURLRequest> request(StartTestRequest(&delegate, kMatchingUrl)); + ASSERT_FALSE(request->is_pending()); - void InitializeExtensionsService() { - DCHECK(!GetExtensionsService()); - service_ = new ExtensionsService(this, - CommandLine::ForCurrentProcess(), - GetPrefs(), - GetExtensionsInstallDir(), - false); - service_->set_extensions_enabled(true); - service_->set_show_extensions_prompts(false); - service_->ClearProvidersForTesting(); - service_->Init(); - } + NotificationService::current()->Notify( + NotificationType::USER_SCRIPTS_UPDATED, + Source<Profile>(profile_.get()), + NotificationService::NoDetails()); + MessageLoop::current()->RunAllPending(); + EXPECT_EQ(kTestData, delegate.data_received()); +} - void ShutdownExtensionsService() { - service_ = NULL; - } +TEST_F(UserScriptListenerTest, DelayAndUnload) { + LoadTestExtension(); + MessageLoop::current()->RunAllPending(); - virtual ExtensionsService* GetExtensionsService() { - return service_.get(); - } + TestDelegate delegate; + scoped_ptr<TestURLRequest> request(StartTestRequest(&delegate, kMatchingUrl)); + ASSERT_FALSE(request->is_pending()); - private: - scoped_refptr<ExtensionsService> service_; + UnloadTestExtension(); + MessageLoop::current()->RunAllPending(); - DISALLOW_COPY_AND_ASSIGN(ExtensionTestingProfile); -}; + // This is still not enough to start delayed requests. We have to notify the + // listener that the user scripts have been updated. + ASSERT_FALSE(request->is_pending()); -class UserScriptListenerTest : public testing::Test { - public: - virtual void SetUp() { - ui_thread_.reset(new ChromeThread(ChromeThread::UI, &loop_)); - file_thread_.reset(new ChromeThread(ChromeThread::FILE, &loop_)); - io_thread_.reset(new MockIOThread()); - base::Thread::Options options(MessageLoop::TYPE_IO, 0); - io_thread_->StartWithOptions(options); - DCHECK(io_thread_->message_loop()); - DCHECK(io_thread_->IsRunning()); + NotificationService::current()->Notify( + NotificationType::USER_SCRIPTS_UPDATED, + Source<Profile>(profile_.get()), + NotificationService::NoDetails()); + MessageLoop::current()->RunAllPending(); + EXPECT_EQ(kTestData, delegate.data_received()); +} - FilePath install_dir = profile_.GetPath() - .AppendASCII(ExtensionsService::kInstallDirectoryName); +TEST_F(UserScriptListenerTest, NoDelayNoExtension) { + TestDelegate delegate; + scoped_ptr<TestURLRequest> request(StartTestRequest(&delegate, kMatchingUrl)); - resource_tester_ = new ResourceDispatcherHostTester(); + // The request should be started immediately. + ASSERT_TRUE(request->is_pending()); - master_ = new MockUserScriptMaster(profile_.GetExtensionsInstallDir(), - &profile_); + MessageLoop::current()->RunAllPending(); + EXPECT_EQ(kTestData, delegate.data_received()); +} - profile_.InitializeExtensionsService(); - } +TEST_F(UserScriptListenerTest, NoDelayNotMatching) { + LoadTestExtension(); + MessageLoop::current()->RunAllPending(); - virtual void TearDown() { - // Shutdown ExtensionsService now, so that it can be destroyed while - // ChromeThreads and MessageLoop are still around (they are used in the - // ExtensionsService destruction process). - profile_.ShutdownExtensionsService(); - io_thread_.reset(); - file_thread_.reset(); - ui_thread_.reset(); - resource_tester_ = NULL; - } + TestDelegate delegate; + scoped_ptr<TestURLRequest> request(StartTestRequest(&delegate, + kNotMatchingUrl)); - protected: - ExtensionTestingProfile profile_; - MessageLoopForUI loop_; - scoped_ptr<ChromeThread> ui_thread_; - scoped_ptr<ChromeThread> file_thread_; - scoped_ptr<MockIOThread> io_thread_; - scoped_refptr<ResourceDispatcherHostTester> resource_tester_; - scoped_refptr<MockUserScriptMaster> master_; -}; + // The request should be started immediately. + ASSERT_TRUE(request->is_pending()); -// Loads a single extension and ensures that requests to URLs with content -// scripts are delayed. -TEST_F(UserScriptListenerTest, SingleExtension) { - FilePath extensions_path; - ASSERT_TRUE(PathService::Get(chrome::DIR_TEST_DATA, &extensions_path)); - extensions_path = extensions_path.AppendASCII("extensions"); - FilePath ext1 = extensions_path - .AppendASCII("good") - .AppendASCII("Extensions") - .AppendASCII("behllobkkfkfnphdnhnkndlbkcpglgmj") - .AppendASCII("1.0.0.0"); - profile_.GetExtensionsService()->LoadExtension(ext1); - loop_.RunAllPending(); - ASSERT_EQ(1u, profile_.GetExtensionsService()->extensions()->size()); - - // Our extension has a content script on google.com. That request should be - // delayed. - resource_tester_->MakeTestRequest(0, GURL("http://google.com/")); - resource_tester_->MakeTestRequest(1, GURL("http://yahoo.com/")); - - EXPECT_FALSE(resource_tester_->IsRequestStarted(0)); - EXPECT_TRUE(resource_tester_->IsRequestStarted(1)); - EXPECT_TRUE(resource_tester_->IsRequestComplete(1)); - - // After scanning, the user scripts should be ready and the request can - // go through. - resource_tester_->WaitForScan(master_.get()); - - EXPECT_TRUE(resource_tester_->IsRequestStarted(0)); - EXPECT_TRUE(resource_tester_->IsRequestComplete(0)); + MessageLoop::current()->RunAllPending(); + EXPECT_EQ(kTestData, delegate.data_received()); } -// Loads two extensions and ensures that requests to URLs with content -// scripts are delayed. -TEST_F(UserScriptListenerTest, UnloadExtension) { - FilePath extensions_path; - ASSERT_TRUE(PathService::Get(chrome::DIR_TEST_DATA, &extensions_path)); - extensions_path = extensions_path.AppendASCII("extensions"); - - FilePath ext1 = extensions_path - .AppendASCII("good") - .AppendASCII("Extensions") - .AppendASCII("behllobkkfkfnphdnhnkndlbkcpglgmj") - .AppendASCII("1.0.0.0"); - profile_.GetExtensionsService()->LoadExtension(ext1); - loop_.RunAllPending(); - ASSERT_EQ(1u, profile_.GetExtensionsService()->extensions()->size()); - - FilePath ext2 = extensions_path - .AppendASCII("good") - .AppendASCII("Extensions") - .AppendASCII("bjafgdebaacbbbecmhlhpofkepfkgcpa") - .AppendASCII("1.0"); - profile_.GetExtensionsService()->LoadExtension(ext2); - loop_.RunAllPending(); - ASSERT_EQ(2u, profile_.GetExtensionsService()->extensions()->size()); - - // Our extension has a content script on google.com. That request should be - // delayed. - resource_tester_->MakeTestRequest(0, GURL("http://google.com/")); - resource_tester_->MakeTestRequest(1, GURL("http://yahoo.com/")); - - EXPECT_FALSE(resource_tester_->IsRequestStarted(0)); - EXPECT_TRUE(resource_tester_->IsRequestStarted(1)); - EXPECT_TRUE(resource_tester_->IsRequestComplete(1)); - - // Unload the first extension and run a scan. Request should complete. - profile_.GetExtensionsService()->UnloadExtension( - "behllobkkfkfnphdnhnkndlbkcpglgmj"); - resource_tester_->WaitForScan(master_.get()); - - EXPECT_TRUE(resource_tester_->IsRequestStarted(0)); - EXPECT_TRUE(resource_tester_->IsRequestComplete(0)); - - // Make the same requests, and they should complete instantly. - resource_tester_->MakeTestRequest(2, GURL("http://google.com/")); - resource_tester_->MakeTestRequest(3, GURL("http://yahoo.com/")); - - EXPECT_TRUE(resource_tester_->IsRequestStarted(2)); - EXPECT_TRUE(resource_tester_->IsRequestComplete(2)); - EXPECT_TRUE(resource_tester_->IsRequestStarted(3)); - EXPECT_TRUE(resource_tester_->IsRequestComplete(3)); -} +} // namespace diff --git a/chrome/browser/renderer_host/resource_dispatcher_host_unittest.cc b/chrome/browser/renderer_host/resource_dispatcher_host_unittest.cc index 7650d9c..38f4dd4 100644 --- a/chrome/browser/renderer_host/resource_dispatcher_host_unittest.cc +++ b/chrome/browser/renderer_host/resource_dispatcher_host_unittest.cc @@ -185,6 +185,8 @@ class ResourceDispatcherHostTest : public testing::Test, DCHECK(test_fixture_ == this); test_fixture_ = NULL; + host_.Shutdown(); + ChildProcessSecurityPolicy::GetInstance()->Remove(0); // The plugin lib is automatically loaded during these test diff --git a/chrome/browser/renderer_host/resource_queue.cc b/chrome/browser/renderer_host/resource_queue.cc index 409f6b9..dca6bd2 100644 --- a/chrome/browser/renderer_host/resource_queue.cc +++ b/chrome/browser/renderer_host/resource_queue.cc @@ -17,8 +17,7 @@ ResourceQueue::ResourceQueue() : shutdown_(false) { } ResourceQueue::~ResourceQueue() { - // TODO(phajdan.jr): Add DCHECK(shutdown_) here when unit tests stop abusing - // ResourceDispatcherHost by not shutting it down in tests. + DCHECK(shutdown_); } void ResourceQueue::Initialize(const DelegateSet& delegates) { |