Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(368)

Side by Side Diff: chrome/browser/spellchecker/spellcheck_custom_dictionary_unittest.cc

Issue 11445002: Sync user's custom spellcheck dictionary (Closed) Base URL: http://git.chromium.org/chromium/src.git@master
Patch Set: Add browser tests for dictionary change notifications in settings Created 7 years, 12 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 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 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include <vector> 5 #include <vector>
6 6
7 #include "base/file_util.h" 7 #include "base/file_util.h"
8 #include "base/string_number_conversions.h"
8 #include "chrome/browser/spellchecker/spellcheck_custom_dictionary.h" 9 #include "chrome/browser/spellchecker/spellcheck_custom_dictionary.h"
9 #include "chrome/browser/spellchecker/spellcheck_factory.h" 10 #include "chrome/browser/spellchecker/spellcheck_factory.h"
10 #include "chrome/browser/spellchecker/spellcheck_service.h" 11 #include "chrome/browser/spellchecker/spellcheck_service.h"
11 #include "chrome/common/chrome_constants.h" 12 #include "chrome/common/chrome_constants.h"
12 #include "chrome/common/spellcheck_common.h" 13 #include "chrome/common/spellcheck_common.h"
13 #include "chrome/test/base/testing_profile.h" 14 #include "chrome/test/base/testing_profile.h"
14 #include "content/public/test/test_browser_thread.h" 15 #include "content/public/test/test_browser_thread.h"
16 #include "sync/api/sync_change.h"
17 #include "sync/api/sync_data.h"
18 #include "sync/api/sync_error_factory.h"
19 #include "sync/api/sync_error_factory_mock.h"
20 #include "sync/protocol/sync.pb.h"
15 #include "testing/gmock/include/gmock/gmock.h" 21 #include "testing/gmock/include/gmock/gmock.h"
16 #include "testing/gtest/include/gtest/gtest.h" 22 #include "testing/gtest/include/gtest/gtest.h"
17 23
18 using content::BrowserThread; 24 using content::BrowserThread;
19 using chrome::spellcheck_common::WordList; 25 using chrome::spellcheck_common::WordList;
20 26
21 static ProfileKeyedService* BuildSpellcheckService(Profile* profile) { 27 static ProfileKeyedService* BuildSpellcheckService(Profile* profile) {
22 return new SpellcheckService(profile); 28 return new SpellcheckService(profile);
23 } 29 }
24 30
25 class SpellcheckCustomDictionaryTest : public testing::Test { 31 class SpellcheckCustomDictionaryTest : public testing::Test {
26 protected: 32 protected:
27 SpellcheckCustomDictionaryTest() 33 SpellcheckCustomDictionaryTest()
28 : ui_thread_(BrowserThread::UI, &message_loop_), 34 : ui_thread_(BrowserThread::UI, &message_loop_),
29 file_thread_(BrowserThread::FILE, &message_loop_), 35 file_thread_(BrowserThread::FILE, &message_loop_),
30 profile_(new TestingProfile()) { 36 profile_(new TestingProfile) {
31 } 37 }
32 38
33 void SetUp() OVERRIDE { 39 void SetUp() OVERRIDE {
34 // Use SetTestingFactoryAndUse to force creation and initialization. 40 // Use SetTestingFactoryAndUse to force creation and initialization.
35 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse( 41 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse(
36 profile_.get(), &BuildSpellcheckService); 42 profile_.get(), &BuildSpellcheckService);
37 } 43 }
38 44
39 void TearDown() OVERRIDE { 45 void TearDown() OVERRIDE {
40 MessageLoop::current()->RunUntilIdle(); 46 MessageLoop::current()->RunUntilIdle();
41 } 47 }
42 48
43 MessageLoop message_loop_; 49 MessageLoop message_loop_;
44 content::TestBrowserThread ui_thread_; 50 content::TestBrowserThread ui_thread_;
45 content::TestBrowserThread file_thread_; 51 content::TestBrowserThread file_thread_;
46 52
47 scoped_ptr<TestingProfile> profile_; 53 scoped_ptr<TestingProfile> profile_;
48 }; 54 };
49 55
50 TEST_F(SpellcheckCustomDictionaryTest, SpellcheckSetCustomWordList) { 56 // A wrapper around SpellcheckCustomDictionary that does not own the wrapped
51 SpellcheckService* spellcheck_service = 57 // object. An instance of this class can be inside of a scoped pointer safely
52 SpellcheckServiceFactory::GetForProfile(profile_.get()); 58 // while the dictionary is managed by another scoped pointer.
59 class SyncChangeProcessorDelegate : public syncer::SyncChangeProcessor {
60 public:
61 explicit SyncChangeProcessorDelegate(SpellcheckCustomDictionary* dictionary)
62 : dictionary_(dictionary) {}
63 virtual ~SyncChangeProcessorDelegate() {}
53 64
54 WordList loaded_custom_words; 65 // Overridden from syncer::SyncChangeProcessor:
55 loaded_custom_words.push_back("foo"); 66 virtual syncer::SyncError ProcessSyncChanges(
56 loaded_custom_words.push_back("bar"); 67 const tracked_objects::Location& from_here,
57 WordList expected(loaded_custom_words); 68 const syncer::SyncChangeList& change_list) OVERRIDE {
58 SpellcheckCustomDictionary* custom_dictionary = 69 return dictionary_->ProcessSyncChanges(from_here, change_list);
59 spellcheck_service->GetCustomDictionary(); 70 }
60 custom_dictionary->SetCustomWordList(&loaded_custom_words); 71
61 EXPECT_EQ(custom_dictionary->GetWords(), expected); 72 private:
62 } 73 SpellcheckCustomDictionary* dictionary_;
74 DISALLOW_COPY_AND_ASSIGN(SyncChangeProcessorDelegate);
75 };
76
77 // An implementation of SyncErrorFactory that does not upload the error message
78 // and updates an outside error counter. This lets us know the number of error
79 // messages in an instance of this class after that instance is deleted.
80 class SyncErrorFactoryStub : public syncer::SyncErrorFactory {
81 public:
82 explicit SyncErrorFactoryStub(int* error_counter)
83 : error_counter_(error_counter) {}
84 virtual ~SyncErrorFactoryStub() {}
85
86 // Overridden from syncer::SyncErrorFactory:
87 virtual syncer::SyncError CreateAndUploadError(
88 const tracked_objects::Location& location,
89 const std::string& message) OVERRIDE {
90 (*error_counter_)++;
91 return syncer::SyncError(location, message, syncer::DICTIONARY);
92 }
93
94 private:
95 int* error_counter_;
96 DISALLOW_COPY_AND_ASSIGN(SyncErrorFactoryStub);
97 };
98
99 // Counts the number of notifications for dictionary load and change.
100 class DictionaryObserverCounter : public SpellcheckCustomDictionary::Observer {
101 public:
102 DictionaryObserverCounter() : loads_(0), changes_(0) {}
103 virtual ~DictionaryObserverCounter() {}
104
105 int loads() const { return loads_; }
106 int changes() const { return changes_; }
107
108 // Overridden from SpellcheckCustomDictionary::Observer:
109 virtual void OnCustomDictionaryLoaded() OVERRIDE { loads_++; }
110 virtual void OnCustomDictionaryChanged(
111 const SpellcheckCustomDictionary::Change* change) OVERRIDE { changes_++; }
112
113 private:
114 int loads_;
115 int changes_;
116 DISALLOW_COPY_AND_ASSIGN(DictionaryObserverCounter);
117 };
63 118
64 TEST_F(SpellcheckCustomDictionaryTest, CustomWordAddedAndRemovedLocally) { 119 TEST_F(SpellcheckCustomDictionaryTest, CustomWordAddedAndRemovedLocally) {
65 SpellcheckService* spellcheck_service = 120 SpellcheckService* spellcheck_service =
66 SpellcheckServiceFactory::GetForProfile(profile_.get()); 121 SpellcheckServiceFactory::GetForProfile(profile_.get());
67 122
68 WordList loaded_custom_words; 123 WordList loaded_custom_words;
69 SpellcheckCustomDictionary* custom_dictionary = 124 SpellcheckCustomDictionary* custom_dictionary =
70 spellcheck_service->GetCustomDictionary(); 125 spellcheck_service->GetCustomDictionary();
71 WordList expected; 126 WordList expected;
72 EXPECT_EQ(custom_dictionary->GetWords(), expected); 127 EXPECT_EQ(custom_dictionary->GetWords(), expected);
128
73 custom_dictionary->CustomWordAddedLocally("foo"); 129 custom_dictionary->CustomWordAddedLocally("foo");
74 expected.push_back("foo"); 130 expected.push_back("foo");
75 EXPECT_EQ(custom_dictionary->GetWords(), expected); 131 EXPECT_EQ(custom_dictionary->GetWords(), expected);
132
76 custom_dictionary->CustomWordAddedLocally("bar"); 133 custom_dictionary->CustomWordAddedLocally("bar");
77 expected.push_back("bar"); 134 expected.push_back("bar");
135 std::sort(expected.begin(), expected.end());
78 EXPECT_EQ(custom_dictionary->GetWords(), expected); 136 EXPECT_EQ(custom_dictionary->GetWords(), expected);
79 137
80 custom_dictionary->CustomWordRemovedLocally("foo"); 138 custom_dictionary->CustomWordRemovedLocally("foo");
81 custom_dictionary->CustomWordRemovedLocally("bar"); 139 custom_dictionary->CustomWordRemovedLocally("bar");
82 expected.clear(); 140 expected.clear();
83 EXPECT_EQ(custom_dictionary->GetWords(), expected); 141 EXPECT_EQ(custom_dictionary->GetWords(), expected);
84 } 142 }
85 143
86 TEST_F(SpellcheckCustomDictionaryTest, SaveAndLoad) { 144 TEST_F(SpellcheckCustomDictionaryTest, SaveAndLoad) {
87 SpellcheckService* spellcheck_service = 145 FilePath path = profile_->GetPath().Append(chrome::kCustomDictionaryFileName);
88 SpellcheckServiceFactory::GetForProfile(profile_.get()); 146 scoped_ptr<WordList> loaded_custom_words =
89 SpellcheckCustomDictionary* custom_dictionary = 147 custom_dictionary::LoadDictionary(path);
90 spellcheck_service->GetCustomDictionary();
91
92 WordList loaded_custom_words;
93 custom_dictionary->LoadDictionaryIntoCustomWordList(&loaded_custom_words);
94 148
95 // The custom word list should be empty now. 149 // The custom word list should be empty now.
96 WordList expected; 150 WordList expected;
97 EXPECT_EQ(loaded_custom_words, expected); 151 EXPECT_EQ(expected, *(loaded_custom_words.get()));
98 152
99 custom_dictionary->WriteWordToCustomDictionary("foo"); 153 custom_dictionary::WriteWordToCustomDictionary("foo", path);
100 expected.push_back("foo"); 154 expected.push_back("foo");
101 155
102 custom_dictionary->WriteWordToCustomDictionary("bar"); 156 custom_dictionary::WriteWordToCustomDictionary("bar", path);
103 expected.push_back("bar"); 157 expected.push_back("bar");
104 158
105 // The custom word list should include written words. 159 // The custom word list should include written words.
106 custom_dictionary->LoadDictionaryIntoCustomWordList(&loaded_custom_words); 160 loaded_custom_words = custom_dictionary::LoadDictionary(path);
107 std::sort(expected.begin(), expected.end()); 161 std::sort(expected.begin(), expected.end());
108 EXPECT_EQ(loaded_custom_words, expected); 162 EXPECT_EQ(expected, *(loaded_custom_words.get()));
109 163
110 // Load in another instance of SpellCheckService. 164 custom_dictionary::EraseWordFromCustomDictionary("foo", path);
111 // The result should be the same. 165 custom_dictionary::EraseWordFromCustomDictionary("bar", path);
112 SpellcheckService spellcheck_service2(profile_.get()); 166 loaded_custom_words = custom_dictionary::LoadDictionary(path);
113 WordList loaded_custom_words2;
114 spellcheck_service2.GetCustomDictionary()->
115 LoadDictionaryIntoCustomWordList(&loaded_custom_words2);
116 EXPECT_EQ(loaded_custom_words2, expected);
117
118 custom_dictionary->EraseWordFromCustomDictionary("foo");
119 custom_dictionary->EraseWordFromCustomDictionary("bar");
120 custom_dictionary->LoadDictionaryIntoCustomWordList(&loaded_custom_words);
121 expected.clear(); 167 expected.clear();
122 EXPECT_EQ(loaded_custom_words, expected); 168 EXPECT_EQ(expected, *(loaded_custom_words.get()));
123 169
124 // Flush the loop now to prevent service init tasks from being run during 170 // Flush the loop now to prevent service init tasks from being run during
125 // TearDown(); 171 // TearDown();
126 MessageLoop::current()->RunUntilIdle(); 172 MessageLoop::current()->RunUntilIdle();
127 } 173 }
128 174
129 TEST_F(SpellcheckCustomDictionaryTest, MultiProfile) { 175 TEST_F(SpellcheckCustomDictionaryTest, MultiProfile) {
130 SpellcheckService* spellcheck_service = 176 SpellcheckService* spellcheck_service =
131 SpellcheckServiceFactory::GetForProfile(profile_.get()); 177 SpellcheckServiceFactory::GetForProfile(profile_.get());
132 SpellcheckCustomDictionary* custom_dictionary = 178 SpellcheckCustomDictionary* custom_dictionary =
133 spellcheck_service->GetCustomDictionary(); 179 spellcheck_service->GetCustomDictionary();
134 TestingProfile profile2; 180 TestingProfile profile2;
135 SpellcheckService* spellcheck_service2 = 181 SpellcheckService* spellcheck_service2 =
136 static_cast<SpellcheckService*>( 182 static_cast<SpellcheckService*>(
137 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse( 183 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse(
138 &profile2, &BuildSpellcheckService)); 184 &profile2, &BuildSpellcheckService));
139 SpellcheckCustomDictionary* custom_dictionary2 = 185 SpellcheckCustomDictionary* custom_dictionary2 =
140 spellcheck_service2->GetCustomDictionary(); 186 spellcheck_service2->GetCustomDictionary();
141 187
142 WordList expected1; 188 WordList expected1;
143 WordList expected2; 189 WordList expected2;
144 190
145 custom_dictionary->WriteWordToCustomDictionary("foo"); 191 custom_dictionary->CustomWordAddedLocally("foo");
146 custom_dictionary->WriteWordToCustomDictionary("bar"); 192 custom_dictionary->CustomWordAddedLocally("bar");
147 expected1.push_back("foo"); 193 expected1.push_back("foo");
148 expected1.push_back("bar"); 194 expected1.push_back("bar");
149 195
150 custom_dictionary2->WriteWordToCustomDictionary("hoge"); 196 custom_dictionary2->CustomWordAddedLocally("hoge");
151 custom_dictionary2->WriteWordToCustomDictionary("fuga"); 197 custom_dictionary2->CustomWordAddedLocally("fuga");
152 expected2.push_back("hoge"); 198 expected2.push_back("hoge");
153 expected2.push_back("fuga"); 199 expected2.push_back("fuga");
154 200
155 WordList actual1; 201 WordList actual1 = custom_dictionary->GetWords();
156 custom_dictionary->LoadDictionaryIntoCustomWordList(&actual1); 202 std::sort(actual1.begin(), actual1.end());
157 std::sort(expected1.begin(), expected1.end()); 203 std::sort(expected1.begin(), expected1.end());
158 EXPECT_EQ(actual1, expected1); 204 EXPECT_EQ(actual1, expected1);
159 205
160 WordList actual2; 206 WordList actual2 = custom_dictionary2->GetWords();
161 custom_dictionary2->LoadDictionaryIntoCustomWordList(&actual2); 207 std::sort(actual2.begin(), actual2.end());
162 std::sort(expected2.begin(), expected2.end()); 208 std::sort(expected2.begin(), expected2.end());
163 EXPECT_EQ(actual2, expected2); 209 EXPECT_EQ(actual2, expected2);
164 210
165 // Flush the loop now to prevent service init tasks from being run during 211 // Flush the loop now to prevent service init tasks from being run during
166 // TearDown(); 212 // TearDown();
167 MessageLoop::current()->RunUntilIdle(); 213 MessageLoop::current()->RunUntilIdle();
168 } 214 }
169 215
170 // Legacy empty dictionary should be converted to new format empty dicitonary. 216 // Legacy empty dictionary should be converted to new format empty dictionary.
171 TEST_F(SpellcheckCustomDictionaryTest, LegacyEmptyDictionaryShouldBeConverted) { 217 TEST_F(SpellcheckCustomDictionaryTest, LegacyEmptyDictionaryShouldBeConverted) {
172 FilePath dictionary_path( 218 FilePath path = profile_->GetPath().Append(chrome::kCustomDictionaryFileName);
173 profile_->GetPath().Append(chrome::kCustomDictionaryFileName));
174 SpellcheckService* spellcheck_service =
175 SpellcheckServiceFactory::GetForProfile(profile_.get());
176 SpellcheckCustomDictionary* custom_dictionary =
177 spellcheck_service->GetCustomDictionary();
178 WordList loaded_custom_words;
179 219
180 std::string content; 220 std::string content;
181 file_util::WriteFile(dictionary_path, content.c_str(), content.length()); 221 file_util::WriteFile(path, content.c_str(), content.length());
182 custom_dictionary->LoadDictionaryIntoCustomWordList(&loaded_custom_words); 222 scoped_ptr<WordList> loaded_custom_words =
183 EXPECT_TRUE(loaded_custom_words.empty()); 223 custom_dictionary::LoadDictionary(path);
224 EXPECT_TRUE(loaded_custom_words->empty());
184 225
185 // Flush the loop now to prevent service init tasks from being run during 226 // Flush the loop now to prevent service init tasks from being run during
186 // TearDown(); 227 // TearDown();
187 MessageLoop::current()->RunUntilIdle(); 228 MessageLoop::current()->RunUntilIdle();
188 } 229 }
189 230
190 // Legacy dictionary with two words should be converted to new format dictionary 231 // Legacy dictionary with two words should be converted to new format dictionary
191 // with two words. 232 // with two words.
192 TEST_F(SpellcheckCustomDictionaryTest, 233 TEST_F(SpellcheckCustomDictionaryTest,
193 LegacyDictionaryWithTwoWordsShouldBeConverted) { 234 LegacyDictionaryWithTwoWordsShouldBeConverted) {
194 FilePath dictionary_path( 235 FilePath path = profile_->GetPath().Append(chrome::kCustomDictionaryFileName);
195 profile_->GetPath().Append(chrome::kCustomDictionaryFileName));
196 SpellcheckService* spellcheck_service =
197 SpellcheckServiceFactory::GetForProfile(profile_.get());
198 SpellcheckCustomDictionary* custom_dictionary =
199 spellcheck_service->GetCustomDictionary();
200 WordList loaded_custom_words;
201 WordList expected;
202 236
203 std::string content = "foo\nbar"; 237 std::string content = "foo\nbar";
204 file_util::WriteFile(dictionary_path, content.c_str(), content.length()); 238 file_util::WriteFile(path, content.c_str(), content.length());
205 custom_dictionary->LoadDictionaryIntoCustomWordList(&loaded_custom_words); 239 scoped_ptr<WordList> loaded_custom_words =
240 custom_dictionary::LoadDictionary(path);
241 WordList expected;
206 expected.push_back("bar"); 242 expected.push_back("bar");
207 expected.push_back("foo"); 243 expected.push_back("foo");
208 EXPECT_EQ(expected, loaded_custom_words); 244 EXPECT_EQ(expected, *(loaded_custom_words.get()));
209 245
210 // Flush the loop now to prevent service init tasks from being run during 246 // Flush the loop now to prevent service init tasks from being run during
211 // TearDown(); 247 // TearDown();
212 MessageLoop::current()->RunUntilIdle(); 248 MessageLoop::current()->RunUntilIdle();
213 } 249 }
214 250
215 // Words with spaces are illegal and should be removed. 251 // Words with spaces are illegal and should be removed.
216 TEST_F(SpellcheckCustomDictionaryTest, 252 TEST_F(SpellcheckCustomDictionaryTest,
217 IllegalWordsShouldBeRemovedFromDictionary) { 253 IllegalWordsShouldBeRemovedFromDictionary) {
218 FilePath dictionary_path( 254 FilePath path = profile_->GetPath().Append(chrome::kCustomDictionaryFileName);
219 profile_->GetPath().Append(chrome::kCustomDictionaryFileName)); 255
220 SpellcheckService* spellcheck_service = 256 std::string content = "foo\nfoo bar\nbar\nfoo bar";
221 SpellcheckServiceFactory::GetForProfile(profile_.get()); 257 file_util::WriteFile(path, content.c_str(), content.length());
222 SpellcheckCustomDictionary* custom_dictionary = 258 scoped_ptr<WordList> loaded_custom_words =
223 spellcheck_service->GetCustomDictionary(); 259 custom_dictionary::LoadDictionary(path);
224 WordList loaded_custom_words;
225 WordList expected; 260 WordList expected;
226
227 std::string content = "foo\nfoo bar\nbar\nfoo bar";
228 file_util::WriteFile(dictionary_path, content.c_str(), content.length());
229 custom_dictionary->LoadDictionaryIntoCustomWordList(&loaded_custom_words);
230 expected.push_back("bar"); 261 expected.push_back("bar");
231 expected.push_back("foo"); 262 expected.push_back("foo");
232 EXPECT_EQ(expected, loaded_custom_words); 263 EXPECT_EQ(expected, *(loaded_custom_words.get()));
233 264
234 // Flush the loop now to prevent service init tasks from being run during 265 // Flush the loop now to prevent service init tasks from being run during
235 // TearDown(); 266 // TearDown();
236 MessageLoop::current()->RunUntilIdle(); 267 MessageLoop::current()->RunUntilIdle();
237 } 268 }
238 269
239 // Write to dicitonary should backup previous version and write the word to the 270 // Write to dictionary should backup previous version and write the word to the
240 // end of the dictionary. If the dictionary file is corrupted on disk, the 271 // end of the dictionary. If the dictionary file is corrupted on disk, the
241 // previous version should be reloaded. 272 // previous version should be reloaded.
242 TEST_F(SpellcheckCustomDictionaryTest, CorruptedWriteShouldBeRecovered) { 273 TEST_F(SpellcheckCustomDictionaryTest, CorruptedWriteShouldBeRecovered) {
243 FilePath dictionary_path( 274 FilePath path = profile_->GetPath().Append(chrome::kCustomDictionaryFileName);
244 profile_->GetPath().Append(chrome::kCustomDictionaryFileName)); 275
245 SpellcheckService* spellcheck_service = 276 std::string content = "foo\nbar";
246 SpellcheckServiceFactory::GetForProfile(profile_.get()); 277 file_util::WriteFile(path, content.c_str(), content.length());
247 SpellcheckCustomDictionary* custom_dictionary = 278 scoped_ptr<WordList> loaded_custom_words =
248 spellcheck_service->GetCustomDictionary(); 279 custom_dictionary::LoadDictionary(path);
249 WordList loaded_custom_words;
250 WordList expected; 280 WordList expected;
251
252 std::string content = "foo\nbar";
253 file_util::WriteFile(dictionary_path, content.c_str(), content.length());
254 custom_dictionary->LoadDictionaryIntoCustomWordList(&loaded_custom_words);
255 expected.push_back("bar"); 281 expected.push_back("bar");
256 expected.push_back("foo"); 282 expected.push_back("foo");
257 EXPECT_EQ(expected, loaded_custom_words); 283 EXPECT_EQ(expected, *(loaded_custom_words.get()));
258 284
259 custom_dictionary->WriteWordToCustomDictionary("baz"); 285 custom_dictionary::WriteWordToCustomDictionary("baz", path);
260 content.clear(); 286 content.clear();
261 file_util::ReadFileToString(dictionary_path, &content); 287 file_util::ReadFileToString(path, &content);
262 content.append("corruption"); 288 content.append("corruption");
263 file_util::WriteFile(dictionary_path, content.c_str(), content.length()); 289 file_util::WriteFile(path, content.c_str(), content.length());
264 custom_dictionary->LoadDictionaryIntoCustomWordList(&loaded_custom_words); 290 loaded_custom_words = custom_dictionary::LoadDictionary(path);
265 EXPECT_EQ(expected, loaded_custom_words); 291 EXPECT_EQ(expected, *(loaded_custom_words.get()));
266 292
267 // Flush the loop now to prevent service init tasks from being run during 293 // Flush the loop now to prevent service init tasks from being run during
268 // TearDown(); 294 // TearDown();
295 MessageLoop::current()->RunUntilIdle();
296 }
297
298 TEST_F(SpellcheckCustomDictionaryTest,
299 GetAllSyncDataAccuratelyReflectsDictionaryState) {
300 SpellcheckCustomDictionary* dictionary =
301 SpellcheckServiceFactory::GetForProfile(
302 profile_.get())->GetCustomDictionary();
303
304 syncer::SyncDataList data = dictionary->GetAllSyncData(syncer::DICTIONARY);
305 EXPECT_TRUE(data.empty());
306
307 SpellcheckCustomDictionary::Change::Result result;
308 result = dictionary->CustomWordAddedLocally("foo");
309 EXPECT_FALSE(result.detected_duplicate_words());
310 EXPECT_FALSE(result.detected_invalid_words());
311
312 result = dictionary->CustomWordAddedLocally("bar");
313 EXPECT_FALSE(result.detected_duplicate_words());
314 EXPECT_FALSE(result.detected_invalid_words());
315
316 data = dictionary->GetAllSyncData(syncer::DICTIONARY);
317 EXPECT_EQ(2UL, data.size());
318 std::vector<std::string> words;
319 words.push_back("bar");
320 words.push_back("foo");
321 for (size_t i = 0; i < data.size(); i++) {
322 EXPECT_TRUE(data[i].GetSpecifics().has_dictionary());
323 EXPECT_EQ(syncer::DICTIONARY, data[i].GetDataType());
324 EXPECT_EQ(words[i], data[i].GetTag());
325 EXPECT_EQ(words[i], data[i].GetSpecifics().dictionary().word());
326 }
327
328 result = dictionary->CustomWordRemovedLocally("foo");
329 EXPECT_FALSE(result.detected_missing_words());
330
331 result = dictionary->CustomWordRemovedLocally("bar");
332 EXPECT_FALSE(result.detected_missing_words());
333
334 data = dictionary->GetAllSyncData(syncer::DICTIONARY);
335 EXPECT_TRUE(data.empty());
336
337 // Flush the loop now to prevent service init tasks from being run during
338 // TearDown();
339 MessageLoop::current()->RunUntilIdle();
340 }
341
342 TEST_F(SpellcheckCustomDictionaryTest, GetAllSyncDataHasLimit) {
343 SpellcheckCustomDictionary* dictionary =
344 SpellcheckServiceFactory::GetForProfile(
345 profile_.get())->GetCustomDictionary();
346
347 SpellcheckCustomDictionary::Change::Result result;
348 for (size_t i = 0;
349 i < chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS - 1;
350 i++) {
351 result = dictionary->CustomWordAddedLocally(
352 "foo" + base::Uint64ToString(i));
353 EXPECT_FALSE(result.detected_duplicate_words());
354 EXPECT_FALSE(result.detected_invalid_words());
355 }
356 EXPECT_EQ(
357 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS - 1,
358 dictionary->GetWords().size());
359 EXPECT_EQ(
360 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS - 1,
361 dictionary->GetAllSyncData(syncer::DICTIONARY).size());
362
363 dictionary->CustomWordAddedLocally("baz");
364 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
365 dictionary->GetWords().size());
366 EXPECT_EQ(
367 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
368 dictionary->GetAllSyncData(syncer::DICTIONARY).size());
369
370 dictionary->CustomWordAddedLocally("bar");
371 EXPECT_EQ(
372 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS + 1,
373 dictionary->GetWords().size());
374 EXPECT_EQ(
375 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
376 dictionary->GetAllSyncData(syncer::DICTIONARY).size());
377
378 dictionary->CustomWordAddedLocally("snafoo");
379 EXPECT_EQ(
380 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS + 2,
381 dictionary->GetWords().size());
382 EXPECT_EQ(
383 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
384 dictionary->GetAllSyncData(syncer::DICTIONARY).size());
385
386 // Flush the loop now to prevent service init tasks from being run during
387 // TearDown();
388 MessageLoop::current()->RunUntilIdle();
389 }
390
391 TEST_F(SpellcheckCustomDictionaryTest, ProcessSyncChanges) {
392 SpellcheckService* spellcheck_service =
393 SpellcheckServiceFactory::GetForProfile(profile_.get());
394 SpellcheckCustomDictionary* dictionary =
395 spellcheck_service->GetCustomDictionary();
396
397 dictionary->CustomWordAddedLocally("foo");
398 dictionary->CustomWordAddedLocally("bar");
399
400 syncer::SyncChangeList changes;
401 {
402 // Add existing word.
403 std::string word = "foo";
404 sync_pb::EntitySpecifics specifics;
405 specifics.mutable_dictionary()->set_word(word);
406 changes.push_back(syncer::SyncChange(
407 FROM_HERE,
408 syncer::SyncChange::ACTION_ADD,
409 syncer::SyncData::CreateLocalData(word, word, specifics)));
410 }
411 {
412 // Add invalid word.
413 std::string word = "foo bar";
414 sync_pb::EntitySpecifics specifics;
415 specifics.mutable_dictionary()->set_word(word);
416 changes.push_back(syncer::SyncChange(
417 FROM_HERE,
418 syncer::SyncChange::ACTION_ADD,
419 syncer::SyncData::CreateLocalData(word, word, specifics)));
420 }
421 {
422 // Add valid word.
423 std::string word = "baz";
424 sync_pb::EntitySpecifics specifics;
425 specifics.mutable_dictionary()->set_word(word);
426 changes.push_back(syncer::SyncChange(
427 FROM_HERE,
428 syncer::SyncChange::ACTION_ADD,
429 syncer::SyncData::CreateLocalData(word, word, specifics)));
430 }
431 {
432 // Remove missing word.
433 std::string word = "snafoo";
434 sync_pb::EntitySpecifics specifics;
435 specifics.mutable_dictionary()->set_word(word);
436 changes.push_back(syncer::SyncChange(
437 FROM_HERE,
438 syncer::SyncChange::ACTION_DELETE,
439 syncer::SyncData::CreateLocalData(word, word, specifics)));
440 }
441 {
442 // Remove existing word.
443 std::string word = "bar";
444 sync_pb::EntitySpecifics specifics;
445 specifics.mutable_dictionary()->set_word(word);
446 changes.push_back(syncer::SyncChange(
447 FROM_HERE,
448 syncer::SyncChange::ACTION_DELETE,
449 syncer::SyncData::CreateLocalData(word, word, specifics)));
450 }
451
452 EXPECT_FALSE(dictionary->ProcessSyncChanges(FROM_HERE, changes).IsSet());
453
454 const chrome::spellcheck_common::WordList& words = dictionary->GetWords();
455 EXPECT_EQ(2UL, words.size());
456 EXPECT_EQ(words.end(), std::find(words.begin(), words.end(), "bar"));
457 EXPECT_NE(words.end(), std::find(words.begin(), words.end(), "foo"));
458 EXPECT_NE(words.end(), std::find(words.begin(), words.end(), "baz"));
459
460 // Flush the loop now to prevent service init tasks from being run during
461 // TearDown();
462 MessageLoop::current()->RunUntilIdle();
463 }
464
465 TEST_F(SpellcheckCustomDictionaryTest, MergeDataAndStartSyncing) {
466 SpellcheckService* spellcheck_service =
467 SpellcheckServiceFactory::GetForProfile(profile_.get());
468 SpellcheckCustomDictionary* custom_dictionary =
469 spellcheck_service->GetCustomDictionary();
470 TestingProfile profile2;
471 SpellcheckService* spellcheck_service2 =
472 static_cast<SpellcheckService*>(
473 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse(
474 &profile2, &BuildSpellcheckService));
475 SpellcheckCustomDictionary* custom_dictionary2 =
476 spellcheck_service2->GetCustomDictionary();
477
478 for (size_t i = 0;
479 i < chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS / 2;
480 ++i) {
481 custom_dictionary->CustomWordAddedLocally("foo" + base::Uint64ToString(i));
482 }
483 for (size_t i = 0;
484 i < chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS / 2;
485 ++i) {
486 custom_dictionary2->CustomWordAddedLocally("bar" + base::Uint64ToString(i));
487 }
488
489 int error_counter = 0;
490 EXPECT_FALSE(custom_dictionary->MergeDataAndStartSyncing(
491 syncer::DICTIONARY,
492 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY),
493 scoped_ptr<syncer::SyncChangeProcessor>(
494 new SyncChangeProcessorDelegate(custom_dictionary2)),
495 scoped_ptr<syncer::SyncErrorFactory>(
496 new SyncErrorFactoryStub(&error_counter))).error().IsSet());
497 EXPECT_EQ(0, error_counter);
498
499 WordList words = custom_dictionary->GetWords();
500 WordList words2 = custom_dictionary2->GetWords();
501 EXPECT_EQ(words.size(), words2.size());
502
503 std::sort(words.begin(), words.end());
504 std::sort(words2.begin(), words2.end());
505 for (size_t i = 0; i < words.size(); ++i)
506 EXPECT_EQ(words[i], words2[i]);
507
508 // Flush the loop now to prevent service init tasks from being run during
509 // TearDown();
510 MessageLoop::current()->RunUntilIdle();
511 }
512
513 TEST_F(SpellcheckCustomDictionaryTest, DictionaryTooBigBeforeSyncing) {
514 SpellcheckService* spellcheck_service =
515 SpellcheckServiceFactory::GetForProfile(profile_.get());
516 SpellcheckCustomDictionary* custom_dictionary =
517 spellcheck_service->GetCustomDictionary();
518 TestingProfile profile2;
519 SpellcheckService* spellcheck_service2 =
520 static_cast<SpellcheckService*>(
521 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse(
522 &profile2, &BuildSpellcheckService));
523 SpellcheckCustomDictionary* custom_dictionary2 =
524 spellcheck_service2->GetCustomDictionary();
525
526 for (size_t i = 0;
527 i < chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS + 1;
528 ++i) {
529 custom_dictionary->CustomWordAddedLocally("foo" + base::Uint64ToString(i));
530 }
531
532 int error_counter = 0;
533 EXPECT_TRUE(custom_dictionary->MergeDataAndStartSyncing(
534 syncer::DICTIONARY,
535 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY),
536 scoped_ptr<syncer::SyncChangeProcessor>(
537 new SyncChangeProcessorDelegate(custom_dictionary2)),
538 scoped_ptr<syncer::SyncErrorFactory>(
539 new SyncErrorFactoryStub(&error_counter))).error().IsSet());
540 EXPECT_EQ(1, error_counter);
541
542 EXPECT_EQ(
543 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS + 1,
544 custom_dictionary->GetWords().size());
545 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
546 custom_dictionary2->GetWords().size());
547
548 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
549 custom_dictionary->GetAllSyncData(syncer::DICTIONARY).size());
550 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
551 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY).size());
552
553 // Flush the loop now to prevent service init tasks from being run during
554 // TearDown();
555 MessageLoop::current()->RunUntilIdle();
556 }
557
558 TEST_F(SpellcheckCustomDictionaryTest, DictionaryTooBigToStartSyncing) {
559 SpellcheckService* spellcheck_service =
560 SpellcheckServiceFactory::GetForProfile(profile_.get());
561 SpellcheckCustomDictionary* custom_dictionary =
562 spellcheck_service->GetCustomDictionary();
563 TestingProfile profile2;
564 SpellcheckService* spellcheck_service2 =
565 static_cast<SpellcheckService*>(
566 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse(
567 &profile2, &BuildSpellcheckService));
568 SpellcheckCustomDictionary* custom_dictionary2 =
569 spellcheck_service2->GetCustomDictionary();
570
571 for (size_t i = 0;
572 i < chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS - 1;
573 ++i) {
574 custom_dictionary->CustomWordAddedLocally("foo" + base::Uint64ToString(i));
575 }
576 custom_dictionary2->CustomWordAddedLocally("bar");
577 custom_dictionary2->CustomWordAddedLocally("baz");
578
579 int error_counter = 0;
580 EXPECT_TRUE(custom_dictionary->MergeDataAndStartSyncing(
581 syncer::DICTIONARY,
582 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY),
583 scoped_ptr<syncer::SyncChangeProcessor>(
584 new SyncChangeProcessorDelegate(custom_dictionary2)),
585 scoped_ptr<syncer::SyncErrorFactory>(
586 new SyncErrorFactoryStub(&error_counter))).error().IsSet());
587 EXPECT_EQ(1, error_counter);
588
589 EXPECT_EQ(
590 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS + 1,
591 custom_dictionary->GetWords().size());
592 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
593 custom_dictionary2->GetWords().size());
594
595 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
596 custom_dictionary->GetAllSyncData(syncer::DICTIONARY).size());
597 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
598 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY).size());
599
600 // Flush the loop now to prevent service init tasks from being run during
601 // TearDown();
602 MessageLoop::current()->RunUntilIdle();
603 }
604
605 TEST_F(SpellcheckCustomDictionaryTest, DictionaryTooBigToContiueSyncing) {
606 SpellcheckService* spellcheck_service =
607 SpellcheckServiceFactory::GetForProfile(profile_.get());
608 SpellcheckCustomDictionary* custom_dictionary =
609 spellcheck_service->GetCustomDictionary();
610 TestingProfile profile2;
611 SpellcheckService* spellcheck_service2 =
612 static_cast<SpellcheckService*>(
613 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse(
614 &profile2, &BuildSpellcheckService));
615 SpellcheckCustomDictionary* custom_dictionary2 =
616 spellcheck_service2->GetCustomDictionary();
617
618 for (size_t i = 0;
619 i < chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS - 1;
620 ++i) {
621 custom_dictionary->CustomWordAddedLocally("foo" + base::Uint64ToString(i));
622 }
623
624 int error_counter = 0;
625 EXPECT_FALSE(custom_dictionary->MergeDataAndStartSyncing(
626 syncer::DICTIONARY,
627 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY),
628 scoped_ptr<syncer::SyncChangeProcessor>(
629 new SyncChangeProcessorDelegate(custom_dictionary2)),
630 scoped_ptr<syncer::SyncErrorFactory>(
631 new SyncErrorFactoryStub(&error_counter))).error().IsSet());
632 EXPECT_EQ(0, error_counter);
633
634 custom_dictionary->CustomWordAddedLocally("bar");
635 EXPECT_EQ(0, error_counter);
636
637 custom_dictionary->CustomWordAddedLocally("baz");
638 EXPECT_EQ(1, error_counter);
639
640 EXPECT_EQ(
641 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS + 1,
642 custom_dictionary->GetWords().size());
643 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
644 custom_dictionary2->GetWords().size());
645
646 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
647 custom_dictionary->GetAllSyncData(syncer::DICTIONARY).size());
648 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
649 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY).size());
650
651 // Flush the loop now to prevent service init tasks from being run during
652 // TearDown();
653 MessageLoop::current()->RunUntilIdle();
654 }
655
656 TEST_F(SpellcheckCustomDictionaryTest, LoadAfterSyncStart) {
657 SpellcheckService* spellcheck_service =
658 SpellcheckServiceFactory::GetForProfile(profile_.get());
659 SpellcheckCustomDictionary* custom_dictionary =
660 spellcheck_service->GetCustomDictionary();
661 TestingProfile profile2;
662 SpellcheckService* spellcheck_service2 =
663 static_cast<SpellcheckService*>(
664 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse(
665 &profile2, &BuildSpellcheckService));
666 SpellcheckCustomDictionary* custom_dictionary2 =
667 spellcheck_service2->GetCustomDictionary();
668
669 custom_dictionary->CustomWordAddedLocally("foo");
670
671 int error_counter = 0;
672 EXPECT_FALSE(custom_dictionary->MergeDataAndStartSyncing(
673 syncer::DICTIONARY,
674 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY),
675 scoped_ptr<syncer::SyncChangeProcessor>(
676 new SyncChangeProcessorDelegate(custom_dictionary2)),
677 scoped_ptr<syncer::SyncErrorFactory>(
678 new SyncErrorFactoryStub(&error_counter))).error().IsSet());
679 EXPECT_EQ(0, error_counter);
680 EXPECT_TRUE(custom_dictionary->IsSyncing());
681
682 scoped_ptr<WordList> custom_words(new WordList);
683 custom_words->push_back("bar");
684 custom_dictionary->OnLoaded(custom_words.Pass());
685 EXPECT_TRUE(custom_dictionary->IsSyncing());
686
687 EXPECT_EQ(2UL, custom_dictionary->GetWords().size());
688 EXPECT_EQ(2UL, custom_dictionary2->GetWords().size());
689
690 EXPECT_EQ(2UL, custom_dictionary->GetAllSyncData(syncer::DICTIONARY).size());
691 EXPECT_EQ(2UL, custom_dictionary2->GetAllSyncData(syncer::DICTIONARY).size());
692
693 // Flush the loop now to prevent service init tasks from being run during
694 // TearDown();
695 MessageLoop::current()->RunUntilIdle();
696 }
697
698 TEST_F(SpellcheckCustomDictionaryTest, LoadAfterSyncStartTooBigToSync) {
699 SpellcheckService* spellcheck_service =
700 SpellcheckServiceFactory::GetForProfile(profile_.get());
701 SpellcheckCustomDictionary* custom_dictionary =
702 spellcheck_service->GetCustomDictionary();
703 TestingProfile profile2;
704 SpellcheckService* spellcheck_service2 =
705 static_cast<SpellcheckService*>(
706 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse(
707 &profile2, &BuildSpellcheckService));
708 SpellcheckCustomDictionary* custom_dictionary2 =
709 spellcheck_service2->GetCustomDictionary();
710
711 custom_dictionary->CustomWordAddedLocally("foo");
712
713 int error_counter = 0;
714 EXPECT_FALSE(custom_dictionary->MergeDataAndStartSyncing(
715 syncer::DICTIONARY,
716 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY),
717 scoped_ptr<syncer::SyncChangeProcessor>(
718 new SyncChangeProcessorDelegate(custom_dictionary2)),
719 scoped_ptr<syncer::SyncErrorFactory>(
720 new SyncErrorFactoryStub(&error_counter))).error().IsSet());
721 EXPECT_EQ(0, error_counter);
722 EXPECT_TRUE(custom_dictionary->IsSyncing());
723
724 scoped_ptr<WordList> custom_words(new WordList);
725 for (size_t i = 0;
726 i < chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS;
727 ++i) {
728 custom_words->push_back("foo" + base::Uint64ToString(i));
729 }
730 custom_dictionary->OnLoaded(custom_words.Pass());
731 EXPECT_EQ(1, error_counter);
732 EXPECT_FALSE(custom_dictionary->IsSyncing());
733
734 EXPECT_EQ(
735 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS + 1,
736 custom_dictionary->GetWords().size());
737 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
738 custom_dictionary2->GetWords().size());
739
740 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
741 custom_dictionary->GetAllSyncData(syncer::DICTIONARY).size());
742 EXPECT_EQ(chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS,
743 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY).size());
744
745 // Flush the loop now to prevent service init tasks from being run during
746 // TearDown();
747 MessageLoop::current()->RunUntilIdle();
748 }
749
750 TEST_F(SpellcheckCustomDictionaryTest, LoadDuplicatesAfterSync) {
751 SpellcheckService* spellcheck_service =
752 SpellcheckServiceFactory::GetForProfile(profile_.get());
753 SpellcheckCustomDictionary* custom_dictionary =
754 spellcheck_service->GetCustomDictionary();
755 TestingProfile profile2;
756 SpellcheckService* spellcheck_service2 =
757 static_cast<SpellcheckService*>(
758 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse(
759 &profile2, &BuildSpellcheckService));
760 SpellcheckCustomDictionary* custom_dictionary2 =
761 spellcheck_service2->GetCustomDictionary();
762
763 for (size_t i = 0;
764 i < chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS / 2;
765 ++i) {
766 custom_dictionary->CustomWordAddedLocally("foo" + base::Uint64ToString(i));
767 }
768
769 int error_counter = 0;
770 EXPECT_FALSE(custom_dictionary->MergeDataAndStartSyncing(
771 syncer::DICTIONARY,
772 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY),
773 scoped_ptr<syncer::SyncChangeProcessor>(
774 new SyncChangeProcessorDelegate(custom_dictionary2)),
775 scoped_ptr<syncer::SyncErrorFactory>(
776 new SyncErrorFactoryStub(&error_counter))).error().IsSet());
777 EXPECT_EQ(0, error_counter);
778 EXPECT_TRUE(custom_dictionary->IsSyncing());
779
780 scoped_ptr<WordList> custom_words(new WordList);
781 for (size_t i = 0;
782 i < chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS / 2;
783 ++i) {
784 custom_words->push_back("foo" + base::Uint64ToString(i));
785 }
786 custom_dictionary->OnLoaded(custom_words.Pass());
787 EXPECT_EQ(0, error_counter);
788 EXPECT_TRUE(custom_dictionary->IsSyncing());
789
790 EXPECT_EQ(
791 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS / 2,
792 custom_dictionary->GetWords().size());
793 EXPECT_EQ(
794 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS / 2,
795 custom_dictionary2->GetWords().size());
796
797 EXPECT_EQ(
798 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS / 2,
799 custom_dictionary->GetAllSyncData(syncer::DICTIONARY).size());
800 EXPECT_EQ(
801 chrome::spellcheck_common::MAX_SYNCABLE_DICTIONARY_SIZE_IN_WORDS / 2,
802 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY).size());
803
804 // Flush the loop now to prevent service init tasks from being run during
805 // TearDown();
806 MessageLoop::current()->RunUntilIdle();
807 }
808
809 TEST_F(SpellcheckCustomDictionaryTest, DictionaryLoadNotification) {
810 SpellcheckService* spellcheck_service =
811 SpellcheckServiceFactory::GetForProfile(profile_.get());
812 SpellcheckCustomDictionary* custom_dictionary =
813 spellcheck_service->GetCustomDictionary();
814
815 DictionaryObserverCounter observer;
816 custom_dictionary->AddObserver(&observer);
817
818 scoped_ptr<WordList> custom_words(new WordList);
819 custom_words->push_back("foo");
820 custom_words->push_back("bar");
821 custom_dictionary->OnLoaded(custom_words.Pass());
822
823 EXPECT_GE(observer.loads(), 1);
824 EXPECT_LE(observer.loads(), 2);
825 EXPECT_EQ(0, observer.changes());
826
827 custom_dictionary->RemoveObserver(&observer);
828
829 // Flush the loop now to prevent service init tasks from being run during
830 // TearDown();
831 MessageLoop::current()->RunUntilIdle();
832 }
833
834 TEST_F(SpellcheckCustomDictionaryTest, DictionaryAddWordNotification) {
835 SpellcheckService* spellcheck_service =
836 SpellcheckServiceFactory::GetForProfile(profile_.get());
837 SpellcheckCustomDictionary* custom_dictionary =
838 spellcheck_service->GetCustomDictionary();
839
840 custom_dictionary->OnLoaded(scoped_ptr<WordList>(new WordList));
841
842 DictionaryObserverCounter observer;
843 custom_dictionary->AddObserver(&observer);
844
845 custom_dictionary->AddWord("foo");
846 custom_dictionary->AddWord("bar");
847 custom_dictionary->AddWord("bar");
848
849 EXPECT_EQ(2, observer.changes());
850
851 custom_dictionary->RemoveObserver(&observer);
852
853 // Flush the loop now to prevent service init tasks from being run during
854 // TearDown();
855 MessageLoop::current()->RunUntilIdle();
856 }
857
858 TEST_F(SpellcheckCustomDictionaryTest, DictionaryWordAddedLocallyNotification) {
859 SpellcheckService* spellcheck_service =
860 SpellcheckServiceFactory::GetForProfile(profile_.get());
861 SpellcheckCustomDictionary* custom_dictionary =
862 spellcheck_service->GetCustomDictionary();
863
864 custom_dictionary->OnLoaded(scoped_ptr<WordList>(new WordList));
865
866 DictionaryObserverCounter observer;
867 custom_dictionary->AddObserver(&observer);
868
869 custom_dictionary->CustomWordAddedLocally("foo");
870 custom_dictionary->CustomWordAddedLocally("bar");
871 custom_dictionary->CustomWordAddedLocally("bar");
872
873 EXPECT_EQ(2, observer.changes());
874
875 custom_dictionary->RemoveObserver(&observer);
876
877 // Flush the loop now to prevent service init tasks from being run during
878 // TearDown();
879 MessageLoop::current()->RunUntilIdle();
880 }
881
882 TEST_F(SpellcheckCustomDictionaryTest, DictionaryRemoveWordNotification) {
883 SpellcheckService* spellcheck_service =
884 SpellcheckServiceFactory::GetForProfile(profile_.get());
885 SpellcheckCustomDictionary* custom_dictionary =
886 spellcheck_service->GetCustomDictionary();
887
888 custom_dictionary->OnLoaded(scoped_ptr<WordList>(new WordList));
889
890 custom_dictionary->AddWord("foo");
891 custom_dictionary->AddWord("bar");
892
893 DictionaryObserverCounter observer;
894 custom_dictionary->AddObserver(&observer);
895
896 custom_dictionary->RemoveWord("foo");
897 custom_dictionary->RemoveWord("bar");
898 custom_dictionary->RemoveWord("baz");
899
900 EXPECT_EQ(2, observer.changes());
901
902 custom_dictionary->RemoveObserver(&observer);
903
904 // Flush the loop now to prevent service init tasks from being run during
905 // TearDown();
906 MessageLoop::current()->RunUntilIdle();
907 }
908
909 TEST_F(SpellcheckCustomDictionaryTest,
910 DictionaryWordRemovedLocallyNotification) {
911 SpellcheckService* spellcheck_service =
912 SpellcheckServiceFactory::GetForProfile(profile_.get());
913 SpellcheckCustomDictionary* custom_dictionary =
914 spellcheck_service->GetCustomDictionary();
915
916 custom_dictionary->OnLoaded(scoped_ptr<WordList>(new WordList));
917
918 custom_dictionary->CustomWordAddedLocally("foo");
919 custom_dictionary->CustomWordAddedLocally("bar");
920
921 DictionaryObserverCounter observer;
922 custom_dictionary->AddObserver(&observer);
923
924 custom_dictionary->CustomWordRemovedLocally("foo");
925 custom_dictionary->CustomWordRemovedLocally("bar");
926 custom_dictionary->CustomWordRemovedLocally("baz");
927
928 EXPECT_EQ(2, observer.changes());
929
930 custom_dictionary->RemoveObserver(&observer);
931
932 // Flush the loop now to prevent service init tasks from being run during
933 // TearDown();
934 MessageLoop::current()->RunUntilIdle();
935 }
936
937 TEST_F(SpellcheckCustomDictionaryTest, DictionarySyncNotification) {
938 SpellcheckService* spellcheck_service =
939 SpellcheckServiceFactory::GetForProfile(profile_.get());
940 SpellcheckCustomDictionary* custom_dictionary =
941 spellcheck_service->GetCustomDictionary();
942 TestingProfile profile2;
943 SpellcheckService* spellcheck_service2 =
944 static_cast<SpellcheckService*>(
945 SpellcheckServiceFactory::GetInstance()->SetTestingFactoryAndUse(
946 &profile2, &BuildSpellcheckService));
947 SpellcheckCustomDictionary* custom_dictionary2 =
948 spellcheck_service2->GetCustomDictionary();
949
950 custom_dictionary->OnLoaded(scoped_ptr<WordList>(new WordList));
951 custom_dictionary2->OnLoaded(scoped_ptr<WordList>(new WordList));
952
953 custom_dictionary->CustomWordAddedLocally("foo");
954 custom_dictionary->CustomWordAddedLocally("bar");
955 custom_dictionary2->CustomWordAddedLocally("foo");
956 custom_dictionary2->CustomWordAddedLocally("baz");
957
958 DictionaryObserverCounter observer;
959 custom_dictionary->AddObserver(&observer);
960
961 DictionaryObserverCounter observer2;
962 custom_dictionary2->AddObserver(&observer2);
963
964 int error_counter = 0;
965 EXPECT_FALSE(custom_dictionary->MergeDataAndStartSyncing(
966 syncer::DICTIONARY,
967 custom_dictionary2->GetAllSyncData(syncer::DICTIONARY),
968 scoped_ptr<syncer::SyncChangeProcessor>(
969 new SyncChangeProcessorDelegate(custom_dictionary2)),
970 scoped_ptr<syncer::SyncErrorFactory>(
971 new SyncErrorFactoryStub(&error_counter))).error().IsSet());
972 EXPECT_EQ(0, error_counter);
973 EXPECT_TRUE(custom_dictionary->IsSyncing());
974
975 EXPECT_EQ(1, observer.changes());
976 EXPECT_EQ(1, observer2.changes());
977
978 custom_dictionary->RemoveObserver(&observer);
979 custom_dictionary2->RemoveObserver(&observer2);
980
981 // Flush the loop now to prevent service init tasks from being run during
982 // TearDown();
269 MessageLoop::current()->RunUntilIdle(); 983 MessageLoop::current()->RunUntilIdle();
270 } 984 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698