package info.freelibrary.djatoka.view;
import gov.lanl.adore.djatoka.util.IOUtils;
import info.freelibrary.djatoka.Constants;
import info.freelibrary.util.FileUtils;
import info.freelibrary.util.RegexFileFilter;
import java.io.BufferedReader;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.Properties;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import nu.xom.Attribute;
import nu.xom.Builder;
import nu.xom.Document;
import nu.xom.Element;
import nu.xom.Elements;
import nu.xom.Nodes;
import nu.xom.ParsingException;
import nu.xom.ValidityException;
import nu.xom.XPathContext;
import org.im4java.core.CommandException;
import org.im4java.core.ConvertCmd;
import org.im4java.core.IM4JavaException;
import org.im4java.core.IMOperation;
import org.im4java.core.IdentifyCmd;
import org.im4java.core.ImageCommand;
import org.im4java.process.OutputConsumer;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class ReportServlet extends HttpServlet implements Constants {
/**
* Generated <code>serialVersionUID</code>.
*/
private static final long serialVersionUID = 1123517462247013351L;
private static final String JETTY_XPATH = "//maven:connector[@implementation='org.eclipse.jetty.server.nio.SelectChannelConnector']";
private static final String MAVEN_NS = "http://maven.apache.org/POM/4.0.0";
private static final XPathContext XPATH_CONTEXT = new XPathContext("maven",
MAVEN_NS);
private static final Logger LOGGER = LoggerFactory
.getLogger(ReportServlet.class);
private Properties myProps;
private String mySourceURL;
@Override
protected void doGet(HttpServletRequest aRequest,
HttpServletResponse aResponse) throws ServletException, IOException {
File tifDir = new File(myProps.getProperty(TIFF_DATA_DIR));
File jp2Dir = new File(myProps.getProperty(JP2_DATA_DIR));
String[] dirPaths = new String[] { jp2Dir.getAbsolutePath(),
tifDir.getAbsolutePath() };
PrintWriter toBrowser = aResponse.getWriter();
Builder bob = new Builder();
try {
// Assuming we're running from Jetty/Maven plugin
Document pom = bob.build(new File("pom.xml"));
Nodes nodes = pom.query(JETTY_XPATH, XPATH_CONTEXT);
String port;
if (nodes.size() == 1) {
Element cElem = (Element) nodes.get(0);
Element pElem = cElem.getFirstChildElement("port", MAVEN_NS);
Integer.parseInt(port = pElem.getValue()); // check for int
mySourceURL = "http://localhost:" + port + "/view/";
}
else {
mySourceURL = "http://localhost:8080/view/"; // default
}
toBrowser.print("<html>");
toBrowser.print(getHead().toXML());
toBrowser.print("<body>");
print("", dirPaths, toBrowser);
toBrowser.print("</body></html>");
toBrowser.close();
}
catch (ValidityException details) {
throw new ServletException(details);
}
catch (ParsingException details) {
throw new ServletException(details);
}
catch (NumberFormatException details) {
throw new ServletException("POM file's port not a valid number");
}
}
@Override
public void init() throws ServletException {
String dir = getServletContext().getRealPath("/WEB-INF/classes") + "/";
String propertiesFile = dir + PROPERTIES_FILE;
try {
myProps = IOUtils.loadConfigByPath(propertiesFile);
if (LOGGER.isDebugEnabled()) {
LOGGER.debug("Loaded properties file: {}", propertiesFile);
}
}
catch (Exception details) {
throw new ServletException(details);
}
}
@Override
public void log(String aMessage, Throwable aThrowable) {
super.log(aMessage, aThrowable);
}
@Override
public void log(String aMessage) {
super.log(aMessage);
}
private void print(String aPath, String[] aPathsArray, PrintWriter aOut)
throws MalformedURLException, ValidityException, ParsingException,
IOException {
URL url = new URL(mySourceURL + aPath);
HttpURLConnection conx = (HttpURLConnection) url.openConnection();
Document doc = new Builder().build(conx.getInputStream());
Element pathElem = (Element) doc.query("//path").get(0);
Elements pathParts = pathElem.getChildElements("part");
String suppliedPath = aPath.equals("") ? "/" : aPath;
StringBuilder path = new StringBuilder("/");
Nodes dirElems = doc.query("//dir");
Nodes fileElems = doc.query("//file");
aOut.print("<div>" + makeLink(suppliedPath) + "</div>");
aOut.print("<div>");
for (int index = 0; index < fileElems.size(); index++) {
Element fileElem = (Element) fileElems.get(index);
Attribute fileName = fileElem.getAttribute("name");
String value = fileName.getValue();
value += getStatus(new File(aPathsArray[0] + aPath, value));
aOut.print(getDiv(value).toXML());
}
System.out.println(doc.toXML());
for (int index = 0; index < pathParts.size(); index++) {
path.append(pathParts.get(index).getValue()).append('/');
}
if (dirElems.size() > 0) {
for (int index = 0; index < dirElems.size(); index++) {
Element dirElem = (Element) dirElems.get(index);
Attribute dirName = dirElem.getAttribute("name");
String newPath = path.toString() + dirName.getValue() + "/";
print(newPath, aPathsArray, aOut);
}
}
aOut.print("</div>");
aOut.flush();
}
private Element getDiv(String aText) {
return getDiv(aText, null);
}
private Element getDiv(String aText, String aClass) {
Element div = new Element("div");
div.appendChild(aText);
if (aClass != null && !aClass.equals("")) {
Attribute clattr = new Attribute("class", aClass);
div.addAttribute(clattr);
}
return div;
}
private Element getHead() {
Element head = new Element("head");
Element title = new Element("title");
Element style = new Element("style");
title.appendChild("djatoka ingest report");
style.addAttribute(new Attribute("type", "text/css"));
style.appendChild("a:link{color:blue;text-decoration:none;}");
style.appendChild("a:visited{color:blue;text-decoration:none;}");
style.appendChild("a:active{color:blue;text-decoration:none;}");
style.appendChild("a:hover{color:blue;text-decoration:none;}");
style.appendChild(".fail{color:red;}");
style.appendChild(".success{color:green;}");
style.appendChild("div{padding-left:10px;}");
head.appendChild(title);
head.appendChild(style);
return head;
}
private String getStatus(File aFile) {
final StringBuilder result = new StringBuilder(" ");
String jp2Path = aFile.getAbsolutePath();
String tifPath = getTiffFileName(jp2Path);
System.out.println(jp2Path + " " + aFile.exists());
System.out.println(tifPath);
try {
IdentifyCmd identify = new IdentifyCmd();
IMOperation op = new IMOperation();
identify.setOutputConsumer(new OutputConsumer() {
public void consumeOutput(InputStream aStream)
throws IOException {
InputStreamReader isReader = new InputStreamReader(aStream);
BufferedReader reader = new BufferedReader(isReader);
String line;
while ((line = reader.readLine()) != null) {
result.append(line);
}
}
});
op.addImage(jp2Path);
identify.run(op);
System.out.println(result.toString());
result.delete(0, result.length());
}
catch (CommandException details) {
System.err.println("Details abbreviated ImageMagick not installed");
}
catch (IM4JavaException details) {
System.out.println(details);
}
catch (InterruptedException details) {
System.out.println(details);
}
catch (IOException details) {
System.out.println(details);
}
return result.toString();
}
private String makeLink(String aPath) {
String url = "/view" + aPath;
String onText = "window.open('" + url + "'); return false";
Attribute onclick = new Attribute("onclick", onText);
Attribute onKeyPress = new Attribute("onkeypress", onText);
Element a = new Element("a");
a.addAttribute(new Attribute("href", url));
a.appendChild(aPath);
a.addAttribute(onclick);
a.addAttribute(onKeyPress);
return a.toXML();
}
private String getTiffFileName(String aJp2FileName) {
if (aJp2FileName.endsWith(JP2_EXT)) {
int end = aJp2FileName.lastIndexOf(JP2_EXT) + 1;
return aJp2FileName.substring(0, end) + TIF_EXTS[0];
}
return aJp2FileName;
}
}