1 // Copyright (c) 2011 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 #ifndef CHROME_RENDERER_TRANSLATE_TRANSLATE_HELPER_H_
6 #define CHROME_RENDERER_TRANSLATE_TRANSLATE_HELPER_H_
10 #if defined(CLD2_DYNAMIC_MODE)
11 #include "base/files/memory_mapped_file.h"
13 #include "base/gtest_prod_util.h"
14 #if defined(CLD2_DYNAMIC_MODE)
15 #include "base/lazy_instance.h"
17 #include "base/memory/weak_ptr.h"
18 #include "base/time/time.h"
19 #include "components/translate/core/common/translate_errors.h"
20 #include "content/public/renderer/render_view_observer.h"
21 #if defined(CLD2_DYNAMIC_MODE)
22 #include "ipc/ipc_platform_file.h"
31 // This class deals with page translation.
32 // There is one TranslateHelper per RenderView.
34 class TranslateHelper
: public content::RenderViewObserver
{
36 explicit TranslateHelper(content::RenderView
* render_view
);
37 virtual ~TranslateHelper();
39 // Informs us that the page's text has been extracted.
40 void PageCaptured(int page_id
, const base::string16
& contents
);
42 // Lets the translation system know that we are preparing to navigate to
43 // the specified URL. If there is anything that can or should be done before
44 // this URL loads, this is the time to prepare for it.
45 void PrepareForUrl(const GURL
& url
);
48 // The following methods are protected so they can be overridden in
50 void OnTranslatePage(int page_id
,
51 const std::string
& translate_script
,
52 const std::string
& source_lang
,
53 const std::string
& target_lang
);
54 void OnRevertTranslation(int page_id
);
56 // Returns true if the translate library is available, meaning the JavaScript
57 // has already been injected in that page.
58 virtual bool IsTranslateLibAvailable();
60 // Returns true if the translate library has been initialized successfully.
61 virtual bool IsTranslateLibReady();
63 // Returns true if the translation script has finished translating the page.
64 virtual bool HasTranslationFinished();
66 // Returns true if the translation script has reported an error performing the
68 virtual bool HasTranslationFailed();
70 // Starts the translation by calling the translate library. This method
71 // should only be called when the translate script has been injected in the
72 // page. Returns false if the call failed immediately.
73 virtual bool StartTranslation();
75 // Asks the Translate element in the page what the language of the page is.
76 // Can only be called if a translation has happened and was successful.
77 // Returns the language code on success, an empty string on failure.
78 virtual std::string
GetOriginalPageLanguage();
80 // Adjusts a delay time for a posted task. This is used in tests to do tasks
81 // immediately by returning 0.
82 virtual base::TimeDelta
AdjustDelay(int delayInMs
);
84 // Executes the JavaScript code in |script| in the main frame of RenderView.
85 virtual void ExecuteScript(const std::string
& script
);
87 // Executes the JavaScript code in |script| in the main frame of RenderView,
88 // and returns the boolean returned by the script evaluation if the script was
89 // run successfully. Otherwise, returns |fallback| value.
90 virtual bool ExecuteScriptAndGetBoolResult(const std::string
& script
,
93 // Executes the JavaScript code in |script| in the main frame of RenderView,
94 // and returns the string returned by the script evaluation if the script was
95 // run successfully. Otherwise, returns empty string.
96 virtual std::string
ExecuteScriptAndGetStringResult(
97 const std::string
& script
);
99 // Executes the JavaScript code in |script| in the main frame of RenderView.
100 // and returns the number returned by the script evaluation if the script was
101 // run successfully. Otherwise, returns 0.0.
102 virtual double ExecuteScriptAndGetDoubleResult(const std::string
& script
);
105 FRIEND_TEST_ALL_PREFIXES(TranslateHelperTest
, AdoptHtmlLang
);
106 FRIEND_TEST_ALL_PREFIXES(TranslateHelperTest
,
107 CLDAgreeWithLanguageCodeHavingCountryCode
);
108 FRIEND_TEST_ALL_PREFIXES(TranslateHelperTest
,
109 CLDDisagreeWithWrongLanguageCode
);
110 FRIEND_TEST_ALL_PREFIXES(TranslateHelperTest
,
111 InvalidLanguageMetaTagProviding
);
112 FRIEND_TEST_ALL_PREFIXES(TranslateHelperTest
, LanguageCodeTypoCorrection
);
113 FRIEND_TEST_ALL_PREFIXES(TranslateHelperTest
, LanguageCodeSynonyms
);
114 FRIEND_TEST_ALL_PREFIXES(TranslateHelperTest
, ResetInvalidLanguageCode
);
115 FRIEND_TEST_ALL_PREFIXES(TranslateHelperTest
, SimilarLanguageCode
);
116 FRIEND_TEST_ALL_PREFIXES(TranslateHelperTest
, WellKnownWrongConfiguration
);
118 // Converts language code to the one used in server supporting list.
119 static void ConvertLanguageCodeSynonym(std::string
* code
);
121 // Returns whether the page associated with |document| is a candidate for
122 // translation. Some pages can explictly specify (via a meta-tag) that they
123 // should not be translated.
124 static bool IsTranslationAllowed(blink::WebDocument
* document
);
126 // RenderViewObserver implementation.
127 virtual bool OnMessageReceived(const IPC::Message
& message
) OVERRIDE
;
129 // Cancels any translation that is currently being performed. This does not
130 // revert existing translations.
131 void CancelPendingTranslation();
133 // Checks if the current running page translation is finished or errored and
134 // notifies the browser accordingly. If the translation has not terminated,
135 // posts a task to check again later.
136 void CheckTranslateStatus();
138 // Called by TranslatePage to do the actual translation. |count| is used to
139 // limit the number of retries.
140 void TranslatePageImpl(int count
);
142 // Sends a message to the browser to notify it that the translation failed
144 void NotifyBrowserTranslationFailed(TranslateErrors::Type error
);
146 // Convenience method to access the main frame. Can return NULL, typically
147 // if the page is being closed.
148 blink::WebFrame
* GetMainFrame();
150 // ID to represent a page which TranslateHelper captured and determined a
154 // The states associated with the current translation.
155 bool translation_pending_
;
156 std::string source_lang_
;
157 std::string target_lang_
;
159 // Time when a page langauge is determined. This is used to know a duration
160 // time from showing infobar to requesting translation.
161 base::TimeTicks language_determined_time_
;
163 // Method factory used to make calls to TranslatePageImpl.
164 base::WeakPtrFactory
<TranslateHelper
> weak_method_factory_
;
166 #if defined(CLD2_DYNAMIC_MODE)
167 // Do not ask for CLD data any more.
168 void CancelCLD2DataFilePolling();
170 // Invoked when PageCaptured is called prior to obtaining CLD data. This
171 // method stores the page ID into deferred_page_id_ and COPIES the contents
172 // of the page, then sets deferred_page_capture_ to true. When CLD data is
173 // eventually received (in OnCLDDataAvailable), any deferred request will be
174 // "resurrected" and allowed to proceed automatically, assuming that the
175 // page ID has not changed.
176 void DeferPageCaptured(const int page_id
, const base::string16
& contents
);
178 // Immediately send an IPC request to the browser process to get the CLD
179 // data file. In most cases, the file will already exist and we will only
180 // poll once; but since the file might need to be downloaded first, poll
181 // indefinitely until a ChromeViewMsg_CLDDataAvailable message is received
182 // from the browser process.
183 // Polling will automatically halt as soon as the renderer obtains a
184 // reference to the data file.
185 void SendCLD2DataFileRequest(const int delay_millis
,
186 const int next_delay_millis
);
188 // Invoked when a ChromeViewMsg_CLDDataAvailable message is received from
189 // the browser process, providing a file handle for the CLD data file. If a
190 // PageCaptured request was previously deferred with DeferPageCaptured and
191 // the page ID has not yet changed, the PageCaptured is reinvoked to
192 // "resurrect" the language detection pathway.
193 void OnCLDDataAvailable(const IPC::PlatformFileForTransit ipc_file_handle
,
194 const uint64 data_offset
,
195 const uint64 data_length
);
197 // After receiving data in OnCLDDataAvailable, loads the data into CLD2.
198 void LoadCLDDData(const IPC::PlatformFileForTransit ipc_file_handle
,
199 const uint64 data_offset
,
200 const uint64 data_length
);
202 // A struct that contains the pointer to the CLD mmap. Used so that we can
203 // leverage LazyInstance:Leaky to properly scope the lifetime of the mmap.
204 struct CLDMmapWrapper
{
208 base::MemoryMappedFile
* value
;
210 static base::LazyInstance
<CLDMmapWrapper
>::Leaky s_cld_mmap_
;
212 // Whether or not polling for CLD2 data has started.
213 bool cld2_data_file_polling_started_
;
215 // Whether or not CancelCLD2DataFilePolling has been called.
216 bool cld2_data_file_polling_canceled_
;
218 // Whether or not a PageCaptured event arrived prior to CLD data becoming
219 // available. If true, deferred_page_id_ contains the most recent page ID
220 // and deferred_contents_ contains the most recent contents.
221 bool deferred_page_capture_
;
223 // The ID of the page most recently reported to PageCaptured if
224 // deferred_page_capture_ is true.
225 int deferred_page_id_
;
227 // The contents of the page most recently reported to PageCaptured if
228 // deferred_page_capture_ is true.
229 base::string16 deferred_contents_
;
233 DISALLOW_COPY_AND_ASSIGN(TranslateHelper
);
236 #endif // CHROME_RENDERER_TRANSLATE_TRANSLATE_HELPER_H_