Bläddra i källkod

Merge pull request #3 from jhonnymertz/starting-from-scratch

Lots of cleanup and refactorings
Patrick Brückner 9 år sedan
förälder
incheckning
1f42788148

+ 35 - 3
README.md

@@ -1,8 +1,40 @@
-WkHtmlToPdf Wrapper
+Java WkHtmlToPdf Wrapper
 =========
 
 A Java based wrapper for the [wkhtmltopdf](http://wkhtmltopdf.org/) command line tool. As the name implies, it uses WebKit to convert HTML documents to PDFs.
 
-**The [wkhtmltopdf](http://wkhtmltopdf.org/) command must be installed and working on your system.**
+Requirements
+------------
+**[wkhtmltopdf](http://wkhtmltopdf.org/) must be installed and working on your system.**
 
-### TODO - Complete
+Usage
+------------
+```
+Pdf pdf = new Pdf();
+
+pdf.addPage("<html><head><meta charset=\"utf-8\"></head><h1>Müller</h1></html>", PageType.htmlAsString);
+pdf.addPage("http://www.google.com", PageType.url);
+
+// Add a Table of contents
+pdf.addToc();
+
+// The `wkhtmltopdf` shell command accepts different types of options such as global, page, headers and footers, and toc. Please see `wkhtmltopdf -H` for a full explanation.
+// All options are passed as array, for example:
+pdf.addParam(new Param("--no-footer-line"), new Param("--html-header", "file:///header.html"));
+pdf.addParam(new Param("--enable-javascript"));
+
+// Save the PDF
+pdf.saveAs("output.pdf");
+```
+
+Wrapper options
+-------------------
+TODO
+
+Error handling
+------------
+TODO
+
+License
+------------
+This project is available under MIT Licence.

+ 8 - 7
pom.xml

@@ -3,20 +3,14 @@
 	<modelVersion>4.0.0</modelVersion>
 	<groupId>br.eti.mertz</groupId>
 	<artifactId>java-wkhtmltopdf-wrapper</artifactId>
-	<version>0.0.2-SNAPSHOT</version>
+	<version>0.0.3-SNAPSHOT</version>
 
 	<dependencies>
-		<dependency>
-			<groupId>org.projectlombok</groupId>
-			<artifactId>lombok</artifactId>
-			<version>1.12.6</version>
-		</dependency>
 
         <dependency>
             <groupId>junit</groupId>
             <artifactId>junit</artifactId>
             <version>4.11</version>
-            <scope>test</scope>
         </dependency>
 
         <dependency>
@@ -25,6 +19,13 @@
             <version>1.8.9</version>
         </dependency>
 
+        <dependency>
+            <groupId>org.apache.commons</groupId>
+            <artifactId>commons-lang3</artifactId>
+            <version>3.4</version>
+        </dependency>
+
+
     </dependencies>
 
 </project>

+ 0 - 14
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/Command.java

@@ -1,14 +0,0 @@
-package br.eti.mertz.wkhtmltopdf.wrapper;
-
-
-public class Command {
-	
-	public static void main(String[] args) {
-
-		Pdf pdf = new Pdf();
-		pdf.addParam(new Param("--enable-javascript"), new Param("--html-header", "file:///lala.html"));
-		System.out.println(pdf);
-
-	}
-
-}

+ 0 - 31
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/Param.java

@@ -1,31 +0,0 @@
-package br.eti.mertz.wkhtmltopdf.wrapper;
-
-import lombok.Data;
-import lombok.NonNull;
-
-@Data
-public class Param {
-
-	@NonNull
-	private String key;
-
-	private String value;
-
-	public Param(String key, String value) {
-		this.key = key;
-		this.value = value;
-	}
-
-	public Param(String key) {
-		this(key, null);
-	}
-
-	public String toString() {
-		StringBuilder sb = new StringBuilder().append(Symbol.separator)
-				.append(Symbol.param).append(key);
-		if (value != null)
-			sb.append(Symbol.separator).append(value);
-		return sb.toString();
-	}
-
-}

+ 0 - 35
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/Params.java

@@ -1,35 +0,0 @@
-package br.eti.mertz.wkhtmltopdf.wrapper;
-
-import java.util.ArrayList;
-import java.util.List;
-
-import lombok.Data;
-
-@Data
-public class Params {
-
-	List<Param> params;
-
-	public Params() {
-		this.params = new ArrayList<Param>();
-	}
-
-	public void add(Param param) {
-		params.add(param);
-	}
-
-	public void add(Param... params) {
-		for (Param param : params) {
-			add(param);
-		}
-	}
-	
-	public String toString(){
-		StringBuilder sb = new StringBuilder();
-		for(Param param : params){
-			sb.append(param);
-		}
-		return sb.toString();
-	}
-
-}

+ 92 - 95
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/Pdf.java

@@ -1,80 +1,61 @@
 package br.eti.mertz.wkhtmltopdf.wrapper;
 
+import br.eti.mertz.wkhtmltopdf.wrapper.configurations.WrapperConfig;
+import br.eti.mertz.wkhtmltopdf.wrapper.configurations.WrapperConfigBuilder;
+import br.eti.mertz.wkhtmltopdf.wrapper.page.Page;
+import br.eti.mertz.wkhtmltopdf.wrapper.page.PageType;
+import br.eti.mertz.wkhtmltopdf.wrapper.params.Param;
+import org.apache.commons.lang3.StringUtils;
+
 import java.io.*;
 import java.util.ArrayList;
-import java.util.Arrays;
 import java.util.List;
 
-import br.eti.mertz.wkhtmltopdf.wrapper.options.GlobalOption;
-import lombok.Data;
-
-@Data
 public class Pdf implements PdfService {
 
-    static final String STDOUT = "-";
-
-	private String command;
-	private List<Param> params;
-	private String htmlInput = null;
-    private boolean htmlFromString = false;
-
-	public Pdf(String wkhtmltopdf, List<Param> params) {
-		this.command = wkhtmltopdf;
-		this.params = params;
-	}
-
-	public Pdf(List<Param> params) {
-		this("wkhtmltopdf", params);
-	}
-
-	public Pdf(Param... params) {
-		this("wkhtmltopdf", Arrays.asList(params));
-	}
-
-	public Pdf() {
-		this("wkhtmltopdf", new ArrayList<Param>());
-	}
-
-	public void addHtmlInput(String input) {
-        this.htmlFromString = true;
-        this.htmlInput = input;
-	}
-
-	/**
-	 * TODO Add a HTML file, a HTML string or a page from a URL
-	 */
-	public void addCover(String cover) {
-		// TODO Auto-generated method stub
-	}
-
-	/**
-	 * TODO just the TOC option from wkhtmltopdf
-	 */
-	public void addToc() {
-		// TODO Auto-generated method stub
-	}
-
-	public void addParam(Param param) {
-		params.add(param);
-	}
-
-	public void addParam(Param... params) {
-		for (Param param : params) {
-			addParam(param);
-		}
-	}
-
-	/**
-	 * @throws IOException
-	 * @throws InterruptedException
-	 */
-	public File saveAs(String path) throws IOException, InterruptedException {
-        File file = new File(path);
-        getPDF(path);
-        return file;
-	}
+    private static final String STDINOUT = "-";
+
+    private WrapperConfig wrapperConfig;
+
+    private List<Param> params;
+
+    private List<Page> pages;
+
+    private boolean hasToc = false;
+
+    public Pdf(WrapperConfig wrapperConfig) {
+        this.wrapperConfig = wrapperConfig;
+        this.params = new ArrayList<Param>();
+        this.pages = new ArrayList<Page>();
+    }
+
+    public Pdf() {
+        this(new WrapperConfigBuilder().build());
+    }
+
+    public void addPage(String source, PageType type) {
+        this.pages.add(new Page(source, type));
+    }
+
+    public void addToc() {
+        this.hasToc = true;
+    }
+
+    public void addParam(Param param) {
+        params.add(param);
+    }
 
-    public File saveAs(String path, byte[] document) throws IOException {
+    public void addParam(Param... params) {
+        for (Param param : params) {
+            addParam(param);
+        }
+    }
+
+    public void saveAs(String path) throws IOException, InterruptedException {
+        saveAs(path, getPDF());
+    }
+
+    private File saveAs(String path, byte[] document) throws IOException {
         File file = new File(path);
 
         BufferedOutputStream bufferedOutputStream = new BufferedOutputStream(new FileOutputStream(file));
@@ -85,18 +66,19 @@ public class Pdf implements PdfService {
         return file;
     }
 
-    public byte[] getPDF(String path) throws IOException, InterruptedException {
+    public byte[] getPDF() throws IOException, InterruptedException {
+
         Runtime runtime = Runtime.getRuntime();
-        if(htmlFromString && !this.params.contains(new Param("-"))) {
-            this.addParam(new Param("-"));
-        }
-        String command = this.commandWithParameters() + Symbol.separator + path;
-        Process process = runtime.exec(command);
-        if(htmlFromString) {
-            OutputStream stdInStream = process.getOutputStream();
-            stdInStream.write(htmlInput.getBytes("UTF-8"));
-            stdInStream.close();
+        Process process = runtime.exec(getCommandAsArray());
+
+        for (Page page : pages) {
+            if (page.getType().equals(PageType.htmlAsString)) {
+                OutputStream stdInStream = process.getOutputStream();
+                stdInStream.write(page.getSource().getBytes("UTF-8"));
+                stdInStream.close();
+            }
         }
+
         InputStream stdOutStream = process.getInputStream();
         InputStream stdErrStream = process.getErrorStream();
         process.waitFor();
@@ -104,37 +86,52 @@ public class Pdf implements PdfService {
         ByteArrayOutputStream stdOut = new ByteArrayOutputStream();
         ByteArrayOutputStream stdErr = new ByteArrayOutputStream();
 
-        while(stdOutStream.available()>0) {
+        while (stdOutStream.available() > 0) {
             stdOut.write((char) stdOutStream.read());
         }
         stdOutStream.close();
-        while(stdErrStream.available()>0) {
+        while (stdErrStream.available() > 0) {
             stdErr.write((char) stdErrStream.read());
         }
         stdErrStream.close();
 
-        if(process.exitValue() != 0) {
-            throw new RuntimeException("Process (" + command + ") exited with status code " + process.exitValue() + ":\n"+new String(stdErr.toByteArray()));
+        if (process.exitValue() != 0) {
+            throw new RuntimeException("Process (" + getCommand() + ") exited with status code " + process.exitValue() + ":\n" + new String(stdErr.toByteArray()));
         }
 
         return stdOut.toByteArray();
     }
 
-    public byte[] getPDF() throws IOException, InterruptedException {
-        return getPDF(STDOUT);
-    }
+    private String[] getCommandAsArray() {
+        List<String> commandLine = new ArrayList<String>();
+        commandLine.add(wrapperConfig.getWkhtmltopdfCommand());
+
+        if (hasToc)
+            commandLine.add("toc");
 
-	public String commandWithParameters() {
-		StringBuilder sb = new StringBuilder();
-		for (Param param : params) {
-			sb.append(param);
-		}
+        for (Param p : params) {
+            commandLine.add(p.getKey());
 
-		return command + sb.toString();
-	}
+            String value = p.getValue();
+
+            if (value != null) {
+                commandLine.add(p.getValue());
+            }
+        }
 
-	public void addParam(GlobalOption option) {
-		addParam(new Param(option.toString()));
-	}
+        for (Page page : pages) {
+            if (page.getType().equals(PageType.htmlAsString)) {
+                commandLine.add(STDINOUT);
+            } else {
+                commandLine.add(page.getSource());
+            }
+        }
+        commandLine.add(STDINOUT);
+        return commandLine.toArray(new String[commandLine.size()]);
+    }
+
+    public String getCommand() {
+        return StringUtils.join(getCommandAsArray(), " ");
+    }
 
 }

+ 15 - 11
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/PdfService.java

@@ -1,17 +1,21 @@
 package br.eti.mertz.wkhtmltopdf.wrapper;
 
-import java.io.File;
+import br.eti.mertz.wkhtmltopdf.wrapper.page.PageType;
+import br.eti.mertz.wkhtmltopdf.wrapper.params.Param;
+
 import java.io.IOException;
 
 public interface PdfService {
-	
-	void addHtmlInput(String page);
-	
-	void addCover(String cover);
-	
-	void addToc();
-	
-	File saveAs(String path) throws IOException, InterruptedException;
-
-	byte[] getPDF() throws IOException, InterruptedException;
+
+    void addPage(String page, PageType type);
+
+    void addToc();
+
+    void addParam(Param param);
+
+    void addParam(Param... params);
+
+    void saveAs(String path) throws IOException, InterruptedException;
+
+    byte[] getPDF() throws IOException, InterruptedException;
 }

+ 0 - 18
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/Symbol.java

@@ -1,18 +0,0 @@
-package br.eti.mertz.wkhtmltopdf.wrapper;
-
-public enum Symbol {
-
-	separator(" "), param("");
-
-	private String symbol;
-
-	Symbol(String symbol) {
-		this.symbol = symbol;
-	}
-
-	@Override
-	public String toString() {
-		return symbol;
-	}
-
-}

+ 0 - 20
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/annotations/WkHtmlToPdf.java

@@ -1,20 +0,0 @@
-package br.eti.mertz.wkhtmltopdf.wrapper.annotations;
-
-import java.lang.annotation.Documented;
-import java.lang.annotation.ElementType;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.annotation.Target;
-
-@Retention(RetentionPolicy.RUNTIME)
-@Target({ ElementType.TYPE })
-@Documented
-public @interface WkHtmlToPdf {
-
-	String command() default "wkhtmltopdf";
-	
-	
-	
-	
-
-}

+ 0 - 23
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/builder/CommandBuilder.java

@@ -1,23 +0,0 @@
-package br.eti.mertz.wkhtmltopdf.wrapper.builder;
-
-import br.eti.mertz.wkhtmltopdf.wrapper.Pdf;
-import br.eti.mertz.wkhtmltopdf.wrapper.options.GlobalOption;
-
-public class CommandBuilder {
-
-	private Pdf pdf;
-
-	public CommandBuilder() {
-		pdf = new Pdf();
-	}
-
-	public CommandBuilder collate() {
-		pdf.addParam(GlobalOption.COLLATE);
-		return this;
-	}
-
-	public Pdf toPdf() {
-		return pdf;
-	}
-
-}

+ 0 - 10
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/builder/PdfService.java

@@ -1,10 +0,0 @@
-package br.eti.mertz.wkhtmltopdf.wrapper.builder;
-
-import java.io.File;
-
-import br.eti.mertz.wkhtmltopdf.wrapper.Command;
-
-public interface PdfService {
-	
-	File execute(Command command);
-}

+ 17 - 0
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/configurations/WrapperConfig.java

@@ -0,0 +1,17 @@
+package br.eti.mertz.wkhtmltopdf.wrapper.configurations;
+
+public class WrapperConfig {
+    private String wkhtmltopdfCommand = "wkhtmltopdf";
+
+    public WrapperConfig(String wkhtmltopdfCommand) {
+        this.wkhtmltopdfCommand = wkhtmltopdfCommand;
+    }
+
+    public String getWkhtmltopdfCommand() {
+        return wkhtmltopdfCommand;
+    }
+
+    public void setWkhtmltopdfCommand(String wkhtmltopdfCommand) {
+        this.wkhtmltopdfCommand = wkhtmltopdfCommand;
+    }
+}

+ 14 - 0
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/configurations/WrapperConfigBuilder.java

@@ -0,0 +1,14 @@
+package br.eti.mertz.wkhtmltopdf.wrapper.configurations;
+
+public class WrapperConfigBuilder {
+    private String wkhtmltopdfCommand = "wkhtmltopdf";
+
+    public WrapperConfigBuilder setWkhtmltopdfCommand(String wkhtmltopdfCommand) {
+        this.wkhtmltopdfCommand = wkhtmltopdfCommand;
+        return this;
+    }
+
+    public WrapperConfig build() {
+        return new WrapperConfig(wkhtmltopdfCommand);
+    }
+}

+ 0 - 20
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/options/GlobalOption.java

@@ -1,20 +0,0 @@
-package br.eti.mertz.wkhtmltopdf.wrapper.options;
-
-public enum GlobalOption {
-
-	COLLATE("collate");
-	
-	//outros
-
-	private String name;
-
-	private GlobalOption(String name) {
-		this.name = name;
-	}
-
-	@Override
-	public String toString() {
-		return this.name;
-	}
-
-}

+ 29 - 0
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/page/Page.java

@@ -0,0 +1,29 @@
+package br.eti.mertz.wkhtmltopdf.wrapper.page;
+
+public class Page {
+
+    private String source;
+
+    private PageType type;
+
+    public Page(String source, PageType type) {
+        this.source = source;
+        this.type = type;
+    }
+
+    public String getSource() {
+        return source;
+    }
+
+    public void setSource(String source) {
+        this.source = source;
+    }
+
+    public PageType getType() {
+        return type;
+    }
+
+    public void setType(PageType type) {
+        this.type = type;
+    }
+}

+ 7 - 0
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/page/PageType.java

@@ -0,0 +1,7 @@
+package br.eti.mertz.wkhtmltopdf.wrapper.page;
+
+public enum PageType {
+    htmlAsString,
+    url,
+    file
+}

+ 42 - 0
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/params/Param.java

@@ -0,0 +1,42 @@
+package br.eti.mertz.wkhtmltopdf.wrapper.params;
+
+public class Param {
+
+    private String key;
+
+    private String value;
+
+    public Param(String key, String value) {
+        this.key = key;
+        this.value = value;
+    }
+
+    public Param(String key) {
+        this(key, null);
+    }
+
+    public String getKey() {
+        return key;
+    }
+
+    public void setKey(String key) {
+        this.key = key;
+    }
+
+    public String getValue() {
+        return value;
+    }
+
+    public void setValue(String value) {
+        this.value = value;
+    }
+
+    public String toString() {
+        StringBuilder sb = new StringBuilder().append(Symbol.separator)
+                .append(Symbol.param).append(key);
+        if (value != null)
+            sb.append(Symbol.separator).append(value);
+        return sb.toString();
+    }
+
+}

+ 32 - 0
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/params/Params.java

@@ -0,0 +1,32 @@
+package br.eti.mertz.wkhtmltopdf.wrapper.params;
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class Params {
+
+    private List<Param> params;
+
+    public Params() {
+        this.params = new ArrayList<Param>();
+    }
+
+    public void add(Param param) {
+        params.add(param);
+    }
+
+    public void add(Param... params) {
+        for (Param param : params) {
+            add(param);
+        }
+    }
+
+    public String toString() {
+        StringBuilder sb = new StringBuilder();
+        for (Param param : params) {
+            sb.append(param);
+        }
+        return sb.toString();
+    }
+
+}

+ 18 - 0
src/main/java/br/eti/mertz/wkhtmltopdf/wrapper/params/Symbol.java

@@ -0,0 +1,18 @@
+package br.eti.mertz.wkhtmltopdf.wrapper.params;
+
+public enum Symbol {
+
+    separator(" "), param("");
+
+    private String symbol;
+
+    Symbol(String symbol) {
+        this.symbol = symbol;
+    }
+
+    @Override
+    public String toString() {
+        return symbol;
+    }
+
+}

+ 15 - 2
src/tests/java/br/eti/mertz/wkhtmltopdf/wrapper/PdfTest.java

@@ -1,5 +1,7 @@
 package br.eti.mertz.wkhtmltopdf.wrapper;
 
+import br.eti.mertz.wkhtmltopdf.wrapper.page.PageType;
+import br.eti.mertz.wkhtmltopdf.wrapper.params.Param;
 import org.apache.pdfbox.pdfparser.PDFParser;
 import org.apache.pdfbox.pdmodel.PDDocument;
 import org.apache.pdfbox.util.PDFTextStripper;
@@ -12,15 +14,26 @@ import static org.hamcrest.core.StringContains.containsString;
 
 public class PdfTest {
 
+    @Test
+    public void testCommand() throws Exception {
+        Pdf pdf = new Pdf();
+        pdf.addToc();
+        pdf.addParam(new Param("--enable-javascript"), new Param("--html-header", "file:///example.html"));
+        pdf.addPage("http://www.google.com", PageType.url);
+        Assert.assertThat("command params should contain the --enable-javascript and --html-header", pdf.getCommand(), containsString("--enable-javascript --html-header file:///example.html"));
+    }
+
     @Test
     public void testPdfFromStringTo() throws Exception {
 
         // GIVEN a html template containing special characters that java stores in utf-16 internally
         Pdf pdf = new Pdf();
-        pdf.addHtmlInput("<html><head><meta charset=\"utf-8\"></head><h1>Müller</h1></html>");
+        pdf.addPage("<html><head><meta charset=\"utf-8\"></head><h1>Müller</h1></html>", PageType.htmlAsString);
+
+        pdf.saveAs("output.pdf");
 
         // WHEN
-        byte[] pdfBytes =  pdf.getPDF();
+        byte[] pdfBytes = pdf.getPDF();
 
         PDFParser parser = new PDFParser(new ByteArrayInputStream(pdfBytes));