blob: d71280ddbb9a5dd312956c2840ea4fbb6e0b780f [file] [log] [blame]
[email protected]c378cca2010-05-14 13:17:401// Copyright (c) 2010 The Chromium Authors. All rights reserved.
license.botbf09a502008-08-24 00:55:552// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
initial.commitd7cae122008-07-26 21:49:384
[email protected]836061b2008-08-13 14:57:515#include <limits>
6
[email protected]f82fb4952009-01-20 21:05:327#include "base/scoped_ptr.h"
[email protected]9101ef1e2010-01-15 20:09:038#include "base/string_util.h"
9#include "base/string16.h"
[email protected]be1ce6a72010-08-03 14:35:2210#include "base/utf_string_conversions.h"
[email protected]9101ef1e2010-01-15 20:09:0311#include "base/values.h"
initial.commitd7cae122008-07-26 21:49:3812#include "testing/gtest/include/gtest/gtest.h"
13
14class ValuesTest: public testing::Test {
[email protected]4aeb94082010-08-04 08:44:3515 protected:
16 void CompareDictionariesAndCheckResult(
17 const DictionaryValue* dict1,
18 const DictionaryValue* dict2,
19 const char* expected_paths[],
20 size_t expected_paths_count) {
21 std::vector<std::string> differing_paths;
22 std::vector<std::string> expected_paths_vector(expected_paths,
23 expected_paths+expected_paths_count);
24 // All comparisons should be commutative, check dict1 against dict2
25 // and vice-versa.
26 dict1->GetDifferingPaths(dict2, &differing_paths);
27 ASSERT_EQ(expected_paths_count, differing_paths.size());
28 EXPECT_TRUE(equal(differing_paths.begin(), differing_paths.end(),
29 expected_paths_vector.begin()));
30 dict2->GetDifferingPaths(dict1, &differing_paths);
31 ASSERT_EQ(expected_paths_count, differing_paths.size());
32 EXPECT_TRUE(equal(differing_paths.begin(), differing_paths.end(),
33 expected_paths_vector.begin()));
34 }
initial.commitd7cae122008-07-26 21:49:3835};
36
[email protected]9e4cda7332010-07-31 04:56:1437// TODO(viettrungluu): I changed the keys for DictionaryValue from std::wstring
38// to std::string. I've temporarily kept the old methods taking std::wstring for
39// compatibility. The ...Deprecated tests are the old tests which use these
40// methods, and remain to test compatibility. They will be removed once the old
[email protected]e2e593d2010-08-03 15:42:5841// methods are removed. There are also parts of tests marked DEPRECATED which
42// are to be deleted.
[email protected]9e4cda7332010-07-31 04:56:1443
[email protected]4aeb94082010-08-04 08:44:3544TEST_F(ValuesTest, Basic) {
initial.commitd7cae122008-07-26 21:49:3845 // Test basic dictionary getting/setting
46 DictionaryValue settings;
[email protected]9e4cda7332010-07-31 04:56:1447 std::string homepage = "http://google.com";
48 ASSERT_FALSE(settings.GetString("global.homepage", &homepage));
49 ASSERT_EQ(std::string("http://google.com"), homepage);
50
51 ASSERT_FALSE(settings.Get("global", NULL));
52 settings.Set("global", Value::CreateBooleanValue(true));
53 ASSERT_TRUE(settings.Get("global", NULL));
54 settings.SetString("global.homepage", "http://scurvy.com");
55 ASSERT_TRUE(settings.Get("global", NULL));
56 homepage = "http://google.com";
57 ASSERT_TRUE(settings.GetString("global.homepage", &homepage));
58 ASSERT_EQ(std::string("http://scurvy.com"), homepage);
59
60 // Test storing a dictionary in a list.
61 ListValue* toolbar_bookmarks;
62 ASSERT_FALSE(
63 settings.GetList("global.toolbar.bookmarks", &toolbar_bookmarks));
64
65 toolbar_bookmarks = new ListValue;
66 settings.Set("global.toolbar.bookmarks", toolbar_bookmarks);
67 ASSERT_TRUE(settings.GetList("global.toolbar.bookmarks", &toolbar_bookmarks));
68
69 DictionaryValue* new_bookmark = new DictionaryValue;
70 new_bookmark->SetString("name", "Froogle");
71 new_bookmark->SetString("url", "http://froogle.com");
72 toolbar_bookmarks->Append(new_bookmark);
73
74 ListValue* bookmark_list;
75 ASSERT_TRUE(settings.GetList("global.toolbar.bookmarks", &bookmark_list));
76 DictionaryValue* bookmark;
77 ASSERT_EQ(1U, bookmark_list->GetSize());
78 ASSERT_TRUE(bookmark_list->GetDictionary(0, &bookmark));
79 std::string bookmark_name = "Unnamed";
80 ASSERT_TRUE(bookmark->GetString("name", &bookmark_name));
81 ASSERT_EQ(std::string("Froogle"), bookmark_name);
82 std::string bookmark_url;
83 ASSERT_TRUE(bookmark->GetString("url", &bookmark_url));
84 ASSERT_EQ(std::string("http://froogle.com"), bookmark_url);
85}
86
87// TODO(viettrungluu): deprecate:
[email protected]4aeb94082010-08-04 08:44:3588TEST_F(ValuesTest, BasicDeprecated) {
[email protected]9e4cda7332010-07-31 04:56:1489 // Test basic dictionary getting/setting
90 DictionaryValue settings;
[email protected]8e50b602009-03-03 22:59:4391 std::wstring homepage = L"http://google.com";
92 ASSERT_FALSE(
93 settings.GetString(L"global.homepage", &homepage));
94 ASSERT_EQ(std::wstring(L"http://google.com"), homepage);
initial.commitd7cae122008-07-26 21:49:3895
[email protected]8e50b602009-03-03 22:59:4396 ASSERT_FALSE(settings.Get(L"global", NULL));
[email protected]4dad9ad82009-11-25 20:47:5297 settings.Set(L"global", Value::CreateBooleanValue(true));
[email protected]8e50b602009-03-03 22:59:4398 ASSERT_TRUE(settings.Get(L"global", NULL));
[email protected]4dad9ad82009-11-25 20:47:5299 settings.SetString(L"global.homepage", L"http://scurvy.com");
[email protected]8e50b602009-03-03 22:59:43100 ASSERT_TRUE(settings.Get(L"global", NULL));
101 homepage = L"http://google.com";
102 ASSERT_TRUE(settings.GetString(L"global.homepage", &homepage));
103 ASSERT_EQ(std::wstring(L"http://scurvy.com"), homepage);
initial.commitd7cae122008-07-26 21:49:38104
105 // Test storing a dictionary in a list.
106 ListValue* toolbar_bookmarks;
107 ASSERT_FALSE(
[email protected]8e50b602009-03-03 22:59:43108 settings.GetList(L"global.toolbar.bookmarks", &toolbar_bookmarks));
initial.commitd7cae122008-07-26 21:49:38109
110 toolbar_bookmarks = new ListValue;
[email protected]8e50b602009-03-03 22:59:43111 settings.Set(L"global.toolbar.bookmarks", toolbar_bookmarks);
initial.commitd7cae122008-07-26 21:49:38112 ASSERT_TRUE(
[email protected]8e50b602009-03-03 22:59:43113 settings.GetList(L"global.toolbar.bookmarks", &toolbar_bookmarks));
initial.commitd7cae122008-07-26 21:49:38114
115 DictionaryValue* new_bookmark = new DictionaryValue;
[email protected]8e50b602009-03-03 22:59:43116 new_bookmark->SetString(L"name", L"Froogle");
117 new_bookmark->SetString(L"url", L"http://froogle.com");
initial.commitd7cae122008-07-26 21:49:38118 toolbar_bookmarks->Append(new_bookmark);
119
120 ListValue* bookmark_list;
[email protected]8e50b602009-03-03 22:59:43121 ASSERT_TRUE(settings.GetList(L"global.toolbar.bookmarks", &bookmark_list));
initial.commitd7cae122008-07-26 21:49:38122 DictionaryValue* bookmark;
[email protected]f297d182008-08-21 16:24:51123 ASSERT_EQ(1U, bookmark_list->GetSize());
initial.commitd7cae122008-07-26 21:49:38124 ASSERT_TRUE(bookmark_list->GetDictionary(0, &bookmark));
[email protected]8e50b602009-03-03 22:59:43125 std::wstring bookmark_name = L"Unnamed";
126 ASSERT_TRUE(bookmark->GetString(L"name", &bookmark_name));
127 ASSERT_EQ(std::wstring(L"Froogle"), bookmark_name);
128 std::wstring bookmark_url;
129 ASSERT_TRUE(bookmark->GetString(L"url", &bookmark_url));
130 ASSERT_EQ(std::wstring(L"http://froogle.com"), bookmark_url);
initial.commitd7cae122008-07-26 21:49:38131}
132
[email protected]4aeb94082010-08-04 08:44:35133TEST_F(ValuesTest, List) {
[email protected]f82fb4952009-01-20 21:05:32134 scoped_ptr<ListValue> mixed_list(new ListValue());
135 mixed_list->Set(0, Value::CreateBooleanValue(true));
136 mixed_list->Set(1, Value::CreateIntegerValue(42));
137 mixed_list->Set(2, Value::CreateRealValue(88.8));
138 mixed_list->Set(3, Value::CreateStringValue("foo"));
139 ASSERT_EQ(4u, mixed_list->GetSize());
[email protected]52a261f2009-03-03 15:01:12140
[email protected]f82fb4952009-01-20 21:05:32141 Value *value = NULL;
142 bool bool_value = false;
143 int int_value = 0;
144 double double_value = 0.0;
145 std::string string_value;
146
147 ASSERT_FALSE(mixed_list->Get(4, &value));
148
149 ASSERT_FALSE(mixed_list->GetInteger(0, &int_value));
150 ASSERT_EQ(0, int_value);
151 ASSERT_FALSE(mixed_list->GetReal(1, &double_value));
152 ASSERT_EQ(0.0, double_value);
153 ASSERT_FALSE(mixed_list->GetString(2, &string_value));
154 ASSERT_EQ("", string_value);
155 ASSERT_FALSE(mixed_list->GetBoolean(3, &bool_value));
156 ASSERT_EQ(false, bool_value);
157
158 ASSERT_TRUE(mixed_list->GetBoolean(0, &bool_value));
159 ASSERT_EQ(true, bool_value);
160 ASSERT_TRUE(mixed_list->GetInteger(1, &int_value));
161 ASSERT_EQ(42, int_value);
162 ASSERT_TRUE(mixed_list->GetReal(2, &double_value));
163 ASSERT_EQ(88.8, double_value);
164 ASSERT_TRUE(mixed_list->GetString(3, &string_value));
165 ASSERT_EQ("foo", string_value);
166}
167
[email protected]4aeb94082010-08-04 08:44:35168TEST_F(ValuesTest, BinaryValue) {
initial.commitd7cae122008-07-26 21:49:38169 char* buffer = NULL;
170 // Passing a null buffer pointer doesn't yield a BinaryValue
[email protected]0a9a0fc2009-03-24 23:37:14171 scoped_ptr<BinaryValue> binary(BinaryValue::Create(buffer, 0));
172 ASSERT_FALSE(binary.get());
initial.commitd7cae122008-07-26 21:49:38173
174 // If you want to represent an empty binary value, use a zero-length buffer.
[email protected]cd679232008-08-13 02:39:51175 buffer = new char[1];
initial.commitd7cae122008-07-26 21:49:38176 ASSERT_TRUE(buffer);
[email protected]0a9a0fc2009-03-24 23:37:14177 binary.reset(BinaryValue::Create(buffer, 0));
178 ASSERT_TRUE(binary.get());
initial.commitd7cae122008-07-26 21:49:38179 ASSERT_TRUE(binary->GetBuffer());
180 ASSERT_EQ(buffer, binary->GetBuffer());
[email protected]f297d182008-08-21 16:24:51181 ASSERT_EQ(0U, binary->GetSize());
initial.commitd7cae122008-07-26 21:49:38182
183 // Test the common case of a non-empty buffer
184 buffer = new char[15];
[email protected]0a9a0fc2009-03-24 23:37:14185 binary.reset(BinaryValue::Create(buffer, 15));
186 ASSERT_TRUE(binary.get());
initial.commitd7cae122008-07-26 21:49:38187 ASSERT_TRUE(binary->GetBuffer());
188 ASSERT_EQ(buffer, binary->GetBuffer());
[email protected]f297d182008-08-21 16:24:51189 ASSERT_EQ(15U, binary->GetSize());
initial.commitd7cae122008-07-26 21:49:38190
191 char stack_buffer[42];
192 memset(stack_buffer, '!', 42);
[email protected]0a9a0fc2009-03-24 23:37:14193 binary.reset(BinaryValue::CreateWithCopiedBuffer(stack_buffer, 42));
194 ASSERT_TRUE(binary.get());
initial.commitd7cae122008-07-26 21:49:38195 ASSERT_TRUE(binary->GetBuffer());
196 ASSERT_NE(stack_buffer, binary->GetBuffer());
[email protected]f297d182008-08-21 16:24:51197 ASSERT_EQ(42U, binary->GetSize());
initial.commitd7cae122008-07-26 21:49:38198 ASSERT_EQ(0, memcmp(stack_buffer, binary->GetBuffer(), binary->GetSize()));
initial.commitd7cae122008-07-26 21:49:38199}
200
[email protected]4aeb94082010-08-04 08:44:35201TEST_F(ValuesTest, StringValue) {
[email protected]4cd5f6a2008-12-11 01:23:17202 // Test overloaded CreateStringValue.
[email protected]0a9a0fc2009-03-24 23:37:14203 scoped_ptr<Value> narrow_value(Value::CreateStringValue("narrow"));
204 ASSERT_TRUE(narrow_value.get());
[email protected]4cd5f6a2008-12-11 01:23:17205 ASSERT_TRUE(narrow_value->IsType(Value::TYPE_STRING));
[email protected]e2e593d2010-08-03 15:42:58206 scoped_ptr<Value> utf16_value(
207 Value::CreateStringValue(ASCIIToUTF16("utf16")));
208 ASSERT_TRUE(utf16_value.get());
209 ASSERT_TRUE(utf16_value->IsType(Value::TYPE_STRING));
210
211 // Test overloaded GetString.
212 std::string narrow = "http://google.com";
213 string16 utf16 = ASCIIToUTF16("http://google.com");
214 ASSERT_TRUE(narrow_value->GetAsString(&narrow));
215 ASSERT_TRUE(narrow_value->GetAsString(&utf16));
216 ASSERT_EQ(std::string("narrow"), narrow);
217 ASSERT_EQ(ASCIIToUTF16("narrow"), utf16);
218
219 ASSERT_TRUE(utf16_value->GetAsString(&narrow));
220 ASSERT_TRUE(utf16_value->GetAsString(&utf16));
221 ASSERT_EQ(std::string("utf16"), narrow);
222 ASSERT_EQ(ASCIIToUTF16("utf16"), utf16);
223}
224
225// TODO(viettrungluu): deprecate:
[email protected]4aeb94082010-08-04 08:44:35226TEST_F(ValuesTest, StringValueDeprecated) {
[email protected]e2e593d2010-08-03 15:42:58227 // Test overloaded CreateStringValue.
228 scoped_ptr<Value> narrow_value(Value::CreateStringValue("narrow"));
229 ASSERT_TRUE(narrow_value.get());
230 ASSERT_TRUE(narrow_value->IsType(Value::TYPE_STRING));
[email protected]0a9a0fc2009-03-24 23:37:14231 scoped_ptr<Value> wide_value(Value::CreateStringValue(L"wide"));
232 ASSERT_TRUE(wide_value.get());
[email protected]4cd5f6a2008-12-11 01:23:17233 ASSERT_TRUE(wide_value->IsType(Value::TYPE_STRING));
[email protected]9101ef1e2010-01-15 20:09:03234 scoped_ptr<Value> utf16_value(
[email protected]e2e593d2010-08-03 15:42:58235 Value::CreateStringValue(ASCIIToUTF16("utf16")));
[email protected]9101ef1e2010-01-15 20:09:03236 ASSERT_TRUE(utf16_value.get());
237 ASSERT_TRUE(utf16_value->IsType(Value::TYPE_STRING));
[email protected]4cd5f6a2008-12-11 01:23:17238
239 // Test overloaded GetString.
240 std::string narrow = "http://google.com";
241 std::wstring wide = L"http://google.com";
[email protected]9101ef1e2010-01-15 20:09:03242 string16 utf16 = ASCIIToUTF16("http://google.com");
[email protected]4cd5f6a2008-12-11 01:23:17243 ASSERT_TRUE(narrow_value->GetAsString(&narrow));
244 ASSERT_TRUE(narrow_value->GetAsString(&wide));
[email protected]e2e593d2010-08-03 15:42:58245 ASSERT_TRUE(narrow_value->GetAsString(&utf16));
[email protected]4cd5f6a2008-12-11 01:23:17246 ASSERT_EQ(std::string("narrow"), narrow);
247 ASSERT_EQ(std::wstring(L"narrow"), wide);
[email protected]9101ef1e2010-01-15 20:09:03248 ASSERT_EQ(ASCIIToUTF16("narrow"), utf16);
249
[email protected]4cd5f6a2008-12-11 01:23:17250 ASSERT_TRUE(wide_value->GetAsString(&narrow));
251 ASSERT_TRUE(wide_value->GetAsString(&wide));
[email protected]e2e593d2010-08-03 15:42:58252 ASSERT_TRUE(wide_value->GetAsString(&utf16));
[email protected]4cd5f6a2008-12-11 01:23:17253 ASSERT_EQ(std::string("wide"), narrow);
254 ASSERT_EQ(std::wstring(L"wide"), wide);
[email protected]9101ef1e2010-01-15 20:09:03255 ASSERT_EQ(ASCIIToUTF16("wide"), utf16);
256
257 ASSERT_TRUE(utf16_value->GetAsString(&narrow));
258 ASSERT_TRUE(utf16_value->GetAsString(&wide));
[email protected]e2e593d2010-08-03 15:42:58259 ASSERT_TRUE(utf16_value->GetAsString(&utf16));
[email protected]9101ef1e2010-01-15 20:09:03260 ASSERT_EQ(std::string("utf16"), narrow);
261 ASSERT_EQ(std::wstring(L"utf16"), wide);
262 ASSERT_EQ(ASCIIToUTF16("utf16"), utf16);
[email protected]4cd5f6a2008-12-11 01:23:17263}
264
initial.commitd7cae122008-07-26 21:49:38265// This is a Value object that allows us to tell if it's been
266// properly deleted by modifying the value of external flag on destruction.
267class DeletionTestValue : public Value {
[email protected]8ab4809b2009-07-03 02:28:55268 public:
[email protected]2fdc86a2010-01-26 23:08:02269 explicit DeletionTestValue(bool* deletion_flag) : Value(TYPE_NULL) {
initial.commitd7cae122008-07-26 21:49:38270 Init(deletion_flag); // Separate function so that we can use ASSERT_*
271 }
272
273 void Init(bool* deletion_flag) {
274 ASSERT_TRUE(deletion_flag);
275 deletion_flag_ = deletion_flag;
276 *deletion_flag_ = false;
277 }
278
279 ~DeletionTestValue() {
280 *deletion_flag_ = true;
281 }
282
[email protected]8ab4809b2009-07-03 02:28:55283 private:
initial.commitd7cae122008-07-26 21:49:38284 bool* deletion_flag_;
285};
286
[email protected]4aeb94082010-08-04 08:44:35287TEST_F(ValuesTest, ListDeletion) {
initial.commitd7cae122008-07-26 21:49:38288 bool deletion_flag = true;
289
290 {
291 ListValue list;
292 list.Append(new DeletionTestValue(&deletion_flag));
293 EXPECT_FALSE(deletion_flag);
294 }
295 EXPECT_TRUE(deletion_flag);
296
297 {
298 ListValue list;
299 list.Append(new DeletionTestValue(&deletion_flag));
300 EXPECT_FALSE(deletion_flag);
301 list.Clear();
302 EXPECT_TRUE(deletion_flag);
303 }
304
305 {
306 ListValue list;
307 list.Append(new DeletionTestValue(&deletion_flag));
308 EXPECT_FALSE(deletion_flag);
309 EXPECT_TRUE(list.Set(0, Value::CreateNullValue()));
310 EXPECT_TRUE(deletion_flag);
311 }
312}
313
[email protected]4aeb94082010-08-04 08:44:35314TEST_F(ValuesTest, ListRemoval) {
initial.commitd7cae122008-07-26 21:49:38315 bool deletion_flag = true;
316 Value* removed_item = NULL;
317
318 {
319 ListValue list;
320 list.Append(new DeletionTestValue(&deletion_flag));
321 EXPECT_FALSE(deletion_flag);
[email protected]f297d182008-08-21 16:24:51322 EXPECT_EQ(1U, list.GetSize());
[email protected]836061b2008-08-13 14:57:51323 EXPECT_FALSE(list.Remove(std::numeric_limits<size_t>::max(),
324 &removed_item));
initial.commitd7cae122008-07-26 21:49:38325 EXPECT_FALSE(list.Remove(1, &removed_item));
326 EXPECT_TRUE(list.Remove(0, &removed_item));
327 ASSERT_TRUE(removed_item);
[email protected]f297d182008-08-21 16:24:51328 EXPECT_EQ(0U, list.GetSize());
initial.commitd7cae122008-07-26 21:49:38329 }
330 EXPECT_FALSE(deletion_flag);
331 delete removed_item;
332 removed_item = NULL;
333 EXPECT_TRUE(deletion_flag);
334
335 {
336 ListValue list;
337 list.Append(new DeletionTestValue(&deletion_flag));
338 EXPECT_FALSE(deletion_flag);
339 EXPECT_TRUE(list.Remove(0, NULL));
340 EXPECT_TRUE(deletion_flag);
[email protected]f297d182008-08-21 16:24:51341 EXPECT_EQ(0U, list.GetSize());
initial.commitd7cae122008-07-26 21:49:38342 }
[email protected]6832cbe2009-11-30 19:59:11343
344 {
345 ListValue list;
346 DeletionTestValue* value = new DeletionTestValue(&deletion_flag);
347 list.Append(value);
348 EXPECT_FALSE(deletion_flag);
349 EXPECT_EQ(0, list.Remove(*value));
350 EXPECT_TRUE(deletion_flag);
351 EXPECT_EQ(0U, list.GetSize());
352 }
initial.commitd7cae122008-07-26 21:49:38353}
354
[email protected]4aeb94082010-08-04 08:44:35355TEST_F(ValuesTest, DictionaryDeletion) {
[email protected]9e4cda7332010-07-31 04:56:14356 std::string key = "test";
357 bool deletion_flag = true;
358
359 {
360 DictionaryValue dict;
361 dict.Set(key, new DeletionTestValue(&deletion_flag));
362 EXPECT_FALSE(deletion_flag);
363 }
364 EXPECT_TRUE(deletion_flag);
365
366 {
367 DictionaryValue dict;
368 dict.Set(key, new DeletionTestValue(&deletion_flag));
369 EXPECT_FALSE(deletion_flag);
370 dict.Clear();
371 EXPECT_TRUE(deletion_flag);
372 }
373
374 {
375 DictionaryValue dict;
376 dict.Set(key, new DeletionTestValue(&deletion_flag));
377 EXPECT_FALSE(deletion_flag);
378 dict.Set(key, Value::CreateNullValue());
379 EXPECT_TRUE(deletion_flag);
380 }
381}
382
383// TODO(viettrungluu): deprecate:
[email protected]4aeb94082010-08-04 08:44:35384TEST_F(ValuesTest, DictionaryDeletionDeprecated) {
[email protected]8e50b602009-03-03 22:59:43385 std::wstring key = L"test";
initial.commitd7cae122008-07-26 21:49:38386 bool deletion_flag = true;
387
388 {
389 DictionaryValue dict;
390 dict.Set(key, new DeletionTestValue(&deletion_flag));
391 EXPECT_FALSE(deletion_flag);
392 }
393 EXPECT_TRUE(deletion_flag);
394
395 {
396 DictionaryValue dict;
397 dict.Set(key, new DeletionTestValue(&deletion_flag));
398 EXPECT_FALSE(deletion_flag);
399 dict.Clear();
400 EXPECT_TRUE(deletion_flag);
401 }
402
403 {
404 DictionaryValue dict;
405 dict.Set(key, new DeletionTestValue(&deletion_flag));
406 EXPECT_FALSE(deletion_flag);
407 dict.Set(key, Value::CreateNullValue());
408 EXPECT_TRUE(deletion_flag);
409 }
410}
411
[email protected]4aeb94082010-08-04 08:44:35412TEST_F(ValuesTest, DictionaryRemoval) {
[email protected]9e4cda7332010-07-31 04:56:14413 std::string key = "test";
414 bool deletion_flag = true;
415 Value* removed_item = NULL;
416
417 {
418 DictionaryValue dict;
419 dict.Set(key, new DeletionTestValue(&deletion_flag));
420 EXPECT_FALSE(deletion_flag);
421 EXPECT_TRUE(dict.HasKey(key));
422 EXPECT_FALSE(dict.Remove("absent key", &removed_item));
423 EXPECT_TRUE(dict.Remove(key, &removed_item));
424 EXPECT_FALSE(dict.HasKey(key));
425 ASSERT_TRUE(removed_item);
426 }
427 EXPECT_FALSE(deletion_flag);
428 delete removed_item;
429 removed_item = NULL;
430 EXPECT_TRUE(deletion_flag);
431
432 {
433 DictionaryValue dict;
434 dict.Set(key, new DeletionTestValue(&deletion_flag));
435 EXPECT_FALSE(deletion_flag);
436 EXPECT_TRUE(dict.HasKey(key));
437 EXPECT_TRUE(dict.Remove(key, NULL));
438 EXPECT_TRUE(deletion_flag);
439 EXPECT_FALSE(dict.HasKey(key));
440 }
441}
442
443// TODO(viettrungluu): deprecate:
[email protected]4aeb94082010-08-04 08:44:35444TEST_F(ValuesTest, DictionaryRemovalDeprecated) {
[email protected]8e50b602009-03-03 22:59:43445 std::wstring key = L"test";
initial.commitd7cae122008-07-26 21:49:38446 bool deletion_flag = true;
447 Value* removed_item = NULL;
448
449 {
450 DictionaryValue dict;
451 dict.Set(key, new DeletionTestValue(&deletion_flag));
452 EXPECT_FALSE(deletion_flag);
453 EXPECT_TRUE(dict.HasKey(key));
[email protected]8e50b602009-03-03 22:59:43454 EXPECT_FALSE(dict.Remove(L"absent key", &removed_item));
initial.commitd7cae122008-07-26 21:49:38455 EXPECT_TRUE(dict.Remove(key, &removed_item));
456 EXPECT_FALSE(dict.HasKey(key));
457 ASSERT_TRUE(removed_item);
458 }
459 EXPECT_FALSE(deletion_flag);
460 delete removed_item;
461 removed_item = NULL;
462 EXPECT_TRUE(deletion_flag);
463
464 {
465 DictionaryValue dict;
466 dict.Set(key, new DeletionTestValue(&deletion_flag));
467 EXPECT_FALSE(deletion_flag);
468 EXPECT_TRUE(dict.HasKey(key));
469 EXPECT_TRUE(dict.Remove(key, NULL));
470 EXPECT_TRUE(deletion_flag);
471 EXPECT_FALSE(dict.HasKey(key));
472 }
473}
474
[email protected]4aeb94082010-08-04 08:44:35475TEST_F(ValuesTest, DictionaryWithoutPathExpansion) {
[email protected]4dad9ad82009-11-25 20:47:52476 DictionaryValue dict;
[email protected]9e4cda7332010-07-31 04:56:14477 dict.Set("this.is.expanded", Value::CreateNullValue());
478 dict.SetWithoutPathExpansion("this.isnt.expanded", Value::CreateNullValue());
479
480 EXPECT_FALSE(dict.HasKey("this.is.expanded"));
481 EXPECT_TRUE(dict.HasKey("this"));
482 Value* value1;
483 EXPECT_TRUE(dict.Get("this", &value1));
484 DictionaryValue* value2;
485 ASSERT_TRUE(dict.GetDictionaryWithoutPathExpansion("this", &value2));
486 EXPECT_EQ(value1, value2);
487 EXPECT_EQ(1U, value2->size());
488
489 EXPECT_TRUE(dict.HasKey("this.isnt.expanded"));
490 Value* value3;
491 EXPECT_FALSE(dict.Get("this.isnt.expanded", &value3));
492 Value* value4;
493 ASSERT_TRUE(dict.GetWithoutPathExpansion("this.isnt.expanded", &value4));
494 EXPECT_EQ(Value::TYPE_NULL, value4->GetType());
495}
496
497// TODO(viettrungluu): deprecate:
[email protected]4aeb94082010-08-04 08:44:35498TEST_F(ValuesTest, DictionaryWithoutPathExpansionDeprecated) {
[email protected]9e4cda7332010-07-31 04:56:14499 DictionaryValue dict;
[email protected]4dad9ad82009-11-25 20:47:52500 dict.Set(L"this.is.expanded", Value::CreateNullValue());
501 dict.SetWithoutPathExpansion(L"this.isnt.expanded", Value::CreateNullValue());
502
503 EXPECT_FALSE(dict.HasKey(L"this.is.expanded"));
504 EXPECT_TRUE(dict.HasKey(L"this"));
505 Value* value1;
506 EXPECT_TRUE(dict.Get(L"this", &value1));
507 DictionaryValue* value2;
508 ASSERT_TRUE(dict.GetDictionaryWithoutPathExpansion(L"this", &value2));
509 EXPECT_EQ(value1, value2);
510 EXPECT_EQ(1U, value2->size());
511
512 EXPECT_TRUE(dict.HasKey(L"this.isnt.expanded"));
513 Value* value3;
514 EXPECT_FALSE(dict.Get(L"this.isnt.expanded", &value3));
515 Value* value4;
516 ASSERT_TRUE(dict.GetWithoutPathExpansion(L"this.isnt.expanded", &value4));
517 EXPECT_EQ(Value::TYPE_NULL, value4->GetType());
518}
519
[email protected]4aeb94082010-08-04 08:44:35520TEST_F(ValuesTest, DeepCopy) {
initial.commitd7cae122008-07-26 21:49:38521 DictionaryValue original_dict;
522 Value* original_null = Value::CreateNullValue();
[email protected]9e4cda7332010-07-31 04:56:14523 original_dict.Set("null", original_null);
524 Value* original_bool = Value::CreateBooleanValue(true);
525 original_dict.Set("bool", original_bool);
526 Value* original_int = Value::CreateIntegerValue(42);
527 original_dict.Set("int", original_int);
528 Value* original_real = Value::CreateRealValue(3.14);
529 original_dict.Set("real", original_real);
530 Value* original_string = Value::CreateStringValue("hello");
531 original_dict.Set("string", original_string);
[email protected]e2e593d2010-08-03 15:42:58532 Value* original_string16 = Value::CreateStringValue(ASCIIToUTF16("hello16"));
533 original_dict.Set("string16", original_string16);
[email protected]9e4cda7332010-07-31 04:56:14534
535 char* original_buffer = new char[42];
536 memset(original_buffer, '!', 42);
537 BinaryValue* original_binary = Value::CreateBinaryValue(original_buffer, 42);
538 original_dict.Set("binary", original_binary);
539
540 ListValue* original_list = new ListValue();
541 Value* original_list_element_0 = Value::CreateIntegerValue(0);
542 original_list->Append(original_list_element_0);
543 Value* original_list_element_1 = Value::CreateIntegerValue(1);
544 original_list->Append(original_list_element_1);
545 original_dict.Set("list", original_list);
546
547 scoped_ptr<DictionaryValue> copy_dict(
548 static_cast<DictionaryValue*>(original_dict.DeepCopy()));
549 ASSERT_TRUE(copy_dict.get());
550 ASSERT_NE(copy_dict.get(), &original_dict);
551
552 Value* copy_null = NULL;
553 ASSERT_TRUE(copy_dict->Get("null", &copy_null));
554 ASSERT_TRUE(copy_null);
555 ASSERT_NE(copy_null, original_null);
556 ASSERT_TRUE(copy_null->IsType(Value::TYPE_NULL));
557
558 Value* copy_bool = NULL;
559 ASSERT_TRUE(copy_dict->Get("bool", &copy_bool));
560 ASSERT_TRUE(copy_bool);
561 ASSERT_NE(copy_bool, original_bool);
562 ASSERT_TRUE(copy_bool->IsType(Value::TYPE_BOOLEAN));
563 bool copy_bool_value = false;
564 ASSERT_TRUE(copy_bool->GetAsBoolean(&copy_bool_value));
565 ASSERT_TRUE(copy_bool_value);
566
567 Value* copy_int = NULL;
568 ASSERT_TRUE(copy_dict->Get("int", &copy_int));
569 ASSERT_TRUE(copy_int);
570 ASSERT_NE(copy_int, original_int);
571 ASSERT_TRUE(copy_int->IsType(Value::TYPE_INTEGER));
572 int copy_int_value = 0;
573 ASSERT_TRUE(copy_int->GetAsInteger(&copy_int_value));
574 ASSERT_EQ(42, copy_int_value);
575
576 Value* copy_real = NULL;
577 ASSERT_TRUE(copy_dict->Get("real", &copy_real));
578 ASSERT_TRUE(copy_real);
579 ASSERT_NE(copy_real, original_real);
580 ASSERT_TRUE(copy_real->IsType(Value::TYPE_REAL));
581 double copy_real_value = 0;
582 ASSERT_TRUE(copy_real->GetAsReal(&copy_real_value));
583 ASSERT_EQ(3.14, copy_real_value);
584
585 Value* copy_string = NULL;
586 ASSERT_TRUE(copy_dict->Get("string", &copy_string));
587 ASSERT_TRUE(copy_string);
588 ASSERT_NE(copy_string, original_string);
589 ASSERT_TRUE(copy_string->IsType(Value::TYPE_STRING));
590 std::string copy_string_value;
[email protected]e2e593d2010-08-03 15:42:58591 string16 copy_string16_value;
[email protected]9e4cda7332010-07-31 04:56:14592 ASSERT_TRUE(copy_string->GetAsString(&copy_string_value));
[email protected]e2e593d2010-08-03 15:42:58593 ASSERT_TRUE(copy_string->GetAsString(&copy_string16_value));
[email protected]9e4cda7332010-07-31 04:56:14594 ASSERT_EQ(std::string("hello"), copy_string_value);
[email protected]e2e593d2010-08-03 15:42:58595 ASSERT_EQ(ASCIIToUTF16("hello"), copy_string16_value);
[email protected]9e4cda7332010-07-31 04:56:14596
[email protected]e2e593d2010-08-03 15:42:58597 Value* copy_string16 = NULL;
598 ASSERT_TRUE(copy_dict->Get("string16", &copy_string16));
599 ASSERT_TRUE(copy_string16);
600 ASSERT_NE(copy_string16, original_string16);
601 ASSERT_TRUE(copy_string16->IsType(Value::TYPE_STRING));
602 ASSERT_TRUE(copy_string16->GetAsString(&copy_string_value));
603 ASSERT_TRUE(copy_string16->GetAsString(&copy_string16_value));
[email protected]9e4cda7332010-07-31 04:56:14604 ASSERT_EQ(std::string("hello16"), copy_string_value);
[email protected]e2e593d2010-08-03 15:42:58605 ASSERT_EQ(ASCIIToUTF16("hello16"), copy_string16_value);
[email protected]9e4cda7332010-07-31 04:56:14606
607 Value* copy_binary = NULL;
608 ASSERT_TRUE(copy_dict->Get("binary", &copy_binary));
609 ASSERT_TRUE(copy_binary);
610 ASSERT_NE(copy_binary, original_binary);
611 ASSERT_TRUE(copy_binary->IsType(Value::TYPE_BINARY));
612 ASSERT_NE(original_binary->GetBuffer(),
613 static_cast<BinaryValue*>(copy_binary)->GetBuffer());
614 ASSERT_EQ(original_binary->GetSize(),
615 static_cast<BinaryValue*>(copy_binary)->GetSize());
616 ASSERT_EQ(0, memcmp(original_binary->GetBuffer(),
617 static_cast<BinaryValue*>(copy_binary)->GetBuffer(),
618 original_binary->GetSize()));
619
620 Value* copy_value = NULL;
621 ASSERT_TRUE(copy_dict->Get("list", &copy_value));
622 ASSERT_TRUE(copy_value);
623 ASSERT_NE(copy_value, original_list);
624 ASSERT_TRUE(copy_value->IsType(Value::TYPE_LIST));
625 ListValue* copy_list = static_cast<ListValue*>(copy_value);
626 ASSERT_EQ(2U, copy_list->GetSize());
627
628 Value* copy_list_element_0;
629 ASSERT_TRUE(copy_list->Get(0, &copy_list_element_0));
630 ASSERT_TRUE(copy_list_element_0);
631 ASSERT_NE(copy_list_element_0, original_list_element_0);
632 int copy_list_element_0_value;
633 ASSERT_TRUE(copy_list_element_0->GetAsInteger(&copy_list_element_0_value));
634 ASSERT_EQ(0, copy_list_element_0_value);
635
636 Value* copy_list_element_1;
637 ASSERT_TRUE(copy_list->Get(1, &copy_list_element_1));
638 ASSERT_TRUE(copy_list_element_1);
639 ASSERT_NE(copy_list_element_1, original_list_element_1);
640 int copy_list_element_1_value;
641 ASSERT_TRUE(copy_list_element_1->GetAsInteger(&copy_list_element_1_value));
642 ASSERT_EQ(1, copy_list_element_1_value);
643}
644
645// TODO(viettrungluu): deprecate:
[email protected]4aeb94082010-08-04 08:44:35646TEST_F(ValuesTest, DeepCopyDeprecated) {
[email protected]9e4cda7332010-07-31 04:56:14647 DictionaryValue original_dict;
648 Value* original_null = Value::CreateNullValue();
[email protected]8e50b602009-03-03 22:59:43649 original_dict.Set(L"null", original_null);
initial.commitd7cae122008-07-26 21:49:38650 Value* original_bool = Value::CreateBooleanValue(true);
[email protected]8e50b602009-03-03 22:59:43651 original_dict.Set(L"bool", original_bool);
initial.commitd7cae122008-07-26 21:49:38652 Value* original_int = Value::CreateIntegerValue(42);
[email protected]8e50b602009-03-03 22:59:43653 original_dict.Set(L"int", original_int);
initial.commitd7cae122008-07-26 21:49:38654 Value* original_real = Value::CreateRealValue(3.14);
[email protected]8e50b602009-03-03 22:59:43655 original_dict.Set(L"real", original_real);
[email protected]4cd5f6a2008-12-11 01:23:17656 Value* original_string = Value::CreateStringValue("hello");
[email protected]8e50b602009-03-03 22:59:43657 original_dict.Set(L"string", original_string);
[email protected]4cd5f6a2008-12-11 01:23:17658 Value* original_wstring = Value::CreateStringValue(L"peek-a-boo");
[email protected]8e50b602009-03-03 22:59:43659 original_dict.Set(L"wstring", original_wstring);
[email protected]e2e593d2010-08-03 15:42:58660 Value* original_utf16 = Value::CreateStringValue(ASCIIToUTF16("hello16"));
[email protected]9101ef1e2010-01-15 20:09:03661 original_dict.Set(L"utf16", original_utf16);
initial.commitd7cae122008-07-26 21:49:38662
663 char* original_buffer = new char[42];
664 memset(original_buffer, '!', 42);
665 BinaryValue* original_binary = Value::CreateBinaryValue(original_buffer, 42);
[email protected]8e50b602009-03-03 22:59:43666 original_dict.Set(L"binary", original_binary);
initial.commitd7cae122008-07-26 21:49:38667
668 ListValue* original_list = new ListValue();
669 Value* original_list_element_0 = Value::CreateIntegerValue(0);
670 original_list->Append(original_list_element_0);
671 Value* original_list_element_1 = Value::CreateIntegerValue(1);
672 original_list->Append(original_list_element_1);
[email protected]8e50b602009-03-03 22:59:43673 original_dict.Set(L"list", original_list);
initial.commitd7cae122008-07-26 21:49:38674
[email protected]8ab4809b2009-07-03 02:28:55675 scoped_ptr<DictionaryValue> copy_dict(
676 static_cast<DictionaryValue*>(original_dict.DeepCopy()));
677 ASSERT_TRUE(copy_dict.get());
678 ASSERT_NE(copy_dict.get(), &original_dict);
initial.commitd7cae122008-07-26 21:49:38679
680 Value* copy_null = NULL;
[email protected]8e50b602009-03-03 22:59:43681 ASSERT_TRUE(copy_dict->Get(L"null", &copy_null));
initial.commitd7cae122008-07-26 21:49:38682 ASSERT_TRUE(copy_null);
683 ASSERT_NE(copy_null, original_null);
684 ASSERT_TRUE(copy_null->IsType(Value::TYPE_NULL));
685
686 Value* copy_bool = NULL;
[email protected]8e50b602009-03-03 22:59:43687 ASSERT_TRUE(copy_dict->Get(L"bool", &copy_bool));
initial.commitd7cae122008-07-26 21:49:38688 ASSERT_TRUE(copy_bool);
689 ASSERT_NE(copy_bool, original_bool);
690 ASSERT_TRUE(copy_bool->IsType(Value::TYPE_BOOLEAN));
691 bool copy_bool_value = false;
692 ASSERT_TRUE(copy_bool->GetAsBoolean(&copy_bool_value));
693 ASSERT_TRUE(copy_bool_value);
694
695 Value* copy_int = NULL;
[email protected]8e50b602009-03-03 22:59:43696 ASSERT_TRUE(copy_dict->Get(L"int", &copy_int));
initial.commitd7cae122008-07-26 21:49:38697 ASSERT_TRUE(copy_int);
698 ASSERT_NE(copy_int, original_int);
699 ASSERT_TRUE(copy_int->IsType(Value::TYPE_INTEGER));
700 int copy_int_value = 0;
701 ASSERT_TRUE(copy_int->GetAsInteger(&copy_int_value));
702 ASSERT_EQ(42, copy_int_value);
703
704 Value* copy_real = NULL;
[email protected]8e50b602009-03-03 22:59:43705 ASSERT_TRUE(copy_dict->Get(L"real", &copy_real));
initial.commitd7cae122008-07-26 21:49:38706 ASSERT_TRUE(copy_real);
707 ASSERT_NE(copy_real, original_real);
708 ASSERT_TRUE(copy_real->IsType(Value::TYPE_REAL));
709 double copy_real_value = 0;
710 ASSERT_TRUE(copy_real->GetAsReal(&copy_real_value));
711 ASSERT_EQ(3.14, copy_real_value);
712
713 Value* copy_string = NULL;
[email protected]8e50b602009-03-03 22:59:43714 ASSERT_TRUE(copy_dict->Get(L"string", &copy_string));
initial.commitd7cae122008-07-26 21:49:38715 ASSERT_TRUE(copy_string);
716 ASSERT_NE(copy_string, original_string);
717 ASSERT_TRUE(copy_string->IsType(Value::TYPE_STRING));
[email protected]4cd5f6a2008-12-11 01:23:17718 std::string copy_string_value;
719 std::wstring copy_wstring_value;
[email protected]9101ef1e2010-01-15 20:09:03720 string16 copy_utf16_value;
initial.commitd7cae122008-07-26 21:49:38721 ASSERT_TRUE(copy_string->GetAsString(&copy_string_value));
[email protected]4cd5f6a2008-12-11 01:23:17722 ASSERT_TRUE(copy_string->GetAsString(&copy_wstring_value));
[email protected]e2e593d2010-08-03 15:42:58723 ASSERT_TRUE(copy_string->GetAsString(&copy_utf16_value));
[email protected]4cd5f6a2008-12-11 01:23:17724 ASSERT_EQ(std::string("hello"), copy_string_value);
725 ASSERT_EQ(std::wstring(L"hello"), copy_wstring_value);
[email protected]9101ef1e2010-01-15 20:09:03726 ASSERT_EQ(ASCIIToUTF16("hello"), copy_utf16_value);
[email protected]4cd5f6a2008-12-11 01:23:17727
728 Value* copy_wstring = NULL;
[email protected]8e50b602009-03-03 22:59:43729 ASSERT_TRUE(copy_dict->Get(L"wstring", &copy_wstring));
[email protected]4cd5f6a2008-12-11 01:23:17730 ASSERT_TRUE(copy_wstring);
731 ASSERT_NE(copy_wstring, original_wstring);
[email protected]52a261f2009-03-03 15:01:12732 ASSERT_TRUE(copy_wstring->IsType(Value::TYPE_STRING));
[email protected]4cd5f6a2008-12-11 01:23:17733 ASSERT_TRUE(copy_wstring->GetAsString(&copy_string_value));
734 ASSERT_TRUE(copy_wstring->GetAsString(&copy_wstring_value));
[email protected]e2e593d2010-08-03 15:42:58735 ASSERT_TRUE(copy_wstring->GetAsString(&copy_utf16_value));
[email protected]4cd5f6a2008-12-11 01:23:17736 ASSERT_EQ(std::string("peek-a-boo"), copy_string_value);
737 ASSERT_EQ(std::wstring(L"peek-a-boo"), copy_wstring_value);
[email protected]9101ef1e2010-01-15 20:09:03738 ASSERT_EQ(ASCIIToUTF16("peek-a-boo"), copy_utf16_value);
739
740 Value* copy_utf16 = NULL;
741 ASSERT_TRUE(copy_dict->Get(L"utf16", &copy_utf16));
742 ASSERT_TRUE(copy_utf16);
743 ASSERT_NE(copy_utf16, original_utf16);
744 ASSERT_TRUE(copy_utf16->IsType(Value::TYPE_STRING));
745 ASSERT_TRUE(copy_utf16->GetAsString(&copy_string_value));
746 ASSERT_TRUE(copy_utf16->GetAsString(&copy_wstring_value));
[email protected]e2e593d2010-08-03 15:42:58747 ASSERT_TRUE(copy_utf16->GetAsString(&copy_utf16_value));
[email protected]9101ef1e2010-01-15 20:09:03748 ASSERT_EQ(std::string("hello16"), copy_string_value);
749 ASSERT_EQ(std::wstring(L"hello16"), copy_wstring_value);
750 ASSERT_EQ(ASCIIToUTF16("hello16"), copy_utf16_value);
initial.commitd7cae122008-07-26 21:49:38751
752 Value* copy_binary = NULL;
[email protected]8e50b602009-03-03 22:59:43753 ASSERT_TRUE(copy_dict->Get(L"binary", &copy_binary));
initial.commitd7cae122008-07-26 21:49:38754 ASSERT_TRUE(copy_binary);
755 ASSERT_NE(copy_binary, original_binary);
756 ASSERT_TRUE(copy_binary->IsType(Value::TYPE_BINARY));
757 ASSERT_NE(original_binary->GetBuffer(),
758 static_cast<BinaryValue*>(copy_binary)->GetBuffer());
759 ASSERT_EQ(original_binary->GetSize(),
760 static_cast<BinaryValue*>(copy_binary)->GetSize());
761 ASSERT_EQ(0, memcmp(original_binary->GetBuffer(),
762 static_cast<BinaryValue*>(copy_binary)->GetBuffer(),
763 original_binary->GetSize()));
764
765 Value* copy_value = NULL;
[email protected]8e50b602009-03-03 22:59:43766 ASSERT_TRUE(copy_dict->Get(L"list", &copy_value));
initial.commitd7cae122008-07-26 21:49:38767 ASSERT_TRUE(copy_value);
768 ASSERT_NE(copy_value, original_list);
769 ASSERT_TRUE(copy_value->IsType(Value::TYPE_LIST));
770 ListValue* copy_list = static_cast<ListValue*>(copy_value);
[email protected]f297d182008-08-21 16:24:51771 ASSERT_EQ(2U, copy_list->GetSize());
initial.commitd7cae122008-07-26 21:49:38772
773 Value* copy_list_element_0;
774 ASSERT_TRUE(copy_list->Get(0, &copy_list_element_0));
775 ASSERT_TRUE(copy_list_element_0);
776 ASSERT_NE(copy_list_element_0, original_list_element_0);
777 int copy_list_element_0_value;
778 ASSERT_TRUE(copy_list_element_0->GetAsInteger(&copy_list_element_0_value));
779 ASSERT_EQ(0, copy_list_element_0_value);
780
781 Value* copy_list_element_1;
782 ASSERT_TRUE(copy_list->Get(1, &copy_list_element_1));
783 ASSERT_TRUE(copy_list_element_1);
784 ASSERT_NE(copy_list_element_1, original_list_element_1);
785 int copy_list_element_1_value;
786 ASSERT_TRUE(copy_list_element_1->GetAsInteger(&copy_list_element_1_value));
787 ASSERT_EQ(1, copy_list_element_1_value);
initial.commitd7cae122008-07-26 21:49:38788}
789
[email protected]4aeb94082010-08-04 08:44:35790TEST_F(ValuesTest, Equals) {
initial.commitd7cae122008-07-26 21:49:38791 Value* null1 = Value::CreateNullValue();
792 Value* null2 = Value::CreateNullValue();
793 EXPECT_NE(null1, null2);
794 EXPECT_TRUE(null1->Equals(null2));
795
796 Value* boolean = Value::CreateBooleanValue(false);
797 EXPECT_FALSE(null1->Equals(boolean));
798 delete null1;
799 delete null2;
800 delete boolean;
801
802 DictionaryValue dv;
[email protected]9e4cda7332010-07-31 04:56:14803 dv.SetBoolean("a", false);
804 dv.SetInteger("b", 2);
805 dv.SetReal("c", 2.5);
806 dv.SetString("d1", "string");
[email protected]ff4c1d82010-08-04 16:58:12807 dv.SetString("d2", ASCIIToUTF16("http://google.com"));
[email protected]9e4cda7332010-07-31 04:56:14808 dv.Set("e", Value::CreateNullValue());
809
810 DictionaryValue* copy = static_cast<DictionaryValue*>(dv.DeepCopy());
811 EXPECT_TRUE(dv.Equals(copy));
812
813 ListValue* list = new ListValue;
814 list->Append(Value::CreateNullValue());
815 list->Append(new DictionaryValue);
816 dv.Set("f", list);
817
818 EXPECT_FALSE(dv.Equals(copy));
819 copy->Set("f", list->DeepCopy());
820 EXPECT_TRUE(dv.Equals(copy));
821
822 list->Append(Value::CreateBooleanValue(true));
823 EXPECT_FALSE(dv.Equals(copy));
824 delete copy;
825}
826
827// TODO(viettrungluu): deprecate:
[email protected]4aeb94082010-08-04 08:44:35828TEST_F(ValuesTest, EqualsDeprecated) {
[email protected]9e4cda7332010-07-31 04:56:14829 Value* null1 = Value::CreateNullValue();
830 Value* null2 = Value::CreateNullValue();
831 EXPECT_NE(null1, null2);
832 EXPECT_TRUE(null1->Equals(null2));
833
834 Value* boolean = Value::CreateBooleanValue(false);
835 EXPECT_FALSE(null1->Equals(boolean));
836 delete null1;
837 delete null2;
838 delete boolean;
839
840 DictionaryValue dv;
[email protected]8e50b602009-03-03 22:59:43841 dv.SetBoolean(L"a", false);
842 dv.SetInteger(L"b", 2);
843 dv.SetReal(L"c", 2.5);
844 dv.SetString(L"d1", "string");
845 dv.SetString(L"d2", L"string");
846 dv.Set(L"e", Value::CreateNullValue());
initial.commitd7cae122008-07-26 21:49:38847
848 DictionaryValue* copy = static_cast<DictionaryValue*>(dv.DeepCopy());
849 EXPECT_TRUE(dv.Equals(copy));
850
851 ListValue* list = new ListValue;
852 list->Append(Value::CreateNullValue());
853 list->Append(new DictionaryValue);
[email protected]8e50b602009-03-03 22:59:43854 dv.Set(L"f", list);
initial.commitd7cae122008-07-26 21:49:38855
856 EXPECT_FALSE(dv.Equals(copy));
[email protected]8e50b602009-03-03 22:59:43857 copy->Set(L"f", list->DeepCopy());
initial.commitd7cae122008-07-26 21:49:38858 EXPECT_TRUE(dv.Equals(copy));
859
860 list->Append(Value::CreateBooleanValue(true));
861 EXPECT_FALSE(dv.Equals(copy));
862 delete copy;
863}
[email protected]ec330b52009-12-02 00:20:32864
[email protected]4aeb94082010-08-04 08:44:35865TEST_F(ValuesTest, RemoveEmptyChildren) {
[email protected]ec330b52009-12-02 00:20:32866 scoped_ptr<DictionaryValue> root(new DictionaryValue);
867 // Remove empty lists and dictionaries.
[email protected]9e4cda7332010-07-31 04:56:14868 root->Set("empty_dict", new DictionaryValue);
869 root->Set("empty_list", new ListValue);
870 root->SetWithoutPathExpansion("a.b.c.d.e", new DictionaryValue);
871 root.reset(root->DeepCopyWithoutEmptyChildren());
872 EXPECT_TRUE(root->empty());
873
874 // Make sure we don't prune too much.
875 root->SetBoolean("bool", true);
876 root->Set("empty_dict", new DictionaryValue);
877 root->SetString("empty_string", "");
878 root.reset(root->DeepCopyWithoutEmptyChildren());
879 EXPECT_EQ(2U, root->size());
880
881 // Should do nothing.
882 root.reset(root->DeepCopyWithoutEmptyChildren());
883 EXPECT_EQ(2U, root->size());
884
885 // Nested test cases. These should all reduce back to the bool and string
886 // set above.
887 {
888 root->Set("a.b.c.d.e", new DictionaryValue);
889 root.reset(root->DeepCopyWithoutEmptyChildren());
890 EXPECT_EQ(2U, root->size());
891 }
892 {
893 DictionaryValue* inner = new DictionaryValue;
894 root->Set("dict_with_emtpy_children", inner);
895 inner->Set("empty_dict", new DictionaryValue);
896 inner->Set("empty_list", new ListValue);
897 root.reset(root->DeepCopyWithoutEmptyChildren());
898 EXPECT_EQ(2U, root->size());
899 }
900 {
901 ListValue* inner = new ListValue;
902 root->Set("list_with_empty_children", inner);
903 inner->Append(new DictionaryValue);
904 inner->Append(new ListValue);
905 root.reset(root->DeepCopyWithoutEmptyChildren());
906 EXPECT_EQ(2U, root->size());
907 }
908
909 // Nested with siblings.
910 {
911 ListValue* inner = new ListValue;
912 root->Set("list_with_empty_children", inner);
913 inner->Append(new DictionaryValue);
914 inner->Append(new ListValue);
915 DictionaryValue* inner2 = new DictionaryValue;
916 root->Set("dict_with_empty_children", inner2);
917 inner2->Set("empty_dict", new DictionaryValue);
918 inner2->Set("empty_list", new ListValue);
919 root.reset(root->DeepCopyWithoutEmptyChildren());
920 EXPECT_EQ(2U, root->size());
921 }
922
923 // Make sure nested values don't get pruned.
924 {
925 ListValue* inner = new ListValue;
926 root->Set("list_with_empty_children", inner);
927 ListValue* inner2 = new ListValue;
928 inner->Append(new DictionaryValue);
929 inner->Append(inner2);
930 inner2->Append(Value::CreateStringValue("hello"));
931 root.reset(root->DeepCopyWithoutEmptyChildren());
932 EXPECT_EQ(3U, root->size());
933 EXPECT_TRUE(root->GetList("list_with_empty_children", &inner));
934 EXPECT_EQ(1U, inner->GetSize()); // Dictionary was pruned.
935 EXPECT_TRUE(inner->GetList(0, &inner2));
936 EXPECT_EQ(1U, inner2->GetSize());
937 }
938}
939
940// TODO(viettrungluu): deprecate:
[email protected]4aeb94082010-08-04 08:44:35941TEST_F(ValuesTest, RemoveEmptyChildrenDeprecated) {
[email protected]9e4cda7332010-07-31 04:56:14942 scoped_ptr<DictionaryValue> root(new DictionaryValue);
943 // Remove empty lists and dictionaries.
[email protected]ec330b52009-12-02 00:20:32944 root->Set(L"empty_dict", new DictionaryValue);
945 root->Set(L"empty_list", new ListValue);
946 root->SetWithoutPathExpansion(L"a.b.c.d.e", new DictionaryValue);
947 root.reset(root->DeepCopyWithoutEmptyChildren());
948 EXPECT_TRUE(root->empty());
949
950 // Make sure we don't prune too much.
951 root->SetBoolean(L"bool", true);
952 root->Set(L"empty_dict", new DictionaryValue);
953 root->SetString(L"empty_string", "");
954 root.reset(root->DeepCopyWithoutEmptyChildren());
955 EXPECT_EQ(2U, root->size());
956
957 // Should do nothing.
958 root.reset(root->DeepCopyWithoutEmptyChildren());
959 EXPECT_EQ(2U, root->size());
960
961 // Nested test cases. These should all reduce back to the bool and string
962 // set above.
963 {
964 root->Set(L"a.b.c.d.e", new DictionaryValue);
965 root.reset(root->DeepCopyWithoutEmptyChildren());
966 EXPECT_EQ(2U, root->size());
967 }
968 {
969 DictionaryValue* inner = new DictionaryValue;
970 root->Set(L"dict_with_emtpy_children", inner);
971 inner->Set(L"empty_dict", new DictionaryValue);
972 inner->Set(L"empty_list", new ListValue);
973 root.reset(root->DeepCopyWithoutEmptyChildren());
974 EXPECT_EQ(2U, root->size());
975 }
976 {
977 ListValue* inner = new ListValue;
978 root->Set(L"list_with_empty_children", inner);
979 inner->Append(new DictionaryValue);
980 inner->Append(new ListValue);
981 root.reset(root->DeepCopyWithoutEmptyChildren());
982 EXPECT_EQ(2U, root->size());
983 }
984
985 // Nested with siblings.
986 {
987 ListValue* inner = new ListValue;
988 root->Set(L"list_with_empty_children", inner);
989 inner->Append(new DictionaryValue);
990 inner->Append(new ListValue);
991 DictionaryValue* inner2 = new DictionaryValue;
992 root->Set(L"dict_with_empty_children", inner2);
993 inner2->Set(L"empty_dict", new DictionaryValue);
994 inner2->Set(L"empty_list", new ListValue);
995 root.reset(root->DeepCopyWithoutEmptyChildren());
996 EXPECT_EQ(2U, root->size());
997 }
998
999 // Make sure nested values don't get pruned.
1000 {
1001 ListValue* inner = new ListValue;
1002 root->Set(L"list_with_empty_children", inner);
1003 ListValue* inner2 = new ListValue;
1004 inner->Append(new DictionaryValue);
1005 inner->Append(inner2);
1006 inner2->Append(Value::CreateStringValue("hello"));
1007 root.reset(root->DeepCopyWithoutEmptyChildren());
1008 EXPECT_EQ(3U, root->size());
1009 EXPECT_TRUE(root->GetList(L"list_with_empty_children", &inner));
1010 EXPECT_EQ(1U, inner->GetSize()); // Dictionary was pruned.
1011 EXPECT_TRUE(inner->GetList(0, &inner2));
1012 EXPECT_EQ(1U, inner2->GetSize());
1013 }
1014}
[email protected]c378cca2010-05-14 13:17:401015
[email protected]4aeb94082010-08-04 08:44:351016TEST_F(ValuesTest, MergeDictionary) {
[email protected]c378cca2010-05-14 13:17:401017 scoped_ptr<DictionaryValue> base(new DictionaryValue);
[email protected]9e4cda7332010-07-31 04:56:141018 base->SetString("base_key", "base_key_value_base");
1019 base->SetString("collide_key", "collide_key_value_base");
1020 DictionaryValue* base_sub_dict = new DictionaryValue;
1021 base_sub_dict->SetString("sub_base_key", "sub_base_key_value_base");
1022 base_sub_dict->SetString("sub_collide_key", "sub_collide_key_value_base");
1023 base->Set("sub_dict_key", base_sub_dict);
1024
1025 scoped_ptr<DictionaryValue> merge(new DictionaryValue);
1026 merge->SetString("merge_key", "merge_key_value_merge");
1027 merge->SetString("collide_key", "collide_key_value_merge");
1028 DictionaryValue* merge_sub_dict = new DictionaryValue;
1029 merge_sub_dict->SetString("sub_merge_key", "sub_merge_key_value_merge");
1030 merge_sub_dict->SetString("sub_collide_key", "sub_collide_key_value_merge");
1031 merge->Set("sub_dict_key", merge_sub_dict);
1032
1033 base->MergeDictionary(merge.get());
1034
1035 EXPECT_EQ(4U, base->size());
1036 std::string base_key_value;
1037 EXPECT_TRUE(base->GetString("base_key", &base_key_value));
1038 EXPECT_EQ("base_key_value_base", base_key_value); // Base value preserved.
1039 std::string collide_key_value;
1040 EXPECT_TRUE(base->GetString("collide_key", &collide_key_value));
1041 EXPECT_EQ("collide_key_value_merge", collide_key_value); // Replaced.
1042 std::string merge_key_value;
1043 EXPECT_TRUE(base->GetString("merge_key", &merge_key_value));
1044 EXPECT_EQ("merge_key_value_merge", merge_key_value); // Merged in.
1045
1046 DictionaryValue* res_sub_dict;
1047 EXPECT_TRUE(base->GetDictionary("sub_dict_key", &res_sub_dict));
1048 EXPECT_EQ(3U, res_sub_dict->size());
1049 std::string sub_base_key_value;
1050 EXPECT_TRUE(res_sub_dict->GetString("sub_base_key", &sub_base_key_value));
1051 EXPECT_EQ("sub_base_key_value_base", sub_base_key_value); // Preserved.
1052 std::string sub_collide_key_value;
1053 EXPECT_TRUE(res_sub_dict->GetString("sub_collide_key",
1054 &sub_collide_key_value));
1055 EXPECT_EQ("sub_collide_key_value_merge", sub_collide_key_value); // Replaced.
1056 std::string sub_merge_key_value;
1057 EXPECT_TRUE(res_sub_dict->GetString("sub_merge_key", &sub_merge_key_value));
1058 EXPECT_EQ("sub_merge_key_value_merge", sub_merge_key_value); // Merged in.
1059}
1060
1061// TODO(viettrungluu): deprecate:
[email protected]4aeb94082010-08-04 08:44:351062TEST_F(ValuesTest, MergeDictionaryDeprecated) {
[email protected]9e4cda7332010-07-31 04:56:141063 scoped_ptr<DictionaryValue> base(new DictionaryValue);
[email protected]c378cca2010-05-14 13:17:401064 base->SetString(L"base_key", "base_key_value_base");
1065 base->SetString(L"collide_key", "collide_key_value_base");
1066 DictionaryValue* base_sub_dict = new DictionaryValue;
1067 base_sub_dict->SetString(L"sub_base_key", "sub_base_key_value_base");
1068 base_sub_dict->SetString(L"sub_collide_key", "sub_collide_key_value_base");
1069 base->Set(L"sub_dict_key", base_sub_dict);
1070
1071 scoped_ptr<DictionaryValue> merge(new DictionaryValue);
1072 merge->SetString(L"merge_key", "merge_key_value_merge");
1073 merge->SetString(L"collide_key", "collide_key_value_merge");
1074 DictionaryValue* merge_sub_dict = new DictionaryValue;
1075 merge_sub_dict->SetString(L"sub_merge_key", "sub_merge_key_value_merge");
1076 merge_sub_dict->SetString(L"sub_collide_key", "sub_collide_key_value_merge");
1077 merge->Set(L"sub_dict_key", merge_sub_dict);
1078
1079 base->MergeDictionary(merge.get());
1080
1081 EXPECT_EQ(4U, base->size());
1082 std::string base_key_value;
1083 EXPECT_TRUE(base->GetString(L"base_key", &base_key_value));
1084 EXPECT_EQ("base_key_value_base", base_key_value); // Base value preserved.
1085 std::string collide_key_value;
1086 EXPECT_TRUE(base->GetString(L"collide_key", &collide_key_value));
1087 EXPECT_EQ("collide_key_value_merge", collide_key_value); // Replaced.
1088 std::string merge_key_value;
1089 EXPECT_TRUE(base->GetString(L"merge_key", &merge_key_value));
1090 EXPECT_EQ("merge_key_value_merge", merge_key_value); // Merged in.
1091
1092 DictionaryValue* res_sub_dict;
1093 EXPECT_TRUE(base->GetDictionary(L"sub_dict_key", &res_sub_dict));
1094 EXPECT_EQ(3U, res_sub_dict->size());
1095 std::string sub_base_key_value;
1096 EXPECT_TRUE(res_sub_dict->GetString(L"sub_base_key", &sub_base_key_value));
1097 EXPECT_EQ("sub_base_key_value_base", sub_base_key_value); // Preserved.
1098 std::string sub_collide_key_value;
1099 EXPECT_TRUE(res_sub_dict->GetString(L"sub_collide_key",
1100 &sub_collide_key_value));
1101 EXPECT_EQ("sub_collide_key_value_merge", sub_collide_key_value); // Replaced.
1102 std::string sub_merge_key_value;
1103 EXPECT_TRUE(res_sub_dict->GetString(L"sub_merge_key", &sub_merge_key_value));
1104 EXPECT_EQ("sub_merge_key_value_merge", sub_merge_key_value); // Merged in.
1105}
[email protected]4aeb94082010-08-04 08:44:351106
1107TEST_F(ValuesTest, GetDifferingPaths) {
1108 scoped_ptr<DictionaryValue> dict1(new DictionaryValue());
1109 scoped_ptr<DictionaryValue> dict2(new DictionaryValue());
1110 std::vector<std::string> differing_paths;
1111
1112 // Test comparing empty dictionaries.
1113 dict1->GetDifferingPaths(dict2.get(), &differing_paths);
1114 EXPECT_EQ(differing_paths.size(), 0UL);
1115
1116 // Compare an empty dictionary with various non-empty dictionaries.
1117 static const char* expected_paths1[] = {
1118 "segment1"
1119 };
1120 dict1->SetString("segment1", "value1");
1121 CompareDictionariesAndCheckResult(dict1.get(), dict2.get(), expected_paths1,
1122 arraysize(expected_paths1));
1123
1124 static const char* expected_paths2[] = {
1125 "segment1",
1126 "segment2",
1127 "segment2.segment3"
1128 };
1129 dict1->SetString("segment2.segment3", "value2");
1130 CompareDictionariesAndCheckResult(dict1.get(), dict2.get(), expected_paths2,
1131 arraysize(expected_paths2));
1132
1133 static const char* expected_paths3[] = {
1134 "segment1",
1135 "segment2",
1136 "segment2.segment3",
1137 "segment4",
1138 "segment4.segment5"
1139 };
1140 dict1->SetString("segment4.segment5", "value3");
1141 CompareDictionariesAndCheckResult(dict1.get(), dict2.get(), expected_paths3,
1142 arraysize(expected_paths3));
1143
1144 // Now various tests with two populated dictionaries.
1145 static const char* expected_paths4[] = {
1146 "segment1",
1147 "segment2",
1148 "segment2.segment3",
1149 "segment4",
1150 "segment4.segment5"
1151 };
1152 dict2->Set("segment2", new DictionaryValue());
1153 CompareDictionariesAndCheckResult(dict1.get(), dict2.get(), expected_paths4,
1154 arraysize(expected_paths4));
1155
1156 static const char* expected_paths5[] = {
1157 "segment1",
1158 "segment4",
1159 "segment4.segment5"
1160 };
1161 dict2->SetString("segment2.segment3", "value2");
1162 CompareDictionariesAndCheckResult(dict1.get(), dict2.get(), expected_paths5,
1163 arraysize(expected_paths5));
1164
1165 dict2->SetBoolean("segment2.segment3", true);
1166 CompareDictionariesAndCheckResult(dict1.get(), dict2.get(), expected_paths4,
1167 arraysize(expected_paths4));
1168
1169 // Test two identical dictionaries.
1170 dict2.reset(static_cast<DictionaryValue*>(dict1->DeepCopy()));
1171 dict2->GetDifferingPaths(dict1.get(), &differing_paths);
1172 EXPECT_EQ(differing_paths.size(), 0UL);
1173
1174 // Test a deep dictionary structure.
1175 static const char* expected_paths6[] = {
1176 "s1",
1177 "s1.s2",
1178 "s1.s2.s3",
1179 "s1.s2.s3.s4",
1180 "s1.s2.s3.s4.s5"
1181 };
1182 dict1.reset(new DictionaryValue());
1183 dict2.reset(new DictionaryValue());
1184 dict1->Set("s1.s2.s3.s4.s5", new DictionaryValue());
1185 CompareDictionariesAndCheckResult(dict1.get(), dict2.get(), expected_paths6,
1186 arraysize(expected_paths6));
1187
1188 // Make sure disjoint dictionaries generate the right differing path list.
1189 static const char* expected_paths7[] = {
1190 "a",
1191 "b",
1192 "c",
1193 "d"
1194 };
1195 dict1.reset(new DictionaryValue());
1196 dict1->SetBoolean("a", true);
1197 dict1->SetBoolean("c", true);
1198 dict2.reset(new DictionaryValue());
1199 dict1->SetBoolean("b", true);
1200 dict1->SetBoolean("d", true);
1201 CompareDictionariesAndCheckResult(dict1.get(), dict2.get(), expected_paths7,
1202 arraysize(expected_paths7));
1203
1204 // For code coverage completeness. Make sure that all branches
1205 // that were not covered are executed.
1206 static const char* expected_paths8[] = {
1207 "s1",
1208 "s1.s2"
1209 };
1210 dict1.reset(new DictionaryValue());
1211 dict1->Set("s1.s2", new DictionaryValue());
1212 dict2.reset(new DictionaryValue());
1213 dict2->SetInteger("s1", 1);
1214 CompareDictionariesAndCheckResult(dict1.get(), dict2.get(), expected_paths8,
1215 arraysize(expected_paths8));
1216}