I've been introduced to the power of PhantomJS and CasperJS to take website screenshots. The article "Responsive Screenshots With Casper" was really helpful to learn about the basics of the two technologies plus the screenshot feature.
Next is to how can this technology be used for integration with a Spring MVC application.
So far I have tried "Screen Capture using PhantomJS, GhostDriver, Selenium Hub"'s code and combined it with the answer provided in "Remote PhantomJS driver in Junit".
What happened is that every time I run the program, I keeps having a ClassNotFoundError
and I kept providing the missing JAR files. I ended up downloading and providing nine new JAR files in my Spring application:
phantomjsdriver-1.0.4.jar
selenium-java-2.39.0.jar
and its source fileasm-all-3.3.1.jar
cglib-3.1.jar
commons-exec-1.2.jar
guava-16.0.1.jar
httpclient-4.3.2.jar
httpcore-4.3.2.jar
json-20140107.jar
until the error below showed
SEVERE: Servlet.service() for servlet [spring] in context with path [/my_spring_app] threw exception [Handler processing failed; nested exception is java.lang.IncompatibleClassChangeError: class net.sf.cglib.core.DebuggingClassWriter has interface org.objectweb.asm.ClassVisitor as super class] with root cause
java.lang.IncompatibleClassChangeError: class net.sf.cglib.core.DebuggingClassWriter has interface org.objectweb.asm.ClassVisitor as super class
Should I keep trying this path just to get a screenshot of my website? I feel like it's a losing battle based on what's going on. I'm not familiar with PhantomJS
and can't find any legitimate tutorial or guide online for this setup. I would go back to iText
and JFreeCharts
if I can't make this work.
Below is the code I use within my Spring application:
package my_spring_app.controller;
import java.io.File;
import java.io.IOException;
import java.net.URI;
import java.net.URISyntaxException;
import java.util.concurrent.TimeUnit;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.io.FileUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.openqa.selenium.OutputType;
import org.openqa.selenium.TakesScreenshot;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.phantomjs.PhantomJSDriverService;
import org.openqa.selenium.remote.Augmenter;
import org.openqa.selenium.remote.DesiredCapabilities;
import org.openqa.selenium.remote.RemoteWebDriver;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
@Controller
public class MyController {
protected final static Log logger = LogFactory
.getLog(MyController.class);
@RequestMapping(value = "/screenshot", method = RequestMethod.GET)
public String showSupplementsPage(ModelMap model,
HttpServletRequest request, HttpServletResponse response) {
tryPhantom();
return "screenshot";
}
private URI uri;
private static PhantomJSDriverService service;
private WebDriver webDriver;
protected static DesiredCapabilities dCaps;
public void tryPhantom() {
service = new PhantomJSDriverService.Builder()
.usingPhantomJSExecutable(new File("classpath:phantomjs.exe"))
.usingAnyFreePort().build();
try {
service.start();
} catch (IOException e) {
e.printStackTrace();
}
try {
uri = new URI("http://localhost:8080/");
} catch (URISyntaxException e) {
e.printStackTrace();
}
dCaps = new DesiredCapabilities();
dCaps.setJavascriptEnabled(true);
dCaps.setCapability("takesScreenshot", true);
webDriver = new RemoteWebDriver(service.getUrl(), dCaps);
webDriver.manage().timeouts().implicitlyWait(30, TimeUnit.SECONDS);
long iStart = System.currentTimeMillis();
webDriver.get("http://localhost:8080/");
webDriver = new Augmenter().augment(webDriver);
File srcFile = ((TakesScreenshot) webDriver)
.getScreenshotAs(OutputType.FILE);
System.out.println("File:" + srcFile);
try {
FileUtils.copyFile(srcFile, new File("classpath:screenshots/pic.png"));
} catch (IOException e) {
e.printStackTrace();
}
System.out.println("Single Page Time:"
+ (System.currentTimeMillis() - iStart));
webDriver.quit();
service.stop();
}
}
Here is a diagram of what I have in mind: