1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "chrome/browser/search/local_ntp_source.h"
7 #include "base/json/json_string_value_serializer.h"
8 #include "base/logging.h"
9 #include "base/memory/ref_counted_memory.h"
10 #include "base/memory/scoped_ptr.h"
11 #include "base/strings/string_util.h"
12 #include "base/strings/stringprintf.h"
13 #include "base/values.h"
14 #include "chrome/browser/search/instant_io_context.h"
15 #include "chrome/browser/search/search.h"
16 #include "chrome/browser/search_engines/template_url_prepopulate_data.h"
17 #include "chrome/browser/search_engines/template_url_service.h"
18 #include "chrome/browser/search_engines/template_url_service_factory.h"
19 #include "chrome/common/url_constants.h"
20 #include "grit/browser_resources.h"
21 #include "grit/generated_resources.h"
22 #include "grit/ui_resources.h"
23 #include "net/url_request/url_request.h"
24 #include "ui/base/l10n/l10n_util.h"
25 #include "ui/base/resource/resource_bundle.h"
26 #include "ui/base/webui/jstemplate_builder.h"
31 // Signifies a locally constructed resource, i.e. not from grit/.
32 const int kLocalResource
= -1;
34 const char kConfigDataFilename
[] = "config.js";
36 const struct Resource
{
39 const char* mime_type
;
41 { "local-ntp.html", IDR_LOCAL_NTP_HTML
, "text/html" },
42 { "local-ntp.js", IDR_LOCAL_NTP_JS
, "application/javascript" },
43 { kConfigDataFilename
, kLocalResource
, "application/javascript" },
44 { "local-ntp.css", IDR_LOCAL_NTP_CSS
, "text/css" },
45 { "images/close_2.png", IDR_CLOSE_2
, "image/png" },
46 { "images/close_2_hover.png", IDR_CLOSE_2_H
, "image/png" },
47 { "images/close_2_active.png", IDR_CLOSE_2_P
, "image/png" },
48 { "images/close_2_white.png", IDR_CLOSE_2_MASK
, "image/png" },
49 { "images/2x/google_logo.png",
50 IDR_LOCAL_NTP_IMAGES_2X_LOGO_PNG
, "image/png" },
51 { "images/2x/white_google_logo.png",
52 IDR_LOCAL_NTP_IMAGES_2X_WHITE_LOGO_PNG
, "image/png" },
55 // Strips any query parameters from the specified path.
56 std::string
StripParameters(const std::string
& path
) {
57 return path
.substr(0, path
.find("?"));
60 bool DefaultSearchProviderIsGoogle(Profile
* profile
) {
64 TemplateURLService
* template_url_service
=
65 TemplateURLServiceFactory::GetForProfile(profile
);
66 if (!template_url_service
)
69 const TemplateURL
* default_provider
=
70 template_url_service
->GetDefaultSearchProvider();
71 return default_provider
&&
72 (TemplateURLPrepopulateData::GetEngineType(*default_provider
) ==
73 SEARCH_ENGINE_GOOGLE
);
76 // Adds a localized string keyed by resource id to the dictionary.
77 void AddString(base::DictionaryValue
* dictionary
,
78 const std::string
& key
,
80 dictionary
->SetString(key
, l10n_util::GetStringUTF16(resource_id
));
83 // Populates |translated_strings| dictionary for the local NTP.
84 scoped_ptr
<base::DictionaryValue
> GetTranslatedStrings() {
85 scoped_ptr
<base::DictionaryValue
> translated_strings(
86 new base::DictionaryValue());
88 AddString(translated_strings
.get(), "thumbnailRemovedNotification",
89 IDS_NEW_TAB_THUMBNAIL_REMOVED_NOTIFICATION
);
90 AddString(translated_strings
.get(), "removeThumbnailTooltip",
91 IDS_NEW_TAB_REMOVE_THUMBNAIL_TOOLTIP
);
92 AddString(translated_strings
.get(), "undoThumbnailRemove",
93 IDS_NEW_TAB_UNDO_THUMBNAIL_REMOVE
);
94 AddString(translated_strings
.get(), "restoreThumbnailsShort",
95 IDS_NEW_TAB_RESTORE_THUMBNAILS_SHORT_LINK
);
96 AddString(translated_strings
.get(), "attributionIntro",
97 IDS_NEW_TAB_ATTRIBUTION_INTRO
);
98 AddString(translated_strings
.get(), "title", IDS_NEW_TAB_TITLE
);
100 return translated_strings
.Pass();
103 // Returns a JS dictionary of configuration data for the local NTP.
104 std::string
GetConfigData(Profile
* profile
) {
105 base::DictionaryValue config_data
;
106 config_data
.Set("translatedStrings", GetTranslatedStrings().release());
107 config_data
.SetBoolean("isGooglePage",
108 DefaultSearchProviderIsGoogle(profile
));
110 // Serialize the dictionary.
112 JSONStringValueSerializer
serializer(&js_text
);
113 serializer
.Serialize(config_data
);
115 std::string config_data_js
;
116 config_data_js
.append("var configData = ");
117 config_data_js
.append(js_text
);
118 config_data_js
.append(";");
119 return config_data_js
;
124 LocalNtpSource::LocalNtpSource(Profile
* profile
) : profile_(profile
) {
127 LocalNtpSource::~LocalNtpSource() {
130 std::string
LocalNtpSource::GetSource() const {
131 return chrome::kChromeSearchLocalNtpHost
;
134 void LocalNtpSource::StartDataRequest(
135 const std::string
& path
,
136 int render_process_id
,
138 const content::URLDataSource::GotDataCallback
& callback
) {
139 const std::string stripped_path
= StripParameters(path
);
140 if (stripped_path
== kConfigDataFilename
) {
141 std::string config_data_js
= GetConfigData(profile_
);
142 callback
.Run(base::RefCountedString::TakeString(&config_data_js
));
145 for (size_t i
= 0; i
< arraysize(kResources
); ++i
) {
146 if (stripped_path
== kResources
[i
].filename
) {
147 scoped_refptr
<base::RefCountedStaticMemory
> response(
148 ResourceBundle::GetSharedInstance().LoadDataResourceBytes(
149 kResources
[i
].identifier
));
150 callback
.Run(response
.get());
157 std::string
LocalNtpSource::GetMimeType(
158 const std::string
& path
) const {
159 const std::string stripped_path
= StripParameters(path
);
160 for (size_t i
= 0; i
< arraysize(kResources
); ++i
) {
161 if (stripped_path
== kResources
[i
].filename
)
162 return kResources
[i
].mime_type
;
164 return std::string();
167 bool LocalNtpSource::ShouldServiceRequest(
168 const net::URLRequest
* request
) const {
169 DCHECK(request
->url().host() == chrome::kChromeSearchLocalNtpHost
);
170 if (!InstantIOContext::ShouldServiceRequest(request
))
173 if (request
->url().SchemeIs(chrome::kChromeSearchScheme
)) {
174 DCHECK(StartsWithASCII(request
->url().path(), "/", true));
175 std::string filename
= request
->url().path().substr(1);
176 for (size_t i
= 0; i
< arraysize(kResources
); ++i
) {
177 if (filename
== kResources
[i
].filename
)
184 std::string
LocalNtpSource::GetContentSecurityPolicyFrameSrc() const {
185 // Allow embedding of most visited iframes.
186 return base::StringPrintf("frame-src %s;",
187 chrome::kChromeSearchMostVisitedUrl
);