Merge Chromium + Blink git repositories
[chromium-blink-merge.git] / content / public / test / test_utils.h
blob522c277f874b20ad9ed2889ac77b5a6f7b9210c9
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 #ifndef CONTENT_PUBLIC_TEST_TEST_UTILS_H_
6 #define CONTENT_PUBLIC_TEST_TEST_UTILS_H_
8 #include "base/callback.h"
9 #include "base/memory/ref_counted.h"
10 #include "base/memory/scoped_ptr.h"
11 #include "base/run_loop.h"
12 #include "content/public/browser/browser_child_process_observer.h"
13 #include "content/public/browser/browser_thread.h"
14 #include "content/public/browser/notification_details.h"
15 #include "content/public/browser/notification_observer.h"
16 #include "content/public/browser/notification_registrar.h"
17 #include "content/public/browser/notification_source.h"
18 #include "content/public/browser/web_contents_observer.h"
20 namespace base {
21 class Value;
22 class CommandLine;
23 } // namespace base
25 // A collection of functions designed for use with unit and browser tests.
27 namespace content {
29 class RenderFrameHost;
31 // Turns on nestable tasks, runs the message loop, then resets nestable tasks
32 // to what they were originally. Prefer this over MessageLoop::Run for in
33 // process browser tests that need to block until a condition is met.
34 void RunMessageLoop();
36 // Variant of RunMessageLoop that takes RunLoop.
37 void RunThisRunLoop(base::RunLoop* run_loop);
39 // Turns on nestable tasks, runs all pending tasks in the message loop,
40 // then resets nestable tasks to what they were originally. Prefer this
41 // over MessageLoop::RunAllPending for in process browser tests to run
42 // all pending tasks.
43 void RunAllPendingInMessageLoop();
45 // Blocks the current thread until all the pending messages in the loop of the
46 // thread |thread_id| have been processed.
47 void RunAllPendingInMessageLoop(BrowserThread::ID thread_id);
49 // Runs until both the blocking pool and the current message loop are empty
50 // (have no more scheduled tasks) and no tasks are running.
51 void RunAllBlockingPoolTasksUntilIdle();
53 // Get task to quit the given RunLoop. It allows a few generations of pending
54 // tasks to run as opposed to run_loop->QuitClosure().
55 base::Closure GetQuitTaskForRunLoop(base::RunLoop* run_loop);
57 // Executes the specified JavaScript in the specified frame, and runs a nested
58 // MessageLoop. When the result is available, it is returned.
59 // This should not be used; the use of the ExecuteScript functions in
60 // browser_test_utils is preferable.
61 scoped_ptr<base::Value> ExecuteScriptAndGetValue(
62 RenderFrameHost* render_frame_host, const std::string& script);
64 // Returns true if all sites are isolated. Typically used to bail from a test
65 // that is incompatible with --site-per-process.
66 bool AreAllSitesIsolatedForTesting();
68 // Appends --site-per-process to the command line, enabling tests to exercise
69 // site isolation and cross-process iframes.
71 // TODO(nick): In some places this method is called from the top of a test
72 // body. That's not strictly safe (it's setting a command line after it
73 // already may have been read). We should try make that pattern safer, as it
74 // makes browser tests easier to write.
75 void IsolateAllSitesForTesting(base::CommandLine* command_line);
77 // Helper class to Run and Quit the message loop. Run and Quit can only happen
78 // once per instance. Make a new instance for each use. Calling Quit after Run
79 // has returned is safe and has no effect.
80 class MessageLoopRunner : public base::RefCounted<MessageLoopRunner> {
81 public:
82 MessageLoopRunner();
84 // Run the current MessageLoop unless the quit closure
85 // has already been called.
86 void Run();
88 // Quit the matching call to Run (nested MessageLoops are unaffected).
89 void Quit();
91 // Hand this closure off to code that uses callbacks to notify completion.
92 // Example:
93 // scoped_refptr<MessageLoopRunner> runner = new MessageLoopRunner;
94 // kick_off_some_api(runner->QuitClosure());
95 // runner->Run();
96 base::Closure QuitClosure();
98 bool loop_running() const { return loop_running_; }
100 private:
101 friend class base::RefCounted<MessageLoopRunner>;
102 ~MessageLoopRunner();
104 // True when the message loop is running.
105 bool loop_running_;
107 // True after closure returned by |QuitClosure| has been called.
108 bool quit_closure_called_;
110 base::RunLoop run_loop_;
112 DISALLOW_COPY_AND_ASSIGN(MessageLoopRunner);
115 // A WindowedNotificationObserver allows code to wait until a condition is met.
116 // Simple conditions are specified by providing a |notification_type| and a
117 // |source|. When a notification of the expected type from the expected source
118 // is received, the condition is met.
119 // More complex conditions can be specified by providing a |notification_type|
120 // and a |callback|. The callback is called whenever the notification is fired.
121 // If the callback returns |true|, the condition is met. Otherwise, the
122 // condition is not yet met and the callback will be invoked again every time a
123 // notification of the expected type is received until the callback returns
124 // |true|. For convenience, two callback types are defined, one that is provided
125 // with the notification source and details, and one that is not.
127 // This helper class exists to avoid the following common pattern in tests:
128 // PerformAction()
129 // WaitForCompletionNotification()
130 // The pattern leads to flakiness as there is a window between PerformAction
131 // returning and the observers getting registered, where a notification will be
132 // missed.
134 // Rather, one can do this:
135 // WindowedNotificationObserver signal(...)
136 // PerformAction()
137 // signal.Wait()
138 class WindowedNotificationObserver : public NotificationObserver {
139 public:
140 // Callback invoked on notifications. Should return |true| when the condition
141 // being waited for is met. For convenience, there is a choice between two
142 // callback types, one that is provided with the notification source and
143 // details, and one that is not.
144 typedef base::Callback<bool(const NotificationSource&,
145 const NotificationDetails&)>
146 ConditionTestCallback;
147 typedef base::Callback<bool(void)>
148 ConditionTestCallbackWithoutSourceAndDetails;
150 // Set up to wait for a simple condition. The condition is met when a
151 // notification of the given |notification_type| from the given |source| is
152 // received. To accept notifications from all sources, specify
153 // NotificationService::AllSources() as |source|.
154 WindowedNotificationObserver(int notification_type,
155 const NotificationSource& source);
157 // Set up to wait for a complex condition. The condition is met when
158 // |callback| returns |true|. The callback is invoked whenever a notification
159 // of |notification_type| from any source is received.
160 WindowedNotificationObserver(int notification_type,
161 const ConditionTestCallback& callback);
162 WindowedNotificationObserver(
163 int notification_type,
164 const ConditionTestCallbackWithoutSourceAndDetails& callback);
166 ~WindowedNotificationObserver() override;
168 // Adds an additional notification type to wait for. The condition will be met
169 // if any of the registered notification types from their respective sources
170 // is received.
171 void AddNotificationType(int notification_type,
172 const NotificationSource& source);
174 // Wait until the specified condition is met. If the condition is already met
175 // (that is, the expected notification has already been received or the
176 // given callback returns |true| already), Wait() returns immediately.
177 void Wait();
179 // Returns NotificationService::AllSources() if we haven't observed a
180 // notification yet.
181 const NotificationSource& source() const {
182 return source_;
185 const NotificationDetails& details() const {
186 return details_;
189 // NotificationObserver:
190 void Observe(int type,
191 const NotificationSource& source,
192 const NotificationDetails& details) override;
194 private:
195 bool seen_;
196 bool running_;
197 NotificationRegistrar registrar_;
199 ConditionTestCallback callback_;
201 NotificationSource source_;
202 NotificationDetails details_;
203 scoped_refptr<MessageLoopRunner> message_loop_runner_;
205 DISALLOW_COPY_AND_ASSIGN(WindowedNotificationObserver);
208 // Unit tests can use code which runs in the utility process by having it run on
209 // an in-process utility thread. This eliminates having two code paths in
210 // production code to deal with unit tests, and also helps with the binary
211 // separation on Windows since chrome.dll doesn't need to call into Blink code
212 // for some utility code to handle the single process case.
213 // Include this class as a member variable in your test harness if you take
214 // advantage of this functionality to ensure that the in-process utility thread
215 // is torn down correctly. See http://crbug.com/316919 for more information.
216 // Note: this class should be declared after the TestBrowserThreadBundle and
217 // ShadowingAtExitManager (if it exists) as it will need to be run before they
218 // are torn down.
219 class InProcessUtilityThreadHelper : public BrowserChildProcessObserver {
220 public:
221 InProcessUtilityThreadHelper();
222 ~InProcessUtilityThreadHelper() override;
224 private:
225 void BrowserChildProcessHostConnected(const ChildProcessData& data) override;
226 void BrowserChildProcessHostDisconnected(
227 const ChildProcessData& data) override;
229 int child_thread_count_;
230 scoped_refptr<MessageLoopRunner> runner_;
232 DISALLOW_COPY_AND_ASSIGN(InProcessUtilityThreadHelper);
235 // This observer keeps track of the last deleted RenderFrame to avoid
236 // accessing it and causing use-after-free condition.
237 class RenderFrameDeletedObserver : public WebContentsObserver {
238 public:
239 RenderFrameDeletedObserver(RenderFrameHost* rfh);
240 ~RenderFrameDeletedObserver() override;
242 // Overridden WebContentsObserver methods.
243 void RenderFrameDeleted(RenderFrameHost* render_frame_host) override;
245 void WaitUntilDeleted();
246 bool deleted();
248 private:
249 int process_id_;
250 int routing_id_;
251 bool deleted_;
252 scoped_ptr<base::RunLoop> runner_;
254 DISALLOW_COPY_AND_ASSIGN(RenderFrameDeletedObserver);
257 // Watches a WebContents and blocks until it is destroyed.
258 class WebContentsDestroyedWatcher : public WebContentsObserver {
259 public:
260 explicit WebContentsDestroyedWatcher(WebContents* web_contents);
261 ~WebContentsDestroyedWatcher() override;
263 // Waits until the WebContents is destroyed.
264 void Wait();
266 private:
267 // Overridden WebContentsObserver methods.
268 void WebContentsDestroyed() override;
270 scoped_refptr<MessageLoopRunner> message_loop_runner_;
272 DISALLOW_COPY_AND_ASSIGN(WebContentsDestroyedWatcher);
275 } // namespace content
277 #endif // CONTENT_PUBLIC_TEST_TEST_UTILS_H_