/* Bug http://crbug/415711 */ @MediumTest @Feature({"Downloads"}) public void testDuplicateHttpPostDownload_Overwrite() throws Exception { // Download a file. loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/post.html")); waitForFocus(); View currentView = getActivity().getActivityTab().getView(); singleClickView(currentView); assertTrue( "Failed to finish downloading file for the first time.", waitForChromeDownloadToFinish()); // Download a file with the same name. loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/post.html")); waitForFocus(); currentView = getActivity().getActivityTab().getView(); singleClickView(currentView); assertPollForInfoBarSize(1); assertTrue( "OVERWRITE button wasn't found", InfoBarUtil.clickPrimaryButton(getInfoBars().get(0))); assertTrue( "Failed to finish downloading file for the second time.", waitForChromeDownloadToFinish()); assertTrue("Missing first download", hasDownload("superbo.txt", SUPERBO_CONTENTS)); assertFalse( "Should not have second download", hasDownload("superbo (1).txt", SUPERBO_CONTENTS)); }
/** Test back and forward buttons. */ @Restriction(RESTRICTION_TYPE_TABLET) @MediumTest @Feature({"Navigation"}) public void testNavigateBackAndForwardButtons() throws InterruptedException { final String[] urls = { TestHttpServerClient.getUrl("chrome/test/data/android/navigate/one.html"), TestHttpServerClient.getUrl("chrome/test/data/android/navigate/two.html"), TestHttpServerClient.getUrl("chrome/test/data/android/navigate/three.html") }; for (String url : urls) { navigateAndObserve(url, url); } final int repeats = 3; for (int i = 0; i < repeats; i++) { singleClickView(getActivity().findViewById(R.id.back_button)); UiUtils.settleDownUI(getInstrumentation()); assertEquals( String.format( Locale.US, "URL mismatch after pressing back button for the 1st time in repetition %d.", i), urls[1], getActivity().getActivityTab().getUrl()); singleClickView(getActivity().findViewById(R.id.back_button)); UiUtils.settleDownUI(getInstrumentation()); assertEquals( String.format( Locale.US, "URL mismatch after pressing back button for the 2nd time in repetition %d.", i), urls[0], getActivity().getActivityTab().getUrl()); singleClickView(getActivity().findViewById(R.id.forward_button)); UiUtils.settleDownUI(getInstrumentation()); assertEquals( String.format( Locale.US, "URL mismatch after pressing fwd button for the 1st time in repetition %d.", i), urls[1], getActivity().getActivityTab().getUrl()); singleClickView(getActivity().findViewById(R.id.forward_button)); UiUtils.settleDownUI(getInstrumentation()); assertEquals( String.format( Locale.US, "URL mismatch after pressing fwd button for the 2nd time in repetition %d.", i), urls[2], getActivity().getActivityTab().getUrl()); } }
/** * Verifies that the referrer is stripped from username and password fields. Bug: * crbug.com/413216 @MediumTest @Feature({"Browser"}) */ @FlakyTest public void testOpenInNewTabSanitizeReferrer() throws InterruptedException, TimeoutException { String url = TestHttpServerClient.getUrl( "chrome/test/data/android/context_menu_test.html", "user", "pass"); String expectedReferrer = TestHttpServerClient.getUrl("chrome/test/data/android/context_menu_test.html"); assertTrue(url.contains("pass")); // Sanity check. triggerContextMenuLoad(url, "testLink", R.id.contextmenu_open_in_new_tab); assertNotNull(mOpenNewTabLoadUrlParams); assertEquals(expectedReferrer, mOpenNewTabLoadUrlParams.getReferrer().getUrl()); }
/** * Test fallback works as intended and that we can go back to the original URL even when * redirected via Java redirection. */ @MediumTest @Feature({"Navigation"}) public void testIntentFallbackRedirection() throws Exception { getInstrumentation().waitForIdleSync(); assertEquals(NEW_TAB_PAGE, getActivity().getActivityTab().getUrl()); final String redirectionUrl = TestHttpServerClient.getUrl("chrome/test/data/android/redirect/about.html"); final String initialUrl = TestHttpServerClient.getUrl( "chrome/test/data/android/redirect/js_redirect.cgi?location=" + URLEncoder.encode( "intent://non_existent/#Intent;scheme=non_existent;" + "S.browser_fallback_url=" + redirectionUrl + ";end", "UTF-8")); final String targetUrl = TestHttpServerClient.getUrl("chrome/test/data/android/redirect/one.html"); typeInOmniboxAndNavigate(initialUrl); // Now intent fallback should be triggered assuming 'non_existent' scheme cannot be handled. CriteriaHelper.pollForCriteria( new Criteria() { @Override public boolean isSatisfied() { return getActivity().getActivityTab().getUrl().equals(targetUrl); } }); // Check if Java redirections were removed from the history. // Note that if we try to go back in the test: NavigateToEntry() is called, but // DidNavigate() does not get called. But in real cases we can go back to initial page // without any problem. // TODO(changwan): figure out why we cannot go back on this test. int index = getActivity() .getActivityTab() .getWebContents() .getNavigationController() .getLastCommittedEntryIndex(); assertEquals(1, index); String previousNavigationUrl = getActivity() .getActivityTab() .getWebContents() .getNavigationController() .getEntryAtIndex(0) .getUrl(); assertEquals(NEW_TAB_PAGE, previousNavigationUrl); }
// @Restriction(RESTRICTION_TYPE_TABLET) // @MediumTest // @Feature({"Navigation"}) // crbug.com/516018 @FlakyTest public void testNavigateMany() throws InterruptedException { final String[] urls = { TestHttpServerClient.getUrl("chrome/test/data/android/navigate/one.html"), TestHttpServerClient.getUrl("chrome/test/data/android/navigate/two.html"), TestHttpServerClient.getUrl("chrome/test/data/android/navigate/three.html") }; final int repeats = 3; for (int i = 0; i < repeats; i++) { for (int j = 0; j < urls.length; j++) { String result = typeInOmniboxAndNavigate(urls[j]); assertEquals(expectedLocation(urls[j]), result); } } }
/** Test Opening a link and verify that the desired page is loaded. */ @MediumTest @Feature({"Navigation"}) public void testOpenLink() throws InterruptedException, TimeoutException { String url1 = TestHttpServerClient.getUrl("chrome/test/data/android/google.html"); String url2 = TestHttpServerClient.getUrl("chrome/test/data/android/about.html"); navigateAndObserve(url1, url1); assertWaitForPageScaleFactorMatch(0.5f); Tab tab = getActivity().getActivityTab(); DOMUtils.clickNode(this, tab.getContentViewCore(), "aboutLink"); ChromeTabUtils.waitForTabPageLoaded(tab, url2); assertEquals("Desired Link not open", url2, getActivity().getActivityTab().getUrl()); }
/** * Test re-direct functionality for a web-page. * * @throws Exception */ @MediumTest @Feature({"Navigation"}) public void testNavigateRedirect() throws Exception { final String initialUrl = TestHttpServerClient.getUrl("chrome/test/data/android/redirect/about.html"); final String redirectedUrl = TestHttpServerClient.getUrl("chrome/test/data/android/redirect/one.html"); typeInOmniboxAndNavigate(initialUrl); CriteriaHelper.pollForCriteria( new Criteria() { @Override public boolean isSatisfied() { return getActivity().getActivityTab().getUrl().equals(redirectedUrl); } }); }
/** Verify Selection on the Location Bar. */ @Smoke @MediumTest @Feature({"Navigation", "Main"}) public void testNavigate() throws InterruptedException { String url = TestHttpServerClient.getUrl("chrome/test/data/android/navigate/simple.html"); String result = typeInOmniboxAndNavigate(url); assertEquals(expectedLocation(url), result); }
/** * Verifies that the referrer is not set for "Open in new incognito tab". Bug: * crbug.com/413216 @MediumTest @Feature({"Browser"}) */ @FlakyTest public void testOpenInIncognitoTabNoReferrer() throws InterruptedException, TimeoutException { String url = TestHttpServerClient.getUrl("chrome/test/data/android/context_menu_test.html"); triggerContextMenuLoad(url, "testLink", R.id.contextmenu_open_in_incognito_tab); assertNotNull(mOpenNewTabLoadUrlParams); assertNull(mOpenNewTabLoadUrlParams.getReferrer()); }
/** Verify Selection on the Location Bar in Landscape Mode */ @MediumTest @Feature({"Navigation"}) public void testNavigateLandscape() throws InterruptedException { // '0' is Landscape Mode. '1' is Portrait. getActivity().setRequestedOrientation(0); String url = TestHttpServerClient.getUrl("chrome/test/data/android/navigate/simple.html"); String result = typeInOmniboxAndNavigate(url); assertEquals(expectedLocation(url), result); }
/** Bug http://crbug/253711 @MediumTest @Feature({"Downloads"}) */ @FlakyTest public void testHttpPostDownload() throws Exception { loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/post.html")); waitForFocus(); View currentView = getActivity().getActivityTab().getView(); singleClickView(currentView); assertTrue(waitForChromeDownloadToFinish()); assertTrue(hasDownload("superbo.txt", SUPERBO_CONTENTS)); }
/** Bug http://crbug.com/253711 @MediumTest @Feature({"Downloads"}) */ @FlakyTest public void testHttpGetDownload() throws Exception { loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/get.html")); waitForFocus(); View currentView = getActivity().getActivityTab().getView(); singleClickView(currentView); assertTrue(waitForGetDownloadToFinish()); checkLastDownload("test.gzip"); }
/* @MediumTest @Feature({"Downloads"}) Bug http://crbug/253711 */ @FlakyTest public void testUrlEscaping() throws Exception { loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/urlescaping.html")); waitForFocus(); View currentView = getActivity().getActivityTab().getView(); singleClickView(currentView); assertTrue(waitForGetDownloadToFinish()); checkLastDownload("[large]wallpaper.dm"); }
/** Bug http://crbug/286315 @MediumTest @Feature({"Downloads"}) */ @FlakyTest public void testDangerousDownload() throws Exception { loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/dangerous.html")); waitForFocus(); View currentView = getActivity().getActivityTab().getView(); singleClickView(currentView); assertPollForInfoBarSize(1); assertTrue("OK button wasn't found", InfoBarUtil.clickPrimaryButton(getInfoBars().get(0))); assertTrue(waitForGetDownloadToFinish()); checkLastDownload("test.apk"); }
/* Bug http://crbug/415711 */ @MediumTest @Feature({"Downloads"}) public void testDuplicateHttpPostDownload_AllowMultipleInfoBars() throws Exception { assertFalse(hasDownload("superbo.txt", SUPERBO_CONTENTS)); // Download a file. loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/post.html")); waitForFocus(); View currentView = getActivity().getActivityTab().getView(); singleClickView(currentView); assertTrue( "Failed to finish downloading file for the first time.", waitForChromeDownloadToFinish()); // Download the file for the second time. loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/post.html")); waitForFocus(); currentView = getActivity().getActivityTab().getView(); singleClickView(currentView); assertPollForInfoBarSize(1); // Download the file for the third time. loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/post.html")); waitForFocus(); currentView = getActivity().getActivityTab().getView(); singleClickView(currentView); assertPollForInfoBarSize(2); // Now create two new files by clicking on the infobars. assertTrue( "CREATE NEW button wasn't found", InfoBarUtil.clickSecondaryButton(getInfoBars().get(0))); assertTrue("Failed to finish downloading the second file.", waitForChromeDownloadToFinish()); assertPollForInfoBarSize(1); assertTrue( "CREATE NEW button wasn't found", InfoBarUtil.clickSecondaryButton(getInfoBars().get(0))); assertTrue("Failed to finish downloading the third file.", waitForChromeDownloadToFinish()); assertTrue("Missing first download", hasDownload("superbo.txt", SUPERBO_CONTENTS)); assertTrue("Missing second download", hasDownload("superbo (1).txt", SUPERBO_CONTENTS)); assertTrue("Missing third download", hasDownload("superbo (2).txt", SUPERBO_CONTENTS)); }
/** Verify New Tab Open and Navigate. */ @MediumTest @Feature({"Navigation"}) public void testOpenAndNavigate() throws InterruptedException { final String url = TestHttpServerClient.getUrl("chrome/test/data/android/navigate/simple.html"); navigateAndObserve(url, url); final int tabCount = getActivity().getCurrentTabModel().getCount(); ChromeTabUtils.newTabFromMenu(getInstrumentation(), getActivity()); UiUtils.settleDownUI(getInstrumentation()); assertEquals( "Wrong number of tabs", tabCount + 1, getActivity().getCurrentTabModel().getCount()); String result = typeInOmniboxAndNavigate(url); assertEquals(expectedLocation(url), result); }
/** Bug http://crbug/253711 Bug http://crbug/415711 @MediumTest @Feature({"Downloads"}) */ @FlakyTest public void testDuplicateHttpPostDownload_CreateNew() throws Exception { // Download a file. loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/post.html")); waitForFocus(); View currentView = getActivity().getActivityTab().getView(); singleClickView(currentView); assertTrue( "Failed to finish downloading file for the first time.", waitForChromeDownloadToFinish()); // Download a file with the same name. loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/post.html")); waitForFocus(); currentView = getActivity().getActivityTab().getView(); singleClickView(currentView); assertPollForInfoBarSize(1); assertTrue( "CREATE NEW button wasn't found", InfoBarUtil.clickSecondaryButton(getInfoBars().get(0))); assertTrue( "Failed to finish downloading file for the second time.", waitForChromeDownloadToFinish()); assertTrue("Missing first download", hasDownload("superbo.txt", SUPERBO_CONTENTS)); assertTrue("Missing second download", hasDownload("superbo (1).txt", SUPERBO_CONTENTS)); }
/** * Test Opening a link and verify that TabObserver#onPageLoadStarted gives the old and new URL. */ @MediumTest @Feature({"Navigation"}) public void testTabObserverOnPageLoadStarted() throws InterruptedException, TimeoutException { final String url1 = TestHttpServerClient.getUrl("chrome/test/data/android/google.html"); final String url2 = TestHttpServerClient.getUrl("chrome/test/data/android/about.html"); navigateAndObserve(url1, url1); assertWaitForPageScaleFactorMatch(0.5f); TabObserver onPageLoadStartedObserver = new EmptyTabObserver() { @Override public void onPageLoadStarted(Tab tab, String newUrl) { tab.removeObserver(this); assertEquals(url1, tab.getUrl()); assertEquals(url2, newUrl); } }; Tab tab = getActivity().getActivityTab(); tab.addObserver(onPageLoadStartedObserver); DOMUtils.clickNode(this, tab.getContentViewCore(), "aboutLink"); ChromeTabUtils.waitForTabPageLoaded(tab, url2); assertEquals("Desired Link not open", url2, getActivity().getActivityTab().getUrl()); }
/** Bug 5431234 @MediumTest @Feature({"Downloads"}) */ @FlakyTest public void testCloseEmptyDownloadTab() throws Exception { loadUrl(TestHttpServerClient.getUrl("chrome/test/data/android/download/get.html")); waitForFocus(); int initialTabCount = getActivity().getCurrentTabModel().getCount(); View currentView = getActivity().getActivityTab().getView(); TouchCommon.longPressView(currentView); getInstrumentation() .invokeContextMenuAction(getActivity(), R.id.contextmenu_open_in_new_tab, 0); assertTrue(waitForGetDownloadToFinish()); checkLastDownload("test.gzip"); assertEquals( "Did not close new blank tab for download", initialTabCount, getActivity().getCurrentTabModel().getCount()); }
/* Bug http://crbug/481758 */ @CommandLineFlags.Add(ChromeSwitches.DISABLE_DOCUMENT_MODE) @MediumTest @Feature({"Downloads"}) public void testDuplicateHttpPostDownload_OpenNewTabAndReplace() throws Exception { final String url = TestHttpServerClient.getUrl("chrome/test/data/android/download/get.html"); // Create the file in advance so that duplicate download infobar can show up. File dir = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS); assertTrue(dir.isDirectory()); final File file = new File(dir, "test.gzip"); if (!file.exists()) { assertTrue(file.createNewFile()); } // Open in a new tab again. loadUrl(url); waitForFocus(); View currentView = getActivity().getActivityTab().getView(); TouchCommon.longPressView(currentView); getInstrumentation() .invokeContextMenuAction(getActivity(), R.id.contextmenu_open_in_new_tab, 0); waitForNewTabToStabilize(2); goToLastTab(); assertPollForInfoBarSize(1); // Now create two new files by clicking on the infobars. assertTrue( "OVERWRITE button wasn't found", InfoBarUtil.clickPrimaryButton(getInfoBars().get(0))); // Try to wait for download to finish. This will fail if there is no external Internet // connection. Android's DownloadManager will abort download request when there is // no Internet connection, even though we are connecting to a local host. waitForGetDownloadToFinish(); }
/** Unit tests for {@link OfflinePageBridge}. */ public class OfflinePageBridgeTest extends ChromeActivityTestCaseBase<ChromeActivity> { private static final String TEST_PAGE = TestHttpServerClient.getUrl("chrome/test/data/android/about.html"); private static final int TIMEOUT_MS = 5000; private static final BookmarkId BOOKMARK_ID = new BookmarkId(1234, BookmarkType.NORMAL); private OfflinePageBridge mOfflinePageBridge; public OfflinePageBridgeTest() { super(ChromeActivity.class); } @Override protected void setUp() throws Exception { super.setUp(); final Semaphore semaphore = new Semaphore(0); ThreadUtils.runOnUiThreadBlocking( new Runnable() { @Override public void run() { Profile profile = Profile.getLastUsedProfile(); mOfflinePageBridge = new OfflinePageBridge(profile); if (mOfflinePageBridge.isOfflinePageModelLoaded()) { semaphore.release(); } else { mOfflinePageBridge.addObserver( new OfflinePageModelObserver() { @Override public void offlinePageModelLoaded() { semaphore.release(); mOfflinePageBridge.removeObserver(this); } }); } } }); assertTrue(semaphore.tryAcquire(TIMEOUT_MS, TimeUnit.MILLISECONDS)); } @Override public void startMainActivity() throws InterruptedException { startMainActivityOnBlankPage(); } @MediumTest public void testLoadOfflinePagesWhenEmpty() throws Exception { List<OfflinePageItem> offlinePages = getAllPages(); assertEquals("Offline pages count incorrect.", 0, offlinePages.size()); } @MediumTest public void testAddOfflinePageAndLoad() throws Exception { loadUrl(TEST_PAGE); savePage(SavePageResult.SUCCESS, TEST_PAGE); List<OfflinePageItem> allPages = getAllPages(); OfflinePageItem offlinePage = allPages.get(0); assertEquals("Offline pages count incorrect.", 1, allPages.size()); assertEquals("Offline page item url incorrect.", TEST_PAGE, offlinePage.getUrl()); assertEquals( "Offline page item bookmark ID incorrect.", BOOKMARK_ID, offlinePage.getBookmarkId()); assertTrue( "Offline page item offline file url doesn't start properly.", offlinePage.getOfflineUrl().startsWith("file:///")); assertTrue( "Offline page item offline file doesn't have the right name.", offlinePage.getOfflineUrl().endsWith(".mhtml")); assertTrue( "Offline page item offline file doesn't have the right name.", offlinePage.getOfflineUrl().contains("About")); // BUG(518758): Depending on the bot the result will be either 626 or 627. long size = offlinePage.getFileSize(); assertTrue("Offline page item size is incorrect: " + size, size == 626 || size == 627); } @MediumTest public void testMarkPageAccessed() throws Exception { loadUrl(TEST_PAGE); savePage(SavePageResult.SUCCESS, TEST_PAGE); OfflinePageItem offlinePage = mOfflinePageBridge.getPageByBookmarkId(BOOKMARK_ID); assertNotNull("Offline page should be available, but it is not.", offlinePage); assertEquals("Offline page access count should be 0.", 0, offlinePage.getAccessCount()); markPageAccessed(BOOKMARK_ID, 1); } @MediumTest public void testGetPageByBookmarkId() throws Exception { loadUrl(TEST_PAGE); savePage(SavePageResult.SUCCESS, TEST_PAGE); OfflinePageItem offlinePage = mOfflinePageBridge.getPageByBookmarkId(BOOKMARK_ID); assertEquals("Offline page item url incorrect.", TEST_PAGE, offlinePage.getUrl()); assertEquals( "Offline page item bookmark ID incorrect.", BOOKMARK_ID, offlinePage.getBookmarkId()); assertTrue( "Offline page item offline file url doesn't start properly.", offlinePage.getOfflineUrl().startsWith("file:///")); assertTrue( "Offline page item offline file doesn't have the right name.", offlinePage.getOfflineUrl().endsWith(".mhtml")); assertTrue( "Offline page item offline file doesn't have the right name.", offlinePage.getOfflineUrl().contains("About")); assertNull( "Offline page is not supposed to exist", mOfflinePageBridge.getPageByBookmarkId(new BookmarkId(-42, BookmarkType.NORMAL))); } @MediumTest public void testDeleteOfflinePage() throws Exception { deletePage(BOOKMARK_ID, DeletePageResult.NOT_FOUND); loadUrl(TEST_PAGE); savePage(SavePageResult.SUCCESS, TEST_PAGE); assertNotNull( "Offline page should be available, but it is not.", mOfflinePageBridge.getPageByBookmarkId(BOOKMARK_ID)); deletePage(BOOKMARK_ID, DeletePageResult.SUCCESS); assertNull( "Offline page should be gone, but it is available.", mOfflinePageBridge.getPageByBookmarkId(BOOKMARK_ID)); } private void savePage(final int expectedResult, final String expectedUrl) throws InterruptedException { final Semaphore semaphore = new Semaphore(0); ThreadUtils.runOnUiThreadBlocking( new Runnable() { @Override public void run() { assertNotNull("Tab is null", getActivity().getActivityTab()); assertEquals( "URL does not match requested.", TEST_PAGE, getActivity().getActivityTab().getUrl()); assertNotNull("WebContents is null", getActivity().getActivityTab().getWebContents()); mOfflinePageBridge.savePage( getActivity().getActivityTab().getWebContents(), BOOKMARK_ID, getActivity().getWindowAndroid(), new SavePageCallback() { @Override public void onSavePageDone(int savePageResult, String url) { assertEquals("Requested and returned URLs differ.", expectedUrl, url); assertEquals("Save result incorrect.", expectedResult, savePageResult); semaphore.release(); } }); } }); assertTrue(semaphore.tryAcquire(TIMEOUT_MS, TimeUnit.MILLISECONDS)); } private void markPageAccessed(final BookmarkId bookmarkId, final int expectedAccessCount) throws InterruptedException { ThreadUtils.runOnUiThreadBlocking( new Runnable() { @Override public void run() { mOfflinePageBridge.markPageAccessed(bookmarkId); } }); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new Criteria() { @Override public boolean isSatisfied() { OfflinePageItem offlinePage = mOfflinePageBridge.getPageByBookmarkId(bookmarkId); return offlinePage.getAccessCount() == expectedAccessCount; } })); } private void deletePage(BookmarkId bookmarkId, final int expectedResult) throws InterruptedException { final Semaphore semaphore = new Semaphore(0); ThreadUtils.runOnUiThreadBlocking( new Runnable() { @Override public void run() { mOfflinePageBridge.deletePage( BOOKMARK_ID, getActivity().getWindowAndroid(), new DeletePageCallback() { @Override public void onDeletePageDone(int deletePageResult) { assertEquals("Delete result incorrect.", expectedResult, deletePageResult); semaphore.release(); } }); } }); assertTrue(semaphore.tryAcquire(TIMEOUT_MS, TimeUnit.MILLISECONDS)); } private List<OfflinePageItem> getAllPages() throws InterruptedException { final Semaphore semaphore = new Semaphore(0); final List<OfflinePageItem> result = new ArrayList<OfflinePageItem>(); ThreadUtils.runOnUiThreadBlocking( new Runnable() { @Override public void run() { result.clear(); for (OfflinePageItem item : mOfflinePageBridge.getAllPages()) { result.add(item); } semaphore.release(); } }); assertTrue(semaphore.tryAcquire(TIMEOUT_MS, TimeUnit.MILLISECONDS)); return result; } }
/** * Verifies that a renderer that crashes in foreground has the correct visibility when recreated. */ @LargeTest @Feature({"ProcessManagement"}) public void testCrashInForeground() throws InterruptedException { // Create a tab in foreground and wait until it is loaded. final Tab tab = ThreadUtils.runOnUiThreadBlockingNoException( new Callable<Tab>() { @Override public Tab call() throws Exception { TabCreator tabCreator = getActivity().getCurrentTabCreator(); return tabCreator.createNewTab( new LoadUrlParams(TestHttpServerClient.getUrl(FILE_PATH)), TabLaunchType.FROM_KEYBOARD, null); } }); ChromeTabUtils.waitForTabPageLoaded(tab, TestHttpServerClient.getUrl(FILE_PATH)); getInstrumentation().waitForIdleSync(); // Kill the renderer and wait for the crash to be noted by the browser process. assertTrue( ChildProcessLauncher.crashProcessForTesting( tab.getContentViewCore().getCurrentRenderProcessId())); assertTrue( "Renderer crash wasn't noticed by the browser.", CriteriaHelper.pollForCriteria( new Criteria() { @Override public boolean isSatisfied() { return tab.getContentViewCore().getCurrentRenderProcessId() == 0; } })); // Reload the tab, respawning the renderer. getInstrumentation() .runOnMainSync( new Runnable() { @Override public void run() { tab.reload(); } }); // Wait until the process is spawned and its visibility is determined. assertTrue( "Process for the crashed tab was not respawned.", CriteriaHelper.pollForCriteria( new Criteria() { @Override public boolean isSatisfied() { return tab.getContentViewCore().getCurrentRenderProcessId() != 0; } })); assertTrue( "isInForeground() was not called for the process.", CriteriaHelper.pollForCriteria( new Criteria() { @Override public boolean isSatisfied() { return mBindingManager.setInForegroundWasCalled( tab.getContentViewCore().getCurrentRenderProcessId()); } })); getInstrumentation() .runOnMainSync( new Runnable() { @Override public void run() { // Verify the visibility of the renderer. assertTrue( mBindingManager.isInForeground( tab.getContentViewCore().getCurrentRenderProcessId())); } }); }
/** Tests the app banners. */ @CommandLineFlags.Add(ChromeSwitches.ENABLE_APP_INSTALL_ALERTS) public class AppBannerManagerTest extends ChromeTabbedActivityTestBase { private static final String NATIVE_APP_URL = TestHttpServerClient.getUrl("chrome/test/data/banners/play_app_test_page.html"); private static final String NATIVE_ICON_URL = TestHttpServerClient.getUrl("chrome/test/data/banners/launcher-icon-4x.png"); private static final String NATIVE_APP_TITLE = "Mock app title"; private static final String NATIVE_APP_PACKAGE = "123456"; private static final String NATIVE_APP_INSTALL_TEXT = "Install this"; private static final String NATIVE_APP_REFERRER = "chrome_inline"; private static final String NATIVE_APP_URL_WITH_MANIFEST_URL = TestHttpServerClient.getUrl("chrome/test/data/banners/play_app_url_test_page.html"); private static final String WEB_APP_URL = TestHttpServerClient.getUrl("chrome/test/data/banners/manifest_test_page.html"); private static final String WEB_APP_TITLE = "Manifest test app"; private static final String INSTALL_ACTION = "INSTALL_ACTION"; private static class MockAppDetailsDelegate extends AppDetailsDelegate { private Observer mObserver; private AppData mAppData; private int mNumRetrieved; private Intent mInstallIntent; private String mReferrer; @Override protected void getAppDetailsAsynchronously( Observer observer, String url, String packageName, String referrer, int iconSize) { mNumRetrieved += 1; mObserver = observer; mReferrer = referrer; mInstallIntent = new Intent(INSTALL_ACTION); mAppData = new AppData(url, packageName); mAppData.setPackageInfo( NATIVE_APP_TITLE, NATIVE_ICON_URL, 4.5f, NATIVE_APP_INSTALL_TEXT, null, mInstallIntent); ThreadUtils.runOnUiThread( new Runnable() { @Override public void run() { mObserver.onAppDetailsRetrieved(mAppData); } }); } @Override public void destroy() {} } private static class TestPackageManager extends MockPackageManager { public boolean isInstalled = false; @Override public List<PackageInfo> getInstalledPackages(int flags) { List<PackageInfo> packages = new ArrayList<PackageInfo>(); if (isInstalled) { PackageInfo info = new PackageInfo(); info.packageName = NATIVE_APP_PACKAGE; packages.add(info); } return packages; } } private static class InfobarListener implements InfoBarContainer.InfoBarAnimationListener { private boolean mDoneAnimating; @Override public void notifyAnimationFinished(int animationType) { if (animationType == AnimationHelper.ANIMATION_TYPE_SHOW) mDoneAnimating = true; } } private MockAppDetailsDelegate mDetailsDelegate; private TestPackageManager mPackageManager; @Override public void startMainActivity() throws InterruptedException { startMainActivityOnBlankPage(); } @Override protected void setUp() throws Exception { mPackageManager = new TestPackageManager(); AppBannerManager.setIsEnabledForTesting(true); AppBannerInfoBarDelegateAndroid.setPackageManagerForTesting(mPackageManager); super.setUp(); // Must be set after native has loaded. mDetailsDelegate = new MockAppDetailsDelegate(); ThreadUtils.runOnUiThreadBlocking( new Runnable() { @Override public void run() { AppBannerManager.setAppDetailsDelegate(mDetailsDelegate); } }); AppBannerManager.disableSecureSchemeCheckForTesting(); // Navigations in this test are all of type ui::PAGE_TRANSITION_LINK, i.e. indirect. // Force indirect navigations to be worth the same as direct for testing. AppBannerManager.forceEngagementWeightsForTesting(1, 1); } private boolean waitUntilNoInfoBarsExist() throws Exception { return CriteriaHelper.pollForUIThreadCriteria( new Criteria() { @Override public boolean isSatisfied() { InfoBarContainer container = getActivity().getActivityTab().getInfoBarContainer(); return container.getInfoBars().size() == 0; } }); } private boolean waitUntilAppDetailsRetrieved(final int numExpected) throws Exception { return CriteriaHelper.pollForUIThreadCriteria( new Criteria() { @Override public boolean isSatisfied() { AppBannerManager manager = getActivity().getActivityTab().getAppBannerManagerForTesting(); return mDetailsDelegate.mNumRetrieved == numExpected && !manager.isFetcherActiveForTesting(); } }); } private boolean waitUntilAppBannerInfoBarAppears(final String title) throws Exception { return CriteriaHelper.pollForUIThreadCriteria( new Criteria() { @Override public boolean isSatisfied() { InfoBarContainer container = getActivity().getActivityTab().getInfoBarContainer(); ArrayList<InfoBar> infobars = container.getInfoBars(); if (infobars.size() != 1) return false; if (!(infobars.get(0) instanceof AppBannerInfoBarAndroid)) return false; TextView textView = (TextView) infobars.get(0).getContentWrapper().findViewById(R.id.app_name); if (textView == null) return false; return TextUtils.equals(textView.getText(), title); } }); } private void runFullNativeInstallPathway(String url, String expectedReferrer) throws Exception { // Visit a site that requests a banner. assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), url))); assertTrue(waitUntilAppDetailsRetrieved(1)); assertEquals(mDetailsDelegate.mReferrer, expectedReferrer); assertTrue(waitUntilNoInfoBarsExist()); // Indicate a day has passed, then revisit the page to get the banner to appear. InfoBarContainer container = getActivity().getActivityTab().getInfoBarContainer(); final InfobarListener listener = new InfobarListener(); container.setAnimationListener(listener); AppBannerManager.setTimeDeltaForTesting(1); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), url))); assertTrue(waitUntilAppDetailsRetrieved(2)); assertTrue(waitUntilAppBannerInfoBarAppears(NATIVE_APP_TITLE)); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new Criteria() { @Override public boolean isSatisfied() { return listener.mDoneAnimating; } })); // Check that the button asks if the user wants to install the app. InfoBar infobar = container.getInfoBars().get(0); final Button button = (Button) infobar.getContentWrapper().findViewById(R.id.button_primary); assertEquals(NATIVE_APP_INSTALL_TEXT, button.getText()); // Click the button to trigger the install. final ActivityMonitor activityMonitor = new ActivityMonitor( new IntentFilter(INSTALL_ACTION), new ActivityResult(Activity.RESULT_OK, null), true); getInstrumentation().addMonitor(activityMonitor); TouchCommon.singleClickView(button); // Wait for the infobar to register that the app is installing. final String installingText = getInstrumentation().getTargetContext().getString(R.string.app_banner_installing); assertTrue( CriteriaHelper.pollForCriteria( new Criteria() { @Override public boolean isSatisfied() { return getInstrumentation().checkMonitorHit(activityMonitor, 1) && TextUtils.equals(button.getText(), installingText); } })); // Say that the package is installed. Infobar should say that the app is ready to open. mPackageManager.isInstalled = true; final String openText = getInstrumentation().getTargetContext().getString(R.string.app_banner_open); assertTrue( CriteriaHelper.pollForCriteria( new Criteria() { @Override public boolean isSatisfied() { return TextUtils.equals(button.getText(), openText); } })); } @SmallTest @Feature({"AppBanners"}) public void testFullNativeInstallPathwayFromId() throws Exception { runFullNativeInstallPathway(NATIVE_APP_URL, ""); } @SmallTest @Feature({"AppBanners"}) public void testFullNativeInstallPathwayFromUrl() throws Exception { runFullNativeInstallPathway(NATIVE_APP_URL_WITH_MANIFEST_URL, NATIVE_APP_REFERRER); } @MediumTest @Feature({"AppBanners"}) public void testBannerAppearsThenDoesNotAppearAgainForMonths() throws Exception { // Visit a site that requests a banner. assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(1)); assertTrue(waitUntilNoInfoBarsExist()); // Indicate a day has passed, then revisit the page. AppBannerManager.setTimeDeltaForTesting(1); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(2)); assertTrue(waitUntilAppBannerInfoBarAppears(NATIVE_APP_TITLE)); // Revisit the page to make the banner go away, but don't explicitly dismiss it. // This hides the banner for a few months. assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(3)); assertTrue(waitUntilNoInfoBarsExist()); // Wait a month until revisiting the page. AppBannerManager.setTimeDeltaForTesting(31); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(4)); assertTrue(waitUntilNoInfoBarsExist()); AppBannerManager.setTimeDeltaForTesting(32); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(5)); assertTrue(waitUntilNoInfoBarsExist()); // Wait two months until revisiting the page, which should pop up the banner. AppBannerManager.setTimeDeltaForTesting(61); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(6)); assertTrue(waitUntilNoInfoBarsExist()); AppBannerManager.setTimeDeltaForTesting(62); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(7)); assertTrue(waitUntilAppBannerInfoBarAppears(NATIVE_APP_TITLE)); } @MediumTest @Feature({"AppBanners"}) public void testBlockedBannerDoesNotAppearAgainForMonths() throws Exception { // Visit a site that requests a banner. assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(1)); assertTrue(waitUntilNoInfoBarsExist()); // Indicate a day has passed, then revisit the page. InfoBarContainer container = getActivity().getActivityTab().getInfoBarContainer(); final InfobarListener listener = new InfobarListener(); container.setAnimationListener(listener); AppBannerManager.setTimeDeltaForTesting(1); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(2)); assertTrue(waitUntilAppBannerInfoBarAppears(NATIVE_APP_TITLE)); // Explicitly dismiss the banner. assertTrue( CriteriaHelper.pollForUIThreadCriteria( new Criteria() { @Override public boolean isSatisfied() { return listener.mDoneAnimating; } })); ArrayList<InfoBar> infobars = container.getInfoBars(); View close = infobars.get(0).getContentWrapper().findViewById(R.id.infobar_close_button); TouchCommon.singleClickView(close); assertTrue(waitUntilNoInfoBarsExist()); // Waiting two months shouldn't be long enough. AppBannerManager.setTimeDeltaForTesting(61); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(3)); assertTrue(waitUntilNoInfoBarsExist()); AppBannerManager.setTimeDeltaForTesting(62); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(4)); assertTrue(waitUntilNoInfoBarsExist()); // Waiting three months should allow banners to reappear. AppBannerManager.setTimeDeltaForTesting(91); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(5)); assertTrue(waitUntilNoInfoBarsExist()); AppBannerManager.setTimeDeltaForTesting(92); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); assertTrue(waitUntilAppDetailsRetrieved(6)); assertTrue(waitUntilAppBannerInfoBarAppears(NATIVE_APP_TITLE)); } @MediumTest @Feature({"AppBanners"}) public void testBitmapFetchersCanOverlapWithoutCrashing() throws Exception { // Visit a site that requests a banner rapidly and repeatedly. for (int i = 1; i <= 10; i++) { assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), NATIVE_APP_URL))); final Integer iteration = Integer.valueOf(i); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new Criteria() { @Override public boolean isSatisfied() { return mDetailsDelegate.mNumRetrieved == iteration; } })); } } @SmallTest @Feature({"AppBanners"}) public void testWebAppBannerAppears() throws Exception { // Create a Tab that doesn't have the AppBannerManager enabled. This prevents race // conditions between service worker activation and AppBannerManager getting triggered. // This race condition is a known problem, which is why the specs include wiggle room for // how many times a site must be visited. AppBannerManager.setIsEnabledForTesting(false); loadUrlInNewTab("about:blank"); // Visit a site that can have a banner, then wait until the service worker is activated. assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), WEB_APP_URL))); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new Criteria() { @Override public boolean isSatisfied() { String url = getActivity().getActivityTab().getUrl(); Uri uri = Uri.parse(url); return TextUtils.equals(uri.getFragment(), "sw_activated"); } })); AppBannerManager.setIsEnabledForTesting(true); // Revisit the site in a new tab, which will have the AppBannerManager enabled. loadUrlInNewTab("about:blank"); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), WEB_APP_URL))); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new Criteria() { @Override public boolean isSatisfied() { AppBannerManager manager = getActivity().getActivityTab().getAppBannerManagerForTesting(); return !manager.isFetcherActiveForTesting(); } })); assertTrue(waitUntilNoInfoBarsExist()); // Indicate a day has passed, then revisit the page to show the banner. AppBannerManager.setTimeDeltaForTesting(1); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new TabLoadObserver(getActivity().getActivityTab(), WEB_APP_URL))); assertTrue( CriteriaHelper.pollForUIThreadCriteria( new Criteria() { @Override public boolean isSatisfied() { AppBannerManager manager = getActivity().getActivityTab().getAppBannerManagerForTesting(); return !manager.isFetcherActiveForTesting(); } })); assertTrue(waitUntilAppBannerInfoBarAppears(WEB_APP_TITLE)); } }
/** * Verifies that the .setProcessInForeground() signal is called correctly when a tab that crashed * in background is restored in foreground. This is a regression test for http://crbug.com/399521. */ @LargeTest @Feature({"ProcessManagement"}) public void testCrashInBackground() throws InterruptedException { // Create two tabs and wait until they are loaded, so that their renderers are around. final Tab[] tabs = new Tab[2]; getInstrumentation() .runOnMainSync( new Runnable() { @Override public void run() { // Foreground tab. TabCreator tabCreator = getActivity().getCurrentTabCreator(); tabs[0] = tabCreator.createNewTab( new LoadUrlParams(TestHttpServerClient.getUrl(FILE_PATH)), TabLaunchType.FROM_KEYBOARD, null); // Background tab. tabs[1] = tabCreator.createNewTab( new LoadUrlParams(TestHttpServerClient.getUrl(FILE_PATH)), TabLaunchType.FROM_LONGPRESS_BACKGROUND, null); // On Svelte devices the background tab would not be loaded automatically, so // trigger the load manually. tabs[1].show(TabSelectionType.FROM_USER); tabs[1].hide(); } }); ChromeTabUtils.waitForTabPageLoaded(tabs[0], TestHttpServerClient.getUrl(FILE_PATH)); ChromeTabUtils.waitForTabPageLoaded(tabs[1], TestHttpServerClient.getUrl(FILE_PATH)); // Wait for the new tab animations on phones to finish. if (!DeviceFormFactor.isTablet(getActivity()) && getActivity() instanceof ChromeActivity) { final ChromeActivity activity = (ChromeActivity) getActivity(); assertTrue( "Did not finish animation", CriteriaHelper.pollForUIThreadCriteria( new Criteria() { @Override public boolean isSatisfied() { Layout layout = activity.getCompositorViewHolder().getLayoutManager().getActiveLayout(); return !layout.isLayoutAnimating(); } })); } getInstrumentation().waitForIdleSync(); getInstrumentation() .runOnMainSync( new Runnable() { @Override public void run() { // Make sure that the renderers were spawned. assertTrue(tabs[0].getContentViewCore().getCurrentRenderProcessId() > 0); assertTrue(tabs[1].getContentViewCore().getCurrentRenderProcessId() > 0); // Verify that the renderer of the foreground tab was signalled as visible. assertTrue( mBindingManager.isInForeground( tabs[0].getContentViewCore().getCurrentRenderProcessId())); // Verify that the renderer of the tab loaded in background was signalled as not // visible. assertTrue( mBindingManager.isInBackground( tabs[1].getContentViewCore().getCurrentRenderProcessId())); } }); // Kill the renderer and wait for the crash to be noted by the browser process. assertTrue( ChildProcessLauncher.crashProcessForTesting( tabs[1].getContentViewCore().getCurrentRenderProcessId())); assertTrue( "Renderer crash wasn't noticed by the browser.", CriteriaHelper.pollForCriteria( new Criteria() { @Override public boolean isSatisfied() { return tabs[1].getContentViewCore().getCurrentRenderProcessId() == 0; } })); // Switch to the tab that crashed in background. getInstrumentation() .runOnMainSync( new Runnable() { @Override public void run() { TabModelUtils.setIndex(getActivity().getCurrentTabModel(), indexOf(tabs[1])); } }); // Wait until the process is spawned and its visibility is determined. assertTrue( "Process for the crashed tab was not respawned.", CriteriaHelper.pollForCriteria( new Criteria() { @Override public boolean isSatisfied() { return tabs[1].getContentViewCore().getCurrentRenderProcessId() != 0; } })); assertTrue( "isInForeground() was not called for the process.", CriteriaHelper.pollForCriteria( new Criteria() { @Override public boolean isSatisfied() { return mBindingManager.setInForegroundWasCalled( tabs[1].getContentViewCore().getCurrentRenderProcessId()); } })); getInstrumentation() .runOnMainSync( new Runnable() { @Override public void run() { // Verify the visibility of the renderers. assertTrue( mBindingManager.isInBackground( tabs[0].getContentViewCore().getCurrentRenderProcessId())); assertTrue( mBindingManager.isInForeground( tabs[1].getContentViewCore().getCurrentRenderProcessId())); } }); }
/** * Ensures correctness of the visibilityDetermined() calls, that should be always preceded by * setInForeground(). * * <p>Bug: https://crbug.com/474543 @LargeTest @Feature({"ProcessManagement"}) */ @FlakyTest public void testVisibilityDetermined() throws InterruptedException { // Create a tab in foreground and wait until it is loaded. final Tab fgTab = ThreadUtils.runOnUiThreadBlockingNoException( new Callable<Tab>() { @Override public Tab call() { TabCreator tabCreator = getActivity().getCurrentTabCreator(); return tabCreator.createNewTab( new LoadUrlParams(TestHttpServerClient.getUrl(FILE_PATH)), TabLaunchType.FROM_KEYBOARD, null); } }); ChromeTabUtils.waitForTabPageLoaded(fgTab, TestHttpServerClient.getUrl(FILE_PATH)); int initialNavigationPid = fgTab.getContentViewCore().getCurrentRenderProcessId(); // Ensure the following calls happened: // - FG - setInForeground(true) - when the tab is created in the foreground // - DETERMINED - visibilityDetermined() - after the initial navigation is committed assertEquals("FG;DETERMINED;", mBindingManager.getVisibilityCalls(initialNavigationPid)); // Navigate to about:version which requires a different renderer. getInstrumentation() .runOnMainSync( new Runnable() { @Override public void run() { fgTab.loadUrl(new LoadUrlParams(ABOUT_VERSION_PATH)); } }); ChromeTabUtils.waitForTabPageLoaded(fgTab, ABOUT_VERSION_PATH); int secondNavigationPid = fgTab.getContentViewCore().getCurrentRenderProcessId(); assertTrue(secondNavigationPid != initialNavigationPid); // Ensure the following calls happened: // - BG - setInForeground(false) - when the renderer is created for uncommited frame // - FG - setInForeground(true) - when the frame is swapped in on commit // - DETERMINED - visibilityDetermined() - after the navigation is committed assertEquals("BG;FG;DETERMINED;", mBindingManager.getVisibilityCalls(secondNavigationPid)); // Open a tab in the background and load it. final Tab bgTab = ThreadUtils.runOnUiThreadBlockingNoException( new Callable<Tab>() { @Override public Tab call() { TabCreator tabCreator = getActivity().getCurrentTabCreator(); Tab tab = tabCreator.createNewTab( new LoadUrlParams(TestHttpServerClient.getUrl(FILE_PATH)), TabLaunchType.FROM_LONGPRESS_BACKGROUND, null); // On Svelte devices the background tab would not be loaded automatically, // so trigger the load manually. tab.show(TabSelectionType.FROM_USER); tab.hide(); return tab; } }); ChromeTabUtils.waitForTabPageLoaded(bgTab, TestHttpServerClient.getUrl(FILE_PATH)); int bgNavigationPid = bgTab.getContentViewCore().getCurrentRenderProcessId(); // Ensure the following calls happened: // - BG - setInForeground(false) - when tab is created in the background // - DETERMINED - visibilityDetermined() - after the navigation is committed assertEquals("BG;DETERMINED;", mBindingManager.getVisibilityCalls(bgNavigationPid)); }