sync_test.h revision 5f1c94371a64b3196d4be9466099bb892df9b88e
1// Copyright 2013 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#ifndef CHROME_BROWSER_SYNC_TEST_INTEGRATION_SYNC_TEST_H_
6#define CHROME_BROWSER_SYNC_TEST_INTEGRATION_SYNC_TEST_H_
7
8#include <string>
9#include <vector>
10
11#include "base/basictypes.h"
12#include "base/compiler_specific.h"
13#include "base/memory/scoped_ptr.h"
14#include "base/memory/scoped_vector.h"
15#include "chrome/test/base/in_process_browser_test.h"
16#include "net/dns/mock_host_resolver.h"
17#include "net/http/http_status_code.h"
18#include "net/url_request/url_request_status.h"
19#include "sync/internal_api/public/base/model_type.h"
20#include "sync/protocol/sync_protocol_error.h"
21#include "sync/test/fake_server/fake_server.h"
22#include "sync/test/local_sync_test_server.h"
23
24class Profile;
25class ProfileSyncService;
26class ProfileSyncServiceHarness;
27class P2PInvalidationForwarder;
28
29namespace base {
30class CommandLine;
31}
32
33namespace fake_server {
34class FakeServer;
35class FakeServerInvalidationService;
36}
37
38namespace net {
39class FakeURLFetcherFactory;
40class ProxyConfig;
41class ScopedDefaultHostResolverProc;
42class URLFetcherImplFactory;
43class URLRequestContextGetter;
44}
45
46// This is the base class for integration tests for all sync data types. Derived
47// classes must be defined for each sync data type. Individual tests are defined
48// using the IN_PROC_BROWSER_TEST_F macro.
49class SyncTest : public InProcessBrowserTest {
50 public:
51  // The different types of live sync tests that can be implemented.
52  enum TestType {
53    // Tests where only one client profile is synced with the server. Typically
54    // sanity level tests.
55    SINGLE_CLIENT,
56
57    // Tests that use one client profile and are not compatible with
58    // FakeServer.
59    // TODO(pvalenzuela): Delete this value when all SINGLE_CLIENT_LEGACY tests
60    // are compatible with FakeServer and switched to SINGLE_CLIENT. See
61    // crbug.com/323265.
62    SINGLE_CLIENT_LEGACY,
63
64    // Tests where two client profiles are synced with the server. Typically
65    // functionality level tests.
66    TWO_CLIENT,
67
68    // Tests that use two client profiles and are not compatible with
69    // FakeServer.
70    // TODO(pvalenzuela): Delete this value when all TWO_CLIENT_LEGACY tests are
71    // compatible with FakeServer and switched to TWO_CLIENT. See
72    // crbug.com/323265.
73    TWO_CLIENT_LEGACY,
74
75    // Tests where three or more client profiles are synced with the server.
76    // Typically, these tests create client side races and verify that sync
77    // works.
78    MULTIPLE_CLIENT
79  };
80
81  // The type of server we're running against.
82  enum ServerType {
83    SERVER_TYPE_UNDECIDED,
84    LOCAL_PYTHON_SERVER,    // The mock python server that runs locally and is
85                            // part of the Chromium checkout.
86    LOCAL_LIVE_SERVER,      // Some other server (maybe the real binary used by
87                            // Google's sync service) that can be started on
88                            // a per-test basis by running a command
89    EXTERNAL_LIVE_SERVER,   // A remote server that the test code has no control
90                            // over whatsoever; cross your fingers that the
91                            // account state is initially clean.
92    IN_PROCESS_FAKE_SERVER, // The fake Sync server (FakeServer) running
93                            // in-process (bypassing HTTP calls). This
94                            // ServerType will eventually replace
95                            // LOCAL_PYTHON_SERVER.
96  };
97
98  // NOTE: IMPORTANT the enum here should match with
99  // the enum defined on the chromiumsync.py test server impl.
100  enum SyncErrorFrequency {
101    // Uninitialized state.
102    ERROR_FREQUENCY_NONE,
103
104    // Server sends the error on all requests.
105    ERROR_FREQUENCY_ALWAYS,
106
107    // Server sends the error on two thirds of the request.
108    // Note this is not random. The server would send the
109    // error on the first 2 requests of every 3 requests.
110    ERROR_FREQUENCY_TWO_THIRDS
111  };
112
113  // A SyncTest must be associated with a particular test type.
114  explicit SyncTest(TestType test_type);
115
116  virtual ~SyncTest();
117
118  // Validates command line parameters and creates a local python test server if
119  // specified.
120  virtual void SetUp() OVERRIDE;
121
122  // Brings down local python test server if one was created.
123  virtual void TearDown() OVERRIDE;
124
125  // Sets up command line flags required for sync tests.
126  virtual void SetUpCommandLine(base::CommandLine* cl) OVERRIDE;
127
128  // Used to get the number of sync clients used by a test.
129  int num_clients() WARN_UNUSED_RESULT { return num_clients_; }
130
131  // Returns a pointer to a particular sync profile. Callee owns the object
132  // and manages its lifetime.
133  Profile* GetProfile(int index) WARN_UNUSED_RESULT;
134
135  // Returns a pointer to a particular browser. Callee owns the object
136  // and manages its lifetime.
137  Browser* GetBrowser(int index) WARN_UNUSED_RESULT;
138
139  // Returns a pointer to a particular sync client. Callee owns the object
140  // and manages its lifetime.
141  ProfileSyncServiceHarness* GetClient(int index) WARN_UNUSED_RESULT;
142
143  // Returns a reference to the collection of sync clients. Callee owns the
144  // object and manages its lifetime.
145  std::vector<ProfileSyncServiceHarness*>& clients() WARN_UNUSED_RESULT {
146    return clients_.get();
147  }
148
149  // Returns a ProfileSyncService at the given index.
150  ProfileSyncService* GetSyncService(int index);
151
152  // Returns the set of ProfileSyncServices.
153  std::vector<ProfileSyncService*> GetSyncServices();
154
155  // Returns a pointer to the sync profile that is used to verify changes to
156  // individual sync profiles. Callee owns the object and manages its lifetime.
157  Profile* verifier() WARN_UNUSED_RESULT;
158
159  // Used to determine whether the verifier profile should be updated or not.
160  bool use_verifier() WARN_UNUSED_RESULT { return use_verifier_; }
161
162  // After calling this method, changes made to a profile will no longer be
163  // reflected in the verifier profile. Note: Not all datatypes use this.
164  // TODO(rsimha): Hook up all datatypes to this mechanism.
165  void DisableVerifier();
166
167  // Initializes sync clients and profiles but does not sync any of them.
168  virtual bool SetupClients() WARN_UNUSED_RESULT;
169
170  // Initializes sync clients and profiles if required and syncs each of them.
171  virtual bool SetupSync() WARN_UNUSED_RESULT;
172
173  // Enable outgoing network connections for the given profile.
174  virtual void EnableNetwork(Profile* profile);
175
176  // Disable outgoing network connections for the given profile.
177  virtual void DisableNetwork(Profile* profile);
178
179  // Sets whether or not the sync clients in this test should respond to
180  // notifications of their own commits.  Real sync clients do not do this, but
181  // many test assertions require this behavior.
182  //
183  // Default is to return true.  Test should override this if they require
184  // different behavior.
185  virtual bool TestUsesSelfNotifications();
186
187  // Kicks off encryption for profile |index|.
188  bool EnableEncryption(int index);
189
190  // Checks if encryption is complete for profile |index|.
191  bool IsEncryptionComplete(int index);
192
193  // Waits until IsEncryptionComplete returns true or a timeout is reached.
194  bool AwaitEncryptionComplete(int index);
195
196  // Blocks until all sync clients have completed their mutual sync cycles.
197  // Returns true if a quiescent state was successfully reached.
198  bool AwaitQuiescence();
199
200  // Returns true if the server being used supports controlling
201  // notifications.
202  bool ServerSupportsNotificationControl() const;
203
204  // Disable notifications on the server.  This operation is available
205  // only if ServerSupportsNotificationControl() returned true.
206  void DisableNotifications();
207
208  // Enable notifications on the server.  This operation is available
209  // only if ServerSupportsNotificationControl() returned true.
210  void EnableNotifications();
211
212  // Sets the mock gaia response for when an OAuth2 token is requested.
213  // Each call to this method will overwrite responses that were previously set.
214  void SetOAuth2TokenResponse(const std::string& response_data,
215                              net::HttpStatusCode response_code,
216                              net::URLRequestStatus::Status status);
217
218  // Trigger a notification to be sent to all clients.  This operation
219  // is available only if ServerSupportsNotificationControl() returned
220  // true.
221  void TriggerNotification(syncer::ModelTypeSet changed_types);
222
223  // Returns true if the server being used supports injecting errors.
224  bool ServerSupportsErrorTriggering() const;
225
226  // Triggers a migration for one or more datatypes, and waits
227  // for the server to complete it.  This operation is available
228  // only if ServerSupportsErrorTriggering() returned true.
229  void TriggerMigrationDoneError(syncer::ModelTypeSet model_types);
230
231  // Triggers a transient error on the server. Note the server will stay in
232  // this state until shut down.
233  void TriggerTransientError();
234
235  // Triggers an XMPP auth error on the server.  Note the server will
236  // stay in this state until shut down.
237  void TriggerXmppAuthError();
238
239  // Triggers a sync error on the server.
240  //   error: The error the server is expected to return.
241  //   frequency: Frequency with which the error is returned.
242  void TriggerSyncError(const syncer::SyncProtocolError& error,
243                        SyncErrorFrequency frequency);
244
245  // Triggers the creation the Synced Bookmarks folder on the server.
246  void TriggerCreateSyncedBookmarks();
247
248  // Returns the FakeServer being used for the test or NULL if FakeServer is
249  // not being used.
250  fake_server::FakeServer* GetFakeServer() const;
251
252 protected:
253  // Add custom switches needed for running the test.
254  virtual void AddTestSwitches(base::CommandLine* cl);
255
256  // Append the command line switches to enable experimental types that aren't
257  // on by default yet.
258  virtual void AddOptionalTypesToCommandLine(base::CommandLine* cl);
259
260  // BrowserTestBase override. Destroys all the sync clients and sync
261  // profiles created by a test.
262  virtual void TearDownOnMainThread() OVERRIDE;
263
264  // InProcessBrowserTest override. Changes behavior of the default host
265  // resolver to avoid DNS lookup errors.
266  virtual void SetUpInProcessBrowserTestFixture() OVERRIDE;
267
268  // InProcessBrowserTest override. Resets the host resolver its default
269  // behavior.
270  virtual void TearDownInProcessBrowserTestFixture() OVERRIDE;
271
272  // Creates Profile, Browser and ProfileSyncServiceHarness instances for
273  // |index|. Used by SetupClients().
274  virtual void InitializeInstance(int index);
275
276  // Implementations of the EnableNotifications() and DisableNotifications()
277  // functions defined above.
278  void DisableNotificationsImpl();
279  void EnableNotificationsImpl();
280
281  // GAIA account used by the test case.
282  std::string username_;
283
284  // GAIA password used by the test case.
285  std::string password_;
286
287  // Locally available plain text file in which GAIA credentials are stored.
288  base::FilePath password_file_;
289
290  // The FakeServer used in tests with server type IN_PROCESS_FAKE_SERVER.
291  scoped_ptr<fake_server::FakeServer> fake_server_;
292
293 private:
294  // Helper to ProfileManager::CreateProfile that handles path creation.
295  static Profile* MakeProfile(const base::FilePath::StringType name);
296
297  // Helper method used to read GAIA credentials from a local password file
298  // specified via the "--password-file-for-test" command line switch.
299  // Note: The password file must be a plain text file with exactly two lines --
300  // the username on the first line and the password on the second line.
301  void ReadPasswordFile();
302
303  // Helper method that starts up a sync test server if required.
304  void SetUpTestServerIfRequired();
305
306  // Helper method used to start up a local python test server. Note: We set up
307  // an XMPP-only python server if |server_type_| is LOCAL_LIVE_SERVER and mock
308  // gaia credentials are in use. Returns true if successful.
309  bool SetUpLocalPythonTestServer();
310
311  // Helper method used to start up a local sync test server. Returns true if
312  // successful.
313  bool SetUpLocalTestServer();
314
315  // Helper method used to destroy the local python sync test server if one was
316  // created. Returns true if successful.
317  bool TearDownLocalPythonTestServer();
318
319  // Helper method used to destroy the local sync test server if one was
320  // created. Returns true if successful.
321  bool TearDownLocalTestServer();
322
323  // Helper method that waits for up to |wait| for the test server
324  // to start. Splits the time into |intervals| intervals, and polls the
325  // server after each interval to see if it has started. Returns true if
326  // successful.
327  bool WaitForTestServerToStart(base::TimeDelta wait, int intervals);
328
329  // Helper method used to check if the test server is up and running.
330  bool IsTestServerRunning();
331
332  // Used to disable and enable network connectivity by providing and
333  // clearing an invalid proxy configuration.
334  void SetProxyConfig(net::URLRequestContextGetter* context,
335                      const net::ProxyConfig& proxy_config);
336
337  void SetupNetwork(net::URLRequestContextGetter* context);
338
339  // Helper method used to set up fake responses for kClientLoginUrl,
340  // kIssueAuthTokenUrl, kGetUserInfoUrl and kSearchDomainCheckUrl in order to
341  // mock out calls to GAIA servers.
342  void SetupMockGaiaResponses();
343
344  // Helper method used to clear any fake responses that might have been set for
345  // various gaia URLs, cancel any outstanding URL requests, and return to using
346  // the default URLFetcher creation mechanism.
347  void ClearMockGaiaResponses();
348
349  // Decide which sync server implementation to run against based on the type
350  // of test being run and command line args passed in.
351  void DecideServerType();
352
353  // Sets up the client-side invalidations infrastructure depending on the
354  // value of |server_type_|.
355  void InitializeInvalidations(int index);
356
357  // Python sync test server, started on demand.
358  syncer::LocalSyncTestServer sync_server_;
359
360  // Helper class to whitelist the notification port.
361  scoped_ptr<net::ScopedPortException> xmpp_port_;
362
363  // Used to differentiate between single-client, two-client, multi-client and
364  // many-client tests.
365  TestType test_type_;
366
367  // Tells us what kind of server we're using (some tests run only on certain
368  // server types).
369  ServerType server_type_;
370
371  // Number of sync clients that will be created by a test.
372  int num_clients_;
373
374  // Collection of sync profiles used by a test. A sync profile maintains sync
375  // data contained within its own subdirectory under the chrome user data
376  // directory. Profiles are owned by the ProfileManager.
377  std::vector<Profile*> profiles_;
378
379  // Collection of pointers to the browser objects used by a test. One browser
380  // instance is created for each sync profile. Browser object lifetime is
381  // managed by BrowserList, so we don't use a ScopedVector here.
382  std::vector<Browser*> browsers_;
383
384  // Collection of sync clients used by a test. A sync client is associated with
385  // a sync profile, and implements methods that sync the contents of the
386  // profile with the server.
387  ScopedVector<ProfileSyncServiceHarness> clients_;
388
389  // A set of objects to listen for commit activity and broadcast notifications
390  // of this activity to its peer sync clients.
391  ScopedVector<P2PInvalidationForwarder> invalidation_forwarders_;
392
393  // Collection of pointers to FakeServerInvalidation objects for each profile.
394  std::vector<fake_server::FakeServerInvalidationService*>
395      fake_server_invalidation_services_;
396
397  // Sync profile against which changes to individual profiles are verified. We
398  // don't need a corresponding verifier sync client because the contents of the
399  // verifier profile are strictly local, and are not meant to be synced.
400  Profile* verifier_;
401
402  // Indicates whether changes to a profile should also change the verifier
403  // profile or not.
404  bool use_verifier_;
405
406  // Indicates whether or not notifications were explicitly enabled/disabled.
407  // Defaults to true.
408  bool notifications_enabled_;
409
410  // Sync integration tests need to make live DNS requests for access to
411  // GAIA and sync server URLs under google.com. We use a scoped version
412  // to override the default resolver while the test is active.
413  scoped_ptr<net::ScopedDefaultHostResolverProc> mock_host_resolver_override_;
414
415  // Used to start and stop the local test server.
416  base::ProcessHandle test_server_handle_;
417
418  // Fake URLFetcher factory used to mock out GAIA signin.
419  scoped_ptr<net::FakeURLFetcherFactory> fake_factory_;
420
421  // The URLFetcherImplFactory instance used to instantiate |fake_factory_|.
422  scoped_ptr<net::URLFetcherImplFactory> factory_;
423
424  DISALLOW_COPY_AND_ASSIGN(SyncTest);
425};
426
427#endif  // CHROME_BROWSER_SYNC_TEST_INTEGRATION_SYNC_TEST_H_
428