2016-09-23 138 views
1

我有一个通过testng运行并行测试的硒项目。当测试失败时,我有一个侦听器类捕获屏幕截图。类是如下Selenium截图侦听器捕获错误的浏览器

public class ScreenshotOnFailure extends TestListenerAdapter { 

@Override 
public void onTestFailure(ITestResult tr) { 
    WebDriver driver = SeleniumSetup.driverrunning; 
    boolean hasQuit = driver.toString().contains("(null)"); 
    if(!hasQuit){ 
     System.out.println(driver); 
     File scrFile = ((TakesScreenshot)driver).getScreenshotAs(OutputType.FILE); 
     DateFormat dateFormat = new SimpleDateFormat("dd_MMM_yyyy__hh_mm_ssaa"); 
     Date date = new Date(); 
     String NewFileNamePath = null; 
     File directory = new File("."); 
     String methodName = tr.getMethod().getMethodName(); 
     try { 
      NewFileNamePath =directory.getCanonicalPath() + "\\target\\surefire-reports\\html\\Screenshots\\"+methodName+"_"+ dateFormat.format(date) +"Listener.png"; 
     } catch (IOException e1) { 
      // TODO Auto-generated catch block 
      e1.printStackTrace(); 
     } 


     try { 
      FileUtils.copyFile(scrFile, new File(NewFileNamePath)); 
     } catch (IOException e) { 
      e.printStackTrace(); 
     } 
     String reportFilePath = ".\\Screenshots\\"+methodName+"_"+ dateFormat.format(date) +".png"; 
     System.setProperty("org.uncommons.reportng.escape-output", "false");  
     Reporter.log("<a href=" + reportFilePath + ">Click to open screenshot</a><img src=" + reportFilePath + " height='350' width='700'>");  
    } 
}} 

在我的测试中,我已如果测试的运行清理测试

@AfterMethod(alwaysRun = true) 
public void tearDown() throws Exception 
{ 
    driver.quit(); 
} 

一个AfterMethod逐一那么正确的浏览器截图但是如果我跑parrallel抓获testsit捕获错误的测试浏览器。 我认为这个问题可能是以下

  • 的之一后,方法已经退出浏览器(这是一个情况下 有时因此为什么我添加的hasQuit布尔)
  • 的listene被引用错误的驱动对象。我相信这是问题,但我不确定如何确保它引用正确的驱动程序。

我有一个解决方法,工作几乎invlaves创建一个静态屏幕捕获对象,然后将其添加到AfterMethod然而,这是不太理想的,因为我想使用一个侦听器。

+0

你确定硒是专注于正确的窗口吗?如果您打开一个新选项卡(例如),硒将继续使用旧选项卡,除非您明确切换到新选项卡。当您拉动驱动程序运行时,您可能会拉动第一个或最后一个启动的驱动程序。 – Brydenr

+0

@Brydenr是的,我相信它可能会拉动最后一名驾驶员。我不知道如何让它拉到正确的驱动程序。有任何想法吗? –

+0

切换标签,你使用窗口句柄http://stackoverflow.com/questions/19112209/how-to-handle-the-new-window-in-selenium-webdriver-using-java – Brydenr

回答

3

从您的代码WebDriver driver = SeleniumSetup.driverrunning看来,driverrunning是SeleniumSetup类中的静态驱动程序实例。所以,在并行执行中它可能会引用一个错误的驱动程序对象。

ThreadLocal可能会帮助您创建一个线程安全驱动程序对象,下面是一个示例。

public class DriverFactory 
{ 

    private DriverFactory() 
    { 
     //Do-nothing..Do not allow to initialize this class from outside 
    } 
    private static DriverFactory instance = new DriverFactory(); 

    public static DriverFactory getInstance() 
    { 
     return instance; 
    } 

    ThreadLocal<WebDriver> driver = new ThreadLocal<WebDriver>() // thread local driver object for webdriver 
    { 
     @Override 
     protected WebDriver initialValue() 
     { 
     return new FirefoxDriver(); // can be replaced with other browser drivers 
     } 
    }; 

    public WebDriver getDriver() // call this method to get the driver object and launch the browser 
    { 
     return driver.get(); 
    } 

    public void removeDriver() // Quits the driver and closes the browser 
    { 
     driver.get().quit(); 
     driver.remove(); 
    } 
} 

使用DriverFactory来获取驱动程序实例。

WebDriver driver = DriverFactory.getInstance().getDriver(); 
+0

你必须传递驱动程序名称为testng配置文件中的一个参数,这可能对你有所帮助。 http://stackoverflow.com/questions/26604745/parameterized-selenium-tests-in-parallel-with-testng –

+0

感谢您的意见。我实施了这个课程,它很有魅力。我还添加了一个setter方法,以便可以基于浏览器类型等构建驱动程序。 –