从jar读取资源不能按预期工作

时间:2014-05-30 18:07:41

标签: java selenium jar resources packaging

我试图为selenium测试创建一个可执行jar。代码需要做的部分事情是设置一个系统属性来告诉Selenium可以找到驱动程序可执行文件(我使用chromedriver)。文件结构如下:

src
   com
      mycompany
           SeleniumTest.java
   chromeDriver
      windows
         chromedriver.exe

代码如下:

private static String WINDOWS_DRIVER = "/chromeDriver/windows/chromedriver.exe";
System.setProperty("webdriver.chrome.driver",
                    SeleniumTest.class.getResource(WINDOWS_DRIVER).getFile());

在eclipse中执行时,此代码工作正常。但是,当我导出到一个可运行的jar文件(来自eclipse)时,我收到以下错误:

Exception in thread "main" java.lang.IllegalStateException: The driver executable 
    does not exist: F:\temp\file:\F:\temp\seleniumTest.jar!\chromeDriver\windows\chromedriver.exe
at com.google.common.base.Preconditions.checkState(Preconditions.java:177)
    at org.openqa.selenium.remote.service.DriverService.checkExecutable(DriverService.java:117)
    at org.openqa.selenium.remote.service.DriverService.findExecutable(DriverService.java:112)
    at org.openqa.selenium.chrome.ChromeDriverService.createDefaultService(ChromeDriverService.java:75)
    at org.openqa.selenium.chrome.ChromeDriver.<init>(ChromeDriver.java:139)

然而seleniumTest.jar存在于F:\temp,错误消息指定的jar中的路径也是如此。

有关错误或建议的任何想法?我尝试将slahses更改为反斜杠,并且(仅作为测试)对路径进行硬编码(例如将系统属性设置为F:\temp\seleniumTest.jar!\chromeDriver\windows\chromedriver.exe),但两者都没有效果。

2 个答案:

答案 0 :(得分:2)

系统属性应该包含文件系统文件的路径,可以在其中找到并执行驱动程序。

驱动程序不是文件。这是你的jar文件的一个条目。捆绑在jar文件中的可执行文件无法执行。

如果你真的想将驱动程序捆绑到jar文件中并执行它,那么你必须从这个类路径资源读取字节,将它们写入临时可执行文件,然后告诉selenium这个临时可执行文件的位置位于。

答案 1 :(得分:1)

尝试类似:

// locate chromedriver in the jar resources
URL res = getClass().getResource("/chromeDriver/windows/chromedriver.exe");
// locate chromedriver in the jar filesystem
File f = new File(res.getFile());
// copy chromedriver out into the real filesystem
File target = new File(System.getProperty("java.io.tmpdir") + System.getProperty("file.separator") + f.getName());
java.nio.file.Files.copy(f.toPath(), target.toPath(), StandardCopyOption.REPLACE_EXISTING);
if (!target.canExecute())
    throw new FileNotFoundException("chrome.exe copy did not work!");
System.setProperty("webdriver.chrome.driver", target.getCanonicalPath());