blob: 51a15afd58033c7ee51e5727266de08d16be6a87 [file] [log] [blame]
#!/usr/bin/python
# Copyright (c) 2011 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.
import glob
import logging
import os
import shutil
import tempfile
import pyauto_functional # Must be imported before pyauto
import pyauto
class TranslateTest(pyauto.PyUITest):
"""Tests that translate works correctly"""
spanish = 'es'
after_translate = 'AFTER_TRANSLATE'
before_translate = 'BEFORE_TRANSLATE'
translating = 'TRANSLATING'
translation_error = 'TRANSLATION_ERROR'
def Debug(self):
""" Test method for experimentation. """
while True:
raw_input('Hit <enter> to dump translate info.. ')
self.pprint(self.GetTranslateInfo())
def _GetDefaultSpanishURL(self):
return self.GetFileURLForDataPath('translate', self.spanish, 'google.html')
def _GetDefaultEnglishURL(self):
return self.GetFileURLForDataPath('title1.html')
def _NavigateAndWaitForBar(self, url, window_index=0, tab_index=0):
self.NavigateToURL(url, window_index, tab_index)
self.assertTrue(self.WaitForInfobarCount(
1, windex=window_index, tab_index=tab_index))
def _ClickTranslateUntilSuccess(self, window_index=0, tab_index=0):
"""Since the translate can fail due to server error, continue trying until
it is successful or until it has tried too many times."""
max_tries = 10
curr_try = 0
while (curr_try < max_tries and
not self.ClickTranslateBarTranslate(window_index=window_index,
tab_index=tab_index)):
curr_try = curr_try + 1
if curr_try == max_tries:
self.fail('Translation failed more than %d times.' % max_tries)
def _AssertTranslateWorks(self, url, original_language):
"""Translate the page at the given URL and assert that the page has been
translated.
"""
self._NavigateAndWaitForBar(url)
translate_info = self.GetTranslateInfo()
self.assertEqual(original_language, translate_info['original_language'])
self.assertFalse(translate_info['page_translated'])
self.assertTrue(translate_info['can_translate_page'])
self.assertTrue('translate_bar' in translate_info)
self._ClickTranslateUntilSuccess()
translate_info = self.GetTranslateInfo()
self.assertTrue(translate_info['can_translate_page'])
self.assertTrue('translate_bar' in translate_info)
translate_bar = translate_info['translate_bar']
self.assertEquals(self.after_translate,
translate_info['translate_bar']['bar_state'])
self.assertEquals(original_language,
translate_bar['original_lang_code'])
def testTranslate(self):
"""Tests that a page was translated if the user chooses to translate."""
self._AssertTranslateWorks(self._GetDefaultSpanishURL(), self.spanish)
def testNoTranslate(self):
"""Tests that a page isn't translated if the user declines translate."""
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
self.SelectTranslateOption('decline_translation')
translate_info = self.GetTranslateInfo()
self.assertEqual(self.spanish, translate_info['original_language'])
self.assertFalse(translate_info['page_translated'])
self.assertTrue(translate_info['can_translate_page'])
# If the user goes to the site again, the infobar should drop down but
# the page should not be automatically translated.
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
translate_info = self.GetTranslateInfo()
self.assertFalse(translate_info['page_translated'])
self.assertTrue(translate_info['can_translate_page'])
self.assertTrue('translate_bar' in translate_info)
self.assertEquals(self.before_translate,
translate_info['translate_bar']['bar_state'])
def testNeverTranslateLanguage(self):
"""Tests that blacklisting a language for translate works."""
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
self.SelectTranslateOption('never_translate_language')
translate_info = self.GetTranslateInfo()
self.assertEqual(self.spanish, translate_info['original_language'])
self.assertFalse(translate_info['page_translated'])
self.assertFalse(translate_info['can_translate_page'])
spanish_wikipedia = 'http://es.wikipedia.org/wiki/Wikipedia:Portada'
self.NavigateToURL(spanish_wikipedia)
translate_info = self.GetTranslateInfo()
self.assertEqual(self.spanish, translate_info['original_language'])
self.assertFalse(translate_info['page_translated'])
self.assertFalse(translate_info['can_translate_page'])
def testAlwaysTranslateLanguage(self):
"""Tests that the always translate a language option works."""
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
self.SelectTranslateOption('toggle_always_translate')
self._ClickTranslateUntilSuccess()
translate_info = self.GetTranslateInfo()
self.assertEquals(self.spanish, translate_info['original_language'])
self.assertTrue(translate_info['page_translated'])
self.assertTrue(translate_info['can_translate_page'])
self.assertTrue('translate_bar' in translate_info)
self.assertEquals(self.after_translate,
translate_info['translate_bar']['bar_state'])
# Go to another spanish site and verify that it is translated.
# Note that the 'This page has been translated..." bar will show up.
self._NavigateAndWaitForBar(
'http://es.wikipedia.org/wiki/Wikipedia:Portada')
translate_info = self.GetTranslateInfo()
self.assertTrue('translate_bar' in translate_info)
curr_bar_state = translate_info['translate_bar']['bar_state']
# We don't care whether the translation has finished, just that it is
# trying to translate.
self.assertTrue(curr_bar_state is self.after_translate or
self.translating or self.translation_error,
'Bar state was %s.' % curr_bar_state)
def testNeverTranslateSite(self):
"""Tests that blacklisting a site for translate works."""
spanish_google = 'http://www.google.com/webhp?hl=es'
self._NavigateAndWaitForBar(spanish_google)
self.SelectTranslateOption('never_translate_site')
translate_info = self.GetTranslateInfo()
self.assertFalse(translate_info['page_translated'])
self.assertFalse(translate_info['can_translate_page'])
french_google = 'http://www.google.com/webhp?hl=fr'
# Go to another page in the same site and verify that the page can't be
# translated even though it's in a different language.
self.NavigateToURL(french_google)
translate_info = self.GetTranslateInfo()
self.assertFalse(translate_info['page_translated'])
self.assertFalse(translate_info['can_translate_page'])
def testRevert(self):
"""Tests that reverting a site to its original language works."""
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
self._ClickTranslateUntilSuccess()
self.RevertPageTranslation()
translate_info = self.GetTranslateInfo()
self.assertFalse(translate_info['page_translated'])
self.assertTrue(translate_info['can_translate_page'])
def testBarNotVisibleOnSSLErrorPage(self):
"""Test Translate bar is not visible on SSL error pages."""
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
translate_info = self.GetTranslateInfo()
self.assertTrue('translate_bar' in translate_info)
self.assertTrue(translate_info['can_translate_page'])
# This page is an ssl error page.
self.NavigateToURL('https://www.sourceforge.net')
self.assertTrue(self.WaitForInfobarCount(0))
translate_info = self.GetTranslateInfo()
self.assertFalse('translate_bar' in translate_info)
def testBarNotVisibleOnEnglishPage(self):
"""Test Translate bar is not visible on English pages."""
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
translate_info = self.GetTranslateInfo()
self.assertTrue('translate_bar' in translate_info)
self.assertTrue(translate_info['can_translate_page'])
# With the translate bar visible in same tab open an English page.
self.NavigateToURL(self._GetDefaultEnglishURL())
self.assertTrue(self.WaitForInfobarCount(0))
translate_info = self.GetTranslateInfo()
self.assertFalse('translate_bar' in translate_info)
def testTranslateDiffURLs(self):
"""Test that HTTP, HTTPS, and file urls all get translated."""
http_url = 'http://www.google.com/webhp?hl=es'
https_url = 'https://www.google.com/webhp?hl=es'
file_url = self._GetDefaultSpanishURL()
for url in (http_url, https_url, file_url):
self._AssertTranslateWorks(url, self.spanish)
def testNotranslateMetaTag(self):
"""Test "notranslate" meta tag."""
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
self.NavigateToURL(self.GetFileURLForDataPath(
'translate', 'notranslate_meta_tag.html'))
self.assertTrue(self.WaitForInfobarCount(0))
translate_info = self.GetTranslateInfo()
self.assertFalse('translate_bar' in translate_info)
def testToggleTranslateOption(self):
"""Test to toggle the 'Always Translate' option."""
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
# Assert the default.
translate_info = self.GetTranslateInfo()
self.assertFalse(translate_info['page_translated'])
self.assertTrue('translate_bar' in translate_info)
# Select 'Always Translate'.
self.SelectTranslateOption('toggle_always_translate')
self._ClickTranslateUntilSuccess()
translate_info = self.GetTranslateInfo()
self.assertTrue(translate_info['page_translated'])
# Reload the tab and confirm the page was translated.
self.GetBrowserWindow(0).GetTab(0).Reload()
self.assertTrue(self.WaitForInfobarCount(1))
success = self.WaitUntilTranslateComplete()
# Sometimes the translation fails. Continue clicking until it succeeds.
if not success:
self._ClickTranslateUntilSuccess()
# Uncheck 'Always Translate'
self.SelectTranslateOption('toggle_always_translate')
self.PerformActionOnInfobar('dismiss', 0)
translate_info = self.GetTranslateInfo()
self.assertTrue(translate_info['page_translated'])
self.assertFalse('translate_bar' in translate_info)
# Reload the tab and confirm that the page has not been translated.
self.GetBrowserWindow(0).GetTab(0).Reload()
translate_info = self.GetTranslateInfo()
self.assertFalse(translate_info['page_translated'])
self.assertTrue('translate_bar' in translate_info)
def testSessionRestore(self):
"""Test that session restore restores the translate infobar and other
translate settings.
"""
# Due to crbug.com/51439, we must open two tabs here.
self.NavigateToURL("http://www.news.google.com")
self.AppendTab(pyauto.GURL("http://www.google.com/webhp?hl=es"))
self.assertTrue(self.WaitForInfobarCount(1, tab_index=1))
translate_info = self.GetTranslateInfo(tab_index=1)
self.assertTrue('translate_bar' in translate_info)
self.SelectTranslateOption('toggle_always_translate', tab_index=1)
self._ClickTranslateUntilSuccess(tab_index=1)
self.SetPrefs(pyauto.kRestoreOnStartup, 1)
self.RestartBrowser(clear_profile=False)
self.assertTrue(self.WaitForInfobarCount(1, tab_index=1))
self.WaitUntilTranslateComplete(tab_index=1)
translate_info = self.GetTranslateInfo(tab_index=1)
self.assertTrue('translate_bar' in translate_info)
# Sometimes translation fails. We don't really care whether it succeededs,
# just that a translation was attempted.
self.assertNotEqual(self.before_translate,
translate_info['translate_bar']['bar_state'])
def testGoBackAndForwardToTranslatePage(self):
"""Tests that translate bar re-appears after backward and forward
navigation to a page that can be translated.
"""
no_trans_url = self._GetDefaultEnglishURL()
trans_url = self._GetDefaultSpanishURL()
self._NavigateAndWaitForBar(trans_url)
translate_info = self.GetTranslateInfo()
self.assertTrue('translate_bar' in translate_info)
self.NavigateToURL(no_trans_url)
self.assertTrue(self.WaitForInfobarCount(0))
self.assertFalse('translate_bar' in self.GetTranslateInfo())
# Go back to the page that should be translated and assert that the
# translate bar re-appears.
self.GetBrowserWindow(0).GetTab(0).GoBack()
self.assertTrue(self.WaitForInfobarCount(1))
self.assertTrue('translate_bar' in self.GetTranslateInfo())
# Now test going forward.
self.NavigateToURL(no_trans_url)
translate_info = self.GetTranslateInfo()
self.assertFalse('translate_bar' in translate_info)
self._AssertTranslateWorks(trans_url, self.spanish)
self.GetBrowserWindow(0).GetTab(0).GoBack()
self.assertTrue(self.WaitForInfobarCount(0))
translate_info = self.GetTranslateInfo()
self.assertFalse('translate_bar' in translate_info)
self.GetBrowserWindow(0).GetTab(0).GoForward()
self.assertTrue(self.WaitForInfobarCount(1))
translate_info = self.GetTranslateInfo()
self.assertTrue(translate_info['can_translate_page'])
self.assertTrue('translate_bar' in translate_info)
def testForCrashedTab(self):
"""Tests that translate bar is dimissed if the renderer crashes."""
crash_url = 'about:crash'
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
translate_info = self.GetTranslateInfo()
self.assertTrue('translate_bar' in translate_info)
self.NavigateToURL(crash_url)
self.assertTrue(self.WaitForInfobarCount(0))
self.assertFalse('translate_bar' in self.GetTranslateInfo())
def testTranslatePrefs(self):
"""Test the Prefs:Translate option."""
# Assert defaults first.
self.assertTrue(self.GetPrefsInfo().Prefs(pyauto.kEnableTranslate))
# Uncheck.
self.SetPrefs(pyauto.kEnableTranslate, False)
self.NavigateToURL(self._GetDefaultSpanishURL())
self.assertFalse('translate_bar' in self.GetTranslateInfo())
# Restart the browser and assert the translate preference stays.
self.RestartBrowser(clear_profile=False)
self.assertFalse(self.GetPrefsInfo().Prefs(pyauto.kEnableTranslate))
self.NavigateToURL(self._GetDefaultSpanishURL())
self.assertFalse('translate_bar' in self.GetTranslateInfo())
def testAlwaysTranslateLanguageButton(self):
"""Test the always translate language button."""
spanish_url = self._GetDefaultSpanishURL()
self._NavigateAndWaitForBar(spanish_url)
# The 'Always Translate' button doesn't show up until the user has clicked
# 'Translate' for a language 3 times.
for unused in range(3):
self._ClickTranslateUntilSuccess()
self.GetBrowserWindow(0).GetTab(0).Reload()
# Click the 'Always Translate' button.
self.assertTrue(self.GetTranslateInfo()\
['translate_bar']['always_translate_lang_button_showing'])
self.SelectTranslateOption('click_always_translate_lang_button')
# Navigate to another Spanish page and verify it was translated.
self._NavigateAndWaitForBar('http://www.google.com/webhp?hl=es')
self.WaitUntilTranslateComplete()
# Assert that a translation was attempted. We don't care if it was error
# or success.
self.assertNotEqual(self.before_translate,
self.GetTranslateInfo()['translate_bar']['bar_state'])
def testNeverTranslateLanguageButton(self):
"""Test the never translate language button."""
spanish_url = self._GetDefaultSpanishURL()
self._NavigateAndWaitForBar(spanish_url)
# The 'Never Translate' button doesn't show up until the user has clicked
# 'Nope' for a language 3 times.
for unused in range(3):
self.SelectTranslateOption('decline_translation')
self.GetBrowserWindow(0).GetTab(0).Reload()
# Click the 'Never Translate' button.
self.assertTrue(self.GetTranslateInfo()\
['translate_bar']['never_translate_lang_button_showing'])
self.SelectTranslateOption('click_never_translate_lang_button')
# Navigate to another Spanish page and verify the page can't be translated.
# First navigate to a French page, wait for bar, navigate to Spanish page
# and wait for bar to go away.
self._NavigateAndWaitForBar('http://www.google.com/webhp?hl=fr')
self.NavigateToURL('http://www.google.com/webhp?hl=es')
self.assertTrue(self.WaitForInfobarCount(0))
self.assertFalse(self.GetTranslateInfo()['can_translate_page'])
def testChangeTargetLanguageAlwaysTranslate(self):
"""Tests that the change target language option works with always translate
on reload.
This test is motivated by crbug.com/37313.
"""
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
self._ClickTranslateUntilSuccess()
# Select a different target language on translate info bar (French).
self.ChangeTranslateToLanguage('French')
translate_info = self.GetTranslateInfo()
self.assertTrue('translate_bar' in translate_info)
self.assertEqual('fr', translate_info['translate_bar']['target_lang_code'])
# Select always translate Spanish to French.
self.SelectTranslateOption('toggle_always_translate')
# Reload the page and assert that the page has been translated to French.
self.GetBrowserWindow(0).GetTab(0).Reload()
self.WaitUntilTranslateComplete()
translate_info = self.GetTranslateInfo()
self.assertTrue(translate_info['page_translated'])
self.assertTrue(translate_info['can_translate_page'])
self.assertTrue('translate_bar' in translate_info)
self.assertEqual('fr', translate_info['translate_bar']['target_lang_code'])
def testSeveralLanguages(self):
"""Verify translation for several languages.
This assumes that there is a directory of directories in the data dir.
The directory is called 'translate', and within that directory there are
subdirectories for each language code. Ex. a subdirectory 'es' with Spanish
html files.
"""
corpora_path = os.path.join(self.DataDir(), 'translate')
corp_dir = glob.glob(os.path.join(corpora_path, '??')) + \
glob.glob(os.path.join(corpora_path, '??-??'))
for language in corp_dir:
files = glob.glob(os.path.join(language, '*.html*'))
lang_code = os.path.basename(language)
logging.debug('Starting language %s' % lang_code)
# Translate each html file in the language directory.
for lang_file in files:
logging.debug('Starting file %s' % lang_file)
lang_file = self.GetFileURLForPath(lang_file)
self._AssertTranslateWorks(lang_file, lang_code)
def _CreateCrazyDownloads(self):
"""Doownload files with filenames containing special chars.
The files are created on the fly and cleaned after use.
"""
download_dir = self.GetDownloadDirectory().value()
filename = os.path.join(self.DataDir(), 'downloads', 'crazy_filenames.txt')
crazy_filenames = self.EvalDataFrom(filename)
logging.info('Testing with %d crazy filenames' % len(crazy_filenames))
def _CreateFile(name):
"""Create and fill the given file with some junk."""
fp = open(name, 'w') # name could be unicode
print >>fp, 'This is a junk file named %s. ' % repr(name) * 100
fp.close()
# Temp dir for hosting crazy filenames.
temp_dir = tempfile.mkdtemp(prefix='download')
# Filesystem-interfacing functions like os.listdir() need to
# be given unicode strings to "do the right thing" on win.
# Ref: http://boodebr.org/main/python/all-about-python-and-unicode
try:
for filename in crazy_filenames: # filename is unicode.
utf8_filename = filename.encode('utf-8')
file_path = os.path.join(temp_dir, utf8_filename)
_CreateFile(os.path.join(temp_dir, filename)) # unicode file.
file_url = self.GetFileURLForPath(file_path)
downloaded_file = os.path.join(download_dir, filename)
os.path.exists(downloaded_file) and os.remove(downloaded_file)
pre_download_ids = [x['id']
for x in self.GetDownloadsInfo().Downloads()]
self.DownloadAndWaitForStart(file_url)
# Wait for files and remove them as we go.
self.WaitForAllDownloadsToComplete(pre_download_ids)
os.path.exists(downloaded_file) and os.remove(downloaded_file)
finally:
shutil.rmtree(unicode(temp_dir)) # unicode so that win treats nicely.
def testHistoryNotTranslated(self):
"""Tests navigating to History page with other languages."""
# Build the history with non-English content.
history_file = os.path.join(
self.DataDir(), 'translate', 'crazy_history.txt')
history_items = self.EvalDataFrom(history_file)
for history_item in history_items:
self.AddHistoryItem(history_item)
# Navigate to a page that triggers the translate bar so we can verify that
# it disappears on the history page.
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
self.NavigateToURL('chrome://history/')
self.assertTrue(self.WaitForInfobarCount(0))
self.assertFalse('translate_bar' in self.GetTranslateInfo())
def testDownloadsNotTranslated(self):
"""Tests navigating to the Downloads page with other languages."""
# Build the download history with non-English content.
self._CreateCrazyDownloads()
# Navigate to a page that triggers the translate bar so we can verify that
# it disappears on the downloads page.
self._NavigateAndWaitForBar(self._GetDefaultSpanishURL())
self.NavigateToURL('chrome://downloads/')
self.assertTrue(self.WaitForInfobarCount(0))
self.assertFalse('translate_bar' in self.GetTranslateInfo())
def testAlwaysTranslateInIncognito(self):
"""Verify that pages aren't auto-translated in incognito windows."""
url = self._GetDefaultSpanishURL()
self._NavigateAndWaitForBar(url)
info_before_translate = self.GetTranslateInfo()
self.assertTrue('translate_bar' in info_before_translate)
self.SelectTranslateOption('toggle_always_translate')
# Navigate to a page in incognito and verify that it is not auto-translated.
self.RunCommand(pyauto.IDC_NEW_INCOGNITO_WINDOW)
self._NavigateAndWaitForBar(url, window_index=1)
info_before_translate = self.GetTranslateInfo()
self.assertTrue('translate_bar' in info_before_translate)
self.assertFalse(info_before_translate['page_translated'])
self.assertTrue(info_before_translate['can_translate_page'])
self.assertEqual(self.before_translate,
info_before_translate['translate_bar']['bar_state'])
def testMultipleTabsAndWindows(self):
"""Verify that translate infobar shows up in multiple tabs and windows."""
url = self._GetDefaultSpanishURL()
def _AssertTranslateInfobarShowing(window_index=0, tab_index=0):
"""Navigate to a Spanish page in the given window/tab and verify that the
translate bar shows up.
"""
self._NavigateAndWaitForBar(
url, window_index=window_index, tab_index=tab_index)
info_before_translate = self.GetTranslateInfo(window_index=window_index,
tab_index=tab_index)
self.assertTrue('translate_bar' in info_before_translate)
_AssertTranslateInfobarShowing()
self.AppendTab(pyauto.GURL('about:blank'))
_AssertTranslateInfobarShowing(tab_index=1)
self.OpenNewBrowserWindow(True)
_AssertTranslateInfobarShowing(window_index=1)
self.AppendTab(pyauto.GURL('about:blank'), 1)
_AssertTranslateInfobarShowing(window_index=1, tab_index=1)
self.RunCommand(pyauto.IDC_NEW_INCOGNITO_WINDOW)
_AssertTranslateInfobarShowing(window_index=2)
self.AppendTab(pyauto.GURL('about:blank'), 2)
_AssertTranslateInfobarShowing(window_index=2, tab_index=1)
def testNoTranslateInfobarAfterNeverTranslate(self):
"""Verify Translate Info bar should not stay on the page after opting
Never translate the page"""
url = self._GetDefaultSpanishURL()
self._NavigateAndWaitForBar(url)
self.SelectTranslateOption('never_translate_language')
self.assertFalse(self.GetBrowserInfo()['windows'][0]['tabs'][0]['infobars'])
if __name__ == '__main__':
pyauto_functional.Main()