package com.codeborne.selenide.impl; import com.codeborne.selenide.proxy.FileDownloadFilter; import com.codeborne.selenide.proxy.SelenideProxyServer; import com.codeborne.selenide.rules.MockWebdriverContainer; import com.google.common.collect.ImmutableSet; import org.junit.Before; import org.junit.Rule; import org.junit.Test; import org.junit.rules.ExpectedException; import org.mockito.invocation.InvocationOnMock; import org.mockito.stubbing.Answer; import org.openqa.selenium.NoSuchWindowException; import org.openqa.selenium.WebDriver; import org.openqa.selenium.WebDriver.TargetLocator; import org.openqa.selenium.WebElement; import java.io.File; import java.io.FileNotFoundException; import java.io.IOException; import static com.codeborne.selenide.WebDriverRunner.webdriverContainer; import static java.util.Arrays.asList; import static org.hamcrest.CoreMatchers.is; import static org.junit.Assert.assertThat; import static org.mockito.Mockito.*; public class DownloadFileWithProxyServerTest { @Rule public MockWebdriverContainer mockWebdriverContainer = new MockWebdriverContainer(); @Rule public ExpectedException thrown = ExpectedException.none(); DownloadFileWithProxyServer command = new DownloadFileWithProxyServer(); WebDriver webdriver = mock(WebDriver.class); SelenideProxyServer proxy = mock(SelenideProxyServer.class); WebElementSource linkWithHref = mock(WebElementSource.class); WebElement link = mock(WebElement.class); FileDownloadFilter filter = spy(new FileDownloadFilter()); @Before public void setUp() { command.waiter = spy(new Waiter()); doNothing().when(command.waiter).sleep(anyLong()); when(webdriverContainer.getWebDriver()).thenReturn(webdriver); when(webdriver.switchTo()).thenReturn(mock(TargetLocator.class)); when(proxy.responseFilter("download")).thenReturn(filter); when(linkWithHref.findAndAssertElementIsVisible()).thenReturn(link); when(linkWithHref.toString()).thenReturn("<a href='report.pdf'>report</a>"); } @Test public void canInterceptFileViaProxyServer() throws IOException { emulateServerResponseWithFiles(new File("report.pdf")); File file = command.download(linkWithHref, link, proxy); assertThat(file.getName(), is("report.pdf")); verify(filter).activate(); verify(link).click(); verify(filter).deactivate(); } @Test public void closesNewWindowIfFileWasOpenedInSeparateWindow() throws IOException { emulateServerResponseWithFiles(new File("report.pdf")); when(webdriver.getWindowHandle()).thenReturn("tab1"); when(webdriver.getWindowHandles()) .thenReturn(ImmutableSet.of("tab1", "tab2", "tab3")) .thenReturn(ImmutableSet.of("tab1", "tab2", "tab3", "tab-with-pdf")); File file = command.download(linkWithHref, link, proxy); assertThat(file.getName(), is("report.pdf")); verify(webdriver.switchTo()).window("tab-with-pdf"); verify(webdriver).close(); verify(webdriver.switchTo()).window("tab1"); verifyNoMoreInteractions(webdriver.switchTo()); } @Test public void ignoresErrorIfWindowHasAlreadyBeenClosedMeanwhile() throws IOException { TargetLocator targetLocator = mock(TargetLocator.class); doReturn(targetLocator).when(webdriver).switchTo(); doThrow(new NoSuchWindowException("no window: tab-with-pdf")).when(targetLocator).window("tab-with-pdf"); emulateServerResponseWithFiles(new File("report.pdf")); when(webdriver.getWindowHandle()).thenReturn("tab1"); when(webdriver.getWindowHandles()) .thenReturn(ImmutableSet.of("tab1", "tab2", "tab3")) .thenReturn(ImmutableSet.of("tab1", "tab2", "tab3", "tab-with-pdf")); File file = command.download(linkWithHref, link, proxy); assertThat(file.getName(), is("report.pdf")); verify(webdriver.switchTo()).window("tab-with-pdf"); verify(webdriver, never()).close(); verify(webdriver.switchTo()).window("tab1"); verifyNoMoreInteractions(webdriver.switchTo()); } @Test public void throwsFileNotFoundException_ifNoFilesHaveBeenDownloadedAfterClick() throws IOException { emulateServerResponseWithFiles(); thrown.expect(FileNotFoundException.class); thrown.expectMessage("Failed to download file <a href='report.pdf'>report</a>"); command.download(linkWithHref, link, proxy); } private void emulateServerResponseWithFiles(final File... files) { doAnswer(new Answer() { @Override public Object answer(InvocationOnMock invocation) throws Throwable { filter.getDownloadedFiles().addAll(asList(files)); return null; } }).when(link).click(); } }