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

Side by Side Diff: components/translate/content/renderer/translate_helper.cc

Issue 2143383002: [Translate] Migrate IPCs to Mojo interfaces. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Address comments from Ken Created 4 years, 4 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 "components/translate/content/renderer/translate_helper.h" 5 #include "components/translate/content/renderer/translate_helper.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/compiler_specific.h" 8 #include "base/compiler_specific.h"
9 #include "base/location.h" 9 #include "base/location.h"
10 #include "base/logging.h" 10 #include "base/logging.h"
11 #include "base/metrics/histogram_macros.h" 11 #include "base/metrics/histogram_macros.h"
12 #include "base/single_thread_task_runner.h" 12 #include "base/single_thread_task_runner.h"
13 #include "base/strings/string16.h" 13 #include "base/strings/string16.h"
14 #include "base/strings/string_util.h" 14 #include "base/strings/string_util.h"
15 #include "base/strings/utf_string_conversions.h" 15 #include "base/strings/utf_string_conversions.h"
16 #include "base/threading/thread_task_runner_handle.h" 16 #include "base/threading/thread_task_runner_handle.h"
17 #include "components/translate/content/common/translate_messages.h"
18 #include "components/translate/core/common/translate_constants.h" 17 #include "components/translate/core/common/translate_constants.h"
19 #include "components/translate/core/common/translate_metrics.h" 18 #include "components/translate/core/common/translate_metrics.h"
20 #include "components/translate/core/common/translate_util.h" 19 #include "components/translate/core/common/translate_util.h"
21 #include "components/translate/core/language_detection/language_detection_util.h " 20 #include "components/translate/core/language_detection/language_detection_util.h "
22 #include "content/public/common/content_constants.h" 21 #include "content/public/common/content_constants.h"
23 #include "content/public/common/url_constants.h" 22 #include "content/public/common/url_constants.h"
24 #include "content/public/renderer/render_frame.h" 23 #include "content/public/renderer/render_frame.h"
25 #include "content/public/renderer/render_thread.h" 24 #include "content/public/renderer/render_thread.h"
26 #include "ipc/ipc_platform_file.h" 25 #include "services/shell/public/cpp/interface_provider.h"
27 #include "third_party/WebKit/public/web/WebDocument.h" 26 #include "third_party/WebKit/public/web/WebDocument.h"
28 #include "third_party/WebKit/public/web/WebElement.h" 27 #include "third_party/WebKit/public/web/WebElement.h"
29 #include "third_party/WebKit/public/web/WebLocalFrame.h" 28 #include "third_party/WebKit/public/web/WebLocalFrame.h"
30 #include "third_party/WebKit/public/web/WebNode.h" 29 #include "third_party/WebKit/public/web/WebNode.h"
31 #include "third_party/WebKit/public/web/WebScriptSource.h" 30 #include "third_party/WebKit/public/web/WebScriptSource.h"
32 #include "url/gurl.h" 31 #include "url/gurl.h"
33 #include "v8/include/v8.h" 32 #include "v8/include/v8.h"
34 33
35 using base::ASCIIToUTF16; 34 using base::ASCIIToUTF16;
36 using blink::WebDocument; 35 using blink::WebDocument;
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
71 if (head.isNull() || !head.hasChildNodes()) 70 if (head.isNull() || !head.hasChildNodes())
72 return false; 71 return false;
73 72
74 const WebString meta(ASCIIToUTF16("meta")); 73 const WebString meta(ASCIIToUTF16("meta"));
75 const WebString name(ASCIIToUTF16("name")); 74 const WebString name(ASCIIToUTF16("name"));
76 const WebString google(ASCIIToUTF16("google")); 75 const WebString google(ASCIIToUTF16("google"));
77 const WebString value(ASCIIToUTF16("value")); 76 const WebString value(ASCIIToUTF16("value"));
78 const WebString content(ASCIIToUTF16("content")); 77 const WebString content(ASCIIToUTF16("content"));
79 78
80 for (WebNode child = head.firstChild(); !child.isNull(); 79 for (WebNode child = head.firstChild(); !child.isNull();
81 child = child.nextSibling()) { 80 child = child.nextSibling()) {
82 if (!child.isElementNode()) 81 if (!child.isElementNode())
83 continue; 82 continue;
84 WebElement element = child.to<WebElement>(); 83 WebElement element = child.to<WebElement>();
85 // Check if a tag is <meta>. 84 // Check if a tag is <meta>.
86 if (!element.hasHTMLTagName(meta)) 85 if (!element.hasHTMLTagName(meta))
87 continue; 86 continue;
88 // Check if the tag contains name="google". 87 // Check if the tag contains name="google".
89 WebString attribute = element.getAttribute(name); 88 WebString attribute = element.getAttribute(name);
90 if (attribute.isNull() || attribute != google) 89 if (attribute.isNull() || attribute != google)
91 continue; 90 continue;
(...skipping 15 matching lines...) Expand all
107 namespace translate { 106 namespace translate {
108 107
109 //////////////////////////////////////////////////////////////////////////////// 108 ////////////////////////////////////////////////////////////////////////////////
110 // TranslateHelper, public: 109 // TranslateHelper, public:
111 // 110 //
112 TranslateHelper::TranslateHelper(content::RenderFrame* render_frame, 111 TranslateHelper::TranslateHelper(content::RenderFrame* render_frame,
113 int world_id, 112 int world_id,
114 int extension_group, 113 int extension_group,
115 const std::string& extension_scheme) 114 const std::string& extension_scheme)
116 : content::RenderFrameObserver(render_frame), 115 : content::RenderFrameObserver(render_frame),
117 page_seq_no_(0),
118 translation_pending_(false),
119 world_id_(world_id), 116 world_id_(world_id),
120 extension_group_(extension_group), 117 extension_group_(extension_group),
121 extension_scheme_(extension_scheme), 118 extension_scheme_(extension_scheme),
119 binding_(this),
122 weak_method_factory_(this) {} 120 weak_method_factory_(this) {}
123 121
124 TranslateHelper::~TranslateHelper() { 122 TranslateHelper::~TranslateHelper() {}
125 }
126 123
127 void TranslateHelper::PrepareForUrl(const GURL& url) { 124 void TranslateHelper::PrepareForUrl(const GURL& url) {
128 ++page_seq_no_; 125 // Navigated to a new page, close the binding for previous page.
129 Send(new ChromeFrameHostMsg_TranslateAssignedSequenceNumber(routing_id(), 126 binding_.Close();
130 page_seq_no_)); 127 translate_callback_pending_.Reset();
131 } 128 }
132 129
133 void TranslateHelper::PageCaptured(const base::string16& contents) { 130 void TranslateHelper::PageCaptured(const base::string16& contents) {
134 PageCapturedImpl(page_seq_no_, contents);
135 }
136
137 void TranslateHelper::PageCapturedImpl(int page_seq_no,
138 const base::string16& contents) {
139 // Get the document language as set by WebKit from the http-equiv 131 // Get the document language as set by WebKit from the http-equiv
140 // meta tag for "content-language". This may or may not also 132 // meta tag for "content-language". This may or may not also
141 // have a value derived from the actual Content-Language HTTP 133 // have a value derived from the actual Content-Language HTTP
142 // header. The two actually have different meanings (despite the 134 // header. The two actually have different meanings (despite the
143 // original intent of http-equiv to be an equivalent) with the former 135 // original intent of http-equiv to be an equivalent) with the former
144 // being the language of the document and the latter being the 136 // being the language of the document and the latter being the
145 // language of the intended audience (a distinction really only 137 // language of the intended audience (a distinction really only
146 // relevant for things like langauge textbooks). This distinction 138 // relevant for things like langauge textbooks). This distinction
147 // shouldn't affect translation. 139 // shouldn't affect translation.
148 WebLocalFrame* main_frame = render_frame()->GetWebFrame(); 140 WebLocalFrame* main_frame = render_frame()->GetWebFrame();
149 if (!main_frame || page_seq_no_ != page_seq_no) 141 if (!main_frame)
150 return; 142 return;
151 143
152 WebDocument document = main_frame->document(); 144 WebDocument document = main_frame->document();
153 std::string content_language = document.contentLanguage().utf8(); 145 std::string content_language = document.contentLanguage().utf8();
154 WebElement html_element = document.documentElement(); 146 WebElement html_element = document.documentElement();
155 std::string html_lang; 147 std::string html_lang;
156 // |html_element| can be null element, e.g. in 148 // |html_element| can be null element, e.g. in
157 // BrowserTest.WindowOpenClose. 149 // BrowserTest.WindowOpenClose.
158 if (!html_element.isNull()) 150 if (!html_element.isNull())
159 html_lang = html_element.getAttribute("lang").utf8(); 151 html_lang = html_element.getAttribute("lang").utf8();
(...skipping 15 matching lines...) Expand all
175 details.cld_language = cld_language; 167 details.cld_language = cld_language;
176 details.is_cld_reliable = is_cld_reliable; 168 details.is_cld_reliable = is_cld_reliable;
177 details.has_notranslate = HasNoTranslateMeta(&document); 169 details.has_notranslate = HasNoTranslateMeta(&document);
178 details.html_root_language = html_lang; 170 details.html_root_language = html_lang;
179 details.adopted_language = language; 171 details.adopted_language = language;
180 172
181 // TODO(hajimehoshi): If this affects performance, it should be set only if 173 // TODO(hajimehoshi): If this affects performance, it should be set only if
182 // translate-internals tab exists. 174 // translate-internals tab exists.
183 details.contents = contents; 175 details.contents = contents;
184 176
185 Send(new ChromeFrameHostMsg_TranslateLanguageDetermined( 177 // For the same render frame with the same url, each time when its texts are
186 routing_id(), details, !details.has_notranslate && !language.empty())); 178 // captured, it should be treated as a new page to do translation.
179 binding_.Close();
180 GetTranslateDriver()->RegisterPage(
181 binding_.CreateInterfacePtrAndBind(), details,
182 !details.has_notranslate && !language.empty());
187 } 183 }
188 184
189 void TranslateHelper::CancelPendingTranslation() { 185 void TranslateHelper::CancelPendingTranslation() {
190 weak_method_factory_.InvalidateWeakPtrs(); 186 weak_method_factory_.InvalidateWeakPtrs();
191 translation_pending_ = false; 187 // Make sure to send the cancelled response back.
188 if (translate_callback_pending_) {
189 translate_callback_pending_.Run(true, source_lang_, target_lang_,
190 TranslateErrors::NONE);
191 translate_callback_pending_.Reset();
192 }
192 source_lang_.clear(); 193 source_lang_.clear();
193 target_lang_.clear(); 194 target_lang_.clear();
194 } 195 }
195 196
196 //////////////////////////////////////////////////////////////////////////////// 197 ////////////////////////////////////////////////////////////////////////////////
197 // TranslateHelper, protected: 198 // TranslateHelper, protected:
198 // 199 //
199 bool TranslateHelper::IsTranslateLibAvailable() { 200 bool TranslateHelper::IsTranslateLibAvailable() {
200 return ExecuteScriptAndGetBoolResult( 201 return ExecuteScriptAndGetBoolResult(
201 "typeof cr != 'undefined' && typeof cr.googleTranslate != 'undefined' && " 202 "typeof cr != 'undefined' && typeof cr.googleTranslate != 'undefined' && "
202 "typeof cr.googleTranslate.translate == 'function'", false); 203 "typeof cr.googleTranslate.translate == 'function'",
204 false);
203 } 205 }
204 206
205 bool TranslateHelper::IsTranslateLibReady() { 207 bool TranslateHelper::IsTranslateLibReady() {
206 return ExecuteScriptAndGetBoolResult("cr.googleTranslate.libReady", false); 208 return ExecuteScriptAndGetBoolResult("cr.googleTranslate.libReady", false);
207 } 209 }
208 210
209 bool TranslateHelper::HasTranslationFinished() { 211 bool TranslateHelper::HasTranslationFinished() {
210 return ExecuteScriptAndGetBoolResult("cr.googleTranslate.finished", true); 212 return ExecuteScriptAndGetBoolResult("cr.googleTranslate.finished", true);
211 } 213 }
212 214
213 bool TranslateHelper::HasTranslationFailed() { 215 bool TranslateHelper::HasTranslationFailed() {
214 return ExecuteScriptAndGetBoolResult("cr.googleTranslate.error", true); 216 return ExecuteScriptAndGetBoolResult("cr.googleTranslate.error", true);
215 } 217 }
216 218
217 bool TranslateHelper::StartTranslation() { 219 bool TranslateHelper::StartTranslation() {
218 std::string script = "cr.googleTranslate.translate('" + 220 std::string script = "cr.googleTranslate.translate('" + source_lang_ + "','" +
Tom Sepez 2016/08/01 17:08:17 Note: pre-existing. Although this is invoked in r
leonhsl(Using Gerrit) 2016/08/02 02:52:23 Understood. I filed an issue crbug.com/633460 to d
219 source_lang_ + 221 target_lang_ + "')";
220 "','" +
221 target_lang_ +
222 "')";
223 return ExecuteScriptAndGetBoolResult(script, false); 222 return ExecuteScriptAndGetBoolResult(script, false);
224 } 223 }
225 224
226 std::string TranslateHelper::GetOriginalPageLanguage() { 225 std::string TranslateHelper::GetOriginalPageLanguage() {
227 return ExecuteScriptAndGetStringResult("cr.googleTranslate.sourceLang"); 226 return ExecuteScriptAndGetStringResult("cr.googleTranslate.sourceLang");
228 } 227 }
229 228
230 base::TimeDelta TranslateHelper::AdjustDelay(int delayInMs) { 229 base::TimeDelta TranslateHelper::AdjustDelay(int delayInMs) {
231 // Just converts |delayInMs| without any modification in practical cases. 230 // Just converts |delayInMs| without any modification in practical cases.
232 // Tests will override this function to return modified value. 231 // Tests will override this function to return modified value.
233 return base::TimeDelta::FromMilliseconds(delayInMs); 232 return base::TimeDelta::FromMilliseconds(delayInMs);
234 } 233 }
235 234
236 void TranslateHelper::ExecuteScript(const std::string& script) { 235 void TranslateHelper::ExecuteScript(const std::string& script) {
237 WebLocalFrame* main_frame = render_frame()->GetWebFrame(); 236 WebLocalFrame* main_frame = render_frame()->GetWebFrame();
238 if (!main_frame) 237 if (!main_frame)
239 return; 238 return;
240 239
241 WebScriptSource source = WebScriptSource(ASCIIToUTF16(script)); 240 WebScriptSource source = WebScriptSource(ASCIIToUTF16(script));
242 main_frame->executeScriptInIsolatedWorld( 241 main_frame->executeScriptInIsolatedWorld(world_id_, &source, 1,
243 world_id_, &source, 1, extension_group_); 242 extension_group_);
244 } 243 }
245 244
246 bool TranslateHelper::ExecuteScriptAndGetBoolResult(const std::string& script, 245 bool TranslateHelper::ExecuteScriptAndGetBoolResult(const std::string& script,
247 bool fallback) { 246 bool fallback) {
248 WebLocalFrame* main_frame = render_frame()->GetWebFrame(); 247 WebLocalFrame* main_frame = render_frame()->GetWebFrame();
249 if (!main_frame) 248 if (!main_frame)
250 return fallback; 249 return fallback;
251 250
252 v8::HandleScope handle_scope(v8::Isolate::GetCurrent()); 251 v8::HandleScope handle_scope(v8::Isolate::GetCurrent());
253 WebVector<v8::Local<v8::Value> > results; 252 WebVector<v8::Local<v8::Value>> results;
254 WebScriptSource source = WebScriptSource(ASCIIToUTF16(script)); 253 WebScriptSource source = WebScriptSource(ASCIIToUTF16(script));
255 main_frame->executeScriptInIsolatedWorld( 254 main_frame->executeScriptInIsolatedWorld(world_id_, &source, 1,
256 world_id_, &source, 1, extension_group_, &results); 255 extension_group_, &results);
257 if (results.size() != 1 || results[0].IsEmpty() || !results[0]->IsBoolean()) { 256 if (results.size() != 1 || results[0].IsEmpty() || !results[0]->IsBoolean()) {
258 NOTREACHED(); 257 NOTREACHED();
259 return fallback; 258 return fallback;
260 } 259 }
261 260
262 return results[0]->BooleanValue(); 261 return results[0]->BooleanValue();
263 } 262 }
264 263
265 std::string TranslateHelper::ExecuteScriptAndGetStringResult( 264 std::string TranslateHelper::ExecuteScriptAndGetStringResult(
266 const std::string& script) { 265 const std::string& script) {
267 WebLocalFrame* main_frame = render_frame()->GetWebFrame(); 266 WebLocalFrame* main_frame = render_frame()->GetWebFrame();
268 if (!main_frame) 267 if (!main_frame)
269 return std::string(); 268 return std::string();
270 269
271 v8::HandleScope handle_scope(v8::Isolate::GetCurrent()); 270 v8::HandleScope handle_scope(v8::Isolate::GetCurrent());
272 WebVector<v8::Local<v8::Value> > results; 271 WebVector<v8::Local<v8::Value>> results;
273 WebScriptSource source = WebScriptSource(ASCIIToUTF16(script)); 272 WebScriptSource source = WebScriptSource(ASCIIToUTF16(script));
274 main_frame->executeScriptInIsolatedWorld( 273 main_frame->executeScriptInIsolatedWorld(world_id_, &source, 1,
275 world_id_, &source, 1, extension_group_, &results); 274 extension_group_, &results);
276 if (results.size() != 1 || results[0].IsEmpty() || !results[0]->IsString()) { 275 if (results.size() != 1 || results[0].IsEmpty() || !results[0]->IsString()) {
277 NOTREACHED(); 276 NOTREACHED();
278 return std::string(); 277 return std::string();
279 } 278 }
280 279
281 v8::Local<v8::String> v8_str = results[0].As<v8::String>(); 280 v8::Local<v8::String> v8_str = results[0].As<v8::String>();
282 int length = v8_str->Utf8Length() + 1; 281 int length = v8_str->Utf8Length() + 1;
283 std::unique_ptr<char[]> str(new char[length]); 282 std::unique_ptr<char[]> str(new char[length]);
284 v8_str->WriteUtf8(str.get(), length); 283 v8_str->WriteUtf8(str.get(), length);
285 return std::string(str.get()); 284 return std::string(str.get());
286 } 285 }
287 286
288 double TranslateHelper::ExecuteScriptAndGetDoubleResult( 287 double TranslateHelper::ExecuteScriptAndGetDoubleResult(
289 const std::string& script) { 288 const std::string& script) {
290 WebLocalFrame* main_frame = render_frame()->GetWebFrame(); 289 WebLocalFrame* main_frame = render_frame()->GetWebFrame();
291 if (!main_frame) 290 if (!main_frame)
292 return 0.0; 291 return 0.0;
293 292
294 v8::HandleScope handle_scope(v8::Isolate::GetCurrent()); 293 v8::HandleScope handle_scope(v8::Isolate::GetCurrent());
295 WebVector<v8::Local<v8::Value> > results; 294 WebVector<v8::Local<v8::Value>> results;
296 WebScriptSource source = WebScriptSource(ASCIIToUTF16(script)); 295 WebScriptSource source = WebScriptSource(ASCIIToUTF16(script));
297 main_frame->executeScriptInIsolatedWorld( 296 main_frame->executeScriptInIsolatedWorld(world_id_, &source, 1,
298 world_id_, &source, 1, extension_group_, &results); 297 extension_group_, &results);
299 if (results.size() != 1 || results[0].IsEmpty() || !results[0]->IsNumber()) { 298 if (results.size() != 1 || results[0].IsEmpty() || !results[0]->IsNumber()) {
300 NOTREACHED(); 299 NOTREACHED();
301 return 0.0; 300 return 0.0;
302 } 301 }
303 302
304 return results[0]->NumberValue(); 303 return results[0]->NumberValue();
305 } 304 }
306 305
307 //////////////////////////////////////////////////////////////////////////////// 306 // mojom::Page implementations.
308 // TranslateHelper, private: 307 void TranslateHelper::Translate(const std::string& translate_script,
309 // 308 const std::string& source_lang,
310 bool TranslateHelper::OnMessageReceived(const IPC::Message& message) { 309 const std::string& target_lang,
311 bool handled = true; 310 const TranslateCallback& callback) {
312 IPC_BEGIN_MESSAGE_MAP(TranslateHelper, message)
313 IPC_MESSAGE_HANDLER(ChromeFrameMsg_TranslatePage, OnTranslatePage)
314 IPC_MESSAGE_HANDLER(ChromeFrameMsg_RevertTranslation, OnRevertTranslation)
315 IPC_MESSAGE_UNHANDLED(handled = false)
316 IPC_END_MESSAGE_MAP()
317 return handled;
318 }
319
320 void TranslateHelper::OnTranslatePage(int page_seq_no,
321 const std::string& translate_script,
322 const std::string& source_lang,
323 const std::string& target_lang) {
324 WebLocalFrame* main_frame = render_frame()->GetWebFrame(); 311 WebLocalFrame* main_frame = render_frame()->GetWebFrame();
325 if (!main_frame || page_seq_no_ != page_seq_no) 312 if (!main_frame) {
313 // Cancelled.
314 callback.Run(true, source_lang, target_lang, TranslateErrors::NONE);
326 return; // We navigated away, nothing to do. 315 return; // We navigated away, nothing to do.
316 }
327 317
328 // A similar translation is already under way, nothing to do. 318 // A similar translation is already under way, nothing to do.
329 if (translation_pending_ && target_lang_ == target_lang) 319 if (translate_callback_pending_ && target_lang_ == target_lang) {
320 // This request is ignored.
321 callback.Run(true, source_lang, target_lang, TranslateErrors::NONE);
330 return; 322 return;
323 }
331 324
332 // Any pending translation is now irrelevant. 325 // Any pending translation is now irrelevant.
333 CancelPendingTranslation(); 326 CancelPendingTranslation();
334 327
335 // Set our states. 328 // Set our states.
336 translation_pending_ = true; 329 translate_callback_pending_ = callback;
337 330
338 // If the source language is undetermined, we'll let the translate element 331 // If the source language is undetermined, we'll let the translate element
339 // detect it. 332 // detect it.
340 source_lang_ = (source_lang != kUnknownLanguageCode) ? source_lang 333 source_lang_ = (source_lang != kUnknownLanguageCode) ? source_lang
341 : kAutoDetectionLanguage; 334 : kAutoDetectionLanguage;
342 target_lang_ = target_lang; 335 target_lang_ = target_lang;
343 336
344 ReportUserActionDuration(language_determined_time_, base::TimeTicks::Now()); 337 ReportUserActionDuration(language_determined_time_, base::TimeTicks::Now());
345 338
346 GURL url(main_frame->document().url()); 339 GURL url(main_frame->document().url());
347 ReportPageScheme(url.scheme()); 340 ReportPageScheme(url.scheme());
348 341
349 // Set up v8 isolated world with proper content-security-policy and 342 // Set up v8 isolated world with proper content-security-policy and
350 // security-origin. 343 // security-origin.
351 main_frame->setIsolatedWorldContentSecurityPolicy( 344 main_frame->setIsolatedWorldContentSecurityPolicy(
352 world_id_, WebString::fromUTF8(kContentSecurityPolicy)); 345 world_id_, WebString::fromUTF8(kContentSecurityPolicy));
353 346
354 GURL security_origin = GetTranslateSecurityOrigin(); 347 GURL security_origin = GetTranslateSecurityOrigin();
355 main_frame->setIsolatedWorldSecurityOrigin( 348 main_frame->setIsolatedWorldSecurityOrigin(
356 world_id_, WebSecurityOrigin::create(security_origin)); 349 world_id_, WebSecurityOrigin::create(security_origin));
357 350
358 if (!IsTranslateLibAvailable()) { 351 if (!IsTranslateLibAvailable()) {
359 // Evaluate the script to add the translation related method to the global 352 // Evaluate the script to add the translation related method to the global
360 // context of the page. 353 // context of the page.
361 ExecuteScript(translate_script); 354 ExecuteScript(translate_script);
362 DCHECK(IsTranslateLibAvailable()); 355 DCHECK(IsTranslateLibAvailable());
363 } 356 }
364 357
365 TranslatePageImpl(page_seq_no, 0); 358 TranslatePageImpl(0);
366 } 359 }
367 360
368 void TranslateHelper::OnRevertTranslation(int page_seq_no) { 361 void TranslateHelper::RevertTranslation() {
369 if (page_seq_no_ != page_seq_no)
370 return; // We navigated away, nothing to do.
371
372 if (!IsTranslateLibAvailable()) { 362 if (!IsTranslateLibAvailable()) {
373 NOTREACHED(); 363 NOTREACHED();
374 return; 364 return;
375 } 365 }
376 366
377 CancelPendingTranslation(); 367 CancelPendingTranslation();
378 368
379 ExecuteScript("cr.googleTranslate.revert()"); 369 ExecuteScript("cr.googleTranslate.revert()");
380 } 370 }
381 371
382 void TranslateHelper::CheckTranslateStatus(int page_seq_no) { 372 ////////////////////////////////////////////////////////////////////////////////
383 // If this is not the same page, the translation has been canceled. 373 // TranslateHelper, private:
384 if (page_seq_no_ != page_seq_no) 374 //
385 return; 375 void TranslateHelper::CheckTranslateStatus() {
386
387 // First check if there was an error. 376 // First check if there was an error.
388 if (HasTranslationFailed()) { 377 if (HasTranslationFailed()) {
389 // TODO(toyoshim): Check |errorCode| of translate.js and notify it here. 378 // TODO(toyoshim): Check |errorCode| of translate.js and notify it here.
390 NotifyBrowserTranslationFailed(TranslateErrors::TRANSLATION_ERROR); 379 NotifyBrowserTranslationFailed(TranslateErrors::TRANSLATION_ERROR);
391 return; // There was an error. 380 return; // There was an error.
392 } 381 }
393 382
394 if (HasTranslationFinished()) { 383 if (HasTranslationFinished()) {
395 std::string actual_source_lang; 384 std::string actual_source_lang;
396 // Translation was successfull, if it was auto, retrieve the source 385 // Translation was successfull, if it was auto, retrieve the source
397 // language the Translate Element detected. 386 // language the Translate Element detected.
398 if (source_lang_ == kAutoDetectionLanguage) { 387 if (source_lang_ == kAutoDetectionLanguage) {
399 actual_source_lang = GetOriginalPageLanguage(); 388 actual_source_lang = GetOriginalPageLanguage();
400 if (actual_source_lang.empty()) { 389 if (actual_source_lang.empty()) {
401 NotifyBrowserTranslationFailed(TranslateErrors::UNKNOWN_LANGUAGE); 390 NotifyBrowserTranslationFailed(TranslateErrors::UNKNOWN_LANGUAGE);
402 return; 391 return;
403 } else if (actual_source_lang == target_lang_) { 392 } else if (actual_source_lang == target_lang_) {
404 NotifyBrowserTranslationFailed(TranslateErrors::IDENTICAL_LANGUAGES); 393 NotifyBrowserTranslationFailed(TranslateErrors::IDENTICAL_LANGUAGES);
405 return; 394 return;
406 } 395 }
407 } else { 396 } else {
408 actual_source_lang = source_lang_; 397 actual_source_lang = source_lang_;
409 } 398 }
410 399
411 if (!translation_pending_) { 400 if (!translate_callback_pending_) {
412 NOTREACHED(); 401 NOTREACHED();
413 return; 402 return;
414 } 403 }
415 404
416 translation_pending_ = false;
417
418 // Check JavaScript performance counters for UMA reports. 405 // Check JavaScript performance counters for UMA reports.
419 ReportTimeToTranslate( 406 ReportTimeToTranslate(
420 ExecuteScriptAndGetDoubleResult("cr.googleTranslate.translationTime")); 407 ExecuteScriptAndGetDoubleResult("cr.googleTranslate.translationTime"));
421 408
422 // Notify the browser we are done. 409 // Notify the browser we are done.
423 render_frame()->Send(new ChromeFrameHostMsg_PageTranslated( 410 translate_callback_pending_.Run(false, actual_source_lang, target_lang_,
424 render_frame()->GetRoutingID(), actual_source_lang, target_lang_, 411 TranslateErrors::NONE);
425 TranslateErrors::NONE)); 412 translate_callback_pending_.Reset();
426 return; 413 return;
427 } 414 }
428 415
429 // The translation is still pending, check again later. 416 // The translation is still pending, check again later.
430 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask( 417 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
431 FROM_HERE, base::Bind(&TranslateHelper::CheckTranslateStatus, 418 FROM_HERE, base::Bind(&TranslateHelper::CheckTranslateStatus,
432 weak_method_factory_.GetWeakPtr(), page_seq_no), 419 weak_method_factory_.GetWeakPtr()),
433 AdjustDelay(kTranslateStatusCheckDelayMs)); 420 AdjustDelay(kTranslateStatusCheckDelayMs));
434 } 421 }
435 422
436 void TranslateHelper::TranslatePageImpl(int page_seq_no, int count) { 423 void TranslateHelper::TranslatePageImpl(int count) {
437 DCHECK_LT(count, kMaxTranslateInitCheckAttempts); 424 DCHECK_LT(count, kMaxTranslateInitCheckAttempts);
438 if (page_seq_no_ != page_seq_no)
439 return;
440
441 if (!IsTranslateLibReady()) { 425 if (!IsTranslateLibReady()) {
442 // The library is not ready, try again later, unless we have tried several 426 // The library is not ready, try again later, unless we have tried several
443 // times unsuccessfully already. 427 // times unsuccessfully already.
444 if (++count >= kMaxTranslateInitCheckAttempts) { 428 if (++count >= kMaxTranslateInitCheckAttempts) {
445 NotifyBrowserTranslationFailed(TranslateErrors::INITIALIZATION_ERROR); 429 NotifyBrowserTranslationFailed(TranslateErrors::INITIALIZATION_ERROR);
446 return; 430 return;
447 } 431 }
448 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask( 432 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
449 FROM_HERE, 433 FROM_HERE, base::Bind(&TranslateHelper::TranslatePageImpl,
450 base::Bind(&TranslateHelper::TranslatePageImpl, 434 weak_method_factory_.GetWeakPtr(), count),
451 weak_method_factory_.GetWeakPtr(), page_seq_no, count),
452 AdjustDelay(count * kTranslateInitCheckDelayMs)); 435 AdjustDelay(count * kTranslateInitCheckDelayMs));
453 return; 436 return;
454 } 437 }
455 438
456 // The library is loaded, and ready for translation now. 439 // The library is loaded, and ready for translation now.
457 // Check JavaScript performance counters for UMA reports. 440 // Check JavaScript performance counters for UMA reports.
458 ReportTimeToBeReady( 441 ReportTimeToBeReady(
459 ExecuteScriptAndGetDoubleResult("cr.googleTranslate.readyTime")); 442 ExecuteScriptAndGetDoubleResult("cr.googleTranslate.readyTime"));
460 ReportTimeToLoad( 443 ReportTimeToLoad(
461 ExecuteScriptAndGetDoubleResult("cr.googleTranslate.loadTime")); 444 ExecuteScriptAndGetDoubleResult("cr.googleTranslate.loadTime"));
462 445
463 if (!StartTranslation()) { 446 if (!StartTranslation()) {
464 NotifyBrowserTranslationFailed(TranslateErrors::TRANSLATION_ERROR); 447 NotifyBrowserTranslationFailed(TranslateErrors::TRANSLATION_ERROR);
465 return; 448 return;
466 } 449 }
467 // Check the status of the translation. 450 // Check the status of the translation.
468 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask( 451 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
469 FROM_HERE, base::Bind(&TranslateHelper::CheckTranslateStatus, 452 FROM_HERE, base::Bind(&TranslateHelper::CheckTranslateStatus,
470 weak_method_factory_.GetWeakPtr(), page_seq_no), 453 weak_method_factory_.GetWeakPtr()),
471 AdjustDelay(kTranslateStatusCheckDelayMs)); 454 AdjustDelay(kTranslateStatusCheckDelayMs));
472 } 455 }
473 456
474 void TranslateHelper::NotifyBrowserTranslationFailed( 457 void TranslateHelper::NotifyBrowserTranslationFailed(
475 TranslateErrors::Type error) { 458 TranslateErrors::Type error) {
476 translation_pending_ = false; 459 DCHECK(translate_callback_pending_);
477 // Notify the browser there was an error. 460 // Notify the browser there was an error.
478 render_frame()->Send(new ChromeFrameHostMsg_PageTranslated( 461 translate_callback_pending_.Run(false, source_lang_, target_lang_, error);
479 render_frame()->GetRoutingID(), source_lang_, target_lang_, error)); 462 translate_callback_pending_.Reset();
463 }
464
465 const mojom::ContentTranslateDriverPtr& TranslateHelper::GetTranslateDriver() {
466 if (!translate_driver_) {
467 render_frame()->GetRemoteInterfaces()->GetInterface(
468 mojo::GetProxy(&translate_driver_));
469 }
470
471 return translate_driver_;
480 } 472 }
481 473
482 void TranslateHelper::OnDestruct() { 474 void TranslateHelper::OnDestruct() {
483 delete this; 475 delete this;
484 } 476 }
485 477
486 } // namespace translate 478 } // namespace translate
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698