Chromium Code Reviews| Index: components/doodle/doodle_types_unittest.cc |
| diff --git a/components/doodle/doodle_types_unittest.cc b/components/doodle/doodle_types_unittest.cc |
| new file mode 100644 |
| index 0000000000000000000000000000000000000000..98f4149f68dfba5118e83b5307128168a9aaca5b |
| --- /dev/null |
| +++ b/components/doodle/doodle_types_unittest.cc |
| @@ -0,0 +1,254 @@ |
| +// Copyright 2017 The Chromium Authors. All rights reserved. |
| +// Use of this source code is governed by a BSD-style license that can be |
| +// found in the LICENSE file. |
| + |
| +#include "components/doodle/doodle_types.h" |
| + |
| +#include <memory> |
| +#include <string> |
| + |
| +#include "base/json/json_reader.h" |
| +#include "base/optional.h" |
| +#include "base/values.h" |
| +#include "testing/gmock/include/gmock/gmock.h" |
| +#include "testing/gtest/include/gtest/gtest.h" |
| +#include "url/gurl.h" |
| + |
| +using testing::Eq; |
| + |
| +namespace doodle { |
| + |
| +namespace { |
| + |
| +// Parses the given |json| string into a base::DictionaryValue and creates a |
| +// DoodleImage out of that. |json| must be a valid json string. |
| +base::Optional<DoodleImage> DoodleImageFromJson( |
| + const std::string& json, |
| + const base::Optional<GURL>& base_url) { |
| + std::unique_ptr<base::DictionaryValue> value = |
| + base::DictionaryValue::From(base::JSONReader::Read(json)); |
| + DCHECK(value); |
| + return DoodleImage::FromDictionary(*value, base_url); |
| +} |
| + |
| +// Parses the given |json| string into a base::DictionaryValue and creates a |
| +// DoodleConfig out of that. |json| must be a valid json string. |
| +base::Optional<DoodleConfig> DoodleConfigFromJson( |
| + const std::string& json, |
| + const base::Optional<GURL>& base_url) { |
| + std::unique_ptr<base::DictionaryValue> value = |
| + base::DictionaryValue::From(base::JSONReader::Read(json)); |
| + DCHECK(value); |
| + return DoodleConfig::FromDictionary(*value, base_url); |
| +} |
| + |
| +} // namespace |
| + |
| +TEST(DoodleImageTest, ParsesMinimalImage) { |
| + std::string json = R"json({ |
| + "url":"https://www.doodle.com/doodle" |
| + })json"; |
| + base::Optional<DoodleImage> image = DoodleImageFromJson(json, base::nullopt); |
| + ASSERT_TRUE(image.has_value()); |
| + EXPECT_THAT(image->url, Eq(GURL("https://www.doodle.com/doodle"))); |
| + EXPECT_THAT(image->height, Eq(0)); |
| + EXPECT_THAT(image->width, Eq(0)); |
| + EXPECT_THAT(image->is_animated_gif, Eq(false)); |
| + EXPECT_THAT(image->is_cta, Eq(false)); |
| +} |
| + |
| +TEST(DoodleImageTest, ParsesFullImage) { |
| + std::string json = R"json({ |
| + "url":"https://www.doodle.com/doodle", |
| + "height":100, |
| + "width":50, |
| + "is_animated_gif":true, |
| + "is_cta":true |
| + })json"; |
| + base::Optional<DoodleImage> image = DoodleImageFromJson(json, base::nullopt); |
| + ASSERT_TRUE(image.has_value()); |
| + EXPECT_THAT(image->url, Eq(GURL("https://www.doodle.com/doodle"))); |
| + EXPECT_THAT(image->height, Eq(100)); |
| + EXPECT_THAT(image->width, Eq(50)); |
| + EXPECT_THAT(image->is_animated_gif, Eq(true)); |
| + EXPECT_THAT(image->is_cta, Eq(true)); |
| +} |
| + |
| +TEST(DoodleImageTest, ResolvesRelativeUrl) { |
| + std::string json = R"json({ |
| + "url":"/the_doodle_path" |
| + })json"; |
| + base::Optional<DoodleImage> image = |
| + DoodleImageFromJson(json, GURL("https://doodle.dood/")); |
| + ASSERT_TRUE(image.has_value()); |
| + EXPECT_THAT(image->url, Eq(GURL("https://doodle.dood/the_doodle_path"))); |
| +} |
| + |
| +TEST(DoodleImageTest, DoesNotResolveAbsoluteUrl) { |
| + std::string json = R"json({ |
| + "url":"https://www.doodle.com/the_doodle_path" |
| + })json"; |
| + base::Optional<DoodleImage> image = |
| + DoodleImageFromJson(json, GURL("https://other.com/")); |
| + ASSERT_TRUE(image.has_value()); |
| + EXPECT_THAT(image->url, Eq(GURL("https://www.doodle.com/the_doodle_path"))); |
| +} |
| + |
| +TEST(DoodleImageTest, RequiresUrl) { |
| + std::string json = R"json({ |
| + "height":100, |
| + "width":50, |
| + "is_animated_gif":true, |
| + "is_cta":true |
| + })json"; |
| + base::Optional<DoodleImage> image = DoodleImageFromJson(json, base::nullopt); |
| + EXPECT_FALSE(image.has_value()); |
| +} |
| + |
| +TEST(DoodleImageTest, PreservesFieldsOverRoundtrip) { |
| + // Set all fields to non-default values. |
| + DoodleImage image(GURL("https://www.doodle.com/doodle")); |
| + image.height = 100; |
| + image.width = 50; |
| + image.is_animated_gif = true; |
| + image.is_cta = true; |
| + |
| + // Convert to a dictionary and back. |
| + base::Optional<DoodleImage> after_roundtrip = |
| + DoodleImage::FromDictionary(*image.ToDictionary(), base::nullopt); |
| + |
| + // Make sure everything survived. |
| + ASSERT_TRUE(after_roundtrip.has_value()); |
| + EXPECT_THAT(*after_roundtrip, Eq(image)); |
| +} |
| + |
| +TEST(DoodleConfigTest, ParsesMinimalConfig) { |
| + std::string json = R"json({ |
| + "large_image":{"url":"https://doodle.com/img.jpg"} |
| + })json"; |
| + base::Optional<DoodleConfig> config = |
| + DoodleConfigFromJson(json, base::nullopt); |
| + ASSERT_TRUE(config.has_value()); |
| + EXPECT_THAT(config->doodle_type, Eq(DoodleType::UNKNOWN)); |
| + EXPECT_THAT(config->alt_text, Eq(std::string())); |
| + EXPECT_THAT(config->interactive_html, Eq(std::string())); |
| + EXPECT_THAT(config->search_url, Eq(GURL())); |
| + EXPECT_THAT(config->target_url, Eq(GURL())); |
| + EXPECT_THAT(config->fullpage_interactive_url, Eq(GURL())); |
| + EXPECT_FALSE(config->large_cta_image.has_value()); |
| + EXPECT_FALSE(config->transparent_large_image.has_value()); |
| +} |
| + |
| +TEST(DoodleConfigTest, ParsesFullConfig) { |
| + std::string json = R"json({ |
| + "doodle_type":"SLIDESHOW", |
| + "alt_text":"some text", |
| + "interactive_html":"<div id='dood'></div>", |
| + "search_url":"https://doodle.com/search", |
| + "target_url":"https://doodle.com/target", |
| + "fullpage_interactive_url":"https://doodle.com/interactive", |
| + "large_image":{"url":"https://doodle.com/img.jpg"}, |
| + "large_cta_image":{"url":"https://doodle.com/cta.jpg"}, |
| + "transparent_large_image":{"url":"https://doodle.com/transparent.jpg"} |
| + })json"; |
| + base::Optional<DoodleConfig> config = |
| + DoodleConfigFromJson(json, base::nullopt); |
| + ASSERT_TRUE(config.has_value()); |
| + EXPECT_THAT(config->doodle_type, Eq(DoodleType::SLIDESHOW)); |
| + EXPECT_THAT(config->alt_text, Eq("some text")); |
| + EXPECT_THAT(config->interactive_html, Eq("<div id='dood'></div>")); |
| + EXPECT_THAT(config->search_url, Eq(GURL("https://doodle.com/search"))); |
| + EXPECT_THAT(config->target_url, Eq(GURL("https://doodle.com/target"))); |
| + EXPECT_THAT(config->fullpage_interactive_url, |
| + Eq(GURL("https://doodle.com/interactive"))); |
| + EXPECT_THAT(config->large_image.url, Eq(GURL("https://doodle.com/img.jpg"))); |
| + ASSERT_TRUE(config->large_cta_image.has_value()); |
| + EXPECT_THAT(config->large_cta_image->url, |
| + Eq(GURL("https://doodle.com/cta.jpg"))); |
| + ASSERT_TRUE(config->transparent_large_image.has_value()); |
| + EXPECT_THAT(config->transparent_large_image->url, |
| + Eq(GURL("https://doodle.com/transparent.jpg"))); |
| +} |
| + |
| +TEST(DoodleConfigTest, RequiresLargeImage) { |
| + std::string json = R"json({ |
| + "doodle_type":"SLIDESHOW", |
| + "alt_text":"some text", |
| + "interactive_html":"<div id='dood'></div>", |
| + "search_url":"https://doodle.com/search", |
| + "target_url":"https://doodle.com/target", |
| + "fullpage_interactive_url":"https://doodle.com/interactive", |
| + "large_cta_image":{"url":"https://doodle.com/cta.jpg"}, |
| + "transparent_large_image":{"url":"https://doodle.com/transparent.jpg"} |
| + })json"; |
| + base::Optional<DoodleConfig> config = |
| + DoodleConfigFromJson(json, base::nullopt); |
| + EXPECT_FALSE(config.has_value()); |
| +} |
| + |
| +TEST(DoodleConfigTest, RequiresValidLargeImage) { |
| + std::string json = R"json({ |
| + "doodle_type":"SLIDESHOW", |
| + "alt_text":"some text", |
| + "interactive_html":"<div id='dood'></div>", |
| + "search_url":"https://doodle.com/search", |
| + "target_url":"https://doodle.com/target", |
| + "fullpage_interactive_url":"https://doodle.com/interactive", |
| + "large_image":{"no_url":"asdf"}, |
| + "large_cta_image":{"url":"https://doodle.com/cta.jpg"}, |
| + "transparent_large_image":{"url":"https://doodle.com/transparent.jpg"} |
| + })json"; |
| + base::Optional<DoodleConfig> config = |
| + DoodleConfigFromJson(json, base::nullopt); |
| + EXPECT_FALSE(config.has_value()); |
| +} |
| + |
| +TEST(DoodleConfigTest, ResolvesRelativeUrls) { |
| + std::string json = R"json({ |
| + "search_url":"/search", |
| + "target_url":"/target", |
| + "fullpage_interactive_url":"/interactive", |
| + "large_image":{"url":"/large.jpg"}, |
| + "large_cta_image":{"url":"/cta.jpg"}, |
| + "transparent_large_image":{"url":"/transparent.jpg"} |
| + })json"; |
| + base::Optional<DoodleConfig> config = |
| + DoodleConfigFromJson(json, GURL("https://doodle.com/")); |
| + ASSERT_TRUE(config.has_value()); |
| + EXPECT_THAT(config->search_url, Eq(GURL("https://doodle.com/search"))); |
| + EXPECT_THAT(config->target_url, Eq(GURL("https://doodle.com/target"))); |
| + EXPECT_THAT(config->fullpage_interactive_url, |
| + Eq(GURL("https://doodle.com/interactive"))); |
| + EXPECT_THAT(config->large_image.url, |
| + Eq(GURL("https://doodle.com/large.jpg"))); |
| + ASSERT_TRUE(config->large_cta_image.has_value()); |
| + EXPECT_THAT(config->large_cta_image->url, |
| + Eq(GURL("https://doodle.com/cta.jpg"))); |
| + ASSERT_TRUE(config->transparent_large_image.has_value()); |
| + EXPECT_THAT(config->transparent_large_image->url, |
| + Eq(GURL("https://doodle.com/transparent.jpg"))); |
| +} |
| + |
| +TEST(DoodleConfigTest, PreservesFieldsOverRoundtrip) { |
| + // Set all fields to non-default values. |
| + DoodleConfig config(DoodleType::SLIDESHOW, |
| + DoodleImage(GURL("https://www.doodle.com/img.jpg"))); |
| + config.alt_text = "some text"; |
| + config.interactive_html = "<div id='dood'></div>"; |
| + config.search_url = GURL("https://doodle.com/search"); |
| + config.target_url = GURL("https://doodle.com/target"); |
| + config.fullpage_interactive_url = GURL("https://doodle.com/interactive"); |
| + config.large_cta_image = DoodleImage(GURL("https://www.doodle.com/cta.jpg")); |
| + config.transparent_large_image = |
| + DoodleImage(GURL("https://www.doodle.com/transparent.jpg")); |
| + |
| + // Convert to a dictionary and back. |
| + base::Optional<DoodleConfig> after_roundtrip = |
| + DoodleConfig::FromDictionary(*config.ToDictionary(), base::nullopt); |
|
sfiera
2017/03/13 13:07:53
Should fields be preserved when round-tripping wit
Marc Treib
2017/03/13 13:29:12
They should be preserved - the resolving only appl
|
| + |
| + // Make sure everything survived. |
| + ASSERT_TRUE(after_roundtrip.has_value()); |
| + EXPECT_THAT(*after_roundtrip, Eq(config)); |
| +} |
| + |
|
sfiera
2017/03/13 13:07:53
Invalid URLs? I think you have a DCHECK when makin
Marc Treib
2017/03/13 13:29:12
Which DCHECK do you mean?
I've added tests with in
sfiera
2017/03/13 13:46:15
GURL::spec() DCHECKs on non-empty, invalid URLs. Y
Marc Treib
2017/03/13 14:04:32
Ah - the GURL construction handles that, it return
sfiera
2017/03/13 14:10:23
Hmm. I wonder how I knew about this, then—I could
|
| +} // namespace doodle |